SSRのはなし

kahirokunn (フリーランス

たまにQiitaで記事投稿してます.

最近やってること

・「コンピュータシステムの理論と実装

・Denoにコントリビュートする為にRustやってます

今のSPA

  • ReactやVue等のライブラリを利用
  • リッチなUIをたった1ファイルのJsで表現
  • 1ファイルのJsで表現できるので、静的なhtmlとセットで簡単に配信できるので楽

※ 今のページに必要なJsコードだけを呼び出す方法もある

※ 昔のSPAはやったことないのでよくわかりません

SPAでよくある質問😗

  • Vuex使っとけばいいの?🤔
  • どうコードを書くのが正解なのかわからない。🤔

せっかくなのでVuexがあると明確に助かるケースを1つ紹介する

Vuexの特徴

  • 単一状態木のメンテが可能
  • 単一状態木の状態を自動でVueに反映してくれる

※ 単一状態木とは、超簡単に言えば状態が詰まったobjectです

SSR

  • サーバー側でHTMLを生成して返す
  • Jsを埋め込む事により、リッチなUIを表現
  • ページ変える度にサーバーに新たなHtmlを要求

Laravel, Rails, Django...etc

代表例

Vueのレンダリングをユーザー端末ではなく、従来のSSRの様にサーバー側でできるだけHTML生成してから返す

Vueのファーストペイントを早くする方法の1つを紹介

利点

  • ネットワーク的に近い距離からAPIが叩ける
  • 比較的安定しているコンピューター上で初期描画を行える
  • サーバー利用に制限されたAPI等を叩ける

※ first paintまで。jsは動かない

ただのHTMLであり、JSがないので当然動かない

ここから普通のSPAの様に操作させれる様にする為の機能がVueにはあるので、それを活用

※ hydrationとかと呼ばれる機能

仕組み

結果が同じなので生成された要素をフロントのVueが引き継げる

※ 構造が違ったらhydrationに失敗する

※ サーバー側でifが非表示でフロントはifがtrueの場合に壊れる

差分が発生すると本当に正しく動いているか怪しくなる😢

課題

  • サーバーからフロントにコンポーネントの状態を正しく復元する必要がある

解決手段の一つでVuexのstate tree等が便利

サーバー側でstoreのstateをjsonシリアライズしてHTML埋め込んで、front側でそれを元にstoreの状態を復元

 

store.stateをwindowに注入

windowからstore.stateを復元

ライフサイクルまとめ

サーバー

  1. serverPrefetch
  2. beforeCreate
  3. created                                                     

フロント

  1. replaceState (ライフサイクルではない
  2. beforeCreate
  3. created
  4. beforeMount
  5. mounted

まとめ

  • SPAとSSRでコードの書き方は全然違うので気をつけよう
  • SSRする場合はcreatedの扱いは細心の注意が必要
  • serverで実行したいコードはserverPrefetchを使おう
  • nuxtの場合はasyncData等
  • フロントでmount後にやりたい事はmountedでやろう
  • シングルトンは危ない

最後に

自分が前に実験的に書いたVue + Vuex + Tsのコード良かったらどうぞ

ありがとうございました!