Azure Static Web Apps に Progressive web apps (PWA) をホストしてみる

#はじめに
##なにをやるのか
[Azure Static Web Apps](https://docs.microsoft.com/ja-jp/azure/static-web-apps/) に [Progressive web apps (PWA)](https://developer.mozilla.org/ja/docs/Web/Progressive_web_apps) をホストして、Windows / Android / iOS のそれぞれのデバイスで、PWA を端末にインストールするところまでの手順を確認します。

##Static Web Apps とは？
Azure Static Web Apps は、コード リポジトリから Azure にフル スタックの Web アプリを自動的にビルドしてデプロイするサービスです。

(Static Web Apps 公式ドキュメントより引用)
![azure-static-web-apps-overview.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/0913916d-dbd4-3330-5774-542266cec68b.png)

主な機能としては、HTML、CSS、JavaScript、画像などの静的コンテンツの Web ホスティングと、バックエンドの API のホスト機能、そして GitHub もしくは Azure DevOps との統合による CI/CD 機能あたりですが、ほかにもこまごまとしたところがあるので、割愛して詳細は公式ドキュメントに任せます

https://docs.microsoft.com/ja-jp/azure/static-web-apps/overview

##PWA とは？
PWA について、[MDN の PWA の項目](https://developer.mozilla.org/ja/docs/Web/Progressive_web_apps)では、以下のように定義されています。

> プログレッシブウェブアプリ (Progressive web apps, PWA) は、新しいウェブ API と伝統的なプログレッシブな拡張戦略を使用して、クロスプラットフォームのウェブアプリケーションにネイティブアプリと同様の使い勝手をもたらすウェブアプリのことです。

PWA は Web アプリケーションでありながら、その特徴の一つとして「端末へのインストールが可能」であることが挙げられており、つまり「この Web アプリ便利だなー」と思った瞬間に、自分の端末にインストールしてあたかもネイティブアプリのように利用可能（もちろんネットワークの制限はありますが）となります。Web アプリ開発者の頭を悩ませる課題の一つ、「このサイトのスマホアプリ版って作らないんですか？」というユーザーからの~~（手間がかかる割にメリットが少ないこともままある）~~要望に対する、一つの解となるかもしれません。

細かい話は、MDN や Google、Microsoft のドキュメントをご参照ください。

https://developer.mozilla.org/ja/docs/Web/Progressive_web_apps

https://web.dev/progressive-web-apps/

https://docs.microsoft.com/ja-jp/microsoft-edge/progressive-web-apps-chromium/

##Static Web Apps に PWA をホストできると何が嬉しいか
Static Web Apps の GitHub 統合により、バージョン管理や競合の調整、テスト環境の運用、本番デプロイの管理といった、大人数で寄ってたかって作業を行う際に課題となりそうな部分がまるっと解決されます。
そのうえで、アプリのマルチプラットフォーム対応も最低限の対応でクリアできるとなれば、様々なデバイスが世にあふれるこの時代にぴったりじゃないかと思うわけです。

:::note info
余談ですが、Static Web Apps の GitHub 統合機能では、GitHub で開発用のブランチを切ると勝手にテスト用のサーバーを Azure に立ち上げてくれます。そして、Pull Request で main ブランチに変更がマージされると、テスト用のサーバーは勝手に削除されます。常に main ブランチには本番で動くコードがあり、開発環境は別ブランチ別サーバーになるわけですね。便利！
:::

### 補足 : Static Web Apps が持っている、ステージング環境の自動管理の機能について
ブランチを切ってテスト用のサーバーを立ち上げる手順、そして Pull Request から本番にマージし、またテスト用のサーバーを自動的に削除するまでの手順は以下のドキュメントにあります。

https://docs.microsoft.com/ja-jp/azure/static-web-apps/review-publish-pull-requests

# Static Web Apps に PWA をデプロイするための手順
ここからは、Static Web Apps に PWA をデプロイするまでの手順をざっとまとめます。

## 前提条件
Static Web Apps は、[様々なフロントエンドフレームワークに対応](https://docs.microsoft.com/ja-jp/azure/static-web-apps/front-end-frameworks)していますが、今回は Vue CLI で作成した Vue.js のひな型プロジェクトを PWA としてデプロイすることにします。OS は、手順書として出来るだけクリーンな環境にしたかったので、Hyper-V 上にデプロイした Windows 11 の試用環境を使いました。

### （おまけ）Windows 11 試用環境のセットアップ
Windows 11 Pro 以上のエディションをご利用の方でしたら、Hyper-V を有効化していただき、Hyper-V マネージャーから「クイック作成」を選んでいただくと Windows 11 開発環境（試用版）をボタン一発でセットアップ可能です。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/8ecf91db-e7f4-2974-5d1f-5e171a21f751.png)

## 開発環境のセットアップ
### Git for Windows のインストール
以下のサイトから Git for Windows のインストーラーをダウンロードしてインストールします。

https://gitforwindows.org/

### Node.js のインストール
以下のサイトから Node.js の LTS をインストールします。

https://nodejs.org/ja/download/

### Vue CLI のインストール
ここまで作業を進めると、Windows コマンドプロンプトで、Git コマンドと Node.js が使えるようになっているはずなので、コマンドプロンプトを開きます。

:::note
「Windows キー + R キー」で開いたウィンドウで、cmd と入力するとコマンドプロンプトが開きます。
:::

以下のコマンドを入力して、Vue CLI のセットアップを完了しましょう。

```
npm install -g @vue/cli
```

## クラウドの準備
### Azure の準備
Azure のサブスクリプションをお持ちでない方は、Azure の無料評価アカウントをまずは作りましょう！

https://azure.microsoft.com/ja-jp/free/

## GitHub の設定
### まずはアカウント作成
GitHub のアカウントを持っていない方はこちらから "Sign up for GitHub" の項目を探して、アカウントを作成しましょう！

https://github.com/

### リポジトリの作成
GitHub にサインインして、今回の成果物を格納するための[リポジトリを作成](https://github.com/new)します。プライベートリポジトリでも大丈夫です。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/3ff84528-8c2c-6108-8f28-c27f9b98055d.png)

リポジトリ作成後に表示される、`…or create a new repository on the command line` 以下のコマンドリストは、どこかにコピーしておくとその後一部がコピペ元として使えると思います。

## Vue CLI を使ったプロジェクトの作成
### プロジェクト作成先のディレクトリにに移動
cd コマンドでプロジェクト作成場所のディレクトリ（フォルダ）まで移動します。
（例えば以下のコマンドで、C ドライブの git フォルダの下に移動です。移動先フォルダはあらかじめエクスプローラか何かで作っておいてください。）

```cmd
cd c:\git
```

### Vue CLI で PWA のプロジェクトを作成
以下のコマンドを入力し、新規プロジェクトを作成します。

```
vue create プロジェクト名（好きなものをつけてください）
```

すると、Vue CLI が色々聞いてきます。今回選択したものをスクリーンショットで貼っておきますが、重要なのはおそらく一番最初の選択肢で、`Manually select features` を選ぶところと、次の選択肢で `Progressive Web App (PWA) Support` にチェックを入れることくらいかなーと思います。他はなんとなく自分にとってのいつも通りな感じで選びましたが、おススメある方コメントいただければ嬉しいです！

![2021-12-22.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/d9c07e85-13b4-b5a5-1987-cd12a6e03857.png)
![2021-12-22 (1).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/d0a06f45-224c-d57a-496f-b2f63b496d88.png)
![2021-12-22 (4).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/507c0d3f-f56c-0a7e-a392-a491a584b8fa.png)

一通りウィザードに対する回答が終わると、何やら画面上でごちゃごちゃと作業をしている雰囲気を感じられるかと思います。
`Successfully created project` の表示が出たら、プロジェクトの作成は完了です。
プロジェクト作成先のディレクトリに移動してみましょう。

```
cd プロジェクト作成先ディレクトリ（Vue CLI に設定したプロジェクト名と一緒）
```

### Git の初期化とリモートリポジトリへの Push
ここまで完了したら、ついでにコードを GitHub へ Push しておきます。
以下のコマンドを、Vue のプロジェクトのディレクトリの中で実行します。

```
git remote add origin https://github.com/アカウント名/リポジトリ名.git
git branch -M main
git push -u origin main
```

初回実行でしたら、GitHub へのサインイン画面が出てくると思うので `Sign in with your browser` を選択して、ブラウザーからログイン操作を完了します。

![2021-12-23 (1).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/3f8cb4d8-54fa-e217-c739-c9bdee3aa4b2.png)

正常にログインが完了すると、ローカルにあった Vue.js のプロジェクトが GitHub のリモートリポジトリにも反映されていることを、ブラウザーからこんな感じで確認できると思います。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/62ef5887-b4fc-720b-19c2-a2bd261a35fd.png)


### Azure Static Web Apps のデプロイ
まずは、Azure ポータルにログインします。
ログインができたら、左上のハンバーガーメニュー（三本線のやつ）を押して、ポータルメニューを開きます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/f81456bc-d3e0-9e3e-bdc8-2e6e1fc4dc0d.png)

一番上の「リソースの作成」を選択し、開いた画面の検索窓で、`static web app` と検索します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/419633e4-a66e-a654-c344-cc5df69d553f.png)

