はじめに
勤務する会社ではSlackを利用しています。話題の分報を導入したところ、投稿されるメッセージ数が多くなり、フリープランの「10,000件制限」で過去の投稿が表示できなくなることが多くなりました。
「有効な投稿が流れちゃうので...、もう少し長期間表示されるようにできませんか?」
通知目的で利用しているチャンネル1には、無駄なメッセージが残っているね...。ということで、特定チャンネルに対し、ある程度昔の投稿を、自動的に削除するツールを作ってみることにしました。
方針
やりたいことは、次の通り。
- 一定期間(とりあえず1週間)を過ぎた過去の投稿を定期的に削除する
- 対象のチャンネルは指定したい(複数)
Excelライクでメンテナンスが容易、さらに定期実行するスクリプトも書けるので、Googleスプレッドシートを利用することにしました。
Googleスプレッドシート
まず、対象チャンネルですが、以下のフォーマットで指定することにしました(チャンネル名の頭の#は無しで)。
Google Apps Script
SlackAppをライブラリへ追加する
Slackを外部から制御するので、Slack APIを利用します。このSlack APIをGoogle Apps Scriptから簡単に呼び出すため、SlackAppライブラリ2を利用させていただきました。
基本情報にあるLibrary Keyを、[リソース]-[ライブラリ]内の[ライブラリを追加]へ入力して[追加]することで利用できるようになります。バージョンは22を使用しました。
SlackのLegacy tokenを発行する
SlackAppを利用するのに必要なので、SlackのLegacy tokensのページでトークン(xoxp-xxxxxxxxxx-xxxxx...といった感じのやつ)を発行しておきます。
また、このトークンはスクリプト内で利用するので、[ファイル]-[プロジェクトのプロパティ]内の[スクリプトのプロパティ]へ、SLACK_API_TOKENとして追加しておきました。
スクリプトを実装する
続いてスクリプトです。まず、スプレッドシートに記載されているチャンネル名を取得します。そして、トークンを渡して作成したSlackAppとともに、下位関数を呼び出します。
function cleanChannels()
{
var sheet = SpreadsheetApp.getActiveSheet();
var values = sheet.getDataRange().getValues();
var channelNames = [];
for (var i = 1; i < values.length; ++i) {
channelNames.push(values[i][0]);
}
var token = PropertiesService.getScriptProperties().getProperty('SLACK_API_TOKEN');
var slackApp = SlackApp.create(token);
for each(var channelName in channelNames) {
cleanChannel(slackApp, channelName);
}
}
呼び出された下位関数では、「1週間前の投稿を取得(channelsHistory())→ 削除(chatDelete())」を、投稿が取得されなくなるまで繰り返します。
function cleanChannel(slackApp, channelName)
{
var channelId = getChannelId(slackApp, channelName);
if (channelId.length == 0) {
return;
}
var date = new Date();
date.setDate(date.getDate() - 7); // 1週間前
var timestamp = Math.round(date.getTime() / 1000) + '.000000';
do {
var optParams = {
latest: timestamp,
count: 1
};
var result = slackApp.channelsHistory(channelId, optParams);
if (result.ok) {
for each(var message in result.messages) {
slackApp.chatDelete(channelId, message.ts);
}
}
} while (result.ok && result.has_more)
}
途中、チャンネル名からチャンネルIDを取得していますが、次のように実装しました。
function getChannelId(slackApp, channelName)
{
var channelId = '';
var result = slackApp.channelsList();
if (result.ok) {
for each(var channel in result.channels) {
if (channel.name == channelName) {
channelId = channel.id;
break;
}
}
}
return channelId;
}
プロジェクトのトリガーを設定する
最後に、[編集]-[現在のプロジェクトのトリガー]から、上記のcleanChannels()を適当なタイミングで指定すれば終了です。とりあえず、1日4回実行するように設定しました。
おわりに
なんとなくですが、以前と比べると、過去の投稿に対して「あ、まだ参照できた」と思うことが多くなったように思います。スタンダードプランへ移行するまでの中継ぎとして、多少は活用できそうだな、と思っています。