简体   繁体   English

服务器端 function 不想运行

[英]Server-side function does not want to run

I'm building a sidebar for Google Sheets using Apps Script, it is a tool to import data from Google Calendar.我正在使用 Apps Script 为 Google Sheets 构建一个侧边栏,它是一个从 Google Calendar 导入数据的工具。 The script is not that complicated:脚本并不复杂:

  • A form to choose the calendar, a start and end date, and a checkbox to include a header用于选择日历、开始和结束日期以及包含 header 的复选框的表单
  • Some client-side javascript一些客户端 javascript
  • Some server-side functions一些服务器端功能

1. I have a file Code.gs in charge of creating a custom menu and rendering the sidebar 1. 我有一个文件 Code.gs 负责创建自定义菜单和渲染侧边栏

function onOpen() {
  SpreadsheetApp.getUi() // Or DocumentApp or SlidesApp or FormApp.
      .createMenu('Custom Menu')
      .addItem('Show sidebar', 'showSidebar')
      .addToUi();
}

function showSidebar() {
  var html = HtmlService.createTemplateFromFile('index').evaluate()
      .setTitle('Extract data from calendar')
      .setWidth(300);
  SpreadsheetApp.getUi() // Or DocumentApp or SlidesApp or FormApp.
      .showSidebar(html);
}

function include(filename){
  return HtmlService.createHtmlOutputFromFile(filename).getContent();
}

2. Index.html: the content of the sidebar 2.Index.html:侧边栏的内容

<!DOCTYPE html>
<html>
<head>
</head>
<body style="margin: 10px;">
<!-- Compiled and minified CSS -->
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/materialize/1.0.0/css/materialize.min.css">

<!-- Compiled and minified -->
<script src="https://cdnjs.cloudflare.com/ajax/libs/materialize/1.0.0/js/materialize.min.js"></script>
            
  <div class="row">
    <form class="col s12">
<!--    CHOOSE CALENDAR ROW    -->   
    <div class="row">
      <div class="input-field col s12">
       <select id='calendar'>
       <? var calendars = CalendarApp.getAllOwnedCalendars();
          calendars.forEach((calendar) => { ?>
         <option value="<?= calendar.getId() ?>"><?= calendar.getName() ?></option>
         
         <? }) ?>
       </select>
       <label>Calendar</label>
       </div>
    </div>

<!--    START TIME ROW    -->
      <div class="row">
        <div class="input-field col s12">
          <input placeholder="Start date" id="startDate" type="date" class="validate">
          <label for="startDate">Start date</label>
        </div>
      </div>
      
<!--    END TIME ROW    -->
      <div class="row">
        <div class="input-field col s12">
          <input placeholder="End date" id="endDate" type="date" class="validate">
          <label for="endDate">End Date</label>
        </div>
      </div>
      
<!--    INCLUDE HEADER    -->
      <div class="row">
         <label>
           <input type="checkbox" class="filled-in" checked="checked" id="includeHeader" />
           <span>Include Header</span>
         </label>
      </div>
      
<!--    EXTRACT BUTTON    -->
      <div class="row">
        <button class="btn waves-effect waves-light" id="extractBtn">EXTRACT</button>
      </div>
    </form>
  </div>
  <?!= include('index-js') ?>
  <script>
      document.addEventListener('DOMContentLoaded', function() {
    var elems = document.querySelectorAll('select');
    var instances = M.FormSelect.init(elems, {});
  });
  </script>
</body>
</html>

3. index-js.html: add an event to the extract button and call the server-side function 3. index-js.html:给解压按钮添加事件,调用服务端function

<script>
var extractBtn = document.getElementById('extractBtn'); 

extractBtn.addEventListener('click', function(e) {
    e.preventDefault();
    
    var calendarId = document.getElementById('calendar').value;
    var startDate = new Date(document.getElementById('startDate').value);
    var endDate = new Date(document.getElementById('endDate').value);
    var includeHeader = document.getElementById('includeHeader').checked;
   
    if(startDate.getTime() < endDate.getTime()) {
      e.target.textContent = 'Extracting...';
      google.script.run.withSuccessHandler(extractCompleted).writeData(calendarId, startDate, endDate, includeHeader);
    } else {
      M.toast({html: "Please enter an end date starting after the selected start date"});
    }
});

function extractCompleted(){
    M.toast({html: 'Extract completed'});
    extractBtn.textContent = 'Extract';
}

</script>

4. extractCalendar.gs in charge of getting the data and adding it to the Google sheet 4. extractCalendar.gs 负责获取数据并将其添加到 Google sheet

function extractCalendar(calendarId, startDate, endDate) {
  var calendar = CalendarApp.getCalendarById(calendarId);
  var events = calendar.getEvents(startDate, endDate);
  
  
//  Initialize variables that will hold information
  var rows = [];
  
  events.forEach((event) => {
                 // Get basic information
                 var eventTitle = event.getTitle();
                 var startTime = event.getStartTime();
                 var endTime = event.getEndTime(); 
                 var description = event.getDescription();
                 var isRecurring = event.isRecurringEvent();
  
  
   // Get the guest list
   var guests = event.getGuestList();
   var emailsParticipantsArray = [];
   var emailsParticipants = '';
  
   // Add each guest email to the array
   guests.forEach(guest => emailsParticipantsArray.push(guest.getEmail()));
   
  // Convert the array to a string
  emailsParticipants = emailsParticipantsArray.join(',');
   
  
   rows.push([eventTitle, startTime, endTime, emailsParticipants, description, isRecurring]);
  
 }
  );

   return rows;

 }
 
 function writeData(calendarId, startDate, endDate, includeHeader=True){
  var ss = SpreadsheetApp.getActiveSpreadsheet();
  var sheet = ss.getActiveSheet();
  var rows = extractCalendar(calendarId, startDate, endDate);

  var numRows = rows.length;
  var lastRow = sheet.getLastRow();
  
  (includeHeader) && rows.unshift(['Title', 'Start Date', 'End Date', 'Participants Email', 'Description', 'Recurring']);
  sheet.getRange(lastRow + 1, 1, numRows, 6).setValues(rows);

 }

The line below does not run and generate the error message: Uncaught TypeError: Failed due to illegal value in property: 12769757186-mae_html_user_bin_i18n_mae_html_user.js:61下面的行不运行并生成错误消息:未捕获的类型错误:由于属性中的非法值而失败:12769757186-mae_html_user_bin_i18n_mae_html_user.js:61

google.script.run.withSuccessHandler(extractCompleted).writeData(calendarId, startDate, endDate, includeHeader);

What's happening right here, why is the server-side function not running?这里发生了什么,为什么服务器端 function 没有运行?

Thank you for your help !谢谢您的帮助 !

Parameters and Return Values 参数和返回值

You can pass year,month and day or the date in a standard string format and use the Date() constructor to recreate the date.您可以传递标准字符串格式的年、月和日或日期,并使用 Date() 构造函数重新创建日期。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM