はじめに
仕事で1週間の作業内容を記録したい!という要望を受け作成しました。
Googleカレンダーに登録されているイベントから以下のような表とグラフが作れます。
プログラミングが全くわからない人でも作業ができるように丁寧に書いているつもりです。
分かる人は適当に改良して使ってください。
JS, GAS共に初心者が作ったものなので粗があるのは勘弁してください
それではどうぞ。
設定方法
-
Googleカレンダーを読み取りたいユーザでログインします。
-
以下のGoogleスプレッドシートにアクセスします。
https://docs.google.com/spreadsheets/ -
「新しいスプレッドシートを作成」から「空白」を選びます。
- 「ツール」 > 「スクリプトエディタ」 を押します。
- 以下のようなエディタが出てくるので中身を消して後ほど出てくるコードをコピペします。
- 三角の実行ボタンを押します。
- プロジェクト(スクリプト)を保存するか聞かれるので「はい」を押します。
- 適当なプロジェクト名をつけて「OK」を押します。
- コードに権限を与えていいか聞かれるので「許可を確認」を押します。
- アカウントを選択します。
- 「このアプリは確認されていません」が出たら「詳細」を押します。
- なんか出るので「作業記録(安全ではないページ)に移動」を押します。(安全です。)
- アカウントへのリクエストを要求してくるので「許可」を押します。
- そしたらエディタに戻るとこんなのが出るのでもう一度6の実行ボタンを押しましょう。
- 3で開いたスプレッドシートに戻ると…
場合によってはアプリの確認とかは出ないかもしれませんがそこは適当にやってください。
作ったもの
詳細はコード内に書いてありますが、集計する期間を設定できたりします。
/*
!!注意!! 1日を超えるイベントが正しく取得できません!!
実行ボタンを押すことでログインしているユーザのカレンダーから
現在の週(日〜土)のイベントの時間を足し上げ新しいシートに出力します。
同じ週で実行すると結果を上書きします。
以下の値を設定することで集計する期間を設定することができます。(形式: YYYY/MM/DD, YYYY/MM/DD HH:mm:ss)
start: 開始日時
end: 終了日時
例: var start = "2019/11/20";
例: var end = "2020/1/2 9:30:00";
*/
var start = "";
var end = "";
function CalendarToSpreadSheet() {
// 所要時間を整形するクラス
var DurationToStr = function(duration) {
this.duration = duration;
this.culc = function() {
var dur_h = Math.floor(this.duration / 60); // 時
var dur_m = this.duration - (dur_h * 60); // 分
// スプレッドシートの表示形式で経過時数01、経過分数01にすると桁がそろって見栄えが良い
var dur_h_str = ('00' + dur_h).slice(-2);
var dur_m_str = ('00' + dur_m).slice(-2);
return dur_h_str + ':' + dur_m_str;
}
}
// カレンダーから取得したイベントを整形して保存しておくクラス
var SimpleEvent = function(title, duration) {
this.title = title;
this.duration = duration;
this.getDurationStr = function() {
return new DurationToStr(this.duration).culc();
};
};
// ログインしているユーザのカレンダーを取得
var calendar = CalendarApp.getCalendarById(Session.getActiveUser().getEmail());
// 現在の週を取得
var today = new Date();
var thisYear = today.getFullYear();
var thisMonth = today.getMonth();
var thisDate = today.getDate();
var thisDay = today.getDay();
var thisSunday = thisDate - thisDay;
var nextSunday = thisSunday + 7;
// 日曜日の年月日
if (start === "") {
var startDate = new Date(thisYear, thisMonth, thisSunday);
} else {
var startDate = new Date(start);
}
// 次の日曜日の年月日
if (end === "") {
var endDate = new Date(thisYear, thisMonth, nextSunday);
} else {
var endDate = new Date(end);
endDate.setDate(endDate.getDate() + 1);
}
// シート名を作成
var startDateStr = startDate.getFullYear() + "/" + (startDate.getMonth() + 1) + "/" + startDate.getDate();
var endDateStr = endDate.getFullYear() + "/" + (endDate.getMonth() + 1) + "/" + (endDate.getDate() - 1);
var week = startDateStr + " - " + endDateStr;
// アクティブなスプレッドシートを取得
var spreadSheet = SpreadsheetApp.getActiveSpreadsheet();
// 今週のシートが既にあれば消す
var oldSheet = spreadSheet.getSheetByName(week);
if (oldSheet) {
spreadSheet.deleteSheet(oldSheet);
}
// 新しいシートを作成
spreadSheet.insertSheet(week);
// シートを取得
var sheet = SpreadsheetApp.getActiveSheet();
// イベントを取得
var events = calendar.getEvents(startDate, endDate);
// 読み出したイベントを登録しておく配列
var readEvent = [];
// イベントの読み出し
for (var i = 0; i < events.length; i++) {
var title = events[i].getTitle(); // 予定のタイトル
var startTime = events[i].getStartTime(); // 開始時刻
var endTime = events[i].getEndTime(); // 終了時刻
// 所要時間の計算
var duration = (endTime - startTime) / (1000 * 60);
// SimpleEvent クラスを生成
var simpleEvent = new SimpleEvent(title, duration);
// 配列に追加済みか判定するフラグ
var added = false;
// 所要時間を足し上げ
for (var j = 0; j < readEvent.length; j++) {
if (title == readEvent[j].title) {
readEvent[j].duration = readEvent[j].duration + duration;
added = true;
break;
}
}
if (!added) {
readEvent.push(simpleEvent);
}
}
// 各行のタイトルを指定
sheet.getRange('A'+(1)).setValue('予定名');
sheet.getRange('B'+(1)).setValue('所要時間');
// シートに出力
for (var i = 0; i < readEvent.length; i++) {
sheet.getRange('A'+(i+2)).setValue(readEvent[i].title);
sheet.getRange('B'+(i+2)).setValue(readEvent[i].getDurationStr());
}
// 合計を出力
var sumDuration = 0;
for (var i = 0; i < readEvent.length; i++) {
sumDuration = sumDuration + readEvent[i].duration;
}
sheet.getRange('A'+(readEvent.length+2)).setValue("合計");
sheet.getRange('B'+(readEvent.length+2)).setValue(new DurationToStr(sumDuration).culc());
// 円グラフを作成
var range=sheet.getRange("A1:B" + String(readEvent.length+1));
var chart=sheet.newChart()
.addRange(range)
.setChartType(Charts.ChartType.PIE)
.setOption("pieSliceText", "value")
.setPosition(1,4,0,0)
.build()
sheet.insertChart(chart);
}
参考
https://tonari-it.com/gas-calendar-spreadsheet/
https://yokonoji.work/google-apps-script-650
https://kiyotatsu.com/gas-script_get-calender/