毎日数十回「👀」「✅」を手で押すのをやめた話。Slack Appによる運用通知の自動化

こんにちは。monoAI technologyエンジニアのシュウです。

毎日数十件の運用通知に「👀」「✅」を手で押し続ける。地味な作業だが、確実に工数を食う。今回、Slack AppにBot自身がリアクションを付ける権限を追加し、人間の手を介さずステータス管理を自動化した取り組みを紹介します。

Slackのリアクションを自動化してみた

運用チームでは監視アラートやデプロイ通知をSlackに集約し、担当者が絵文字リアクションで対応状況を表現していました(👀=確認中、✅=完了など)。管理者はリアクション状況を見て進捗を把握する運用でしたが、通知件数の増加に伴い「リアクションを押す」行為自体が定型作業化し、対応の手を止める原因になっていました。

今回、内製Slack Appにreactions:writeスコープを追加し、通知投稿と同時にBotが自分の投稿へリアクションを管理する仕組みを構築。手動オペレーションを排除し、ステータス可視化を自動化しました。

手動リアクションという隠れた運用コスト

運用チャンネルには、デプロイ完了通知・バッチジョブの実行結果・監視アラートなど、多様な通知が流れます。担当者は各通知に目を通し、対応を開始したら👀を付け、完了したら✅に変える運用でした。管理者はチャンネルを遡り、リアクションの有無で進捗を把握していました。

通知件数が1日20〜30件程度の頃は問題なかったのですが、監視対象が増えるにつれ、リアクションを押すために作業フローを中断する回数が増えました。本質的には自動判定できる状態遷移(通知送信→処理開始→完了)を、わざわざ人間が手動で可視化している構造が非効率でした。

リアクション1回は数秒の作業ですが、1日数十回×チーム全員となると無視できません。しかも「押し忘れ」が発生すると、管理者が個別に進捗確認する手間が生じます。

Slackリアクション機能とBot Tokenスコープ

Slackのリアクション(絵文字スタンプ)は、メッセージへの軽量なフィードバック手段として広く使われています。通常はユーザーが手動で押しますが、Slack AppのBot Tokenにreactions:writeスコープを付与すると、Bot自身がメッセージにリアクションを追加できます。

このスコープは絵文字リアクションの追加と削除を許可し、reactions.addおよびreactions.removeのAPIメソッドと互換性があります。スコープの追加はWorkspace管理者の承認が必要で、App再インストールで反映されます。今回は管理者の承認を得て、内製Appへスコープを追加しました。

設計方針:通知投稿とステータス更新を同一Botに集約

従来は「通知を投稿するBot」と「リアクションを押す人間」が分離していましたが、今回は通知Botが自分の投稿に対してライフサイクル全体でリアクションを管理する設計に変更しました。

具体的には、通知送信時に👀を自動付与し、処理が完了したタイミングで👀を外して✅を付けます。これにより「通知=未対応」「👀=処理中」「✅=完了」という状態遷移が、人間の介入なしに可視化されます。管理者は各メッセージのリアクションを見るだけで進捗を把握でき、担当者は本来の対応作業に集中できます。

従来の運用

  • Bot:通知を投稿するのみ
  • 担当者:手動で👀を付け、完了時に✅へ変更
  • 管理者:リアクション状況を目視確認
  • 課題:リアクション押し忘れ、作業中断、進捗確認の手間

自動化後

  • Bot:通知投稿と同時に👀を付与、完了時に✅へ更新
  • 担当者:リアクション操作不要
  • 管理者:リアクションを見るだけで進捗把握
  • 効果:手動オペレーション削減、ステータス可視化の自動化

実装の詳細

Slack Web APIのreactions.addおよびreactions.removeメソッドを使用しました。通知投稿時に返されるts(メッセージのタイムスタンプID)とチャンネルIDを保持しておき、後続処理でリアクション操作の対象を特定します。

実装の流れ

  1. 通知投稿:chat.postMessageでメッセージを送信し、レスポンスからtsを取得
  2. 処理開始:reactions.addで👀を付与
  3. 処理完了:reactions.removeで👀を削除、reactions.addで✅を追加
  4. エラー発生:reactions.addで❌を付与し、異常系も可視化
// 通知投稿例(疑似コード)
const result = await slackClient.chat.postMessage({
  channel: CHANNEL_ID,
  text: 'デプロイ完了:v1.2.3'
});
const messageTs = result.ts;

// 処理開始時に👀を付与
await slackClient.reactions.add({
  channel: CHANNEL_ID,
  timestamp: messageTs,
  name: 'eyes'
});

// 処理完了時に👀を削除、✅を追加
await slackClient.reactions.remove({
  channel: CHANNEL_ID,
  timestamp: messageTs,
  name: 'eyes'
});
await slackClient.reactions.add({
  channel: CHANNEL_ID,
  timestamp: messageTs,
  name: 'white_check_mark'
});

Rate Limitへの配慮

reactions.addreactions.removeはTier 3のRate Limit(50+リクエスト/分)が適用されます。通知件数が多い場合は、短時間に大量のリアクション操作を行うとRate Limitに抵触する可能性があります。今回の運用では1日数十件程度のため、Range内で運用できています。

スコープ追加とApp再インストール

Slack App管理画面からreactions:writeスコープを追加し、Workspace管理者の承認を経てAppを再インストールしました。スコープの追加には管理者の承認が必要で、承認後にAppを再インストールすることでBot Tokenに権限が反映されます。

導入後の変化

通知への手動リアクションが不要になり、担当者が「リアクションを押す」ために作業フローを中断する回数が減りました。管理者側も、リアクションの有無だけで対応状況を判断できるため、個別に進捗確認する手間が削減されました。

定量的な工数削減は未計測ですが、チーム内では「地味に楽になった」という声が複数挙がっています。リアクション押し忘れによる確認コストもなくなり、ステータス管理の信頼性が向上しました。

項目従来自動化後
手動リアクション1日数十回0回
作業中断リアクション押下のたびに発生なし
進捗確認個別に問い合わせリアクション目視で完結
押し忘れ発生していたなし

よくある質問

Q1. 既存のメッセージへのリアクションも自動化できますか?

可能です。reactions.addtsを指定すれば過去のメッセージにもリアクションを追加できます。ただし、Botが投稿したメッセージ以外へのリアクション追加は、権限設計とユースケース次第で慎重に検討する必要があります。

Q2. リアクションの削除権限はどうなっていますか?

reactions:writeスコープは、Bot自身が追加したリアクションの削除のみを許可します。他のユーザーが付けたリアクションを削除することはできません。

Q3. Rate Limitに引っかかったらどうなりますか?

Slack APIは429 Too Many Requestsを返し、Retry-Afterヘッダーで再試行までの待機時間を通知します。今回の運用では通知件数が少なくLimit内に収まっていますが、大量の通知を扱う場合はリトライロジックの実装が必要です。

まとめ

運用通知の状態遷移を自動リアクションで可視化することで、手動オペレーションの隠れたコストを削減できました。Slack Appにreactions:writeスコープを追加し、通知投稿とステータス更新を同一Botに集約する設計により、人間の介入なしに対応状況を管理者が把握できる仕組みを実現しました。

手動リアクションという小さな作業の積み重ねが、実は運用チーム全体の集中力を削いでいたことに気づけたのは収穫でした。同じような「地味だが確実に工数を食う定型作業」に悩むチームの参考になれば幸いです。

🔗 参考リンク