メドピア開発者ブログ

集合知により医療を再発明しようと邁進しているヘルステックカンパニーのエンジニアブログです。読者に有用な情報発信ができるよう心がけたいので応援のほどよろしくお願いします。

Vue Fes Japan 2023 After Meetupを開催しました!

この画像は「Vue Fes Japan 2023 After Meetup」というイベントのバナーです。

MedPeerの開発をしている栗崎 (Ryohei Kurisaki (@0ryo0ryo) / X )です。

11月7日(火)に弊社オフィスにて、MNTSQ株式会社、株式会社hacomonoと3社合同でVue Fes Japan 2023 After Meetup を開催しました。

5年ぶりのオフライン開催となった Vue Fes Japan 2023の感想や思い出を語り合いました。

セッションのハイライト

メインセッション

Vue Fes Japan 2023のオーガナイザーであるkazuponさんによる 「Vue & Vite Rustify」のお話でした。

まずはViteの現状の課題についてお話されていました。

  • productionビルドが遅い
  • dev環境とproduction環境のbundleの一貫性がない

※ dev環境はesbuild, production環境はRollup

ViteはRollup互換のAPIを使用したRust製バンドラーRolldown*1をbytedance社のRspackチームと協力して開発を進めているそうです。

kazuponさんからはRolldownの構造についての解説や、webpackと比較したパフォーマンスの向上について話がありました。

また、Rust製のツールOXC について紹介されていました。

OXCはbytedance社のweb-infra-dev チームにより作成され、JavaScript、TypeScript向けのツールチェインになります。

Playgroundを始め、VSCodeの拡張機能も存在するそうです。

さらに、APIの提供もされており、今後もコミュニティとコラボし、より開発が進んでいくということでした。

終盤には、VSCode リポジトリを例にOXCを使ったLinterのが実行のデモされていました。

一瞬すぎて何が起きたのかわからない速さでLinterの実行が終わりびっくりしました!!

GitHubのREADMEにも記載があったので、私も手元でVSCodeリポジトリをcloneしLinterの実行をしてみました。 github.com

 $ npx oxlint@latest .

をディレクトリで実行すると、以下のような結果になりました。

Finished in 1.6s on 4560 files with 64 rules using 8 threads.
Found 1609 warnings and 0 error

1、2秒弱でリポジトリ内全てのソースコードの解析が終わりました(すごい!!)

ご紹介のあった、Rolldown、OXCを始め、すでに存在するvue-compiler等Rustを利用したツールが増えてきており、Rustの波がやってきているのを実感できました。

さらにエコシステムが強化され今後が楽しみだなと感じました。

LTの様子

「Vue Fes Japan を振り返る」 

トップバッターは弊社メドピアの岡澤さんの発表です。

Vue.jsクリニック*2で公開されていた質問とエキスパートの回答を聞き、過去のコンポーネント設計を振り返り、現在の考えをお話しされていました。

過去の失敗からの教訓

  • Pagesコンポーネントから書き始める
  • ファイル分割しすぎない
  • 共通処理以外は外部ファイルにしない

個人的にはコンポーネント設計に悩ましく同様の課題を感じていたため、岡澤さんの発表、Vue.jsクリニックでのエキスパートの回答のように、まずはシンプルに始め、リファクタリングしやすい小さいコンポーネントを作ることを意識したいなと思いました。

「UI フレームワークから始めるアクセシビリティ」

speakerdeck.com

続いては、MNTSQ株式会社の中島晃さんの発表でした。

Vue Fes Japan 2023での以下の2つのセッションを聞き、自身の関わるプロダクトに関するアクセシビリティの向き合い方についてお話しされていました。

アクセシビリティ対応を2つの具体的な方法で紹介されていました。

  1. 最低限の部分から対応

  2. オリジナルのデザインシステムで対応する

2つの方法にはそれぞれメリット、デメリットがあり、どちらもハードルは低くないため、 a11y*3に対応したFW、ライブラリを選定することが大切だというお話でした。

また、必要に応じて、独自のデザインシステムを利用するのが良いということでした。

個人的に印象的だったのが、MNTSQさんのビジョン「すべての合意をフェアにする」とa11y対応をやる意義を関連づけ待ったなしで対応したというのが素敵だなと思いました。

「Nuxt2 -> 3 を戦っていくには」

最後は、株式会社hacomonoのみゅーとんさんの発表でした。

Vue Fes Japan 2023のセッションを聞き、どこの会社もバージョンアップに苦労しているんだなという感想とVue Fes Japan 2023で得た知見について話されていました。

具体的にはNuxt 3 化の方法の知見をお話されていました。

  1. 一気に乗り換える
  2. Nuxt Bridge を導入
  3. 段階的に乗り換える

hacomonoさんは巨大リポジトリ、Nuxt Bridgeを使えない背景からもっともパワーのいる段階的に乗り換える方法を取ったそうです。

iframeを使い、Nuxt 2 側のページを開くという方法は驚きでした!

似たような話を聞いたなと思っていたのですが、Vue Fes Japan 2023のランチセッションで弊社の小林さんがVue2から3へのマイグレーションについても似たような対応方法のまとめを話されていましたね。

(こちらも併せてご覧ください。)

speakerdeck.com

パネルディスカッションの様子

kazuponさんとVue Fes Japan 2023のランチセッションで登壇された3名をパネリストに迎え、モデレーターをメドピアVPoTの平川さんが行いました。

