手書きの紙シフト表からGoogleカレンダーに半自動登録する

#はじめに

妻の職場から手書きの紙でシフト表を渡されるのですが、夫婦で共有しているカレンダーアプリに全て手で入れるのは面倒くさい！と思い、ライフハックの一環で自動登録するスクリプトを組んでみました。

#環境情報

今回利用したアプリやプラットフォームは以下のとおりです。
- Google スプレッドシート
- Google カレンダー
- LINE MessangerAPI

#インプット情報
シフト区分がA：9:00〜18:00、Bが10:00〜１９:00、CがXXXのように書いてあって
5/1がA、5/3がB、５/10がC、、、、のような手書きの表です。
（キャプチャ載せるのはまずそうだったので文章説明ごめんなさい。。）

#詳細

（１）手書きの紙シフトからGoogle スプレッドシートに日にちとシフト区分を入力します。
　　（ここだけは手作業、タイトルの半自動はそういう意味です。）
（２）Line Botに「シフト登録して」とお願いすると、Googleカレンダーに（１）で入力した内容が登録されます。

##Google スプレッドシートのフォーマット
こんな感じのシートにアルファベットのシフト区分を入力します。
<img width="999" alt="スクリーンショット 2018-05-13 12.27.45.png" src="https://qiita-image-store.s3.amazonaws.com/0/172460/8850105c-02c3-b08f-ebb2-c35dc0df4dc8.png">

##Line Bot
Line Botはダミアンと名付けました笑
アレクサ（Amazon）とかIBM Watoson（IBM)とか割とAIが絡むアプリケーションには人物名が名付けられるイメージがあるので、我が家もダミアンくんに効率化してもらおうと思っています。（ダミアンはAIは全く絡んでいません）
<img width="1107" alt="スクリーンショット 2018-05-13 12.32.32.png" src="https://qiita-image-store.s3.amazonaws.com/0/172460/74b6b474-fd94-d53d-1163-d74e26e12fd9.png">

#ソースコード
一部自分のアカウントに払い出されたアクセストークンとかURLはぼかしてますが、Google Apps Scriptで書きました。

```javascript:registShift.gs
var monthlyDay = [];
var shiftArray = [];
var startTimeArray = [];
var endTimeArray = [];
var CHANNEL_ACCESS_TOKEN = 'xxx';


// Google Calendar登録
function registShift() {
  var calendar = CalendarApp.getCalendarById('xxx@gmail.com');
  
  // スプレッドシートを読込
  fetchCalendar();
  
  // 登録ずみのシフトを一括削除
  deleteShift(monthlyDay[0],monthlyDay[monthlyDay.length-1]);
  
  for (var i = 0;i < monthlyDay.length;i++) {
    if (shiftArray[i] != '') {
      calendar.createEvent('WORK AS WIFE', new Date(monthlyDay[i] + ' ' + startTimeArray[i]), new Date(monthlyDay[i] + ' ' + endTimeArray[i]), {description:'AUTO APPLY BY DAMIAN@LINE BOT'});
    }
  }
}

// Google Calendar削除
function deleteShift(startTime,endTime){
  var calendar = CalendarApp.getCalendarById('xxx@gmail.com');
  var events = calendar.getEvents(new Date(startTime + ' 00:00:00'), new Date(endTime + ' 23:59:00'));
  for (var i = 0;i < events.length;i++) {
    events[i].deleteEvent();
       }
}

// calendarシートの読込
function fetchCalendar() {
  var spreadsheet = SpreadsheetApp.openByUrl('https://docs.google.com/spreadsheets/xxx');
  var calendarSheet = spreadsheet.getSheetByName('calendar');
  var month = calendarSheet.getRange("A2").getValue();
  var lastRow = calendarSheet.getLastRow();
  for (var i = 1;i < lastRow;i++) {
    var day = calendarSheet.getRange(i+1,2).getValue();
    var shift = calendarSheet.getRange(i+1,4).getValue();
    var startTime = calendarSheet.getRange(i+1,5).getValue();
    var endTime = calendarSheet.getRange(i+1,6).getValue();
    monthlyDay.push(month.substr(0,4)  + '/' + month.substr(5,6) + '/' + day);
    shiftArray.push(shift);
    startTimeArray.push(startTime);
    endTimeArray.push(endTime);
    Logger.log(monthlyDay[i-1] + ':' + shiftArray[i-1] + ':startTime=' + startTimeArray[i-1] + ':endTime=' + endTimeArray[i-1]);
    //return monthlyDay;
       }
}

// LINEからcallされるエンドポイント

function doPost(e) {
  var reply_token= JSON.parse(e.postData.contents).events[0].replyToken;
  if (typeof reply_token === 'undefined') {
    return;
  }
  var user_message = JSON.parse(e.postData.contents).events[0].message.text;
  var resp_message;
  
  if (user_message === 'ダミアン、シフト登録して') {
    registShift();
     resp_message = '登録完了しました！お仕事頑張ってね！';
  } else {
     resp_message = '僕はシフトを自動登録するBot、ダミアンだよ！';
  }

  var url = 'https://api.line.me/v2/bot/message/reply';
  UrlFetchApp.fetch(url, {
    'headers': {
      'Content-Type': 'application/json; charset=UTF-8',
      'Authorization': 'Bearer ' + CHANNEL_ACCESS_TOKEN,
    },
    'method': 'post',
    'payload': JSON.stringify({
      'replyToken': reply_token,
      'messages': [{
        'type': 'text',
        'text': resp_message,
      }],
    }),
  });
  return ContentService.createTextOutput(JSON.stringify({'content': 'post ok'})).setMimeType(ContentService.MimeType.JSON);
}
```

このスクリプトはスプレッドシートから日付とシフトの開始時間、終了時間を読み込んで
GoogleカレンダーにAPI経由で登録しています。

あとはLine Botのダミアンくんから、このスクリプトをフックして実行するという仕組みです。

#まとめ
こんな感じでGWの連休中にサクッと作ったので改善の余地が結構あります。
（改善点①） 
インプットがスプレッドシートなのでどうしてもダサい、かつブラウザからでないと入力しにくい。
どうやらBootStrap Studioという簡単UI作成ツールがあるみたいなのでスマホからでも入力しやすいUIに作り変えたいです。
（改善点②）
改善点という訳ではないですが、ゴミ出しの日をカレンダーに登録するのも、この仕組みで応用できるかと思いました。
なので次回は上記２つの改善をやってみたいと思います。