Slide 1

Slide 1 text

1 福岡のCXPチームの紹介と開発の工夫 フロントエンドカンファレンス福岡スピンオフ 〜フロントエンドの現場 in 福岡〜 2021.09.22

Slide 2

Slide 2 text

2 Camp5(CRE)
 CXP team - Tech Lead
 2020/02 Join
 
 主にフロントエンド領域をやっている 
 フロントエンドカンファレンス福岡の 
 初代委員長
 渋田 達也 (@mya_ake)


Slide 3

Slide 3 text

3 CXP teamについて 今日の話 開発フローや工夫について 採用について 02 03 01 Reactなどのライブラリの知見についてなどの話はありません mm

Slide 4

Slide 4 text

4 多分時間足りない 見返せるように文量多めにスライド作ってるのでよろしくmm

Slide 5

Slide 5 text

5 CXP teamついて

Slide 6

Slide 6 text

6 ● CREについてなどは過去に「Mercari CS/CRE Tech Talk #1 CSプラット フォームの裏側」というイベントを行っているのでそちらをご覧ください ● https://www.youtube.com/watch?v=qasx6PiNAyQ Camp5(CRE)に所属しているチームで、Customer Experience Platform teamという名称 CXP team

Slide 7

Slide 7 text

7 CXPチームのミッション Misson  お客さまの課題解決を後押しする  カスタマーサービスプラットフォームを提供する  お問い合わせなどを通した顧客体験の改善、お問い合わせ対応業務の効率化・品質向上を  エンジニアリングでサポートする Help Center Contact Form Contact Tool

Slide 8

Slide 8 text

8 メルカリの中では珍しいクロスファンクショナルなチーム チーム構成 ● 各人数 ○ Product Manager: 1人 ○ Engineering Manager: 1人 ○ Frontend Engineer: 3人 ○ Backend Engineer: 3人 ● この他の役割としてTech LeadとScrum Masterを各1名担当する ● FE / BEでメンバーはそれぞれいるが ”BEがFEのタスクをやる” またはその逆 などクロスファンクショナルに仕事をしている ○ ※それぞれのスキルは必須ではない

Slide 9

Slide 9 text

9 CXPが所有するサービスについて

Slide 10

Slide 10 text

10 ● Next.js ○ Static HTML Export ● API: GraphQL ○ Apollo Client ○ データが最新であることが重要 なのでキャッシュは非活用 ● Global Store: Redux ○ データの操作が多いため Flux Architectureに載せたくなり導 入を進めている ● UI: Ant Design ● Testing: Jest ○ E2E(Client only)には Playwrightを利用 Contact Tool - CSが使うお問い合わせ対応業務に関するツール

Slide 11

Slide 11 text

11 ● Next.js ○ Static HTML Export ● API: Protocol Buffers ● Global Store: Recoil ○ シンプルな状態の共有が主とな るためRecoilを選択 ● UI: Design System Web + Tailwind CSS ○ Tailwind CSSからDSが主に なっていく予定 ● Testing: Jest ○ E2E(Client only)には Playwrightを利用 Help Center - お問い合わせに関するアプリケーション

Slide 12

Slide 12 text

12 開発フローについて

Slide 13

Slide 13 text

13 現在は 2 weeks スプリントのスクラムでプロジェクトを進めている。チームで運用し ていくなかで独自に定義しているものもある 開発フロー - スクラム ● Sprint Planning(スプリント頭1回): 次のスプリントに実施するチケットの確認 &決定と スプリントゴールの策定 ● Daily Stand up(毎日): スプリントの現状の確認と課題共有 ● Product Backlog Refinement(週1): 新規チケットの共有、既存チケットの確認 & 修正 ● Mid Sprint Review(スプリント中1回): Dailyよりも細かに進捗の確認や課題の共有 を行いスプリントゴールの達成に向け調整する ● Sprint Retrospective(スプリント末1回): スプリントがどうだったかを振り返り、プロセ スの改善に向けたTRYを定める

Slide 14

Slide 14 text

14 Development → PR → Review → Merge to Main Branch → Release to Development & Check → Release to Production ● メインブランチのコードは本番で稼働している状態であること ○ 本番リリースは定期ではなくPRがマージされた数だけ行う ■ 直近の実績でいくと昨日今日でHelpCenterは8回リリースしている ○ Feature Flagを用いて、本番では開発途中の機能が利用できない様にし、機能開発が 完了するとFeature Flagを外して、機能を利用できるようにする機能リリースを行う ● 開発時はペアプロやモブプロをすることもある ● PRのレビュー時にペアレビュー、モブレビューをすることもある ○ でかくなってしまったPRや難しいPRの場合にReviewerとRevieweeが会話しながらレ ビューし、レビュー時間の短縮と知見共有を行う 開発フロー - 開発からリリースまで

