Magicode logo
Magicode
0
4 min read

[GAS] 具体事例から学ぶScriptAppによるトリガー生成コードサンプル(1)~毎日指定時間(○時○分)に実行したい場合

https://cdn.apollon.ai/media/notebox/2d642c9e-204a-4a91-8eec-bbeaf7db45b2.jpeg

はじめに

スプレッドシートを始めとしたGoogleのクラウドアプリは、時間主導型トリガー(以降、タイムトリガー)を使用して、定型処理を定期的に自動実行させることができます。
タイムトリガーはUI画面から簡単に設定可能ですが、UIにて設定できる項目が限られているため、要望する内容によってはGASのScriptAppを使ってプログラム側からトリガーを生成する必要があります。
本稿では、UI画面からの設定では対応できない内容について、当方にご相談頂いた内容を元にした事例別の参考コードを不定期連載形式で紹介していきたいと思います。(ネタが溜まってきたら、随時公開予定です)
今回は初回ということで、比較的実装が容易なケースとして、毎日指定時間(○時○分)に実行したい場合のご紹介です。

前提条件

  1. 仕様上、実行遅延(タイムラグ)がおよそ数分以内のレベルで発生します。そのため、厳密な時間管理が必要な処理には不向きです。(公式にて一部メソッドにおいては±15分と明記されています)
  2. 同様に、仕様上、エラー通知の頻度をスクリプト側で設定できないため、「毎日通知を受け取る」がデフォルトとなります。
  3. こちらの記事を参考にタイムゾーンの設定が実行環境と合っているか確認してください。
  4. サンプルコードでは1日あたりの総実行時間、1ユーザーあたり20トリガーまで等、GASの制限事項は考慮していません。

設置時の共通事項

  1. トリガー生成ロジックは独立した関数として定義し、メイン処理内に組み込みます。組み込み位置は末尾を推奨しておきますが、好みや状況に合わせて適宜ご対応ください。
  2. GASの制限事項を考慮し、適宜メイン処理の軽量化、高速化をしましょう。また、実行回数に関係なく、実行済みトリガーの削除処理の実装を推奨します。
  3. 初回のトリガー設定のみ手動で行いますが、設定画面経由でもエディタから当該関数の直接実行でもどちらでも結構です。

比較的実装が容易なケース(1)

毎日指定時間(○時○分)に実行したい

UI画面にて時間主導型日付ベースのタイマーでできそう、という安易なイメージでハマる場合が多いようです。
ハマるポイントとしては、日付ベースのタイマーでは1時間単位の時間帯しか指定できず、かと言って、特定の日時 の場合は指定日時の1回しか実行されないことです。
ご相談いただいた方の多くのは、指定時間を含む時間帯か、指定時間以降の時間帯で日付ベースのタイマーを使用していました。

ロジック

  • Javascriptにて翌日の指定日時を設定する
  • ScriptAppにて特定の日時としてトリガーを生成する
つまり、当日実行時に翌日の処理を実行予約するイメージです。結果、これが毎回繰り返されることで、毎日指定時間(仮に午後12時34分とします)に自動実行されます。

サンプルコード

// 毎日午後12:34にメイン処理を実行する

// 初期設定用オブジェクト
function init(){
  return {
    START_TIME: '12:34', // hh:mm形式で指定
    TRIGGER_HUNDLER: 'main' // 自動実行対象の関数名
  };
}

// メイン処理
function main() {
  /* メイン処理省略 */

  setTrigger();
}

// トリガー生成処理
function setTrigger() {
  const now = new Date();
  const INIT = init();
  const startTime = INIT.START_TIME.split(':');
  const targetDate = new Date(now.getFullYear(), now.getMonth(), now.getDate()+1, startTime[0]*1, startTime[1]*1);

  ScriptApp.newTrigger(INIT.TRIGGER_HUNDLER)
  .timeBased()
  .at(targetDate)
  .create();
}

初回設定

初回はUI画面より特定の日時mainを実行させるか、エディタ画面よりsetTriggerを実行します。

最後に

今回は初回ということで、比較的実装が容易なケースとして、毎日指定時間(○時○分)に実行したい場合のご紹介をしましたが、もちろん最適解ということではございません。
上記のサンプルコードを例に、mainからsetTriggerを切り離した上で、UI画面にて時間主導型日付ベースのタイマーにて、stTriggerを実行させても同様の結果を得られます。
両者の違いはメイン処理直後に翌日の実行予約をするか、メイン処理とは別に定期的な時間帯で翌日の実行予約をするか、ということになります。効率面では前者となりますが、メイン処理とは切り離したい場合もありますので、状況に応じた実装対応ということになりますね。
誰かのお役に立てたなら幸いです。

Discussion

コメントにはログインが必要です。