【初心者】slackで指定日付の投稿をPDFダウンロードするbotをGASで作ってみた
18536 ワード
参考
slackとgasを連携して自動応答するなどは、全て↑の手順通りに行わせていただきました
【Slack BotをGASでいい感じで書くためのライブラリを作った - Qiita】
また、↑こちらのライブラリを使用させていただきました
私はslack、gasの初心者です。間違っていたりもっと良いやり方などありましたら指摘いただけるとありがたいです。
botの動作
- slackで指定の語を(今回は「ポチ:」と)投稿する
- GASの
doPost
関数が実行される
- Google Spreadsheetに、slackの指定日の投稿を書き込む
- Google Spreadsheetのurlに
/export?format=pdf
と加えたリンクをbotが返答する
- slackでリンクをクリックするとPDFをダウンロードできる
doPost
関数が実行される/export?format=pdf
と加えたリンクをbotが返答する
コード
function doPost(e) {
var token = PropertiesService.getScriptProperties().getProperty('SLACK_ACCESS_TOKEN');
var bot_name = "ポチ";
var bot_icon = PropertiesService.getScriptProperties().getProperty('BOT_ICON');
if (PropertiesService.getScriptProperties().getProperty('VERIFY_TOKEN') != e.parameter.token) {
throw new Error("invalid token.");
}
var app = SlackApp.create(token);
var message = getMessage(app, e.parameter, token)
// slackにメッセージを送信
return app.postMessage(
'#' + e.parameter.channel_name,
message,
{
username: bot_name,
icon_url: bot_icon
}
);
}
function getMessage(app, parameter, token) {
var dateMatch = parameter.text.match(/\d{4}\/\d{2}\/\d{2}/)
if (!dateMatch) {
return "読み取れませんでした、「ポチ: XXXX/XX/XX #チャンネル名」の形式で投稿する";
}
var channelIdMatch = parameter.text.match(/#(.+?)\|/);
if (!channelIdMatch) {
return "読み取れませんでした、「ポチ: XXXX/XX/XX #チャンネル名」の形式で投稿する";
}
// slackのユーザー名を取得
var userData = app.usersList().members.reduce(function(obj, cur) {
obj[cur.id] = cur.profile.display_name
return obj
}, {});
// 投稿を取得する時間の範囲をタイムスタンプで取得する
var oldest = new Date(dateMatch[0]).getTime() / 1000
var latest = oldest + (24 * 60 * 60)
// 指定した日のslackの投稿を取得
var url = "https://slack.com/api/channels.history?token="+token+"&channel="+channelIdMatch[1]+"&oldest="+oldest+"&latest="+latest;
var response = UrlFetchApp.fetch(url);
var json = response.getContentText();
var postData = JSON.parse(json)
.messages
.reverse() // 新しい投稿順のようなので、古い順からにするために逆にする
.map(function(item) {
return {
user: userData[item.user],
text: item.text,
date: new Date(item.ts * 1000).toLocaleString(),
};
});
// シート内削除
var Spreadsheet = SpreadsheetApp.getActiveSpreadsheet();
var Sheet = Spreadsheet.getSheetByName('シート1');
Sheet.clear();
// チャンネル名を取得
var tille = parameter.text.match(/\|(.+?)>/)[1] + '_' + dateMatch[0].split('/').join('');
// シートに入力
Sheet.getRange(1, 1).setValue(tille);
postData.forEach(function(item, i) {
Sheet.getRange(i+3+(i*3), 1).setValue(item.date);
Sheet.getRange(i+4+(i*3), 1).setValue(item.user);
// 本文が50文字以上の場合は改行する(※折り返しの設定をしても良さそう)
var chars = [];
item.text.split('\n').forEach(function(splitTxit) {
for (var j = 0; j < splitTxit.length; j += 50) {
chars.push(splitTxit.substring(j, j + 50));
}
})
Sheet.getRange(i+5+(i*3), 1).setValue(chars.join('\n'));
})
// シート名がダウンロードするファイル名になるので、シート名を変更
Spreadsheet.rename(tille)
// PDFダウンロードのリンクを返す
return 'ワンワン!\nご主人様完了しました。\nリンクをクリックしてPDFをダウンロードするんだワン!\n'+'https://docs.google.com/spreadsheets/d/'+Spreadsheet.getId()+'/export?format=pdf&size=A4&fzr=false&portrait=true&fitw=true&gridlines=false';
}
function doPost(e) {
var token = PropertiesService.getScriptProperties().getProperty('SLACK_ACCESS_TOKEN');
var bot_name = "ポチ";
var bot_icon = PropertiesService.getScriptProperties().getProperty('BOT_ICON');
if (PropertiesService.getScriptProperties().getProperty('VERIFY_TOKEN') != e.parameter.token) {
throw new Error("invalid token.");
}
var app = SlackApp.create(token);
var message = getMessage(app, e.parameter, token)
// slackにメッセージを送信
return app.postMessage(
'#' + e.parameter.channel_name,
message,
{
username: bot_name,
icon_url: bot_icon
}
);
}
function getMessage(app, parameter, token) {
var dateMatch = parameter.text.match(/\d{4}\/\d{2}\/\d{2}/)
if (!dateMatch) {
return "読み取れませんでした、「ポチ: XXXX/XX/XX #チャンネル名」の形式で投稿する";
}
var channelIdMatch = parameter.text.match(/#(.+?)\|/);
if (!channelIdMatch) {
return "読み取れませんでした、「ポチ: XXXX/XX/XX #チャンネル名」の形式で投稿する";
}
// slackのユーザー名を取得
var userData = app.usersList().members.reduce(function(obj, cur) {
obj[cur.id] = cur.profile.display_name
return obj
}, {});
// 投稿を取得する時間の範囲をタイムスタンプで取得する
var oldest = new Date(dateMatch[0]).getTime() / 1000
var latest = oldest + (24 * 60 * 60)
// 指定した日のslackの投稿を取得
var url = "https://slack.com/api/channels.history?token="+token+"&channel="+channelIdMatch[1]+"&oldest="+oldest+"&latest="+latest;
var response = UrlFetchApp.fetch(url);
var json = response.getContentText();
var postData = JSON.parse(json)
.messages
.reverse() // 新しい投稿順のようなので、古い順からにするために逆にする
.map(function(item) {
return {
user: userData[item.user],
text: item.text,
date: new Date(item.ts * 1000).toLocaleString(),
};
});
// シート内削除
var Spreadsheet = SpreadsheetApp.getActiveSpreadsheet();
var Sheet = Spreadsheet.getSheetByName('シート1');
Sheet.clear();
// チャンネル名を取得
var tille = parameter.text.match(/\|(.+?)>/)[1] + '_' + dateMatch[0].split('/').join('');
// シートに入力
Sheet.getRange(1, 1).setValue(tille);
postData.forEach(function(item, i) {
Sheet.getRange(i+3+(i*3), 1).setValue(item.date);
Sheet.getRange(i+4+(i*3), 1).setValue(item.user);
// 本文が50文字以上の場合は改行する(※折り返しの設定をしても良さそう)
var chars = [];
item.text.split('\n').forEach(function(splitTxit) {
for (var j = 0; j < splitTxit.length; j += 50) {
chars.push(splitTxit.substring(j, j + 50));
}
})
Sheet.getRange(i+5+(i*3), 1).setValue(chars.join('\n'));
})
// シート名がダウンロードするファイル名になるので、シート名を変更
Spreadsheet.rename(tille)
// PDFダウンロードのリンクを返す
return 'ワンワン!\nご主人様完了しました。\nリンクをクリックしてPDFをダウンロードするんだワン!\n'+'https://docs.google.com/spreadsheets/d/'+Spreadsheet.getId()+'/export?format=pdf&size=A4&fzr=false&portrait=true&fitw=true&gridlines=false';
}
Google SpreadsheetをPDFダウンロードする際のパラメータは以下を参考にさせていただきました。
見ていただいてありがとうございましたm(_ _)m
Author And Source
この問題について(【初心者】slackで指定日付の投稿をPDFダウンロードするbotをGASで作ってみた), 我々は、より多くの情報をここで見つけました https://qiita.com/okumurakengo/items/cbf7644a520b066ad3a3著者帰属:元の著者の情報は、元のURLに含まれています。著作権は原作者に属する。
Content is automatically searched and collected through network algorithms . If there is a violation . Please contact us . We will adjust (correct author information ,or delete content ) as soon as possible .