🤔

改めて人に聞かれると説明が微妙に難しいやつ[1] SSR, SPA編

2023/01/30に公開

Zenn初投稿です。

これを読む前の前提知識

  • HTML,CSSが何か、かつ用途について知っている or 自力で調べることができる
  • JavaScript(以降 JS と記載します)の基本構文 const, if, for などの文法知識(あると理解しやすい)

💡 参考ページ(MDN Web Docs)

本記事の想定読者

  • webデザイン/HTML,CSSは出来るけど、JSの実装もしてみたい方
  • 企画・営業職などの方でwebエンジニアと一緒に仕事しているものの、具体的な技術の話になると意味不明で困っている方
  • フロントエンドエンジニアの立場から、上記の方に技術的な説明をしたい方

本記事では取り扱わないこと

  • TypeScript(TS)について
  • Vue.jsやReact等に関する詳細
  • SEO観点での両者比較

本題

■ そもそもSSRとかSPAとかなんのための技術なの?

→ 一言で言えばwebブラウザ[1]でwebサイトを画面表示する為のものです。
ここは両者共通しており、違いはその手法にあります。
そしてその手法の違いゆえの特徴がそれぞれにあります。
※ 他にも SSG[2]等色々やり方はありますが割愛します(いずれ記事化します)

もう少しだけ具体的なお話をするために、例えばこんなケースを考えてみましょう

登場人物[3]

  • スマートフォン・PCからwebブラウザを操作するユーザー(人間)
  • フロントエンドのプログラム(画面表示係)
  • サーバーサイドのプログラム(画面表示に必要なデータの調達・調整係)

webサイトが表示されるまで(ざっくり)

ユーザーさん(人間): ブラウザから見たいサイトのURLを入力しアクセスする(ボタンやリンクのクリック含む)

フロントエンドくん: ユーザーさんの要求(=リクエスト)を受け取る

フロントエンドくん: 受け取ったリクエストの情報をサーバーサイドくんに渡す

サーバーサイドくん: リクエストに対して適切な返事(=レスポンス)をフロントエンドくんに返す

フロントエンドくん: もらったレスポンスの情報をもとに、サイトの画面を組み立てる

ユーザーさん(人間): 見たいサイトがブラウザに表示された!

基本的にはこの流れに沿って処理が行われます[3:1]

では次に、SSRおよびSPAとはなにか?
何が違って、それぞれがどのようなケースに向いている/向いていないのかについて、両者の良し悪し含め説明を進めていきます。

■ SSR (Server Side Rendering)

直訳すると「サーバーサイドが(webサイトを)レンダリング[4]すること」という意味になりますね🤔
前述した通り、 サーバーサイドくん(webサーバー[5]) が画面表示に必要なページ全体のデータを用意して、フロントエンドくんにパスしてくれます。

■ 具体例

  • WordPress
  • EC-CUBE
  • PHPやJava等、MVCフレームワーク[6]でのサイト開発

🌈 向いているケース・メリット

  • 初回のサイト表示速度を重視する場合には向いている🚀
  • ページ数の少ないサイトを構築する場合であれば選択肢としてはあり
    ex: コーポレートサイトやランディングページなど
  • アクセスが集中しない前提のサイト構築をする場合であれば選択肢としてはあり
  • サーバーサイドで画面表示処理がほぼ完結するため、JSの記述量が少なく済む
    → JSの専門的エンジニアがいなくても、開発自体は可能
  • JSによるアニメーション表現などを多用しないシンプルなサイト構築に向いている

🌀 向いていないケース・デメリット

一方で不利な面も存在します。ここでは2点紹介します。

①パフォーマンス問題
例えば、WordPressのようなCMS[7]ではSSRで画面表示を行いますが、下記の通りパフォーマンス低下の可能性があります[8]

サーバー側レンダリング (Server-side rendering、SSR) は、ウェブサイトがサーバー上でレンダリングされるという意味で、初回の読み込みは速くなりますが、
ページ間で移動すると新しい HTML コンテンツをダウンロードする必要があります。
これはブラウザーが変わってもうまく動作しますが、
ページ間で移動する時間が不利であり、したがって一般的にパフォーマンスが悪くなります。
ページを読み込むごとに、サーバーへの新しい往復が必要になるからです。

