GASからSlackに自動通知する方法
Incoming Webhookで実装
スプレッドシートやフォームの動きを、GAS(Google Apps Script、Googleのサービスを自動化する開発環境)からUrlFetchAppでSlackに自動通知する方法を、コピーして動く実装コードで解説します。
Table of Contents
なぜGAS×Slack通知が便利なのか
「フォームに回答が届いたらすぐ気づきたい」「在庫が一定数を下回ったら知らせてほしい」—— こうした通知はメールだと埋もれがちです。GASからSlackに送れば、チームが普段見ているチャンネルに即座に届き、対応漏れを防げます。 しかもSlackのIncoming Webhook(受信専用の投稿用URL)を使えば、Slackアプリの開発やAPIトークンの管理なしに、URLへPOSTするだけで投稿できます。
問い合わせの即時共有
フォーム回答をチャンネルに流し、担当者がすぐ一次対応できる
エラー・異常の検知
定期処理が失敗したときにアラートを飛ばし、放置を防ぐ
在庫・数値のしきい値通知
スプレッドシートの数値が基準を超えたら自動でお知らせ
日次サマリーの配信
1日の集計結果を毎朝チャンネルに投稿する
準備:Slack Incoming Webhookを取得する
まずは投稿先のWebhook URLを発行します。Slackの管理画面から数分で取得できます。
手順
- Slack APIのアプリ管理ページ(
api.slack.com/apps)で「Create New App」を選び、ワークスペースにアプリを作成します。 - 左メニューの「Incoming Webhooks」を開き、スイッチをオンにします。
- 「Add New Webhook to Workspace」を押し、投稿先のチャンネルを選んで許可します。
- 発行された
https://hooks.slack.com/services/...というURLをコピーします。これがWebhook URLです。
※ このURLを知っている人は誰でもそのチャンネルに投稿できます。取り扱いはパスワードと同じく慎重に。
最小コード:Slackにメッセージを送る
Webhook URLに対して、UrlFetchApp.fetch()でJSONをPOSTするだけで投稿できます。まずはテキスト1行を送る最小構成です。
function sendSlackMessage(text) {
// スクリプトプロパティに保存したWebhook URLを読み込む
const url = PropertiesService
.getScriptProperties()
.getProperty("SLACK_WEBHOOK_URL");
const payload = { text: text };
const options = {
method: "post",
contentType: "application/json",
payload: JSON.stringify(payload),
muteHttpExceptions: true, // エラー時も例外にせずレスポンスを受け取る
};
const res = UrlFetchApp.fetch(url, options);
Logger.log("status: " + res.getResponseCode()); // 200なら成功
}
function testSend() {
sendSlackMessage("GASからのテスト通知です :rocket:");
}muteHttpExceptions: trueを付けると、失敗しても例外で止まらずレスポンスを受け取れるので、原因調査がしやすくなります。
Webhook URLを安全に保管する
Webhook URLはコードに直書きせず、PropertiesService(スクリプト単位で値を保存できる保管庫)に入れておきます。下の関数を1度だけ実行してURLを登録し、その後は関数を消しておくと、コードにURLが残りません。
function saveWebhookUrl() {
// 実行後、この関数はコードから消しておくと安全
PropertiesService.getScriptProperties().setProperty(
"SLACK_WEBHOOK_URL",
"https://hooks.slack.com/services/XXXX/YYYY/ZZZZ"
);
}エディタの「プロジェクトの設定 › スクリプト プロパティ」から画面上で直接登録することもできます。GitHubなどにコードを公開する場合は、必ずこの方式にしてください。
Block Kitでリッチな通知にする
項目が複数あるときは、SlackのBlock Kit(通知の見た目を組み立てる仕組み)を使うと読みやすくなります。blocks配列に見出し(header)と項目(fields)を並べます。
function sendSlackBlocks(title, fields) {
const url = PropertiesService
.getScriptProperties()
.getProperty("SLACK_WEBHOOK_URL");
const payload = {
blocks: [
{
type: "header",
text: { type: "plain_text", text: title, emoji: true },
},
{
type: "section",
// fields は [{label, value}, ...] を想定
fields: fields.map((f) => ({
type: "mrkdwn",
text: "*" + f.label + "*\n" + f.value,
})),
},
],
};
UrlFetchApp.fetch(url, {
method: "post",
contentType: "application/json",
payload: JSON.stringify(payload),
muteHttpExceptions: true,
});
}
function testBlocks() {
sendSlackBlocks("新規お問い合わせ", [
{ label: "お名前", value: "山田 太郎" },
{ label: "会社名", value: "株式会社サンプル" },
{ label: "内容", value: "GAS開発の見積もり依頼" },
]);
}mrkdwn形式では、アスタリスクで囲むと太字になります。改行はコード上では\nで表現します。
フォーム送信をトリガーに通知する
Googleフォームと連携したスプレッドシートなら、「フォーム送信時」トリガーで回答が届いた瞬間に通知できます。 トリガーから渡されるe.valuesに回答が配列で入っているので、必要な項目を取り出して送ります。
function onFormSubmit(e) {
// フォーム送信トリガーから渡される回答値の配列
const values = e.values; // [タイムスタンプ, 名前, メール, 内容, ...]
const name = values[1];
const email = values[2];
const content = values[3];
sendSlackBlocks("新規フォーム回答が届きました", [
{ label: "お名前", value: name },
{ label: "メール", value: email },
{ label: "内容", value: content },
]);
}トリガーはコードから登録できます。二重登録を防ぐため、既存の同名トリガーを削除してから作るのがポイントです。
function createFormSubmitTrigger() {
const ss = SpreadsheetApp.getActive();
// 二重登録を防ぐため既存の同名トリガーを削除
ScriptApp.getProjectTriggers().forEach((t) => {
if (t.getHandlerFunction() === "onFormSubmit") {
ScriptApp.deleteTrigger(t);
}
});
ScriptApp.newTrigger("onFormSubmit")
.forSpreadsheet(ss)
.onFormSubmit()
.create();
}※ 列の並び順はフォームの質問順に対応します。実際のシートを見て、名前やメールが何番目の列(0始まり)かを合わせてください。
エラー処理と実務での注意点
通知は「届かなくても気づきにくい」のが怖いところです。送信結果を必ずチェックし、失敗をログに残しておきましょう。
function sendSlackSafe(text) {
const url = PropertiesService
.getScriptProperties()
.getProperty("SLACK_WEBHOOK_URL");
if (!url) {
Logger.log("Webhook URLが未設定です");
return false;
}
const res = UrlFetchApp.fetch(url, {
method: "post",
contentType: "application/json",
payload: JSON.stringify({ text: text }),
muteHttpExceptions: true,
});
const code = res.getResponseCode();
if (code !== 200) {
// 失敗内容をログに残す(Slackの応答は "invalid_payload" などの文字列)
Logger.log("Slack通知失敗 status=" + code + " body=" + res.getContentText());
return false;
}
return true;
}1. レート制限に注意する
Incoming Webhookは短時間に大量送信すると制限がかかります。ループの中で1件ずつ送るのではなく、内容をまとめて1通にする設計が安全です。
2. Webhook URLはチャンネル固定
1つのIncoming Webhookは発行時に選んだチャンネルに紐づきます。複数チャンネルに投げ分けたい場合は、チャンネルごとにWebhookを発行して使い分けます。
3. 個人情報の送りすぎに注意
通知にはチャンネルの参加者全員がアクセスできます。氏名や連絡先など、共有範囲に応じて送る項目を絞るか、詳細はスプレッドシートへのリンクに留める運用が安全です。
まとめ
GASからSlackへの通知は、Incoming Webhookを発行し、UrlFetchApp.fetch()でJSONをPOSTするだけで実装できます。テキスト1行から始め、Block Kitで見やすく整え、フォーム送信トリガーと組み合わせれば、業務の動きをリアルタイムでチームに届けられます。 Webhook URLはPropertiesServiceで安全に保管し、送信結果のチェックを忘れないことが、実務で安定運用するコツです。
よくある質問
単純な通知だけならAPIトークンは不要です。SlackのIncoming Webhook(受信専用のURL)を発行し、そのURLにGASのUrlFetchApp.fetch()でPOSTするだけで投稿できます。メッセージの編集・削除や過去ログの取得など高度な操作が必要な場合のみ、Bot TokenとWeb APIを使います。
LINE Notifyは2025年3月31日にサービス終了しましたが、SlackのIncoming Webhookは現在も提供されている標準機能です。ただし古い「レガシーIncoming Webhook」ではなく、Slackアプリ(App)経由で発行する現行のIncoming Webhookを使うのが推奨です。
おすすめしません。Webhook URLを知っている人は誰でもそのチャンネルに投稿できるため、URLは秘密情報です。コードに直書きせず、PropertiesService(スクリプトプロパティ)に保存して読み込む方法が安全です。GitHubなどにコードを公開する場合は特に必須です。
できます。フォーム連携シートなら「フォーム送信時」トリガー、手入力や外部連携なら「編集時」トリガーや時間主導トリガーで新規行を検知し、その内容をSlackへ送る関数を呼び出します。本記事ではフォーム送信トリガーの実装例を紹介しています。
できます。SlackのBlock Kitという仕組みを使い、blocks配列に見出し(header)やフィールド(fields)を指定すると、整形された通知を送れます。左端に色を付けたい場合はattachmentsのcolorを併用します。本記事にコード例を掲載しています。
まずUrlFetchApp.fetch()の戻り値のステータスコードを確認します。200以外なら、Webhook URLの誤り、送信先チャンネルのアーカイブ、JSONの形式ミスが主な原因です。muteHttpExceptions: trueを付けてレスポンス本文をLogger.logで確認すると原因を特定しやすくなります。