JavaScriptフレームワークを取り巻く状況は、常に変化を続けています。近年では、サーバーサイドレンダリング(SSR)とクライアントサイドレンダリング(CSR)のバランスは、重要な検討事項です。
ChatGPTのRemix採用
2024年9月、ChatGPTがNext.jsからRemixに移行したことが明らかになりました。この出来事は、Remixの母体であるReact Router系のコミュニティで大きな話題となり、移行の理由について様々な憶測を呼びました。
JavaScriptエキスパートのWes Bos氏(学習動画教材とかを作っている人)は、ChatGPTのフロントエンドのソースコードを分析し、OpenAIがRemixを採用した理由について独自の考察を展開しました。
緊急で動画を回すWes Bos氏
Wes Bos氏の分析によると、ChatGPTのアプリケーションは、ほぼ完全にクライアントサイドレンダリングで動作しています。初期表示に必要なデータはサーバーサイドでHTMLに埋め込まれ(SSR)、その後の画面遷移やデータ更新はクライアントサイドでAPIを呼び出しを行うという、ハイブリッドなアプローチを採用しています。
内部APIを通常のfetchで呼び出すのでactionも使っていません。isSpaMode=false
になっていることからSPAモードではないです。ウェブサーバーはExpressを使っています。
初期データの埋め込みは、Remixのloader API(useLoaderData)を用いることでサーバーサイドで取得し、クライアントサイドに渡しています。クライアントサイドでは、ページ読み込み完了時点で受け取ったデータを用いてレンダリングを行うため、読み込み後の追加のAPI呼び出しを待つことなく、ユーザーにコンテンツを表示できます。
このように、サーバーサイドとクライアントサイドの役割を調整することで、目的のアーキテクチャが実現されています。
ではなぜOpenAIはこの変更をしたのか? と想像するところがこの話の面白い部分です。
Remix SPAモード*1ではサーバーサイドでのSSRが不要です。起点となる静的なindex.htmlからクライアントサイドレンダリングな単体のシングルページアプリケーションを起動します。
ChatGPTはこのindex.htmlに相当するエントリポイントでユーザー情報などを動的にSSRしてセットして、それをクライアントサイドで画面に描画しています。SSRを起点にしていますが定義上はSPAにもCSRにも当てはまります*2。
これはアイランドアーキテクチャ系のフレームワークで提唱されている、静的なコンテンツと動的なコンテンツの描画をコントロールするという考え方にも似ていますが*3、ChatGPTのアーキテクチャより前段の処理なのでシンプルです。
さかのぼるとreact-rails*4のような従来型MVCフレームワークを用いたJavaScript MPAの構築に近いアプローチとも言えるかもしれません。react-railsはRailsビュー内でサーバーで取得したデータを埋め込み、Reactコンポーネントで使用するための機能を提供します。しかしクライアントサイドのルーティングは提供しません。
近年、SSRの必要性が高まり、BFF (Backend For Frontend) が登場する一方で、ページ埋め込み値(props)にクレデンシャル混入する事故が起きたりして安全なSSRが模索されてきた歴史があります。
Remixのloader APIのように、サーバーサイドで取得したデータをSSRでクライアントサイドにどう渡すのかという部分も最終的な責務を負うJavaScriptフレームワークに移譲され、また世代が一周してきた感じです。
ユーザー体験を重視したSPA開発の潮流
一見すると、Next.jsでも同様のアプローチが可能に思えます*5。 App RouterとNext.js 13で導入されたReact Server Component (RSC) を使用することで、サーバーサイドでデータフェッチを行い、その結果をクライアントサイドに渡してレンダリングすることが可能になります。
OpenAIがRemixを選択した理由は定かではありませんが、ChatGPTの「ログインしたユーザーにサービスを提供する」とか「初期読み込み以降はクライアントサイドに処理を寄せたい」「全世界ユーザーのアクセス規模やセキュリティ」という要件を考慮すると、RemixのCSRに特化したアーキテクチャの方がシンプルに実装できた可能性があります。App Router移行とのトレードオフを考慮して決めたのかもしれません。
ChatGPTの事例は、SPA開発においてユーザー体験を最優先に考えてCSRとSSRのリバランスを行った結果フレームワークの移行にまで繋がった、と想像させます。
パフォーマンスとユーザー体験の両立を目指す、アイランドアーキテクチャ以降の今後のSaaS型のWebアプリケーション開発のトレンドを予見しており注目しています。
私としては公開メディアサイトならRSCやアイランドアーキテクチャのような方向に舵を切リたくなります。しかしVercel自体のサービスのコンソールはSSRでRSC活用してるしコンポーネント要件次第で向き不向きが・・・?
*1:SPA Mode | Remix https://remix.run/docs/en/main/guides/spa-mode
*2:訂正:https://x.com/koichik/status/1832426756147397001
*3:Islands Architecture https://www.patterns.dev/vanilla/islands-architecture/
*4:reactjs/react-rails: Integrate React.js with Rails views and controllers, the asset pipeline, or webpacker. https://github.com/reactjs/react-rails