cronの失敗をGoogle Apps Scriptで通知する
はじめに
cronが面倒くさい。特に失敗を通知するのが。
そもそも標準エラー出力があった時だけ通知されるようにするのも面倒なんですが、
AWSを使ってると迷惑メール扱いされないようにAmazon SES使うなり、DNS逆引き設定するなりしないといけないわけです。
こんなのサーバ毎にやってられんわけです。
ということで、そんな面倒なcronの失敗通知をGoogle Apps Scriptを使うことで楽にします。
スプレッドシート
まずは以下のようなスプレッドシートを作ります。
Google Apps Script
スプレッドシートの [ ツール ] > [ スクリプトエディタ ] を開き、以下の関数を登録します。
function doPost(e) { var sheet = SpreadsheetApp.getActive().getSheetByName('メーリングリスト'); var to_emails = sheet.getRange(1, 1, sheet.getLastRow()).getValues(); var subject = 'エラー通知'; var body = "以下の処理でエラーが発生しました。\n\n"; body += "タスク名: " + e.parameter.task_name; GmailApp.sendEmail(to_emails.join(','), subject, body); }
続いて、作成した関数を公開します。
スクリプトエディタの [ 公開 ] > [ ウェブアプリケーションとして導入... ] を選択します。
GASを初めて公開する場合、Googleの認証が出るので許可してください。
公開の設定は以下になります。
ここで表示される「現在のウェブアプリケーションのURL」にリクエストを送ることでメールが送信されるようになります。
スクリプトを更新する場合
再度、 [ 公開 ] > [ ウェブアプリケーションとして導入... ] が必要になります。
この時にプロジェクトバージョンを上げないと反映されないので注意してください。
自分も毎回やり忘れます。
cron
cronの処理は何でもいいんですが、
例としてLet's Encriptの更新処理をcronに登録します。
/etc/crontab
# エラーはGASで通知するので、全ての出力をリダイレクト 0 6 * * mon root /opt/cron/certbot_renew.sh >> /var/log/certbot_renew.log 2>&1
certbot_renew .sh
#!/usr/bin/env bash /opt/certbot/certbot-auto renew --no-self-upgrade --deploy-hook "systemctl restart nginx" # 証明書の更新に失敗したらGAS経由でメール通知 if [ $? != 0 ]; then TASK_NAME="certbot_renew.sh" curl -X POST -d task_name=$TASK_NAME https://script.google.com/macros/s/${APP_ID}/exec fi
最後に
メールにこだわらなくていいなら、Slackとかに通知した方が楽。
以上、現場からでした。