LoginSignup
8
10

More than 3 years have passed since last update.

【GAS】Webページが更新されたらGmailに通知する

Last updated at Posted at 2019-09-07

2021/2/23追記

以下の記事がより新しいです.キャッシュを利用した改良版です.
【GAS】メールに含まれるURL先の更新を自動で確認
https://qiita.com/golyat/items/3798f17f1836fcffe993

概要

GASによるウェブページの汎用的な簡易更新チェッカーです。任意のWebサイトの更新をGmailに通知します。
スマホからの利用を想定してGmailの下書きにURLを貼り付ければ通知してくれます。
作った動機は宅配のページ確認が面倒くさかったからです。

UI

  • スマホで更新確認したいサイトを見つける
  • Gmailに共有またはURLコピーでGmailの下書き保存
  • サイトが更新された場合はメールで通知してくれる
  • 更新確認をやめる場合は下書き削除

プログラムのフロー

  • Gmail下書きからURLを取得
  • GASでUrlFetch
  • ページ中の文字列をハッシュ値に変換
  • 古いハッシュ値と比較
  • ハッシュ値が変化していればメール通知とプロパティ更新

ソース

function webMonitor() {
  const myThreads = GmailApp.search('in:draft');
  const myMsgs = GmailApp.getMessagesForThreads(myThreads);
  const urls = myMsgs.map(function(msg) {
    return msg[0].getPlainBody().match(/(http(s)?:\/\/[-_.!~*\'()a-zA-Z0-9;\/?:\@&=+\$,%#]+)/gi);
  }).filter(function(x) {
    return x != null;
  });

  urls.map(function(url) {
    const response = UrlFetchApp.fetch(url);
    //文字コード(UTF-8など)の取得(適当、なくてもいいかもしれない)
    const code = response.getHeaders()['Content-Type'].slice(19);
    const html = response.getContentText(code);
    //タイトルとボディーの取得(適当、見た目の問題なので必要ない)
    const title = html.match(/<title>([\s\S]*?)<\/title>/i)[0].replace(/(<|{)("[^"]*"|'[^']*'|[^'">])*(>|})/g,'')
    const body =  html.replace(/<head>[\S|\s]*?<\/head>/g,'').replace(/(<|{)("[^"]*"|'[^']*'|[^'">])*(>|})/g,'').replace(/\s+/g, "");
    //文字コードの総和でハッシュ値化。
    const hashValue = makeHash(body);
    //プロパティにアクセス。プロパティは実行終了後も保存される。
    //文字列全部はサイズが大きすぎるのでハッシュ値化。
    //オブジェクトも保存できない。初期値null。プロパティのkeyにはURLを使う。
    //数字を保存しても文字列として出てくる。
    const dp = PropertiesService.getScriptProperties(); 
    const beforeValue = dp.getProperty(url);

    if(hashValue != Number(beforeValue)) {
      dp.setProperty(url, hashValue);
      if(beforeValue != null) {
        GmailApp.sendEmail('xxx@email.address', '【update】'+ title, url)
      }
    }
  });

  function makeHash(str) {
    var sum = 0;
    for(var i = 0; i < str.length; i++) {
      sum += str.charCodeAt(i)
      sum %= 1000000
    }
    return sum;
  }
}

終わりに

ハッシュ値がぶつかることもあるので100%通知されるとは限らない。個人利用ということで気にしない。
ちゃんと通知させたい方はハッシュ関数をもっとちゃんとしたものにすると良いかもしれない。
GASに限りませんがフェッチする頻度が高いとGASサーバにも相手サーバにも負荷をかけることになるのでご利用は計画的に。
サイトによってはフェッチできないのでエラー処理で通知はあった方がいいかもしれない。
LINE、Slack、Twitterでやりたい方はそれぞれのAPI叩いてください。

更新

2019.9.20:ちょっとした書き換え。修正。

参考資料

https://developers.google.com/apps-script/reference/url-fetch/url-fetch-app
https://developers.google.com/apps-script/reference/url-fetch/http-response
https://developer.mozilla.org/ja/docs/Web/JavaScript/Reference/Global_Objects/String/charCodeAt

8
10
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
8
10