定額給付金の案内ページを監視して更新があれば Slack に通知するボット

最近，定額給付金が話題になっていますが，自分が住む市町村区はいつから申請開始になるのか気になって自治体のホームページを定期的に確認しているのは時間がもったいないです。
そこで特定のページを定期的に取得して更新があれば Slack に通知するボットを作成します。

## 前提条件
[Google Apps Script (GAS)](https://developers.google.com/apps-script) で定期実行・監視を行い，更新があれば [Slack Incoming WebHooks](https://slack.com/apps/A0F7XDUAZ-incoming-webhooks) を用いて Slack で通知します。
今回は条件さえ満たせば無料で定期監視できます（Slack の接続アプリ数と GAS の URLFetch の呼び出し回数とURLFetch のデータの受信量にご注意ください）。

また，ご自身がお住まいの自治体のホームページなどに定額給付金のページがあることを確認しましょう。
私が住む札幌市は次のページになるかと思います:

* 札幌市: 特別定額給付金について - [https://www.city.sapporo.jp/2019n-cov/hokenfukushi/teigakukyuhu.html](https://www.city.sapporo.jp/2019n-cov/hokenfukushi/teigakukyuhu.html)

## 処理の流れ
フローは以下の通りです:

1. 特定の URL にアクセスする
2. 更新がされたか確認する
3. 更新がされていれば通知する

この流れを定期的に繰り返し行うようにします。

更新がされたかどうかは Web ページのハッシュを保存し，前回アクセスした時のハッシュと比較して，一致しないときは更新されたものとして扱います。

## スクリプトの作成
まずは GAS のプロジェクトを作成するため，[https://script.google.com/home](https://script.google.com/home) にアクセスし，ログインします。

1. 左上の新しいプロジェクトをクリックしてスクリプトの編集画面を表示します。
2. 編集画面が表示されるので，ここにソースコードを入力します。

|1.|2.|
|---|---|
|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/e964dc58-39f2-98f7-4abc-0b03b0a8e481.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/1d97352f-9808-b380-f2f5-d6f3bfd05ab1.png)|

編集画面に以下のソースコードを貼り付けます:

```javascript:コード.gs
const scriptProperties = PropertiesService.getScriptProperties();
function myFunction() {
  const url = scriptProperties.getProperty('webpage_url');
  const response = UrlFetchApp.fetch(url);
  const html = response.getContent();
  const digest = Utilities.base64EncodeWebSafe(Utilities.computeDigest(Utilities.DigestAlgorithm.MD5, html));
  const lated_md5 = scriptProperties.getProperty('lated_md5');

  if (digest !== lated_md5) {
    scriptProperties.setProperty('lated_md5', digest);
    postSlack(`Webページの更新を確認しました: ${url}`);
  }
}

function postSlack(text){
  const url = scriptProperties.getProperty('webhook');
  const options = {
    "method" : "POST",
    "headers": {"Content-type": "application/json"},
    "payload" : `{"text":"${text}"}`
  };
  UrlFetchApp.fetch(url, options);
}
```

貼り付けできましたら，「_無題のプロジェクト_」と書かれているところをクリックしてお好みの名前に変更して保存してください。
私は「札幌市定額給付金」としました。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/4fbdef79-d881-0091-0fcc-14fa6af6cf5e.png)

## Slack Incoming WebHooks の設定
スクリプトを保存したら，次は [Slack Incoming WebHooks](https://slack.com/apps/A0F7XDUAZ-incoming-webhooks) 側の設定を行います （英語の画面で紹介します，もしかしたら日本語の画面があるかもしれません）。

1. [https://slack.com/apps/A0F7XDUAZ-incoming-webhooks](https://slack.com/apps/A0F7XDUAZ-incoming-webhooks) にアクセスし，左側「Add to Slack」をクリック
2. 投稿先のチャンネル (Post to Channel) を選択して「Add Incoming WebHooks integration」をクリック
3. 細かい設定ができる画面が出てくるので「Webhook URL」のところの「`https://hooks.slack.com/~`」をコピーしておく

|1.|2.|3.|
|---|---|---|
|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/03d5e555-3d31-279e-2c25-809d7407c8c4.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/1ca85c9b-eafc-83ca-e9b7-ee17ac5606df.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/14469e93-4867-cebb-7ffd-794e917cca57.png)|

この Webhook URL は次の設定で使用します。

## スクリプトのプロパティの設定
上で紹介したスクリプトは監視先 URL と更新通知先 URL はスクリプトのプロパティから取得するようにしてあるので，それぞれ設定します。

スクリプトのプロパティの設定画面は以下にあります:

1. メニューの「ファイル」をクリックして出てきた中にある「プロジェクトのプロパティ」をクリック
2. モーダルが表示されるので「スクリプトのプロパティ」をクリック
3. この画面でスクリプトのプロパティを設定します

|1.|2.|3.|
|---|---|---|
|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/cb554660-2e66-1228-134d-2a00c134891d.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/798db974-0c6e-ba70-425c-5e934ed45b6e.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/b45c58d2-d93f-16ee-6819-f990619b78f4.png)|

「行を追加」をクリックして行を追加して，「`webpage_url`」プロパティと「`webhook`」プロパティを設定します。
`webpage_url` の値は監視先のページの URL （今回の例では `https://www.city.sapporo.jp/2019n-cov/hokenfukushi/teigakukyuhu.html`），`webhook` の値は通知先の URL (先ほどコピーした Webhook URL) を入力して，「保存」をクリックします。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/b66cd866-c416-fe40-d5db-a9558dc66149.png)

