デプロイの自動化と History API のフォールバック設定を行うことで、GitHub Pages で SPA を公開できるようにする。
具体的なゴールは以下の通り。
master
ブランチにプッシュすると、自動的にビルドが行われる- ビルドした内容が GitHub Pages として公開される
- History API のフォールバックが設定されており、SPA として問題なく機能する
以下がサンプルコード。
上記のリポジトリによって公開されたページ。内容はない。
https://numb86.github.io/spa-sample/
なお、この記事では SPA の作り方そのものは扱わない。
ビルド用のコマンドを用意し、ビルドの出力先を決める
サンプルコードでは、$ yarn build
でビルドし、その結果をpublic/
に出力するようにしている。
public/
の内容を GitHub Pages として公開することになるので、公開に必要なものは全てこのディレクトリに含まれるようにしておく。
GitHub Actions の設定を行う
デプロイを行うための GitHub Actions の設定を行う。
ここがこの記事の主題ではあるのだが、まさにそのための Action を公開している方がいたので、そのままそれを使うことにした。
README に記載されているサンプルも、ほぼそのまま流用した。
これを元にしたコードを.github/workflows/gh-pages.yml
として保存した。
これで、GitHub Actions が有効になる。
以下のように記載することで、master
ブランチにプッシュされたときにのみ、実行されるようになる。
on: push: branches: - master
最後の行のpublish_dir: ./public
で、public/
の中身がgh-pages
ブランチに展開されるように設定している。
その前に$ yarn build
でビルドすることを忘れないようにする。
${{ secrets.GITHUB_TOKEN }}
と記載してトークンを使用しているが、このトークンは自動的に生成されるので、改めて何かする必要はない。
これもREADME に書かれてあるが、初回デプロイ時のみ、リポジトリの設定ページで GitHub Pages の設定し、改めてもう一度デプロイする必要がある。
History API のフォールバックを設定する
GitHub Pages に限らず、SPA を公開する場合は History API のフォールバックを設定する必要がある。
フォールバックを設定しない場合、https://numb86.github.io/spa-sample/about
に直接アクセスしたり、このページでリロードしたりすると、404 ページが表示されてしまう。
今回のサンプルページの場合、まずindex.html
が表示され、そこに記載されている JavaScript が読み込まれることで、SPA が展開される。
そのため、まず最初にindex.html
を表示する必要がある。だがhttps://numb86.github.io/spa-sample/about
にアクセスするとabout.html
を表示しようとするため、ファイルが見つからず 404 エラーになってしまう。
通常はサーバ側で対応するが GitHub Pages ではそういったことはできないため、JavaScript で対応する。
まず、オリジナルの 404 ページを用意する。デフォルトだと GitHub が用意した 404 ページが表示されるが、404.html
という名前のファイルを用意することで、404 エラーのときにそのファイルが表示されるようになる。
今回はsrc/404.html
を用意し、それをGitHub Actions のなかでpublic/
にコピーすることにした。
そしてその 404 ページにスクリプトを書き込み、index.html
にリダイレクトさせる。
その際に URL にクエリパラメータをつけることで、どこからリダイレクトされてきたのかが分かるようにする。
最後にindex.html
にもスクリプトを書き、リダイレクト元に応じてページの内容を書き換える。
https://numb86.github.io/spa-sample/about
の場合、以下のような流れになる。
https://numb86.github.io/spa-sample/about.html
が存在しないため、https://numb86.github.io/spa-sample/404.html
が表示される404.html
のスクリプトによって、https://numb86.github.io/spa-sample/?originalPath=/about
にリダイレクトされるhttps://numb86.github.io/spa-sample/index.html
が返され、そこに書かれているスクリプトによって URL がhttps://numb86.github.io/spa-sample/about
に書き換えられ、React Router によって処理されてThis is about page.
と表示される