Googleフォームの選択項目（プルダウン）にカレンダーの予定がない時間を自動反映するやり方のプログラムメモ

# プルダウンに予定追加
YouTubeでの解説：https://youtu.be/npqXVS1gq5U

プログラミングやGoogleの仕組みを全く知らない超初心者でも、動画の通りにやれば動くと思います。業務効率化や自動化に取り組もうとしている人にとって、参考になればと思います。

```js:formCreate.gs
// https://docs.google.com/forms/d/**************************************/edit
const FORM_ID  = "**************************************"; // フォームIDを入力
const MAIL_ID  = "**************************************"; // メールアドレスを入力
const FORM     = FormApp.openById(FORM_ID);                // フォーム紐付け
const CALENDAR = CalendarApp.getCalendarById(MAIL_ID);     // カレンダー紐付け
function shareSchedule() {
  const NOW = new Date(); // 現在時刻

  // チームメンバーの出勤予定日から候補を作る
  let startTime = new Date( NOW.getTime() + (      24 * 60 * 60 * 1000 ) ); // 24時間後
  let endTime   = new Date( NOW.getTime() + ( 30 * 24 * 60 * 60 * 1000 ) ); // 1ヶ月後
  const options = {
    search: '出勤予定日'
  }

  // 1ヶ月間のイベントを取得し、出勤予定日を取得
  const workingDays = CALENDAR.getEvents( startTime, endTime, options );
  const aPreferredDateList = [];

  // 候補日リストを作る
  for ( event of workingDays ) {
    const date    = new Date( event.getEndTime().getFullYear(), event.getEndTime().getMonth(), event.getEndTime().getDate() - 1 );
    for ( t = 11; t <= 16; t++ ) { // 11時〜16時　の間で取得
      date.setHours( t );
      const sDate = Utilities.formatDate( date, 'Asia/Tokyo', 'yyyy/MM/dd H:mm' );
      if ( aPreferredDateList.indexOf( sDate ) === -1 )
        aPreferredDateList.push( sDate);
    }
  }

  // 当日の候補は削除
  for ( i = 0; i < aPreferredDateList.length; i++ ) {
    date = new Date( aPreferredDateList[ i ] ).getDate();
    if ( date === NOW.getDate() ) {
      aPreferredDateList.splice( i, 1 );
      i -= 1;
    }
  }

  // 他のスケジュールと重複する場合は候補から削除する
  startTime = new Date( NOW.getTime() + (      24 * 60 * 60 * 1000 ) ); // 24時間後
  endTime   = new Date( NOW.getTime() + ( 30 * 24 * 60 * 60 * 1000 ) ); // 1ヶ月後
  const allEvents = CALENDAR.getEvents( startTime, endTime );
  for ( event of allEvents ) {
    if ( !event.getTitle().match( /出勤予定日/ ) ) {
      startTime = event.getStartTime().getTime() - ( 1 * 60 * 60 * 1000 );
      endTime = event.getEndTime().getTime();
      for ( i = 0; i < aPreferredDateList.length; i++ ) {
        date = new Date( aPreferredDateList[ i ] ).getTime();
        if (( startTime <= date ) && ( date <= endTime ) ) {
          aPreferredDateList.splice( i, 1 );
          i -= 1;
        }
      }
    }
  }

  // プルダウンに選択肢を追加
  const items = FORM.getItems( FormApp.ItemType.LIST );
  for ( item of items ) {
    if ( item.getTitle() === '第一希望' || item.getTitle() === '第二希望' || item.getTitle() === '第三希望' ) {
      const list = item.asListItem();
      list.setChoiceValues( aPreferredDateList );
    }
  }
  console.log(aPreferredDateList);
}
```

# 予定をカレンダーに追加＆メール通知

*2023年9月22日18時更新
*フォームを「第一希望〜第三希望」ではなく、「開催日」に変更してください。あと、アジェンダも追加してください。

解説YouTube： https://youtu.be/j-XN8lGbDG0

```js:updateCalendar.gs
function sendForm(e) {
  // 名前	メールアドレス 開催日	アジェンダ
  const name   = e.namedValues['名前'][0] // 名前
  const email  = e.namedValues['メールアドレス'][0] // メールアドレス
  const date   = e.namedValues['開催日'][0] // 開催日
  const agenda = e.namedValues['アジェンダ'][0] // アジェンダ

  // 予定をGoogleカレンダーに追加
  const title = `${name} 様とのミーティング`; // タイトル
  const start_time = new Date(date); // 予定の開始時間
  const end_time   = new Date(start_time.getTime() + (1000 * 60 * 30)); // 予定の終了時間
  let options = {
    description: `${agenda}\n\nフォームからの自動追加`
  }
  CALENDAR.createEvent(title, start_time, end_time, options);
  
  // 予約追加のメール送信
  const message = `${name} 様より、ミーティング予約\n\n日時：${date}\n内容：${agenda}`;
  // options = {
  //   bcc: MAIL_ID
  // }
  GmailApp.sendEmail(email, title, message);
  
  // フォームの開催日を更新
  shareSchedule();
```