## アクセス許可の設定とテスト
このままではまだ GAS から Web ページにはアクセスできません。
なのでアクセスの許可設定を行います:

1. メニュー「実行」をクリック，「関数を実行」から「`myFunction`」をクリック
2. 「Authorization Required」というモーダルが表示されるので「許可を確認」をクリック
3. アカウントを選択（クリック）
4. 「このアプリは確認されていません」という画面ファ出てくるので，左下の「詳細」をクリック
5. 4. の画面のさらに下に表示が出てくるので，最下部の「`プロジェクト名`（安全ではないページ）に移動」をクリック
6. 「`プロジェクト名`が Google アカウントへのアクセスをリクエストしています」と出てくるので右下の「許可」をクリック

すると元の画面に戻ります。
その裏で実際に作成したスクリプトが実行されています。

|1.|2.|3.|
|---|---|---|
|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/70df71c3-a468-d9ef-7e8f-83cd4686ae41.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/d1de886f-4030-db48-f7da-b841676cfb6f.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/c7ca09ed-8dc2-6214-e758-5e4366cb00ab.png)|

|4.|5.|6.|
|---|---|---|
|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/a2a45af0-42ae-1d7c-1459-691c62557d75.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/94ccf2f3-8376-83ba-8ffc-605f7cb6f71c.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/983a878e-7098-1b5f-fd27-d68bbefa3999.png)|

初回実行時は前回のデータがないため必ず 更新あり と判断され通知がくるので，通知先を確認してみてください。
無事，ボットから下のような投稿があれば成功です。

![スクリーンショット.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/2283d4a5-3241-4bd9-8061-5990d482c544.png)


## 定期実行の設定
許可周りや動作の確認が済んだので最後に定期実行の設定を行います。

1. メニュー「編集」をクリックして，「現在のプロジェクトのトリガー」をクリック
2. トリガーの設定ページに移動したら，右下の「トリガーを追加」をクリック
3. お好みの設定に変更して「保存」をクリックする（実行する関数と実行するデプロイは変更しない）

|1.|2.|3.|
|---|---|---|
|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/588c2565-5a0a-1ab8-7e85-aafb4f73c9f2.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/d8fdbfcd-e88f-ed5a-52fc-c85c6b2a2259.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59163/e6440007-68dd-5de3-6ecc-4573f6d6f3af.png)|

初期設定では 1 時間おきになっていますがお好みの時間に変更してください。
ただしあまりに高頻度に実行すると GASの無料枠を使い切ってしまう可能性があります。
また，常識的ではない頻度に設定した場合は最悪訴えられる可能性がありますのでご注意ください。 (5分や15分なら何もないとは思いますが，あくまで自己責任で。)

## まとめ
GAS と Slack Incoming WebHooks を組み合わせて，Webページの更新通知を実現しました。
今回の定額給付金ページの更新確認以外にも色々と使い道がありそうです。

今回は1時間もかからずに作成から下書き投稿までできました👏
<blockquote class="twitter-tweet" data-partner="tweetdeck"><p lang="ja" dir="ltr">定期アクセスして md5 比較して更新あったら slack incoming webhook で slack 通知ぐらいならすぐできそうだよなぁ</p>&mdash; 高木さん (𝔂_𝓴) (@YetAnother_yk) <a href="https://twitter.com/YetAnother_yk/status/1258891144546545664?ref_src=twsrc%5Etfw">May 8, 2020</a></blockquote>
<script async src="https://platform.twitter.com/widgets.js" charset="utf-8"></script>

ところでいつになったら札幌市は受付開始するのでしょうか🤔

### 紹介
他にもやってくださった方がいたので紹介します。

* [#! - 定額給付金のページに更新がアレば通知する](http://0x6d61.com/post.sh?id=%E5%AE%9A%E9%A1%8D%E7%B5%A6%E4%BB%98%E9%87%91%E3%81%AE%E3%83%9A%E3%83%BC%E3%82%B8%E3%81%AB%E6%9B%B4%E6%96%B0%E3%81%8C%E3%82%A2%E3%83%AC%E3%81%B0%E9%80%9A%E7%9F%A5%E3%81%99%E3%82%8B): shell script × cron で Web ページの取得と定期実行を実現して，更新があれば Discord に通知がいくようにしています。(自分も Discord の API も触ってみたい…！)

## 参考
- [Google Developers: Apps Script](https://developers.google.com/apps-script)