引用元: MDN アプリのアーキテクチャ

また、サーバー側の負荷が高くなるため、仮にサイトへのアクセス量が多くなった場合、
サーバーエラーによってサイトが表示不可となる可能性があります。
このようなリスクを軽減する方法としては、サーバーの増強や負荷分散などが考えられますが相応のコストが発生します(札束で殴って解決するということです💴)

②ソースコードの管理問題

  • JSとサーバーサイド言語(PHP, Java等)の共存管理を怠ると、複雑で難解なソースコードに変貌する恐れがある
  • サーバーサイド言語のテンプレートエンジン(HTMLの素)とJSの組み合わせ方を間違えると軌道修正が難しい
  • 上記の状態のソースコードはテスト(=動作検証)が困難・テスト工数が増加する
    →結果、不具合の発見が遅れ運用トラブルに繋がる

■ SPA (Single Page Application)

直訳すると「単一なページ(画面)によるアプリケーション」ということになります。
こちらはSSRと比べて、どういうものなのか言葉だけ見てもちょっと捉えにくいかもしれません。

ここは一つ、前述したSSRの特徴を思い出してみましょう。以下SSRの説明からの抜粋です。

サーバーサイドくん(webサーバー)が画面表示に必要なページ全体のデータを用意して、フロントエンドくんにパスしてくれます。

これに対しSPAでは、ページ移動の度に全体を丸ごとデータ取得するのではなく、ページを部分単位で必要なデータの取得〜画面表示を行うことが出来るのです。

■ 具体例

noteやはてなブログのような記事編集画面で説明します
(※ ↑これらのブログサービスが実際にSPAを使っているかは分かりません。ここでは仮定として考えてください)

  1. 会員登録をしてログイン後にログインユーザー用のトップページが表示された場合(satou_sanというユーザー名とします)
  2. そのページが https://blog.com/user/satou_san/ というURLだったとします。
    そのページの内容は、

① ページ上部にヘッダー(ナビ)部分のパーツ
② ページ左側にメニューが縦方向・一列に並んだパーツ
③ 画面の大半にユーザー用のメニュートップページのパーツ
④ 画面下部にフッター部分のパーツ

このような4つのパーツ(構成要素)で1つのページが成り立っているとします。
3. 次に、2.のメニューから記事一覧ページのリンクがあり、クリックします。
4. <<ここがポイント>>
記事一覧ページに移動しました。
URLは 'https://blog.com/user/satou_san/articles' (仮)になりましたが、
実はこの時、ページ内容の③以外は読み込み処理が行われることなく、③のみが変化しているのです。

これがSPAで構築したwebサイトの特徴です。一部のみ変化させれば良いのでその分ページの表示速度は早くなります🚀
もしこの処理をSSRで行う場合、基本的には①〜④のパーツ全てを読み込み直さなければなりません。
つまり、その分データを送る / 返す量が増加するため表示までの速度が遅くなってしまうということです[8:1]

なぜ一部のパーツだけを変化させることが出来るのか?
もし疑問が湧いた方は、
'非同期通信', 'Ajax', '仮想DOM' 等のキーワードで調べてみてください💡
※なおこれらの技術は、経験を積んだフロントエンドの専門的技術者でも頭を悩ませることがある少々厄介な領域なので、
難しいなぁと感じたら深く理解するのは一旦後回しにして問題ないと思います👍

🌈 向いているケース・メリット

  • 上記例で挙げたように必要な部分だけ読み込めば良いため、ページ間の移動が早い🚀
  • 業務用アプリケーション(管理画面)の開発に向いている(=初回読み込みの速度を考慮しなくても良いケース)
  • フロントエンドとサーバーサイドのソースコードを明確に分割することが出来るため、開発時の役割分担が明確になる
  • ↑その結果ソースコードがシンプルで読みやすい形で残しやすくなるため、開発担当者が変わった場合でも引き継ぎ作業がスムーズに進みやすくなる[9]
  • もう一つの恩恵として、フロントエンド・サーバーサイドで個別にテスト(動作検証)できるため、より安全なシステム開発がしやすい[9:1]
  • 開発ユーザーが多く、その分情報収集が容易(現在はReact, Vue.jsが主流)
    [補足]
    • React等の登場によって、純粋に実現可能な機能が増えた
    • React等に対応したライブラリ[10]が豊富かつ比較的頻繁にアップデートが行われているため、現在はjQueryより安全性は高い[11]