検索結果に表示された「静的 Web アプリ」を作成します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/c7c3ee91-a9ca-7516-705b-9bb19b602e41.png)

作成用のウィザードが表示されますので、以下の例のように選択していきます。

* プロジェクトの詳細
    * サブスクリプション : Static Web Apps を作成したい Azure の契約を選択
    * リソースグループ : ドロップダウン下の「新規作成」のリンクをクリックし、任意の名前を入力して OK をクリック
* 静的 Web アプリの詳細
    * 名前 : 任意の名前を入力
* ホスティングプラン
    * 必要に応じて無償・有償を選択しますが、今回は Free を選んで無償版を使います
* Azure Functions とステージングの詳細
    * Azure Functions API とステージング環境のリージョン : East Asia
* デプロイの詳細
    * ソース : GitHub

こんな感じの入力になると思います。
![スクリーンショット 2021-12-23 132635.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/b6a9cd00-fd01-de02-5aef-ab0ba3701e79.jpeg)

ここまで入力したら、「GitHub アカウントでサインイン」します。GitHub へのサインイン処理が行われ、最後に下記の画面が出ますので、"Authorize Azure-App-Service-Static-Web-App" を選択することで、Azure と GitHub の連携処理が実行されます。

![スクリーンショット 2021-12-23 141221.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/021414db-f307-4571-6134-b98ac8a2f827.jpeg)

