Google Apps ScriptでSlackのメッセージを削除する

# はじめに

定期実行されるバッチがSlackチャンネルにその実行結果を通知する処理を行っていたため、
年単位で見ると結構な量のメッセージが溜まっていた。

Slack無料版ではメッセージを過去10000件？までしか表示できないみたいなので、無駄なメッセージは削除したかった。

一番手っ取り早いのはチャンネルを削除→再作成すれば早いが、WEBHookのURLをいろいろな場所で使っていたためチャンネルの削除は避けたかった。

そのため今回はGAS（Google Apps Script）からSlack APIを実行して、特定のチャンネルに存在するメッセージをすべて削除する方法をとった。

# 事前準備
SlackAPIでメッセージを削除するには「トークン」と「チャンネルID」が必要となる。

「チャンネルID」はSlackチャンネル名をクリックすると開くモーダルの一番下に書いてある。
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2347087/bb8866c4-8624-82c6-563f-3df89b90c178.png" width="600">

「トークン」はSlackAPIから発行する必要がある。

[SlackAPI](https://api.slack.com/apps)へアクセスし、「Create new App」をクリック。
「From scratch」を選択し「App Name」を適当に入力。
「Pick a workspace to develop your app in:」には設定するSlackワークスペースを選択する。

Appが作成できたら「Permissions」で権限設定を行う。

![名称未設定.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2347087/54186a91-bf93-c47e-f8ce-b24b1f2420b3.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2347087/f19a561f-4d74-7504-81f9-bb420d77250c.png)
channels:read：チャンネルを取得
channels:history：チャンネル内の削除対象となる投稿を取得
chat:write：投稿を削除
あたりの権限を付与する。

「OAuth Tokens for Your Workspace」の「Install to Workspace」からワークスペースへインストールする。
![名称未設定2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2347087/0b1ef3d1-464f-02c0-1093-03da4e1b3108.png)

完了すると「トークン」が得られる。
![名称未設定3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2347087/72aa046e-e213-5e8e-b3e4-e876c3b200d1.png)


# コード
GASで新規にプロジェクトを作成し下記コードを記載する。

```javascript
function del_slack_posts() {
  var token =
    "xoxp-XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"; // トークン
  var channel_id = "XXXXXXXXX"; // チャンネルID

  // チャンネル内からタイムスタンプの一覧を取得
  var payload = {
    token: token,
    channel: channel_id,
    limit: 1000,
  };

  var options = {
    method: "post",
    payload: payload,
  };

  var url = "https://slack.com/api/conversations.history";

  var response = UrlFetchApp.fetch(url, options);
  var json = response.getContentText();
  var data = JSON.parse(json);
  console.log(data.messages.length);
  // 繰り返し削除
  for (var i = 0; i < data.messages.length; i++) {
    var urldelete = "https://slack.com/api/chat.delete";
    var payload = {
      token: token,
      channel: channel_id,
      ts: data.messages[i]["ts"],
    };

    var options = {
      method: "post",
      payload: payload,
    };
    var response = UrlFetchApp.fetch(urldelete, options);
  }
}

```


# APIの実行制限について

上記を実行するとSlackのメッセージは削除されるが、何件か削除した後エラーとなった。
![名称未設定4.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2347087/311d1274-2349-ebc6-0cb3-d106381e3ae2.png)

これはSlackAPIの実行回数の上限値「Rate Limits」が決まっており、その回数に達したためエラーになった模様。
今回使っている`chat.delete`はTier 3なので1分間に50回が上限になっている。

https://api.slack.com/docs/rate-limits

https://api.slack.com/methods/chat.delete

今回は上限エラーになってもお構い無しで、1分間隔で定期実行することにした:innocent:

定期実行するには「トリガー」のタブから新規トリガー追加すればできる。
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2347087/2dd6dd3d-04a2-42d8-4e84-7db085ba6ead.png" width="600">

# おわりに
上記を仕掛けてまる1日放置したところ、チャンネルのすべてのメッセージが削除された。
ただし、スレッドは削除されないようで、これを削除するには
上記コードの`data.messages[i]["ts"]` の部分を `data.messages[i]["latest_reply"]`にする必要がある模様。
※今回はあえて残した。


<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2347087/dd73cfd5-d654-0aba-754e-efc66fb87c42.png" width="600">