🌀 向いていないケース・デメリット

  • ページの初回読み込み速度はSSRに劣るため、速度を重視するケースには向いていない
  • JS及びJSフレームワークの知識が必要(学習コストが高くなる)[12]
  • 非同期通信を行うため、処理が複雑になる場合は開発の難易度が上がりやすい(より丁寧な設計[13]が必要になる)
  • フロントエンドエンジニアがいないチームの場合、サーバーサイドエンジニアが兼任するケースが増す(=サーバーサイドエンジニアの負担が大きくなる)[14]
  • JSフレームワークのバージョンアップデート対応が必要(ex: Vue2 -> Vue3)

あとがき

最後までお読みいただきありがとうございました🙏

今回改めて、自分の知識の薄さを実感しました。
開発の場面では、ちょっと調べればどうとでもなることもたくさんありますが、最低限のことはその場でパッと正確に説明できる能力がもっと必要だなぁと・・・

Typo指摘, ここは正しく無いのでは?等のコメントを寄せていただけるととてもうれしいです😇
都度修正・追記を続けてブラッシュアップしたいと思います👍

それでは次のシリーズ記事でまたお会いしましょう!(更新がんばります)


脚注
  1. GoogleChrome, Edge, Safari, FireFoxなど ↩︎

  2. Static Site Generator -> 静的サイトジェネレータ ↩︎

  3. 実際には他にも様々な要素が絡んできますが、今回は詳細を省いて説明しています ↩︎ ↩︎

  4. webブラウザ画面に情報を描画・表示をすることを指します ↩︎

  5. 厳密に言えば、サーバーサイドアプリケーション(PHP, Java等で作られるソースコード)に加え、ミドルウェアと呼ばれる物が内包されたコンピュータを指します。また、ミドルウェアの代表的なものにはApache(アパッチ), Nginx(エンジンエックス)などが存在し、用途によって使い分けします ↩︎

  6. Model(モデル)・View(ビュー)・Controller(コントローラー)という3つの役割分担の形を採用したシステム開発の初期プログラム群を指します ↩︎

  7. Contents Management System -> コンテンツ・マネジメント・システム。プログラミングの専門的な知識がなくても一通りの要素を兼ね備えたwebサイトを構築出来るシステムの総称 ↩︎

  8. 回避策もありますが、専門的な知識と時間的コストが必要になります ↩︎ ↩︎

  9. いかなるケースにおいても適切な設計が不可欠です。SPAだから絶対的に楽、というわけではありません。SSRと相対的に比較した場合の見解です ↩︎ ↩︎

  10. ここでは追加機能を容易に追加可能なプログラムの一セットを指します。ライブラリを利用することで追加機能を一から開発するコストを削減できます ↩︎

  11. 開発が放棄されたライブラリを使用・放置し続けると、システム不具合に繋がる危険があるという意図で記載しました ↩︎

  12. 逆に言えば、フロントエンドにReact、サーバーサイドにNode.jsを用いれば、JSの学習だけで双方の開発が可能になります。開発チームのスタイルによってはPHP等以外の選択肢としてNode.jsを採用する余地があるでしょう ↩︎

  13. 開発者がプログラムを書く前に行う工程を指します。「どんな課題を解決するためのwebシステム(サイト)か」→「課題解決に必要な機能は何か」→「機能を実現するためのシステムはどんな構造になるか」→「システム構造の中に存在する個々の機能を実現するためのプログラムには何が必要・妥当か」の考慮・検討を指します ↩︎

  14. 余談: 幅広い技術領域をカバーするwebエンジニアを一般的に「フルスタックエンジニア」と呼称することがあります ↩︎

Discussion