サインインが完了すると、追加設定項目が表示されますので、以下の通り設定します。

* デプロイの詳細
    * ソース : GitHub
    * 組織 : リポジトリが所属する組織（既定は自分の GitHub アカウント名）
    * リポジトリ : 先ほど作ったリポジトリ
    * 分岐 : main
* ビルドの詳細
    * ビルドのプリセット : Vue.js
    * アプリの場所 : /
    * API の場所 : 今のところは空欄。API をホストする場合には、API の保存先ディレクトリを指定。
    * 出力先 : dist

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/95be337f-e212-e863-63a2-36cf4821987e.png)

ここまで進めたら、画面下部の「確認および作成」をクリックし、次に表示される確認画面でも検証完了後に「作成」ボタンをクリックすれば、Azure Static Web Apps がデプロイされ、その後自動的に GitHub のリポジトリからコードがビルドされてデプロイされます。

![スクリーンショット 2021-12-23 141951-2.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/12a78e83-8bbb-f9a6-c445-c7a6049b460d.jpeg)


「デプロイが完了しました」という画面が出たら、画面内にある「リソースに移動」というボタンを探してクリックします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/07aeb52a-9e39-2c38-8150-ee230d8e4806.png)

### デプロイされたリソースを確認
「リソースに移動」ボタンの移動先として、作成した Static Web Apps の画面が表示されます。そこから、`azurestaticapps.net` で終わる URL を探してクリックしてみましょう。
![スクリーンショット 2021-12-23 142507.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/4f390e51-f9f2-0644-0254-a9293e7f92c9.jpeg)