Slide 15

Slide 15 text

15 工夫について どのようにして高頻度リリースを実現しているのか

Slide 16

Slide 16 text

16 高頻度リリースができる要因 Feature Flag テスト自動化 開発中の機能が含まれる コードでも本番にリリース することができる CIがパスすればアプリ ケーションとしての動作が 一定保証できる状態にあ る

Slide 17

Slide 17 text

17 スキーマ駆動開発 ● Contact ToolではGraphQL、Help CenterではProtocol Buffersを利用 ● スキーマを間に立たせて、お互いに生成されたコードを利用することで、インターフェースの ズレが発生しないようになっている ● もちろんTypeScriptの型も生成される FE/BEともにスキーマからコード生成し、インターフェースを統一している

Slide 18

Slide 18 text

18 データの生成関数 ● テスト向けにデフォルトで値 を入れつつ引数で任意の値を 設定可能にしている ● デフォルト値はfaker.jsなど を利用しランダム性を持た せることもある ● as を使って適宜書くこともできるが、プロパティが不足していた場合は正しいデータとは言 い切れない。またプロパティ数が多いと都度書くのも手間となってくる ... ● Objectではなく関数で生成している理由は参照を使い回さないため ● 生成された型から生成関数も自動生成したいなと思ってはいる スキーマから生成された型を元に生成関数を作り、型を維持しつつテストなどで任意 の値を利用できるようにする

Slide 19

Slide 19 text

19 ● Apollo ServerやExpressなどなんでもよいのでAPIサーバーを作る ● ランダム性のある各APIのレスポンスを用意する ○ 文字列の長い短い、データの有無などの対応漏れに早く気づく ● DBは用意せずにメモリ上にデータを持たせておくだけで十分 ○ Redux Tool Kitを利用するとデータの操作が作りやすい ● Apollo Serverのモック機能を利用して、簡易的にレスポンスを作ることもできる ○ ただ実際はデータの整合性がないと動かしながら開発するには不十分であり、自作し た方が任意の状態を再現しやすく役に立つことも多い ○ 整合性が不要な部分に関しては存分にモック機能を使えば OK ● 作るまでが大変ではあるが、開発時テスト時にも使えるので作るメリットは多い モックサーバー データの生成関数を利用して、APIのレスポンスを再現させたサーバーを作り、開発 時やテストで利用できるようにしている

Slide 20

Slide 20 text

20 E2E Testing (Client only) ● Contact Toolであれば、お問い合わせ業務が一通りできることをこのテストで担保させて いる ○ CIが通ればクライアント起因でCSの業務が停止することはないと言える状態となる ● ただランダム性のあるデータのため、たまにテストが通らないことがある ○ 原因は高速でテストが実行されていくため、通知が積み重なり次の動作の ボタンが押せなくなる現象が起こりタイムアウトしてしまう ○ 落ちたときは合計3回までリトライする仕様にしている モックサーバーを相手にフロントエンド側だけのE2Eテストを行い、最低限動作する かどうかをCIで担保させる

Slide 21

Slide 21 text

21 Feature Flag ● Feature Toggleともいう ● →のようにFeatureNameと いう型を用意して、その型を 引数とする判定関数+この関数 を元にレンダリングを判定 するコンポーネントを用意 ● 機能の利用可否が分かれる箇所にこの関数やコンポーネントを配置し、条件を満たすかど うかで機能が使えるかどうかを切り分ける ● 機能リリースをするときはFeatureName型から機能名を消すことで、該当箇所が型エ ラーとなるので、それを解消していけばもれのない機能リリースに繋げられる 機能を利用可否を制御することで開発中の機能が含まれるコードでも本番環境へリ リースできる仕組み

Slide 22

Slide 22 text

22 まとめ

Slide 23

Slide 23 text

23 今回のまとめ ● フロントエンドはNext.jsを利用していて、スキーマを元に APIのインターフェースを決定し開 発している ● メインブランチにマージされたコードは問題なければすぐにリリースする ● 高頻度リリースを可能にするためにテスト自動化と Feature Flagによる機能制御を行って いる ● モックサーバーを用意しローカル開発 &E2E Testing(Client only)で利用 ○ ランダム性のあるデータを用いることで開発時に UIの崩れや考慮漏れがないかを早 期にチェックできる ○ E2E Testingでは落ちることがあるのでリトライさせている。それでも落ちるならそれ はデグレていることになる チームや持っているサービスの紹介、開発フローやそのフローを実現するために工 夫の話をした

