Google Sheets 可安装 onEdit() 触发器无权添加日历事件

2023-12-26

我正在编写附加到 Google 电子表格的脚本,该脚本可以帮助我为员工生成轮班时间表、创建 Google 日历并在人们换班时更新日历。我在电子表格上附加了一个 onEdit() 可安装触发器,用于检查用户是否更改了特定范围内的单元格(以交换班次),然后在电子表格中的日历上查找单元格,交换它们,然后调用并更新GoogleCalendar。

从脚本编辑器执行时它可以完美运行。但是当从电子表格上的触发器执行时,我收到此错误:

“执行失败:您无权调用 getOwnedCalendarsByName(第 204 行,文件“代码”)[总运行时间 1.021 秒]”

在谷歌应用程序权限中,它对脚本这样说:“谷歌日历 管理您的日历”,因此应该获得授权。

这是可安装触发器 OnEdit 调用的函数

function onEdit(e) {
  var sheets = SpreadsheetApp.getActive();
  var dutySwitchSheet = sheets.getSheetByName('Duty Switches');

  if(!e){
    var e = {};
    e.range = dutySwitchSheet.getRange(30, 9);
  }
  Logger.log(e.range.getValue());

  var changedRow = e.range.getRow();
  var changedCol = e.range.getColumn();
  var RAInitials = sheets.getRangeByName("dutySwitchRAInitials");
  var rangeTop = RAInitials.getRow();
  var rangeBottom = RAInitials.getLastRow();
  var rangeLeft = RAInitials.getColumn();
  var rangeRight = RAInitials.getLastColumn();
  Logger.log("changedRow: %s, changedCol: %s, rangeTop: %s, rangeBottom: %s, rangeLeft: %s, rangeRight: %s", changedRow, changedCol, rangeTop, rangeBottom, rangeLeft, rangeRight);
  if( changedRow >= rangeTop && changedRow <= rangeBottom && changedCol >= rangeLeft && changedCol <= rangeRight && e.range.getSheet().getName().toUpperCase() === dutySwitchSheet.getName().toUpperCase()){
    Logger.log("event sheet name: %s, Duty Switch Sheet Name: %S", e.range.getSheet().getName().toUpperCase(), dutySwitchSheet.getName().toUpperCase());
    var relRow = changedRow - rangeTop + 1;
    Logger.log("Checking if both initials are present");
    if(RAInitials.getCell(relRow, 1).getValue() && RAInitials.getCell(relRow,2).getValue()){
      var ui = SpreadsheetApp.getUi()
      ui.showModalDialog(HtmlService.createHtmlOutput(""), "Checking Your input, please wait..");
      Logger.log("updating");
      var RA1Range = sheets.getRangeByName("dutySwitchRA1");
      var RA2Range = sheets.getRangeByName("dutySwitchRA2");
      var calendarRange = sheets.getRangeByName("dutyDays");
      var startDate = new Date(sheets.getRangeByName("startDate").getValue());
      var startDay = startDate.getDay();

      var RA1 = {name: RA1Range.getCell(relRow, 1).getValue(), shiftNum: RA1Range.getCell(relRow, 2).getValue(), date: new Date(RA1Range.getCell(relRow, 3).getValue()) };
      if(RA1.shiftNum != "N/A"){
        RA1.day = Math.floor( (RA1.date.getTime() - startDate.getTime())/(24*60*60*1000) ) + startDay;
        RA1.SwappedCell = calendarRange.getCell( Math.floor(RA1.day / 7) * 3 + Number(RA1.shiftNum) + 1, (RA1.day % 7) + 1 );
        RA1.cellValue = String(RA1.SwappedCell.getValue());
      }

      var RA2 = {name: RA2Range.getCell(relRow, 1).getValue(), shiftNum: RA2Range.getCell(relRow, 2).getValue(), date: new Date(RA2Range.getCell(relRow, 3).getValue()) };
      if(RA2.shiftNum != "N/A"){
        RA2.day = Math.floor( (RA2.date.getTime() - startDate.getTime())/(24*60*60*1000) ) + startDay;
        RA2.SwappedCell = calendarRange.getCell( Math.floor(RA2.day / 7) * 3 + Number(RA2.shiftNum) + 1, (RA2.day % 7) + 1 );
        RA2.cellValue = String(RA2.SwappedCell.getValue());
      }
      Logger.log("RA1 name: %s, date: %s, cellValue: %s; RA2 name: %s, date: %s, cellValue: %s" , RA1.name, RA1.date, RA1.cellValue, RA2.name, RA2.date, RA2.cellValue);
      Logger.log("RA1 name matches: %s, RA2 name matches: %s", RA1.cellValue.indexOf(RA1.name) != -1, RA2.cellValue.indexOf(RA2.name) != -1);
      if(RA1.cellValue.indexOf(RA1.name) != -1 || RA1.shiftNum == "N/A" && RA2.cellValue.indexOf(RA2.name) != -1 || RA2.shiftNum == "N/A" ){
        Logger.log("Swapping Cells");
        if(RA1.shiftNum != "N/A"){
          RA1.SwappedCell.setValue( String(RA1.SwappedCell.getValue()).replace(RA1.name, RA2.name) );
        }
        if(RA2.shiftNum != "N/A"){
          RA2.SwappedCell.setValue( String(RA2.SwappedCell.getValue()).replace(RA2.name, RA1.name) );
        }
        Logger.log("Syncing Google Calendar");
        syncGoogleCalendar();
        ui.showModalDialog(HtmlService.createHtmlOutput(""), "The Google Calendar has been updated! :)");
        Logger.log("Done Updating!");
      } 
      else {
        Logger.log("Did Not Swap Cells");
        ui.showModalDialog(HtmlService.createHtmlOutput(""), "The info input does not match the spreadsheet.  Couldn't update :(");
      }
    }
  }
}