ここで、下記の Vue.js のサンプルプロジェクトの画面が表示されたら、デプロイは完了しています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/a703d43d-3732-f5a5-3ecc-8fd9ef5cbc0d.png)

もし、表示されない場合には、GitHub Actions のビルドとデプロイのアクションが実行中かもしれません。

その場合には、GitHub のリポジトリに移動して、"Actions" のタブを選択し、ワークフローの実行状態を確認してみましょう。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/906b9109-403b-a200-334b-d314b34264db.png)

ここが、緑のチェックマーク以外になっている場合は、実行中、もしくは何らかのエラーが発生している可能性がありますので、状況を確認してください。

#いろいろな環境に PWA をインストールしてみよう！
Static Web Apps に PWA をデプロイできましたので、いろいろな環境にインストールして遊んでみます。

## Windows デバイスにインストール
Edge もしくは Chrome ブラウザーで、先ほどデプロイした Static Web Apps のサイトを開くと、ブラウザーのアドレスバーの右端に、インストール用のアイコンが追加されているはずですので、そこをマウスでホバーしてみましょう。「アプリを利用できます」という表示が出てくると思いますので、インストール用のアイコンをクリックします。
![2021-12-23 (3).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/1349304e-6324-f786-3131-6fe8c0d80216.png)

インストールの最終確認が出ますので、こちらも承諾し、インストールを完了します。
![2021-12-23 (6).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/f9ab6719-669e-1c1f-5159-bdfbecb7fa96.png)

すると、ブラウザーの枠が外れた状態で、あたかも Windows のアプリケーションのようにサイトが表示されるはずです。これでインストールは完了です。
![2021-12-23 (5).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/4e86e8b2-2d2b-93aa-1197-e673fb851255.png)

スクリーンショットにあるように、アプリの設定を行うことで、Windows アプリと同じようにタスクバーにピン止めしたり、スタートメニューにピン止めしたり、デスクトップショートカットを作成したり、デバイスログイン時の自動実行を行ったりできるようになります。また、アドレスバーも消えており、ちゃんとアプリっぽい見かけになっていることも確認いただけると思います。

サイトの作りこみ次第ではありますが、ほぼ Windows アプリと同じような操作性で Web アプリをデスクトップで利用可能なことがお分かりいただけるのではないでしょうか。

::: note info
実は、Outlook や Teams のブラウザー版は PWA 対応しており、ブラウザーでサイトを開いた後に「インストール」を行うと、あたかも Windows アプリであるかのように Outlook や Teams のブラウザー版を使うことが可能です。

Teams で複数のテナントとやり取りをするときに、いちいちディレクトリを切り替えるのがめんどくさいことってあると思います。そういう時には、Teams デスクトップアプリでメインのテナントにログインし、Teams Web 版を PWA としてインストールして、そちらで別のテナントにログインすることで、複数の Teams アプリを同時に立ち上げているかのような使い勝手でやり取りが可能だったりします。
:::

## Android デバイスにインストール
Android でも同様に Chrome からインストールが可能です。

デプロイした Static Web Apps にアクセスし、画面下部の「ホーム画面に追加」のボタンを選択してアプリをインストールすると、ホーム画面にアプリのアイコンが表示されます。

![Screenshot_2021-12-23-14-48-54-57.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/78cd97a2-d79e-4e25-e751-e5ace2838d15.png)
![Screenshot_2021-12-23-14-52-25-59.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/e74b0a5d-05d7-f156-0172-0d153ad88b3a.png)
![Screenshot_2021-12-23-14-53-43-66.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/4f7e4666-deb1-eac0-0f1d-e0cd96c97d1b.png)