Slide 24

Slide 24 text

24 採用について ● 「メルカリ 採用」で検索 ○ エンジニアリングポジションだけで 67件の募集(2021/09/22時点) ○ https://careers.mercari.com/jp/search-jobs/?dep=engineering ● YOUR CHOICEが始まり働く場所が自由に(国内である必要はある) ○ 九州にいながら東京のポジションで働くということも可能に ○ https://about.mercari.com/press/news/articles/20210901_yourchoice/ ● Meetyでも多くのメルカリ社員の人とカジュアル面談できるのでお気軽にどうぞ ○ 僕ともできるので気になる方は↓からどうぞ ○ https://meety.net/matches/koeeMSidgnjo 現在メルカリは全社的に採用を強化しています!

Slide 25

Slide 25 text

25 質問に対する回答 参加者の事前アンケートにあった質問に回答していく

Slide 26

Slide 26 text

26 今のポジションへのキャリアパス ● 略歴 ○ 情報系学部 → 独立系SIer → フリーランス → 起業に参画して一応CTO → ウミーベ → フリーランス → メルカリ ● CXP team では Tech Lead はローテーションしている ○ メルカリにおける Tech Lead はあくまで役割 ○ 各チームごとに決めているので決められたなり方は特にない 今はメルカリのTech Leadという役割

Slide 27

Slide 27 text

27 後進の育成について ● 入社してしばらくはメンバーと一緒に作業して仕事に慣れてもらう ● 週に1回 FE/BE でそれぞれMeetingをしている ○ ライブラリのアップデート情報の共有 ○ コードの構造やリファクタリングの方向性の話 ○ FEがBEのMeetingに参加するなどは任意 ● ペアプロやコードレビューを通して知識を合わせる ● 社内にGo道場などの資料もあるので、社内の資料を活用したりもする 特に変わったことはしてないように思う

Slide 28

Slide 28 text

28 副業について ● むしろ推奨している ○ https://careers.mercari.com/jp/benefits/ ● 自分は副業してるかどうか ○ 現状はしていない ■ 昔書いた本の収入がちょこちょこあるぐらい ○ 今は子どももいて副業している余裕はないので当面はやらないつもりでいる メルカリとしては副業OK

Slide 29

Slide 29 text

29 環境や現場について ● 他に聞きたいことがあれば質問してください 今日書いたスライドを見てください🙏

Slide 30

Slide 30 text

30 リモートワークでのコミュニケーション・開発方法の工夫 ● コミュニケーション ○ Google meetやSlack huddleをいつでもつないでいい ■ 必要なときに必要な人に声をかける ■ 毎日 15:00 に Tea time があり雑談をしている ○ それぞれがSlackの個人チャンネルを持ってたりするのでそこを Twitterのように使っ てみたりなど ● 開発方法の工夫 ○ 今日のスライドの途中でも出てきましたがペアプロやペアレビューなど ○ 話す必要があるような事柄があれば都度 Meetingで話す 常に通話しているわけではなく必要なときにつなぐスタイル

Slide 31

Slide 31 text

31 補足 本題に入れなかった情報たち

Slide 32

Slide 32 text

32 ライブラリアップデート ● チケット化されており、ライブラリアップデートがスプリントの進捗に組み込まれる状態になっ ている ● CIの自動テストで機能的な担保はできているので、細かな動作確認はしなくても問題がな く、主に変更内容の確認をしてからマージするというような作業であり、負担はそこまで大き くない ○ リリース前に実機確認はしている ライブラリアップデートするためのチケットが存在し、毎週実施できるようにスプリント に組み込まれている

Slide 33

Slide 33 text

33 システム要件とビジネス要件の分離① ● ここでいうシステム要件とビジネス要件 ○ システム要件:サービスを提供する上で欠かせない要件 ○ ビジネス要件:なにかしらを計測をしたいや Google Analyticsでトラッキングしたい などの要件 ● ビジネス要件というのは後から入りがちでシステム要件に食い込んできがち ○ テストコードなどでも考慮する必要が出てくる ● そこでなるべく分離したコード構成にしたい ● 具体的にはEventObserverを作り、クリックイベントやReduxのActionなどを集約して、 必要な要件についてはEventをsubscribeする形でシステム要件の外に置くようにしたい と思っている これからの展望の話

Slide 34

Slide 34 text

34 システム要件とビジネス要件の分離② ● 必要そうなEventをあらかじめ 集めておいて、必要な機能が出て きたら、それをSubscribeして 作るイメージ ※まだ構想段階なのであくまでイメージ 図にするとこんな感じ