这是更新 Google Calendar() 函数,直到抛出错误

function syncGoogleCalendar(){

  var dutyCalendars = CalendarApp.getOwnedCalendarsByName("RA Duty Calendar");

简短回答

更改onEdit函数的名称

解释

不要使用保留函数的名称来命名可安装触发器调用的函数。

onEdit是 Google Apps 脚本保留函数,用于告诉 Google Apps 脚本引擎在编辑事件发生时应运行该函数。它无法调用需要授权才能运行的服务。看简单的触发器 https://developers.google.com/apps-script/guides/triggers/了解更多详情。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Google Sheets 可安装 onEdit() 触发器无权添加日历事件 的相关文章

  • 为什么我们使用 SpreadsheetApp.flush()?

    我的理解是 flush https developers google com apps script reference spreadsheet spreadsheet app flush有助于在功能发生时执行这些功能 而无需将它们捆绑在
  • 从 Google Apps 脚本运行保存的 bigquery 查询?

    我们经常使用 Google Apps 脚本来运行 BigQuery 查询并将其放入 Google Sheet 中 然而 工作流程很烦人 在 BigQuery 中运行查询 直到正确为止 复制 粘贴到文本编辑器以放入换行斜杠 在应用程序脚本中运
  • 我们可以使用 Google Spreadsheet 作为后端数据库吗

    我正在尝试开发一个应用程序 在其中从与某些事务相关的多个客户端获取数据 现在我想使用 Google Spreadsheet 进行一些分析 有什么方法可以使用 ASP Net MVC 使用 C 实现此目的 Google 提供 OAuth 当我
  • 如何在谷歌电子表格中获取台湾证券交易所指数

    如何在谷歌电子表格中获取台湾证券交易所指数 该索引确实存在于谷歌金融中https www google com finance q TPE 3ATAIEX https www google com finance q TPE 3ATAIEX
  • 使用 JavaScript 以编程方式编辑 Google 文档

    我想做的是运行一些 JavaScript 代码 将文本输入到 Google 文档中 到目前为止 我所做的是在我的个人网页上创建一个嵌入 Google 文档的 iframe 元素 目前我想做的是使用 Google 源代码中的函数来输入文本 当
  • 您可以在不是在 Google 协作平台下创建的网站上使用 Google 脚本吗? [复制]

    这个问题在这里已经有答案了 Google 脚本有一种方法可以嵌入到 Google 网站中 但我想知道是否可以在非 Google 托管的网站上使用 Google 脚本 此 google 脚本的目的是作为 Javascript 的简单替代方案
  • 在 Google Apps 脚本中,如何为我实现的服务设置 HTTP 响应代码?

    假设我有一个返回 XML 文档的 服务 function doGet var result
  • 谷歌脚本循环性能

    我是 google 脚本的新手 我不确定为什么与 Excel VBA 的简单循环相比 我的性能如此差 我附上了下面的代码 它是一个大约 1200 行的循环 每秒删除大约 2 3 行 我写的脚本效率很低吗 我还不熟悉 Javascript 但
  • 如何隐藏工作表?

    如何使用 googleScript 隐藏电子表格应用程序中的一些工作表 我有一个包含多个工作表的电子表格 我想使用 googlScript 将电子表格缩小为仅第一个可见工作表和所有其他隐藏工作表 sheet hideSheet https
  • window.location.href = window.location.href 返回空白页

    我正在使用 Google App Script 创建一个网页 单击按钮后 我尝试重新加载页面 但以下操作均无效 窗口 位置 href 窗口 位置 href window location reload true 他们正在重定向到空白页面 下
  • 重命名带有“完整工作表”图表的工作表会导致电子表格重新加载

    Google 表格允许将图表移动到自己的表格中 不过 谷歌脚本似乎无法重命名这些工作表 而不会使电子表格崩溃并强制其重新加载 要明白我的意思 请尝试以下操作 1 创建新的电子表格并在其中放入一些数据 2 使用数据创建任何类型的图表 3 编辑
  • 向文档添加动态页眉/页脚

    我想知道是否有一种方法可以向文档添加动态页眉或页脚 即在页脚中添加每个页面都不同的 页面标题 据我所知 编辑内置页眉或页脚将反映在每个页面上 我想知道是否有人想到了一种解决方法 通过访问页面上的第一行 最后一行并在那里插入文本来 强制 它
  • Google 脚本:如何编写从驱动器中的 txt 自动导入电子表格的脚本?

    我以前从未使用过 Javascript 而且多年来我一直在尝试这样做 但没有成功 而且我找不到任何以前的人尝试过 我想直接从驱动器中的 txt 文档复制文本数据 可以手动完成此操作 但我希望每天自动完成 文本文件 Boxes Made 3
  • 联系人应用程序性能

    对谷歌脚本的 ContactsApp 进行一些测试并加载联系人 看起来运行 ContactsApp getContacts 加载所有联系人 所需的时间与运行 ContactsApp getContact email 特定联系人 所需的时间一
  • XPath 将元素中的所有文本作为一个值获取,删除换行符

    我试图获取以下一组节点中的所有文本并作为一个值返回 而不是多个节点 p I love eating out br br This is my favorite restaurant br I will definitely be back
  • 有没有办法将 Google 文档分割成多个 PDF?

    我想在 Google Scripts VBA 代码中复制我为 Word 文档编写的代码 基本上 它通过搜索我插入文档中的标签 将文档 切片 为多个 PDF 文件 目的是允许合唱团使用 forScore 管理乐谱的应用程序 在切片点插入先前注
  • 移动设备:缺少操作

    我正在尝试执行该操作的 POST 但是 当我发出请求时 我收到代码 400 表示操作值丢失 my code function mobileAPIPOST var response UrlFetchApp fetch https www go
  • 将 html 嵌入 google 工作表

    我想通过创建一个 html 元素并将其放在电子表格顶部来在电子表格顶部显示 HTML 例如 如果我通过合并 A1 G5 在工作表顶部创建了一个大单元格 是否可以在其中嵌入 html div h1 Hello World h1 div 我注意
  • 测量填写部分的时间 - 谷歌表单

    我正在尝试使用谷歌表单进行研究调查问卷 对于某些部分 我想自动测量用户填写所需的时间 谷歌表单中没有这样的选项 我尝试复制表单源 并用 javascript 填充时间 但它不起作用 跨源问题 未能成功托管复制的表单 如何做到 我如何衡量回答
  • 根据日期自动对数据进行排序

    我正在尝试使我的电子表格根据日期自动对数据进行排序 我附上了我正在使用的电子表格的照片 您会注意到 G 列中有一个工作日公式 目前 一旦我更新了配药日期 重新订购日期就会根据公式进行更新 基于安排的工作日 然后我对 G 列使用 SORT R

随机推荐

  • 有哪些模式可以用于原型继承而不能用于类?

    大家似乎都普遍认为原型继承比类继承更简单 更灵活 在我读过的文献中 我没有看到很多可以用原型继承来做而经典继承却做不到的事情的例子 所以我提出一个简单的问题 有哪些模式可以用于原型继承 而不能用于类继承 以及何时 如果使用它 您会给出什么指
  • 使横幅广告具有响应性

    朋友们 我正在努力向我的网站添加横幅广告 我添加的用于显示横幅的 html 已打开https jsfiddle net 1r1kydjz 2 https jsfiddle net 1r1kydjz 2 div height 90 width
  • python 存储在自变量中与传递给 def

    我应该如何在类的方法之间传递变量 像这样 作为一个论点 class Yadayada def foo self for i in somelist pass var i blah blah blah output self bar pass
  • 无法在 Fedora 机器上从源代码构建 pdftk

    我正在尝试在 fedora 机器上从源代码构建 pdftk 我已经解压 pdftk jar 并尝试执行 make f Makefile Redhat 但我的控制台上出现以下错误 gcjh 4 7 2 force classpath usr
  • 如何使用 Firefox 插件读取特定 URL 的 html 内容?

    我想创建一个插件 它将加载特定网址的 html 内容并保存该页面的特定行 然后移动到该网址 我在 Mozila org 上阅读了很多有关网页内容的内容 但我不明白如何阅读 html 内容 这是一个执行 XHR 请求的简单代码片段 没有 co
  • 使用 java 配置在单个应用程序中使用多种身份验证机制

    目前 我的应用程序中有一个身份验证机制 即使用 LDAP 进行身份验证和授权 我的安全配置如下 Configuration EnableWebMvcSecurity public class SecurityConfig extends W
  • Mac RStudio [版本 1.4.1106] 调试器仍然无法工作并显示“调试位置是近似的,因为源不可用”

    问题是 在 RStudio 中 当我设置断点来调试代码时 调试器无法正确单步执行我的函数 相反 它带我到一些未知的地方 并给出警告消息 调试位置是近似的 因为源不可用 我过去可以看到类似的堆栈溢出问题Rstudio问题 https stac
  • 跟踪未命名的对象

    我想使用 libgdx 制作一个自上而下的 2D 射击游戏 会有很多子弹对象 我想在它们离开屏幕时对其进行跟踪和处理 我想我会用类似的东西 static ArrayList
  • 我如何确定 DOM 元素的 XPath?

    在 JavaScript 中 假设我有一个元素的引用 如何检索选择它的 XPath 表达式 有没有类似的东西objElement xpath 由于 Annibigi 不想发布解决方案 所以我会这样做 参见这个片段 http snippets
  • PyQt5:在 QTabBar 中看不到关闭按钮

    使用 PyQt5 时 我看不到各个选项卡上的关闭按钮 当我单击我知道关闭按钮应该在的位置时 我可以关闭各个选项卡 但无法完全看到该按钮 bin python3 import sys from PyQt5 QtWidgets import Q
  • 使用 Scipy 与 ROOT 等进行拟合(高斯)

    我现在多次偶然发现 python 中的拟合scipy curve fit某种程度上比其他工具 例如 根 https root cern ch https root cern ch For example when fitting a gau
  • 尽管符号存在于链接库中,但符号查找错误

    我的可执行文件链接到多个库 见下文 但在运行时崩溃并出现以下错误 symbol lookup error bin gcc TestHarmonic undefined symbol ZN3fmm8harmonic7details6helpe
  • JVM 垃圾收集应用程序停止时间差异

    我正在使用以下 java 版本运行一个大型 tomcat 实例 java版本 1 6 0 20 OpenJDK运行环境 IcedTea6 1 9 7 6b20 1 9 7 0ubuntu1 10 04 1OpenJDK 64 位服务器 VM
  • 如何告诉 rspec 在没有挂起的测试输出的情况下运行?

    有没有办法 也许是一些关键 告诉 rspec 跳过待处理的测试并且不打印有关它们的信息 我有一些自动生成的测试 例如 pending add some examples to or delete FILE 我运行 bundle exec r
  • C 中的半继承:此代码片段如何工作?

    在 C 中破解有限形式的多态性的一种方法是执行以下操作 typedef struct int x base typedef struct base super int y derived 现在 您可以将派生实例引用为基本实例 具体取决于变量
  • Oracle关于集合和顺序的表表达式

    我正在分析一些现有的 PL SQL 代码 我可以看到 Oracle 集合在使用表表达式的查询中未嵌套的情况 没有 order 子句 并且代码显然假设项目将按存储在集合中的顺序返回 我知道如果没有 order by 则不能假设 select
  • 以编程方式访问 Google Chrome 主页或起始页

    Chrome 在哪里保存主页或起始页 URL 我想使用 C 以编程方式访问它 默认位置是 视窗XP 谷歌浏览器 C Documents and Settings
  • 如何在 ASP.NET MVC3 控制器中返回部分视图?

    我有一个控制器 其方法之一 操作 访问我的项目数据库 该方法检查项目类型 仅当从数据库检索的项目属于特定类型时 如何显示我的部分视图 控制器动作示例 public ActionResult CheckItem Koko model var
  • jquery 中是否有原型序列化()的等效项

    我正在尝试将表单的数据传递给jquery ajax请求 我找到了制作原型的简单方法 formid serialize 这将需要一个字符串 其中包含该表单中的所有元素名称及其值 以方便的方式为 ajax 请求做好准备 这很容易 那么jquer
  • Google Sheets 可安装 onEdit() 触发器无权添加日历事件

    我正在编写附加到 Google 电子表格的脚本 该脚本可以帮助我为员工生成轮班时间表 创建 Google 日历并在人们换班时更新日历 我在电子表格上附加了一个 onEdit 可安装触发器 用于检查用户是否更改了特定范围内的单元格 以交换班次