Application)フレームワークを組み合わせたアプリケーションでSSR(サーバサイドレンダリング)を行うための仕組みについてサーバ側の構成を中心に説明しました。今回はクライアント側の構成について説明し、実際にページを追加する手順についても紹介します。本稿では、以下の環境で動作を確認しています。CoreとSPAフレームワークの連携箇所を確認しよう(クライアントサイド)SPAの実装となるクライアント側のコード(HTML、CSS、JavaScript等)は、ClientAppディレクトリに配置されています。AngularやReactなどのSPAフレームワークを使ったコードはここに、各SPAフレームワークのコーディングルールに従って実装していくことになります。今回、SPAフレームワークとして選択したAngularの詳しい内容については、こちらの連載も参考にしてください。以下はClientApp配下のディレクトリ構造で、サーバサイドレンダリングに関連するものを抜粋したものです。これらはプロジェクトテンプレートからプロジェクトを作成した際にあらかじめ用意されているものですが、それぞれどのような役割を担っているのかをコードを見ながら確認していきます。webpackでひとまとめにビルドした結果のファイルboot.server.tsboot.server.tsは、サーバサイドレンダリングを実行する際のクライアント側のエントリーポイントです。Coreが提供するサーバサイドレンダリング用のモジュール(createServerRenderer)でラップしています。Coreより提供されているnpmパッケージである「aspnet-prerendering」のcreateServerRenderer関数を呼び出しています。この関数は、「Angularによるクライアントモジュールの初期化処理結果」を引数にとり、実際にNode.jsを使ってサーバサイドでHTMLを構築する役割を持っています。「Angularによるクライアントモジュールの初期化処理」を行っているのが(2)以降の処理です。(2)ではまず、Angularが提供するサーバサイドレンダリング用のnpmパッケージ「@angular/platform-server」内のplatformDynamicServer関数を呼び出しています。platformDynamicServer関数の引数にはそのすぐ上で定義しているprovides配列を渡しています。providers配列では、アプリケーションの初期設定情報を定義しています。platformDynamicServer関数の戻り値を使い、次にbootstrapModule関数を呼び出しています。この関数はルートモジュールであるAppModuleを引数にとりモジュールを起動します(AppModuleについては後ほど説明します)。モジュールを起動すると、モジュールの参照を非同期で取得できるので、それを使用してレンダリング結果を表すPromiseオブジェクトを生成します(3)。モジュールの参照から取得できるレンダリング結果文字列を(4)のようにオブジェクトのhtmlプロパティに設定してPromiseオブジェクトのresolveとして返すことで、(1)のcreateServerRenderer関数内部でその文字列をDOMに注入することができるようになります。簡潔化した処理の流れは図1の通りです。boot.server.tsの処理の流れapp/app.module.server.ts(ルートモジュール)Angularアプリケーションのルートモジュールと呼ばれるモジュールです。ルートと呼ばれる通り、Angularを使って作成したコンポーネントは、依存関係をたどると必ずこのルートモジュールに行き着くように実装する必要があります。{}ここでも「ServerModule」という、Angularが提供するサーバサイドレンダリング用のモジュールをインポートします(1)。各画面の実装であるコンポーネントを一括管理しているAppModuleSharedもインポートしています(2)。app/app.module.shared.ts(AppModuleSharedモジュール)AppModuleSharedモジュールでは、前述したコンポーネントの一括管理とアプリケーションのルーティング定義を行っています。{}このアプリケーションで実装するコンポーネントを@NgModuleデコレータのdeclarationで宣言しています。ページを追加実装する際は、ここにコンポーネントを追記していくことになります。RouterModuleというAngularが提供するルーターを使用し、URLとコンポーネントの対応づけを行っています。ルーター内の「path」の値がそのままURLとなり、アクセスすると対応するコンポーネントの処理が実行されます。app/components/app/app.component.ts(ルートコンポーネント)ルートコンポーネントはアプリケーションの中で最初に呼び出されるコンポーネントです。対応するページ(app.component.html)がベースHTMLとなり、このHTMLのDOMを各ページのものに差し替えていくことでSPAを実現します。{}dist/main-server.jsmain-server.jsはwebpackによってバンドル・ビルドされたクライアント側のコードです。boot.server.tsを起点としてappディレクトリ配下のコードがひとまとまりになっています。Coreでのサーバサイドレンダリングが有効になります。