登壇者のご紹介

  • メドピア株式会社: 小林さん
  • MNTSQ 株式会社: 安積さん
  • 株式会社hacomono: みゅーとんさん

テーマ1.「Vue.jsコミュニティと企業の関わり方」

いくつか話されていた内容をご紹介します。

Q 企業側に求めていることはありますか?

kazuponさん「Vueコミュニティの支援、フルタイムのコミッターが少ないため、支援があると嬉しいです。」

Q Vue Fes Japan 2023の登壇のきっかけは?

小林さん 「メドピアグループの多くのプロダクトでVueを使用しています。Vueを使っているため、報告とスポンサーシップをするのは当たり前の状態でした。」

安積さん「 会社の認知度向上のために行っています。 v-tokyoのイベントをきっかけに関与しやすくなりました。」

Q 企業からコミュニティへの貢献についてのお考えはありますか?

みゅーとんさん「自分が主導して、会社内のGitHubにPublic Organizationを作成して、公開したりしています。」

安積さん「eslintとか自分達が使う場面が多い、ユーティリティ的な機能はOSSで公開したいと思っています。」

安積さん「自分達が作っているものがVueでできているんよというのも公開していくといいのではと思います!最近だとOpenAIのサイトもVueで作られているんですよ。」

小林さん 「Apple 開発者向けのドキュメントページもVueで作られていますしね!」

kazuponさん「OSSではなくてもテックブログとかの記事公開することもコミュティへの貢献につながると思います。」

スポンサーで参加された企業だけでなく、個人スポンサーも行われていて、Vue Fes Japan 2023に参加して、多くの方がコミュニティへの貢献をされているなと思いました。

そして、このブログもコミュニティの貢献になったら嬉しいです 🙂

テーマ2.「WebFrontendを学んだ後のキャリアパス Now and Then」

時間が少しオーバーしてしまうほどの盛り上がりを見せたこちらのテーマについてもいくつかご紹介します。

Q WebFrontendを学んだ後のキャリアパスについてどうお考えですか?

安積さん「フロントエンドエンジニアを含む、 エンジニアチームのスキルマップを作成しています。」

※ Xでも公開されていました。

安積さん「マインドマップの近しい部分から勉強してみて、領域を広げていくのが良いと思います。 」

この後、登壇者の皆さんの過去の経験談がお話されました。

懐かしい技術と感じる方も多くいらっしゃったようで会場は沸いていました。

みゅーとんさん「好きなところを勉強していくのは大切だと思います。フロントエンドの見た目があって使い勝手の良さを追求できるのが好きです。それに加えて、開発者体験やデザイナーのデザインを再現できるのが良いと思います。」

小林さん「フロントエンドが好きで勉強を続けるのは大事です。私も中学生くらいからHP制作をしていまして、今も好きが高じてキャリアができています。」

個人的にはスキルマインドマップのお話がとても印象に残っております。

私自身、Ruby on Railsを使ったサーバサイドの開発がメイン業務ですが、業務の中でVueを使ったフロントエンドを始め、フロントエンドに興味を持ち、プライベートでは、Nuxt3を使ったアプリケーションなどを作成しています。

その時に、Ruby on Railsとの類似箇所や、接点になる部分などは、勉強もしやすく、理解しやすいことを痛感しました。

懇親会の様子

リアルイベントならでは懇親会の様子を写真を交えてご紹介します。

大量のピザとドリンクを手に交流を行いました。

メドベアチョコも作りました 🎉

登壇者を始め、多くの参加者と交流することができ、いい情報交換ができとても刺激的な時間になりました。

最後に

登壇者の皆さん、合同開催のMNTSQ株式会社、株式会社hacomonoの皆さんありがとうございました。

セッション、パネルディスカッションにもあったように、コミュニティとVueの関わりはとても強く、大切なものだなと感じました。

これからもVue、Nuxtのコミュニティが発展することを願っています。

来年のVue Fes Japanも楽しみにしています!!


メドピアでは一緒に働く仲間を募集しています。
ご応募をお待ちしております!

■募集ポジションはこちら

medpeer.co.jp

■エンジニア紹介ページはこちら

engineer.medpeer.co.jp

*1:現時点では、private repositryでの開発みたいです。

*2:Vue Fes Japan 2023で行われた、Vue.js に関して困っていること、素朴な疑問、ベストプラクティスなどをエキスパートに聞けるコーナー

*3:Web アクセシビリティの略語

Vue Fes Japan 2023にゴールドスポンサーとして参加しました!#vuefes

こんにちは、サーバーエンジニアの千葉です。

今回は日本最大級のVue.jsのカンファレンス「Vue Fes Japan 2023」に参加してきましたので、そのレポートをお届けしたいと思います。

私は今年が初参加でしたが、ブースやセッショントラックがいっぱいになるほどの盛り上がりを見せていました。

企業名、参加者の名前がずらり

ゴールドスポンサーとして

メドピアは今年、ゴールドスポンサーとして協賛させていただきました。それに加え、セッションルームネーミングライツスポンサーやスペシャルランチスポンサーとしても協賛しました。

セッションルームネーミングライツスポンサー

セッションルームネーミングライツスポンサーでは「メドピアトラック」という名前のルームを開設し、満席で立ち席ができるほど多くの方に来場していただきました。

メドピアトラックの様子

スペシャルランチスポンサー

スペシャルランチスポンサーでは、フロントエンド テックリーダーの小林さんが「Vue 2のEOLまで二ヶ月ですが進捗どうですか?」というタイトルで登壇しました。

Vue2 EOLの2023/12/31が迫る中、メドピアの各サービスがどのようにVue3へのmigrationにアプローチしているのかについて紹介しました。

まだVue2を使っているという参加者も多く見受けられたため、Vue3化への対応方針を考える上で参考になった方も多かったのではないでしょうか。

フロントエンド エンジニアの小林さんが登壇

speakerdeck.com

スポンサーブース

メドピアはスポンサーブースも出展し、多くの方がアルコールパッチテストを実施してくださいました。

お酒を飲める方が半数以上という結果となったので、アフターパーティでも安心してお酒を楽しめたはずですね👍

Vue開発者のEvanさんにもアルコールパッチテストを試してもらいました!

セッションの様子

今回のVue Fes Japanでは34ものセッションが行われました。その中で私が聞いたセッションを3つほど紹介したいと思います。

Vue.jsを活用して開発リードタイムが1/3になった話

Vue.jsを活用して開発リードタイムが1/3になった話ではなく、価値を生む技術提案についてのセッションです。 (登壇者曰く、急遽話したいことが変わったらしい)

提案の質がソフトウェア改善の成功要因になるということを、自身の経験則を元に話していただきました。開発内容ではなく、開発前の提案に関するプレゼンを聞くことは初めてだったため、とても新鮮で勉強になるセッションでした。

speakerdeck.com

vuefes.jp

Vueを使ってGrid Systemを実装した話

Vue.jsを使ってGrid Systemをライブコーディングするセッションです。

Grid Systemの実装はmedia queryにおける仕様上の問題もあり、上手く実装・運用できないことが多々あるため、セッションとして話すことにしたそうです。

個人的には業務でGrid Systemを使った実装を行い、苦戦したという背景があったのでとても参考になった回でした。

speakerdeck.com

vuefes.jp

18営業日で350コンポーネント規模のVueアプリにデザインシステムを導入する方法

18営業日で350コンポーネント規模のVueアプリにデザインシステムを導入する方法や知見を共有するセッションです。

技術的知見

  • AST を使用して事前にできる限り自動でマイグレーションした上で判別できない部分に全て TODO コメントを自動付与
  • ESLint のカスタムルールを実装してできる限りレビューは自動化
  • デザインシステムが壊れていないか確認するために VRT を実施
  • Autify による E2E テスト

プロジェクト管理上の知見

  • 手作業は短期集中でタスクのスイッチングコストをゼロに
  • 進捗は数値で管理
  • マニュアルテストを複数回実施してバグに対処
  • 最後にデザイナーとペアプロで細かいデザインを修正

システム導入ではBig Bangリリース(一度に大きな変更を加えるリリース手法)を採用したとのことで、その知見を聞けたことは個人的に一番の収穫でした。

speakerdeck.com

vuefes.jp

アフターパーティの様子

アフターパーティでは、Vue.js 日本ユーザーグループ代表のkazuponさんやNuxtコアメンバーのHarlanさんといったプロフェッショナルな方々とも交流することができました。

NuxtコアメンバーのHarlanさんと

まとめ

文字通り「Fes = お祭り」のように大盛り上がりのカンファレンスでした。

個人的には業務でフロントエンドを触る機会があり、Vueに対する熱が高まったため参加しましたが、とても良い経験と機会になりました。

フロントエンド少し触っただけ、触ったことないけど興味がある程度でも、分かりやすいセッションとお祭りのような雰囲気を味わうことができるため、まだ参加したことがない方は来年参加してみてはいかがでしょうか。

最後に

2023年11月7日(火)にメドピア株式会社、MNTSQ 株式会社、及び株式会社 hacomono でVue Fes Japan 2023 After Meetupをメドピアオフィスでオフライン開催します。

Vue.js 日本ユーザーグループ代表のkazuponさんを特別ゲストとして迎え、セッションやパネルディスカッションといったコンテンツを用意しています。

こちらのイベントもご興味がある方はぜひご参加ください!

medpeer.connpass.com


メドピアでは一緒に働く仲間を募集しています。
ご応募をお待ちしております!

■募集ポジションはこちら

medpeer.co.jp

■エンジニア紹介ページはこちら

engineer.medpeer.co.jp

Kaigi on Rails 2023 セッションレポート #kaigionrails

こんにちは!サーバーサイドエンジニアの近藤です。

Kaigi on Rails 2023 が、10月27日から10月28日にかけて開催されました。 2020年から続くKaigi on Railsですが、今年が初のオンライン&オフライン同時のハイブリット開催となります。 メドピアはゴールドスポンサーとして協賛し、15名ほどのメンバーが現地で参加しました。

当記事では、現地で聴いたセッションのうち印象に残った発表をピックアップしてご紹介したいと思います。

Exceptional Rails

speakerdeck.com

メドピアで技術顧問をしていただいている前島さんによるセッションです。 Railsにおいて例外をいかにして扱うか、というお話でした。

Railsコード中の例外処理ひとつ取っても、考えることは数多くあります。

  • いつ例外を発生させるか
  • 発生した例外をいつどのようにrescueするのか
  • 通知が必要な例外をどのように開発者に通知するのか
  • エラーページをユーザにどう表示するのか

エラーを扱う際のこれらの観点について、方針とその理由を身近な具体例を交えながら解説していました。

個人的に印象的だった話題は、外部サービス起因のエラーの通知についての話題です。 エラーを通知するか否かについて

  1. エラーが起きる状況を考えてみる
  2. そのエラーが開発者側では対応できないこと(外部サービスの不具合など)が原因で起きるものであれば(即時の)通知はしない
    • 対応できないエラーが来てもノイズになるため
    • レベルをwarningなどに設定し、短期間に頻発するようであれば通知するのはあり

といった判断基準を紹介しており、通知に対する考え方の面で学びになったお話でした。

全体的に、今後例外を扱う際にぜひ見返したくなるようなセッションでした。

Update Billion Records

speakerdeck.com

レコード数が50~60億という巨大なテーブルに対してカラムを追加し埋める際に、なにを考えどのような手段を取ったかについてのお話です。

この巨大なテーブルを更新するにあたって、
「更新中にサービスを止めてはいけない」
「更新処理はいつでも中断・再開できなければならない」
などの要件がありました。

適切な更新手段を見つけるために、最初は既存手法の踏襲から始め、

(要件や現状の)整理 →(手段の)発案 → 検証

というサイクルを繰り返し、最終的にたどり着いた手段は「更新対象をqueueで管理し非同期jobで少しずつ更新する」というものでした。

発表の後半で、スピーカーのtokutomiさんは今回の改修を次のように振り返っています。

最終的な構成も参考になるものでしたが、それと同じくらい、 最終的な構成に至るまでの改善プロセスも参考になる発表でした。

Turbolinksアレルギー患者に捧げるTurbo & Stimulusでの時短実装術

speakerdeck.com

弊社エンジニアの草分さんが「Turbolinksアレルギー患者に捧げるTurbo & Stimulusでの時短実装術」というタイトルで登壇しました。

[草分さん]「Hotwireという名前をご存知でしょうか?」

[会場] 「👏 👏 」

[草分さん]「では、Hotwireを本番環境等でちゃんと使っていましたでしょうか?」

[会場] 「......」

[草分さん]「🤯」

という笑い溢れる導入から始まったこのセッションは、 なにかと避けられがちなHotwireを実プロダクトで採用した話と、 その際にどのようにHotwireを使い時短を実現したかについての発表でした。

タイトルにもある「時短」について、

  • create (= フォームのsubmit) 前の確認画面
  • フォームの動的切り替え

という2つの状況を例に、 Hotwireを使った時短実装術をデモと共に紹介していました。

確認画面をモーダルで出すことでユーザー入力の再描画処理を省けたり、 Hotwireを使うことでリッチなUIもお手軽に実装できたとのことです。

スライドの左半分がデモ画面になっている超絶プレゼン技術でした

Hotwireをオススメできる状況として

  • 画面側がHotwireで十分実現できるとき
  • 社内向けの管理画面
  • バックエンドエンジニアが多いプロジェクト

を挙げており、実際にヤクチエの開発で採用した実例も紹介していました。

スライドの所々に小ネタが散りばめられており、会場から笑い声が絶えないセッションでした。

32個のPRでリリースした依存度の高いコアなモデルの安全な弄り方

speakerdeck.com

既存システムを動かしたままREAD/WRITEの多いテーブルのカラムを置き換えるために、MySQLのオンラインDDL機能(ロックを取得せずにマイグレーションを行える機能)を利用したお話です。

一言で「オンラインDDL機能を利用」といっても、考慮すべき点は数多くあります。

たとえばオンラインDDLそのものに対する注意点として、

  • 本来はオンラインDDLの対象になる操作であっても、場合によってはそうならない場合がある
  • オンラインDDLは一部の期間でメタデータロックというロックを取得するため、ロックを取る他の処理の確認が必要

などの注意点を紹介していました。

また、リリースフローに関する注意として、 コンテナを用いてBlue/Greenデプロイをしているような環境では、
「マイグレーションの完了タイミング」と
「コンテナの入れ替わりタイミング」にずれが生じてしまいます。

これにより、古いアプリが新しいデータベースを見に行ってしまう状況が発生するため、 単純に「カラム名の変更」をするのではなく「カラムの追加 → 役割の置き換え → 古いカラムの削除」という手順を踏んでリリースしたとのことです。

実際のリリースでは下図のような段階的な対応を行ったとのことで、このリリースに万全の体制で臨んだことが伺えます。

現在私が携わっているプロダクトでも大きなテーブルのマイグレーションには苦しんでおり、オンラインDDLの注意点や段階的なリリース手法など、ぜひ今後の参考にしたいセッションでした。

おわりに

全体的なセッションの傾向として、実際のプロダクト開発に関連する内容のものが多くを占めており、 drinkupや懇親会の会場でもプロダクト開発の話題が数多く飛び交っていたように思えます。 Kaigi on Railsを軸にして、Railsまわりの知見の交換が行われているのを感じました。

今回のイベントで得た知見を、私も日々のプロダクト開発に活かしたいなと思いました。 Kaigi on Railsへの参加は初めてだったのですが、とても充実した2日間でした!

Afterイベントやります!

connpass.com

11/9(木)の19時から、メドピア株式会社、株式会社スマートバンクさん、株式会社マイベストさんの3社合同で、アフターイベント「After Kaigi on Rails LT Night」を行います。

各社から1名ずつのLTと公募によるLTが3つの、計6つのLTが行われる予定です。 会場はメドピアのオフィスで、最寄り駅は東銀座駅となります。 RubyやRailsの関連技術について、食事とともにお話できる場になればなと思います。

ご興味ありましたら上記リンクからぜひご参加ください!


是非読者になってください!


メドピアでは一緒に働く仲間を募集しています。
ご応募をお待ちしております!

■募集ポジションはこちら

medpeer.co.jp

■エンジニア紹介ページはこちら

engineer.medpeer.co.jp

Vue 2 の EOL まで 2 ヶ月ですが進捗どうですか?~Vue Fes Japan 2023 ゴールドスポンサーとして登壇します~

フロントエンドの小林和弘です。

遂にオフラインでの開催となった Vue Fes Japan 2023 が今月末に迫っています。
2019 年は台風、2020 年、2021 年は新型コロナウィルス感染症による開催見送り、去年は感染予防のためオンライン開催となっていました。
2018 年以来、実に 5 年ぶりのオフラインカンファレンスです(めでたい)🎉🎉🎉

vuefes.jp

メドピアは例年に引き続き Vue Fes Japan 2023 にゴールドスポンサーとして協賛しています。
(去年に引き続き、個人スポンサーもさせてもらいました)

その他にセッションルームネーミングライツスポンサー、スペシャルランチスポンサーとしても協賛しています。
タイムテーブル上の 4 つのトラックのうちのひとつが「メドピアトラック」という名前になっていて、さらにランチタイムでは「メドピアトラック」にてスペシャルランチセッションのお時間をいただいています。 そこでは Vue3 の migration についてのお話をする予定です。

セッションの概要

メドピアではいくつもの医療系サービスを開発・運用しています。そのほとんどのサービスで Vue を使わせてもらっています。

Vue は Single File Component で双方向データバインディングができるため Multi Page Application で部分的にリッチな UI が簡単につくれたり、Nuxt を使って Single Page Application が構築できたりする非常に便利なフレームワークだと思っています。

その Vue ですが Vue2 が 2023 年 12 月 31 日に LTS が終了して EOL を迎えてしまいます。Nuxt2 も同日に EOL になります。
年始にも Vue の開発者の Evan You がブログのポストで EOL についてリマインドのアナウンスを行っていました。今年は Vue2 / Nuxt2 の migration に追われたプロジェクトがいくつもあると思います。

Vue Fes Japan 2023 のランチセッションでは、メドピアで利用している Vue2 / Nuxt2 の migration をどのようにして行っているのか紹介したいと思います。
migration 中のプロジェクト、migration を考えているプロジェクトの一助になれば幸いです。

vuefes.jp

ご興味がある方は、Vue Fes Japan 2023 のランチセッションに足を運んでみてください。

ブース出展について

会場ではブースも出展します。

ブースに足を運んでいただくと、お酒との相性をセルフチェックできる「アルコールパッチテスト」をお試しいただけます。アフターパーティーで飲酒される方はぜひ試してみてください🍻
「アルコールパッチテスト」をお試しいただいて、X(旧 Twitter)で結果投票に参加いただくと大きなオリジナルバッグがもらえます 👜

アルコールパッチテストをするとオリジナルバッグがもらえます

また、メドピアのノベルティグッズも配布する予定です。
LINE スタンプにもなっているメドピア公式キャラクター「メドベア」がプリントされたかわいいノベルティグッズです。ご興味がある方は会場でゲットしてみてください。

メドベアのノベルティグッズと現場猫の VPoT

アフターイベントについて

Vue Fes Japan 2023 の 2 週間後、2023 年 11 月 7 日(火)にメドピア株式会社、MNTSQ 株式会社、及び株式会社 hacomono で Vue Fes Japan 2023 After Meetup を開催します。
Vue.js 日本ユーザーグループ代表の kazupon さんを特別ゲストとして迎え、セッションやパネルディスカッションを行います。

Vue Fes Japan 2023 と同じく、アフターイベントもオフライン開催を予定しています。
会場はメドピアのオフィスで、最寄り駅は東銀座駅になっています。

medpeer.connpass.com

こちらのイベントもご興味がある方はぜひ参加してみてください。


是非読者になってください!


メドピアでは一緒に働く仲間を募集しています。
ご応募をお待ちしております!

■募集ポジションはこちら

medpeer.co.jp

■エンジニア紹介ページはこちら

engineer.medpeer.co.jp

A/BテストツールとしてCloudWatch Evidentlyを導入してみた

サーバーサイドエンジニアの熊木(@k_kumaki_)です。

先日、私が担当しているヤクメドにA/BテストツールとしてAWSのサービスであるCloudWatch Evidentlyを導入したので、その経緯や内容についてまとめます。

目次

CloudWatch Evidentlyとは

AWS上でA/Bテストやフィーチャーフラグの管理ができるサービスです。 比較的新しいサービスのため、馴染みのない方も多いかもしれません。

aws.amazon.com

導入に至った経緯

私が開発しているサービスであるヤクメドでは、UX向上のためA/Bテストを実施しています。

そのA/Bテストツールとして、Google Optimizeを使用していましたが、この度2023年9月30日をもってサポートが終了することが発表されました。そのため、A/Bテストの代替案を探す必要がありました。

導入理由

一番の理由は低価格であることです。 CloudWatch EvidentlyではEvidentlyイベントとEvidently分析ユニットに基づいて課金が発生する仕組みになっています。 これをもとに料金を試算すると、他のサービスに比べてかなり低額でA/Bテストを実施できるためCloudWatch Evidentlyを採用することとしました。

docs.aws.amazon.com

導入方法

構成図

1. プロジェクトの作成

ここではプロジェクト名と説明を設定するのみです。 また、データストアとしてS3かCloudWatch Logsが選択できるので、今回はS3を選択しました。 発生したイベントをデータストアに保存して、他のサービスと組み合わせることでより柔軟な分析が可能になります。

ヤクメドではTerraformでAWSリソースの管理をしており、以下のコードで作成しました。

resource "aws_evidently_project" "evidently" {
  name        = "${local.prefix}-evidently"
  description = "${local.prefix}-evidently"

  data_delivery {
    s3_destination {
      bucket = aws_s3_bucket.evidently_logs.id
      prefix = "${local.prefix}-evidently"
    }
  }

  tags = {
    Name = "${local.prefix}-evidently"
  }

  depends_on = [aws_s3_bucket_policy.evidently_logs]
}

2. 機能の追加

次に作成したプロジェクトに機能を追加します。 どういった分岐をするか、ユーザートラフィックを何%ずつ割り振るかなどの設定を行います。

3. アプリ側の対応

ヤクメドではバックエンドはRailsで書かれているため、CloudWatch EvidentlyのSDKを導入しました。

docs.aws.amazon.com

どこからでも使用できるA/Bテスト用のモジュールを作成し、以下のようなリクエストをCloudWatch Evidentlyに送信します。

evidently_client.evaluate_feature(
  {
    entity_id: entity_id, # ユーザーを特定する一意のID
    feature: feature, # 設定した機能名
    project: project, # 設定したプロジェクト名
  }
)

レスポンスとして、以下のような形式で返ってきます。 今回は機能でブール値を設定したためvalueとしてbool_value が返却されており、これをもとにアプリ内で分岐をさせることができます。

#<struct Aws::CloudWatchEvidently::Types::EvaluateFeatureResponse
 details="{}",
 reason="DEFAULT",
 value=#<struct Aws::CloudWatchEvidently::Types::VariableValue::BoolValue bool_value=true, double_value=nil, long_value=nil, string_value=nil, unknown=nil>,
 variation="LP">

よかった点

自分で細かな定義が可能

  • アプリ側で設定している情報に対して細かく制御が可能
    • 例えば、特定の地域のユーザーやChromeを使用しているユーザーなど細かく分けられます

参考: https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/CloudWatch-Evidently-segments.html

導入が簡単

  • この記事にも書いた通り、元々AWSを使っているサービスであればかなり簡単に導入することが可能です

終わりに

今回は、シンプルな構成での導入をご紹介しました。

CloudWatch Evidentlyを導入してみてまだ数週間ですが、Google Optimizeと遜色なくA/Bテストを行うことができています。 この記事が、A/Bテストツールでお悩み中の方の参考になれば幸いです。


是非読者になってください!


メドピアでは一緒に働く仲間を募集しています。
ご応募をお待ちしております!

■募集ポジションはこちら

medpeer.co.jp

■エンジニア紹介ページはこちら

engineer.medpeer.co.jp

Kaigi on Rails 2023に@lni_Tが登壇します & メドピアが協賛します #kaigionrails

皆様こんにちは、メドピアのサーバーサイドエンジニアの草分( @lni_T )です。

この度、2023/10/27(金)-28(土)の2日間で開催される「Kaigi on Rails 2023」に登壇させていただくこととなりました!
タイトルは「Turbolinksアレルギー患者に捧げるTurbo & Stimulusでの時短実装術」となります。

kaigionrails.org

スケジュールは、
Day1 16:50 〜 17:05 / Room B
を予定しています。 ぜひセッションにお越しくださいませ。

9月には大阪ruby会議03松江Ruby会議10 にて登壇させていただきましたが、それに続いて今月は東京での登壇となります。
先月のセッションも聞いていただいた方は、今月もぜひよろしくお願いします!

協賛について

メドピアはGold SponsorsとしてKaigi on Rails 2023に協賛しております!

kaigionrails.org

登壇内容について

セッションでは以下の内容をお伝えします。

皆様、Railsのフロントエンドツール「Hotwire」は使っていますか?
Rails 7からはデフォルトで採用されており、「Turbo」や「Stimulus」といったライブラリが利用できます。

ですが、利用者があまり多くなかった「Turbolinks」のイメージに影響されて、利用を避けている方は居ませんか?

このトークでは、実際のバックエンドリプレイス案件において、
Turbo & Stimulusを採用することで開発工数を大幅に削減できた事例、および実装方法についてご紹介します。

Hotwireは、JavaScriptをあまり書かずにモダンなWebアプリケーションを実現するフレームワークで、JSONではなくHTMLをやりとりすることが特徴です。
RailsのController/Viewのみでは手間がかかる画面の実装において、Hotwireは大きな効力を発揮してくれます。

セッションでは、そんなHotwireの活用例やノウハウを皆様に紹介します。

見どころは?

公式ページにも記載した通り、Hotwireを実際の開発案件での活用事例をお話しします。

背景となったメドピアの事業はこちらです。

medpeer.co.jp

「事業譲受」をおこなったため、システムもそのまま移行したかのように見えますが、実はバックエンド側については、ほぼ全てをRailsアプリでリプレイスしています。

限られた時間でリプレイスを進めるにあたり、画面実装だけに時間を割いている余裕はありません。
そんな中でも、Hotwireの「少ない労力でフロントエンドが実装できる」利点を活かすことで、無事にサービスをリリースすることができました。

今回のセッションでは、そんな【鉄火場での活用事例】をお伝えできればと考えています。

おわりに

Kaigi on Railsとしては初のオフライン/オンライン同時開催とのことで、どのような会になるのか非常に楽しみですね。
チケット購入がまだの方はこちらよりお求めください。 kaigionrails.doorkeeper.jp

それでは皆様、お会いできることを楽しみにしております!


是非読者になってください!


メドピアでは一緒に働く仲間を募集しています。
ご応募をお待ちしております!

■募集ポジションはこちら

medpeer.co.jp

■エンジニア紹介ページはこちら

engineer.medpeer.co.jp

【Nuxt 3移行】ユニットテストをNuxt 2から移行し、実行速度が4倍速くなった話

こんにちは。フロントエンドエンジニアの相澤 ( @ttt3pu ) です。

みなさま、Nuxt 2 から Nuxt 3 へのアップグレードは順調でしょうか。

メドピアでは、2023年末のVue 2のEOLへ向けて、
各プロダクトで積極的にNuxt 3へのアップグレードを進めています。

現在私の担当しているプロダクトでは、マイグレーション作業自体はほぼ完了しており、
残すはQAテストなどを行うのみと言う段階で、本番リリースまであと一歩というところまで進んでおります! 🎉

マイグレーションの事例も徐々に増え始めてきて、Nuxt 3のリリース当初よりも段々と移行はしやすくなってきましたが、
個人的に結構大変だったのがユニットテストのマイグレーション作業でした。

当記事では、マイグレーションに当たっての Tips と、ついでに Vitest を導入したことにより、
実行速度が 約 10分 -> 約2分30秒 ( 約 4倍 ! ) まで跳ね上がった話をご紹介します。

目次

対象プロジェクトのユニットテスト周りのライブラリ構成

まず、今回マイグレーション作業を行なったプロジェクトは、以下のようなライブラリ構成で構築されていました。

移行後は、以下のようなライブラリ構成となりました。

Jest は廃止し、 Vitest へ移行しています。

vue-test-utilsについては、Vue 3対応しているのがv2以降となるため、バージョンが上がっています。

今回肝となったのが「nuxt-vitest」の導入でした。
Nuxt 3 + Vitest の実行環境を用意してくれるライブラリです。
詳しい内容については後述させていただきます。

移行完了までのステップ

プロダクトの実装状況によって多少順番が変わってくるとは思いますが、
テストが全て通るまでに、以下のステップで作業を行いました。

  1. Jest から Vitest へ移行
  2. nuxt-vitestを導入
  3. vue-test-utils の v1 から v2 へのマイグレーション作業を実施
  4. 落ちているテストごとの個別修正
  5. Vitest の設定を調整し速度改善

ここから先は、それぞれのステップで行なった作業について、詳しくご紹介させていただきます。

Jest から Vitest への移行

一番最初のステップとして、nuxt-vitestを導入する前準備として、JestからVitestへの移行を行いました。

Jestとは互換性が高いので、導入はほとんど苦になりませんでした。

ざっくりとまとめると、以下の作業を行うだけで移行が完了しました。

  • jest.config.ts の各設定を vitest.cofig.ts へ移行する
  • jest メソッドを vi へ置換する
    • 例: jest.fn -> vi.fnjest.spyOn-> vi.spyOn など
  • npm scripts等にCLIの記述があれば変更する

詳細については、公式の Migration Guide をご参照ください!

vitest.dev

nuxt-vitest の導入

続いて nuxt-vitest を導入します。

nuxt-vitest は、Nuxt の開発コアメンバーである Daniel さんによって開発されている、Nuxt 3 + Vitest の実行環境を用意してくれるライブラリです。

github.com

導入することより、自分で実装しようとするとかなり複雑になってしまうような設定を、ある程度自動で行なってくれるようになります。
コアメンバーが開発しているということもあり、メンテナンスもNuxt本体のアップグレードに合わせて頻繁に行われているので安心です。

導入方法もとても簡単です。
nuxt-vitest をインストール後、 nuxt.config.tsvitest.config.ts にそれぞれ読み込ませたら完了です!

※ バージョンによって導入方法が変わる可能性があるため、詳細は公式の README をご参照ください。

github.com

// nuxt.config.ts の設定例
export default defineNuxtConfig({
  // ...
  modules: [
    'nuxt-vitest'
  ]
})

// vitest.config.ts の設定例
import { defineVitestConfig } from 'nuxt-vitest/config'

export default defineVitestConfig({
  test: {
    environment: 'nuxt',
  },
});

実はこの時点でこのライブラリの恩恵をかなり受けることができており、
vitest.config.ts 内の記述をかなりスッキリさせることができています。

この時点で nuxt-vitest なしで実行しようとした場合、
useNuxtApp や useRoute 等の、 #importsから使用するメソッド類 の import 周りだったり・・・
composables と component のAuto Import 周りだったり・・・
等の問題が出てきてコケてしまいます。

