この記事はモチベーションクラウドシリーズアドベントカレンダー2020の9日目の記事です。
最近GASでツールを作成したので、その経験を基に、GASツールを作成するための4つの技を紹介します。
この4つの技を覚えれば、GASツールで煩わしい作業から解放されます!
4つの技
GASツールを作成するために覚える4つの技は「関数」「イベントトリガー」「スプレッドシート連携」「外部API連携」です。
この4つを覚えればGASツールを作成できます。
関数:プログラムを定義する技
イベントトリガー:関数を起動する技
スプレッドシート連携:スプレッドシートを読み込んだり書き込んだりする技
外部API連携:Slackなどの外部APIと連携する技
関数:プログラムを定義する技
プログラムを定義するために関数を作成します。GASは定義した関数を実行することができます。
スプレッドシートのメニューバーからツール>スクリプトエディタの順にクリックすると、別タブにスクリプトエディタが表示されます。
スクリプトエディタからgsファイルを編集して、以下のように関数を定義します。
function hello() {
// 実行するプログラム
}
例ではhello関数を定義しました。helloは定義したい関数の名前にあわせて入力してください。
イベントトリガー:関数を起動する技
作成した関数も起動しなければ動きません。作成したプログラムを起動するための3つのイベントトリガーを紹介します。
ボタン
関数を起動するためのボタンを作成して、ボタンがクリックされたら関数が起動するようにできます。
ボタンの作成方法
スプレッドシートのメニューバーから挿入>図形描画をクリックすると、図形描画モーダルが表示されます。
図形描画モーダルでボタンを作成することができます。
図形描画モーダルのメニューバーから図形>図形>ボタンのような図形を選択して図形描画モーダルにボタンを追加します。
図形描画モーダルにボタンを追加したら、ボタンに文言を入力しましょう。
保存して終了ボタンをクリックすると、シートにボタンを作成できます。
作成したボタンを右クリックすると、ボタンの右上に**︙**が表示されます。
︙>スクリプトを割り当てをクリックすると、スクリプトを割り当てモーダルが表示されます。
hello関数を割り当てる場合は、helloと入力してOKボタンをクリックすれば、hello関数を割り当てることができます。
タイマー
タイマーを設定して、関数を特定の時間に起動するようにできます。
タイマーの設定方法
スプレッドシートのメニューバーからツール>スクリプトエディタの順にクリックすると、別タブにスクリプトエディタが表示されます。
スクリプトエディタのメニューバーから現在のプロジェクトトリガーをクリックすると、別タブにトリガー画面が表示されます。
トリガーを追加ボタンをクリックすると、GAS Botsのトリガーを追加モーダルが表示されます。
設定項目 | 設定内容 |
---|---|
実行する関数を選択 | タイマーで起動したい関数を選択します。 |
実行するデプロイを選択 | Headを選択します。 |
イベントのソースを選択 | タイマーを設定したいので時間主導型を選択します。 |
イベントのソースを選択で時間主導型を選択すると、時間ベースのトリガーのタイプを選択が設定できるようになります。
- 特定の日時・・・特定の日時に1回関数を起動します。
- 分ベースのタイマー・・・指定の分おき毎に関数を起動します。1分おきから30分おきの範囲で選択できます。
- 時間ベースのタイマー・・・指定の時間おき毎に関数を起動します。1時間おきから12時間おきの範囲で選択できます。
- 日付ベースのタイマー・・・特定の時刻に関数を起動します。午前0時〜1時から午後11時〜午前0時の範囲で選択できます。
- 週ベースのタイマー・・・特定の曜日の特定の時刻に関数を起動します。週は毎週月曜日から毎週日曜日の範囲で選択できます。時刻は午前0時〜1時から午後11時〜午前0時の範囲で選択できます。
- 月ベースのタイマー・・・特定の日の特定の時刻に関数を起動します。日は1日から31日の範囲で選択できます。時刻は午前0時〜1時から午後11時〜午前0時の範囲で選択できます。
Webhook
WebhookとはSlackなどの外部サービスのイベントを受信するための仕組みです。
WebhookでイベントをHTTPリクエストとして受信して、関数を起動するようにできます。
Webhookの実装方法
WebhookはdoGet関数/doPost関数で実装します。
doGet関数は連携する外部サービスがGETメソッドでリクエストを送信する場合に利用します。
doPost関数は連携する外部サービスがPOSTメソッドでリクエストを送信する場合に利用します。
連携する外部サービスがどのようなリクエストを送信するかによってdoGet関数/doPost関数のどちらを利用するかは変わります。
doGetの実装例
function doGet(event) {
const target = event.parameter.target;
hello(target)
}
例ではリクエストのtargetパラメータを取得して、hello関数を実行します。
event.parameterプロパティからリクエストのパラメータを取得できます。
doPostの実装例
function doPost(event) {
const parameter = JSON.parse(event.postData.contents);
const target = parameter.target;
hello(target)
}
例ではリクエストのtargetプロパティを取得して、hello関数を実行します。
event.postData.contentsからリクエストのbodyを取得できるので、JSON.parseでパースしてオブジェクトに変換して利用します。
複数の外部サービスからリクエストを受け付ける場合
doGet関数/doPost関数は1つしか実装できないため、doGet関数/doPost関数内でif文などを利用して外部サービス毎に処理を切り替える必要があります。
Webhook URLの生成方法
Webhookの関数を作成した後、Webhookを起動するためのURLを生成する必要があります。
スプレッドシートのメニューバーからツール>スクリプトエディタの順にクリックすると、別タブにスクリプトエディタが表示されます。
スクリプトエディタのメニューバーから**公開>ウェブ アプリケーションとして導入…**をクリックすると、「Deploy as web app」モーダルが表示されます。
設定項目 | 設定内容 |
---|---|
Project version | Newを選択します。 |
Execute the app as | 自分のメールアドレスを選択します。 |
Who has access to the app: | Anyone, even anonymousを選択します。 |
Deploy
ボタンをクリックします。
Current web app URL
が表示されます。このURLが外部サービスからリクエストを送信するとWebhookが実行できるWebhook用のURLです。
「非公開」にはできませんので、第三者に漏洩しないように取り扱いには十分にご注意ください。
Webhook用のURLを生成した後に修正した場合
修正を反映するためにWebhook用のURLを再生成する必要があります。
スプレッドシート連携:スプレッドシートを読み込んだり書き込んだりする技
スプレッドシートと連携して、関数の実行結果をスプレッドシートに書き込んだり、関数を実行する用の設定をスプレッドシートから読み込んだりすることができます。
対象のセルを取得
スプレッドシートに書き込みをする場合でも読み込みをする場合でも、操作対象のセル範囲を取得する必要があります。
操作対象のセル範囲を取得するには、以下のメソッドを利用します。
-
SpreadsheetApp.getActiveSpreadsheet()
・・・対象のスプレッドシートを取得します。 -
Spreadsheet#getSheetByName(name)
・・・指定のシート名に該当するシートを取得します。 -
Sheet#getRange(row, column)
・・・指定の引数に該当するセル範囲を取得します。 -
Sheet#getRange(row, column, numRows)
・・・指定の引数に該当するセル範囲を取得します。row, column
で範囲の開始位置を指定して、numRows
で範囲の終了位置を開始位置から相対的に指定します。 -
Sheet#getRange(row, column, numRows, numColumns)
・・・指定の引数に該当するセル範囲を取得します。row, column
で範囲の開始位置を指定して、numRows, numColumns
で範囲の終了位置を開始位置から相対的に指定します。 -
Sheet#getRange(a1Notation)
・・・指定の引数に該当するセル範囲を取得します。文字列でgetRange("A1")
、getRange("A1:B2")
、getRange("A2:A")
などと指定します。
Sheet#getRange(*)
の指定方法が分かりづらい場合、こちらが分かりやすいかもしれません。
書き込み
対象のセル範囲に値を書き込むには、Range#setValues(values)
メソッドを利用します。valuesは値の2次元配列です。
以下の例シートのように値を設定する場合は、
A | B | C | |
---|---|---|---|
1 | A1 | B1 | C1 |
2 | A2 | B2 | C2 |
以下のように実装します。
const spreadsheet = SpreadsheetApp.getActiveSpreadsheet();
const sheet = spreadsheet.getSheetByName("例");
const range = sheet.getRange("A1:C2");
range.setValues([
["A1", "B1", "C1"],
["A2", "B2", "C2"]
]);
読み込み
対象のセル範囲から値を読み込むには、Range#getValues()
メソッドを利用します。戻り値は値の2次元配列です。
以下の例シートから値を設定する場合は、
A | B | C | |
---|---|---|---|
1 | A1 | B1 | C1 |
2 | A2 | B2 | C2 |
以下のように実装します。
const spreadsheet = SpreadsheetApp.getActiveSpreadsheet();
const sheet = spreadsheet.getSheetByName("例");
const range = sheet.getRange("A1:C2");
const values = range.getValues();
console.log(values); // output: [["A1", "B1", "C1"], ["A2", "B2", "C2"]]
外部API連携:Slackなどの外部APIと連携する技
関数から外部APIにHTTPリクエストを送信することができます。
外部API連携することでGASからSlackにメッセージを送信するなどができます。
URL Fetch App
GASから外部APIにHTTPリクエストを送信するには、UrlFetchApp.fetch(url[, params])
メソッドを利用します。戻り値はHTTPResponseです。
引数は主に以下の値を指定します。
引数 | 型 | 説明 |
---|---|---|
url | String | HTTPリクエストを送信する宛先のURL |
params.contentType | String | リクエストのContent-Typeを指定します。JSONを送信する場合は"application/json" を指定します。 |
params.headers | Object | リクエストヘッダをkey/valueのオブジェクトで指定します。 |
params.method | String | HTTPメソッドを指定します。デフォルトは"get" です。 |
params.payload | String | リクエストボディを指定します。GETメソッドの場合は指定できません。オブジェクトを指定するとapplication/x-www-form-urlencoded かmultipart/form-data かとして扱われます。 |
HTTPResponseは主に以下のメソッドを利用します。
メソッド | 戻り値の型 | 説明 |
---|---|---|
getContentText() | String | レスポンスボディを取得します。 |
getHeaders() | Object | レスポンスヘッダを取得します。 |
getResponseCode() | Integer |
200 などのHTTPステータスコードを取得します。 |
Slackのsampleチャンネルに"hello"というメッセージを送信する場合は、以下のように実装します。
const data = {
channel: "sample",
text: "hello"
};
response = UrlFetchApp.fetch(
"https://slack.com/api/chat.postMessage",
{
contentType: "application/json"
headers: {
"Authorization": "Bearer xoxp-xxxxxxxxx-xxxx"
},
method: "post",
payload: JSON.stringify(data)
});
console.log(response.getResponseCode()); // output: 200
console.log(response.getContentText()); // output: '{ "OK": true, ... }'
まとめ
GASでツールを作成するための4つの技を紹介しました。
ほとんどのツールは4つの技の組み合わせで作成することができます。
日々の業務やプライベートで自動化したい作業があれば、ぜひ自動化して楽になってもらえれば嬉しいです!
私は4つの技を駆使して、単純作業だった勤怠連絡をツール化して、楽をしてます!
皆様もGASでツールを作成してエンジョイライフを過ごしましょう!
【補足】なぜ、GAS?
GUI/CUIを作るコストが少ない
GUIはスプレッドシートの機能で簡単に作成することができます。
実行環境を準備する必要がない
GASはGoogleのスプレッドシート上で動作するため、実行環境を準備する必要がありません。
簡単に共有できる
GASはGoogleのスプレッドシート上で動作するため、他のユーザーにも簡単に共有できます。
【おまけ】GASで何を作った?
私は4つの技を駆使して、毎日Slackに勤怠連絡していた作業をツール化しました。
勤怠連絡
ワンクリックで勤怠連絡を行いたかったので、ボタンをクリックしたらSlackに勤怠連絡できるようにしました。
イベントトリガーのボタンを作成して、ボタンクリックに割り当てた関数から外部API連携を実行して、Slackに勤怠連絡メッセージを送信できるようにしました。
ボタンは「勤務開始ボタン/勤務終了ボタン/休憩開始ボタン/休憩終了ボタン」を実装し、ボタン毎に勤怠連絡メッセージが変わります。
ツールを作る前はSlackでメッセージと勤怠日時を手動入力してました。
ユーザ設定
ツールは他の開発メンバーにも共有したかったので、ユーザ設定シートを作って、勤怠連絡メッセージのユーザ名とアイコンを開発メンバー毎に設定できるようにしました。
スプレッドシート連携でユーザ設定シートと連携して、ユーザ設定シートからユーザ名とアイコンを読み込んで、勤怠連絡メッセージのパラメータに設定するようにしました。
タイムカード
勤怠連絡した日時を簡単に視認できるようにしたかったので、タイムカードシートを作成して、タイムカードに勤怠日時を記録するようにしました。
勤怠連絡の操作時に、スプレッドシート連携でタイムカードシートと連携して、タイムカードシートに勤怠日時を書き込みました。
タイムカードシートに日々の稼働状況が記録されているため、「日付/出勤時間/退勤時間/非稼働時間」を一覧で見ることができます。
ツールを作る前はSlackに連絡した内容をスクロールで遡って確認してました。月次の稼働報告のために1ヶ月分も遡っていたので大変でした。