Форма ответа Таблица - триггер onChange

Я хотел бы спросить о запуске триггера onChange после внесения изменений в электронную таблицу с помощью формы Google.

У меня есть этот исходный код для отправки электронной почты после внесения изменений:

function onChange(e){

    var sheet = SpreadsheetApp.getActiveSheet();

    var helpRange = sheet.getRange(2, 16);
    var debugRange = sheet.getRange(2,17);
    var startRow = helpRange.getValue();
    var numRows = sheet.getLastRow() - startRow + 1;   // Number of rows to process
    debugRange.setValue(numRows);
    var dataRange = sheet.getRange(startRow, 1, numRows, 11);
    var data = dataRange.getValues();
    var cal = CalendarApp.getDefaultCalendar();
    for (i in data) {
      var row = data[i];
      var title = row[3];
      var desc = "Description: " + row[4] + " Requested Accounts: " + row[5] + " Marketing Support: " + row[6] + " Responsible Salesman " + row[8] + " Email: " + row[9] + " " + row[10];      // Second column
      var tstart = row[1];
      var tstop = row[2];
      var loc = row[7];

      cal.createEvent(title, new Date(tstart), new Date(tstop), {description:desc,location:loc});


      helpRange.setValue(sheet.getLastRow() + 1);
      var emailAddress = sheet.getRange(sheet.getLastRow(), 10).getValue(); 
      var subject = "New Event Created: " + title;
      Browser.msgBox(emailAddress + " " + subject + " "+ desc);
      MailApp.sendEmail(emailAddress, subject, desc); 

    }
}

Эта таблица должна автоматически заполняться формой Google (когда пользователь отправляет ответ), и никто другой не должен вносить в нее изменения. Этот триггер onChange срабатывает каждый раз, когда я вносил физические изменения (как и ожидалось, но этого не произошло), но когда я отправляю ответ из формы Google, он также отображается в электронной таблице, но триггер onChange не срабатывает.

Зачем?

Могу ли я написать его так, чтобы триггер сработал после внесения изменений в форму Google?

1 ответ

Есть 4 основных момента, почему это не работает:

  1. Как сказал Райан-Рот, в этом случае следует использовать следующий метод: onFormSubmit().
  2. Этот метод, в частности, должен использоваться в устанавливаемом триггере, поэтому вы должны создать его через панель инструментов сценария приложений или программно с помощью службы ScriptApp, которую я рекомендую, потому что так проще понять, что происходит. Следующий код является примером функции для создания триггера для этого случая:
       function createTriggerFunction(){
  //Get the target spreadsheet
  var ss = SpreadsheetApp.openById('XXXXXXXXXXXX');
  //Create a new trigger using ScriptApp service passing your function as parameter
  ScriptApp.newTrigger("yourMailFunction")
  .forSpreadsheet(ss)
  .onFormSubmit()
  .create()
  
}
  1. Теперь, чтобы установить этот новый триггер, в редакторе скриптов Google App нужно выбрать этот createTriggerFunction()в списке " Выбрать функцию" и "Запустить ее один раз", в противном случае вы создаете один и тот же триггер для каждого ее запуска.

  2. Этот момент важен для того, чтобы это работало: функции перезаписи предназначены для простых триггеров, в которых onChange() и onFormSubmit() нет. Итак, в этом случае ваш код будет работать, используя его в новой функции с именем yourMailFunction ради этого примера.

       function yourMailFunction(e){

    var sheet = SpreadsheetApp.openById('XXXXXXXXXXXX');

    ...

    }
}

ВАЖНЫЙ

Обратите внимание, что я использовал SpreadsheetApp.openById('XXXXXXXXXXXX') вместо SpreadSheetApp.getActiveSheet(). Это очень важно, потому что, когда форма отправляет и вставляет новую строку в связанную электронную таблицу, активной электронной таблицы нет, поэтому вы должны вызывать ее по ее идентификатору.

Как утверждает eddyparkinson, вам определенно нужен триггер отправки формы, а не триггер изменения или редактирования.

Триггер отправки формы можно настроить либо в форме Google, либо в Google Sheet, который получает ответы формы. Триггерное событие в каждом случае немного отличается; событие отправки формы в Google Sheets содержит значения записи формы в простых массивах (e.values, e.namedValues), в то время как событие отправки формы Forms содержит объект FormResponse, который можно запрашивать для получения всей информации о представлении формы.