この問題を手動で直すのはかなり難易度が高いため、自動で補完してくれるのはかなり助かりました。

また、 nuxt-vitest には、環境構築用の module だけでなく、
mockNuxtImport 等のユニットテスト用のヘルパーも用意されています。

これらの詳しい使い方については後述させていただきます。

vue-test-utils のマイグレーション作業を実施

ひとまずこの時点で vitest コマンドが正常に実行できる状態にはなるはずなので、
ここから先はspecファイル内の記述の修正を行なっていきます。

公式で Migration Guide が用意されているため、これに沿って実施を行なっていきます。

test-utils.vuejs.org

変更内容としてはそこまで難しくはないのですが、変更量はどうしても多くなってしまう感じでした。

大きいところだと stubsplugins 等のオプションを global の中に入れる必要が出てきたこと等でしょうか。
これが地味に結構大変でした・・。

// before
const wrapper = mount(Component, {
  stubs: {
    ...
  },
})

// after
const wrapper = mount(Component, {
  global: {
    stubs: {
      ...
    },
  },
})

落ちているテストごとの個別修正

この時点である程度テストは通るようになったと思います。
ここから先はテストごとに個別修正をしていきます。

ここから先はプロダクトによって臨機応変に対応を行う必要がありそうですが、
個人的に大変だった部分をいくつかピックアップして記載させていただきます。

Composition API 内で setData メソッドを使用している箇所の修正

vue-test-utils で用意されている、 data の値を変更するメソッドとして setData というものがあります。

test-utils.vuejs.org

このメソッドは v1 の時はComposition API を使用しているコンポーネントでも動いていてくれたのですが、 v2 からはうまく動作がしなくなってしまいました。

そのため、以下のような形で代用することで対応しました。

// before
const wrapper = mount(Component);
await wrapper.setData({ count: 1 });  
expect(wrapper.html()).toContain('Count: 1')

// after
const wrapper = mount(Component);
wrapper.vm.count = 1;
await flushPromises();
expect(wrapper.html()).toContain('Count: 1')

useRoute などの #imports から使用するメソッドのモック化

色々やり方はあると思いますが、
私たちのプロダクトでは、useRoute のモック化を Nuxt 2 環境では以下のような形で行なっていました。

// hoge.vue
<script>
const useRoute();
...
</script>

// hoge.spec.ts
const wrapper = mount(Component, {
  mocks: {
    $route: {
        path: '/hoge',
    },
  },
}) 
...

Nuxt 3 ではこの方法ではモック化ができなくなるため、修正を行う必要があります。

ここで nuxt-vitest に用意されているヘルパーメソッドが活躍します。
mockNuxtImport を使用することによって、以下のような記述で mock 化を行うことができます。

import { mockNuxtImport } from 'nuxt-vitest/utils'

mockNuxtImport('useRoute', () => {
  return () => {
    return {
      path: '/hoge',
    },
  }
})

ここも nuxt-vitest を使わなかったら更にひと工夫がいるであろう箇所のため、かなりの助かりポイントでした。

useRoute 以外のメソッドに関しても、同様の方法で対応を行うことができます。

Vitest の設定を調整し速度改善

なんとかテストが全て通るようになりましたが、
ここでせっかく Jest から Vitest に移行したのにあまり速度が変わっていないことに気づきます。

詳しく調べてみると --single-thread と言うオプションがあることがわかり、
このオプションを有効にしたところ、
冒頭に記載した通り速度が 10分 -> 2分30秒 ( 約 4倍 ! ) にまで跳ね上がりました!

vitest.dev

# コマンドの実行例
yarn vitest --single-thread --coverage

このオプションは名前の通り、シングルスレッドでテストを実行させるオプションで、
ざっくりとまとめると、

  • 無効にした場合 -> テストごとに別々の環境を作成した上で実行される
  • 有効にした場合 -> 同一の環境でテストが実行されるため、初期化を繰り返すコストを回避できる

という挙動を実現してくれるようです。

今回対応を行なったプロダクトは弊社内では規模が大きめのもので、 テストファイル総数 178件、テスト総数 854件 と実行される数も多いです。
そんな中、しかもcoverage付きでこの速度というのはなかなか感動しました・・・ ✨

ただし、公式の Docs に記載されている通り、実行する環境によっては、このオプションを使用した場合うまくいかない場合もあるようなので、そこに関しては注意が必要そうです。

WARNING

Even though this option will force tests to run one after another, this option is different from Jest's --runInBand. Vitest uses workers not only for running tests in parallel, but also to provide isolation. By disabling this option, your tests will run sequentially, but in the same global context, so you must provide isolation yourself.

This might cause all sorts of issues, if you are relying on global state (frontend frameworks usually do) or your code relies on environment to be defined separately for each test. But can be a speed boost for your tests (up to 3 times faster), that don't necessarily rely on global state or can easily bypass that.

最後に

Nuxt 3 本体のマイグレーションについては事例が徐々に出てきてはいるものの、テスト周りはまだ情報が少なくなかなか大変でした。
この記事がみなさまの Nuxt 3 アップグレードの助けになれば幸いです!


是非読者になってください!


メドピアでは一緒に働く仲間を募集しています。
ご応募をお待ちしております!

■募集ポジションはこちら

medpeer.co.jp

■エンジニア紹介ページはこちら

engineer.medpeer.co.jp