あとはホーム画面のアプリアイコンから、あたかも Android アプリのように利用可能です。（スクリーンショットのタアドレスバーが消えているのを確認いただけますでしょうか。）
![Screenshot_2021-12-23-14-53-52-83.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/08678e3b-035c-518a-f09a-9b848ae82fe1.png)

## iOS デバイスにインストール
iOS デバイスも似たような手順で OK です。

Safari でデプロイした Static Web Apps にアクセスし、画面下部の赤丸で囲んだアイコンをタップします。
![20211223_060026000_iOS.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/80d6e8a5-7093-3aa3-1d96-240adbfcd92e.png)

そして「ホーム画面に追加」→「追加」と選択。
![20211223_060038000_iOS.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/bd8f97f8-7dbc-2b15-1575-656bef3d376a.png)
![20211223_060043000_iOS.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/87577507-a4f3-877b-d349-ed9e3be8fac1.png)

すると、ホーム画面にアイコンが追加され、あたかも iOS アプリのように利用可能となります。
![20211223_060501000_iOS.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/bbc3a3b5-601c-3a63-e202-9ccfba415b72.png)
![20211223_060803000_iOS.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/199379/4c25989a-3513-399e-21af-2203c978c922.png)

#まとめ
##ここまでにやったこと
ここまでの手順にて、いろいろなデバイスにあたかもネイティブアプリのようにインストールできるような Web アプリケーションを、Azure Static Web Apps にホストすることが可能なことをご理解いただけたかと思います。

##この先やらなければいけないこと
PWA のドキュメントをよく読んでいただいた方ならお気づきのことと思いますが、実はまだまだ PWA として設定しなければいけないことはたくさんあります。例えば、オフライン時の処理を定義するための "Service Workers" や、再エンゲージを可能とするためのプッシュ通知の構成などです。また、アプリのインストール時に表示される情報も、ウィザードが吐き出したそのままなので、本来であればマニフェストの内容を自分自身でカスタマイズしなければいけません。

また、バックエンドの API については今回ノータッチでしたので、API も実装しなければいけませんし、API を Static Web Apps のプロジェクトに追加して、Azure にホストさせることもしなければなりません。

そういった手順がこの先にあることをご理解いただきつつ、このドキュメントが PWA を Azure Static Web Apps にホストする際の参考になれば幸いです。

#おまけ
##Vue.js 以外のフレームワークも使えるの？
Azure Static Web Apps ではたくさんのフロントエンドフレームワークに対応しています。
下記ドキュメントにある、フレームワークごとに Static Web Apps のビルド設定を参考にしていただければ幸いです。

https://docs.microsoft.com/ja-jp/azure/static-web-apps/front-end-frameworks

##バックエンドの API を追加する方法ってどうやるの？
ここにチュートリアルがあります。ご参照ください。

https://docs.microsoft.com/ja-jp/azure/static-web-apps/add-api?tabs=vue

## その他 Static Web Apps のドキュメントを読みたい
ここのページから辿っていくと色々あります。

https://docs.microsoft.com/ja-jp/azure/static-web-apps/

## 自習用のコンテンツとかありませんか？
Microsoft Learn を探すと、Static Web Apps だけじゃなくて、たくさんの自習用のコンテンツがあります。
しかも、Azure などマイクロソフトクラウドが、自習用に無料で払い出されるようになっているので、無料評価版の貴重な無料枠を削らずとも自習が可能です。ぜひ活用ください！

自習の際には、是非「サインイン」してから使っていただけると、自分の達成度合いがポイントで表示されて楽しいですよ！

https://docs.microsoft.com/ja-jp/learn/

Static Web Apps に関するラーニングパスのおススメ（自習コンテンツ）はこちらです。２～３時間でクリアできるように作ってありますので、冬休みにちょっと遊んでみるのにちょうどいいと思います。

https://docs.microsoft.com/ja-jp/learn/paths/azure-static-web-apps/