業務でReactを書くためのハンズオン(toC Web向け)
事前準備
今回、既存のAPI(GraphQL)を使ったページを作るので、以下ブランチに切り替えをお願いします。
‣
npm install
LIPSのフロントエンドについて
知ってる人が多いかもだけどとりあえずこんな感じ
- LIPS (toC)
- 主にRailsのtemplate
- (これから書くときはjQuery使わないようにね。。。)
- LIPS Web
- 新しい画面の一部はこちら
- PC診断・肌診断…
- Next.jsで実装されてます
- 今日扱うのはこれ
- LIPS Shopping
- ショッピング向けの商品一覧・検索画面
- Next.jsで実装されてます
- SaaS (for Brands)
- ほぼReact(SPA)
- あんまり触る人は少ないかも(僕とかkawamitsuさんとか)
- Admin
- Railsのテンプレートが多いが新しいものはReact(SPA)で書かれている
- (なんか大昔のHackdayでハンズオンしたような)
早速作ってみる
今回は単純に商品一覧を表示する画面を作っていきます。
以下ブランチを利用します
‣
ページを実装する
frontend/web/src/pages内にエントリポイントファイル(tsx)をおくと、Next.jsが勝手にルーティングしてくれます。
例えば、今回、`/products/lists`にホスティングしたいなら
内に`lists.page.tsx`を配置して以下のように書いてみてください
もし、stagingでだけ(本番では出したくない)場合は、
ファイル名を`frontend/web/src/pages/products/lists.previewpage.tsx`にするとページにアクセスできなくなります。
しかし、以下のenvを追加するとページにアクセスできるようになります。
コンポーネントを実装する
Reactのコンポーネントを実装します。
今回、商品を一覧で表示したいので商品のセル(カード)が必要なのですが、すでに実装されてます。
Storybookを開いてみましょう。以下コマンドで開くことができます。
Storybookを軽く説明すると、
- コンポーネントを単体で開発できる(ページとかに置かずとも画面に描画できる)
- 実装効率はこちらの方が高い
- コンポーネントのカタログになる
- いろいろなパラメータをUI上で簡単に変更してUIを確認できる
- いろんな機能(Viewport変更)等でコンポーネントの確認がよりやりやすい
- chromatic(外部サイト)とかにもホスティングできて、デザイナへの共有もやりやすい
のでコンポーネントを作る際は基本的にStorybookのファイルも作成してください(大事)
Product>ProductCellに実装されています。
とりあえず商品を引っ張ってこれるようにしておく
基本的にAPI Callは昔懐かしいrestではなく、GraphQLで引っ張ってきます。
localでRailsを実行していると、graphiqlが動いているので、
http://localhost:3000/graphiqlにアクセスして下記queryを実行してみましょう。
ちゃんと実行できていたら、frontend/web/src/graphql内に、productsOnHandson.graphqlとしてクエリを保存し、以下コマンドを実行してください
graphqlの情報から必要な型情報、hooks等が生成されます。
続いて、先ほど書いたを以下のように編集してみましょう
LIPS/Webではapi callにurqlを使っています。
諸々の設定は今回省略しますが、今回、主に以下がパフォーマンス的に重要になるかと思います。
- cacheExchange
- queryとvariable(apiパラメータ)のセットでキャッシュしてくれる
- これを有効化すると子供コンポーネントでのapi callがいい感じにSSR化される
続いて、実際に画面に商品を表示してみましょう
src/components/standalones/Product配下にProcductListPage.tsxを作成してください
useProductsOnHandsonQueryは、先ほどのnpm run gen:webで生成されたcustom hookです。これを元にAPI callを行っています。
今回はSSRを有効化しているので初回表示時はSSR、つまりサーバー側でAPI callが行われます。
先ほどのssrをfalseにすると、Client側で実行されます。
このデータを元にいい感じに整形してproductsに保存、そいつをProductCellに渡して表示してます。
無限ローディングをやってみる
本来だと無限スクロールは自分で実装(DOMの要素が下までスクロールされているかチェックする)とかしないといけないですが、便利なライブラリでそこら辺は簡略化できます。
今回はpagingではなくてoffsetでデータを追加取得する戦略で実装しています。
Reactのhooksに慣れ親しんだ方ならわかるかと思いますが、
- スクロールしてが呼ばれる
- が呼ばれて、fetchの最中でなければoffsetを増やす()
- 副作用により再レンダリングされる
- 内のoffsetが変更されていて、そちらをhookにfetchが走る
という流れです。
おまけ
ページが公開されていない
おそらくnginx側の設定ができてないので、追加してあげる必要がある
(Railsだけでもapi.lipscosme.comにしたい)
認証まわりをアレしたい
Rails側でいい感じにRedirectしてあげないとダメらしい
(認証だけでもマイクロサービスに切り出せるといいなぁ)