🐣
Googleカレンダーの2日分の予定をslackに通知する
背景・概要
自分は日々のタスク管理にGoogleカレンダーを活用しているのですが、こちらは今日と明日のGoogleカレンダーの予定をslackで通知させるGASです。
予定の優先度は随時変わりますが、2日分をslackで通知することでざっくり把握できます。
土日祝はSlack通知をスキップさせる設定にしています。
slack通知のサンプル
---
■ 2023/05/08(月)
カレンダー1
- 10:30-11:30 予定が入る
カレンダー2
- 13:30-14:30 予定が入る
- 14:30-15:30 予定が入る
- 16:00-17:45 予定が入る
---
■ 2023/05/09(火)
カレンダー1
- 09:45-15:15 予定が入る
- 12:30-13:30 予定が入る
Googleカレンダーの2日分の予定をslackに通知する
- トリガーを毎日特定の時間に動くように設定してください。土日祝はスキップする設定になっています。
- 金曜日に通知されますが、金曜日が祝日の場合は木曜日に通知されます。
- カレンダーIDとSlackのWebhook URLを定数に設定してください。
- 複数のGoogleカレンダーを設定できます。
function checkWhenToSendNotification() {
const today = new Date();
const dayOfWeek = today.getDay();
if (isBusinessDay(today)) {
if (dayOfWeek === 5) {
sendUpcomingWeekScheduleNotifications(3, 4); // 月曜日と火曜日の予定を通知
} else {
sendUpcomingWeekScheduleNotifications(0, 1); // 今日と明日の予定を通知
}
} else if (dayOfWeek === 4 && !isBusinessDay(new Date(today.getTime() + 24 * 60 * 60 * 1000))) {
sendUpcomingWeekScheduleNotifications(3, 4); // 金曜日が祝日の場合、木曜日に次の月曜日と火曜日の予定を通知
}
}
function sendUpcomingWeekScheduleNotifications(startOffset, endOffset) {
const calendarIds = [
"calendarId1を入れる",
"calendarId2を入れる",
"calendarId3を入れる"
]; // Add more calendar IDs here.
const slackWebhookUrl = "slackWebhookUrlを入れる";
const slackPayload = {
"text": "",
"link_names": 1
};
const today = new Date();
for (let dayOffset = startOffset; dayOffset <= endOffset; dayOffset++) {
const date = new Date(today.getTime() + dayOffset * 24 * 60 * 60 * 1000);
const dateStr = Utilities.formatDate(date, "JST", "yyyy/MM/dd");
const dayOfWeek = ["(日)", "(月)", "(火)", "(水)", "(木)", "(金)", "(土)"][date.getDay()];
let dailySchedules = {};
for (const calendarId of calendarIds) {
const calendar = CalendarApp.getCalendarById(calendarId);
const events = calendar.getEventsForDay(date);
if (events.length > 0) {
for (const event of events) {
const title = event.getTitle();
const start = event.getStartTime();
const end = event.getEndTime();
const startStr = Utilities.formatDate(start, "JST", "HH:mm");
const endStr = Utilities.formatDate(end, "JST", "HH:mm");
const timeStr = `${startStr}-${endStr}`;
if (!dailySchedules[calendarId]) {
dailySchedules[calendarId] = [];
}
dailySchedules[calendarId].push(`${timeStr} ${title}`);
}
}
}
if (Object.keys(dailySchedules).length > 0) {
slackPayload.text += `\n---\n\n*■ ${dateStr}${dayOfWeek}*\n`;
for (const calendarId in dailySchedules) {
const calendarName = CalendarApp.getCalendarById(calendarId).getName();
slackPayload.text += `\n*${calendarName}*\n`;
dailySchedules[calendarId].forEach(schedule => {
slackPayload.text += `- ${schedule}\n`;
});
}
}
}
if (slackPayload.text === "") {
return;
}
const options = {
"method": "post",
"contentType": "application/json",
"payload": JSON.stringify(slackPayload)
};
UrlFetchApp.fetch(slackWebhookUrl, options);
}
function isBusinessDay(date) {
const dayOfWeek = date.getDay();
// 土日は営業日ではない
if (dayOfWeek === 0 || dayOfWeek === 6) {
return false;
}
// 祝日は営業日ではない
const calendar = CalendarApp.getCalendarById("ja.japanese#holiday@group.v.calendar.google.com");
const holidays = calendar.getEventsForDay(date);
if (holidays.length > 0) {
return false;
}
// 営業日の場合はtrueを返す
return true;
}
Discussion