编辑器插件的触发器

Apps 脚本触发器会导致每当指定事件 发生时,执行指定的脚本 函数(即触发器函数)。只有某些事件才能导致触发器触发,并且每个 Google Workspace 应用都支持一组不同的事件。

触发器触发时,系统会创建一个事件对象。 此 JSON 结构包含有关所发生事件的详细信息。事件对象结构中的信息会根据触发器类型的不同而以不同的方式进行组织。

创建事件对象后,Apps 脚本会将其作为参数传递给触发器函数。触发器函数是一个回调函数,您必须自行实现该函数,以采取适当的操作来响应事件。例如,在编辑器插件中,当文档打开时,系统会使用触发器来创建插件菜单项。在这种情况下,您可以在 onOpen(e) 触发器函数中实现,以创建插件所需的菜单项,并可能使用事件对象中的数据。

本页面提供了有关在编辑器插件项目中使用触发器的指南。

编辑器插件触发器类型

您可以在编辑器插件中使用 Google Apps 脚本 项目提供的大部分通用触发器类型,包括 简单触发器和大多数 可安装的触发器。可用的确切触发器类型取决于要扩展的应用。

与编辑器插件不同,Google Workspace 插件无法使用通用的 Apps 脚本简单触发器或可安装的触发器。相反,它们使用专门为 Google Workspace 插件设计的触发器。如需了解更 多信息,请参阅 Google Workspace 插件触发器

下表显示了编辑器插件可以使用的简单触发器和可安装的触发器类型,并提供了指向相应事件对象的链接:

事件 事件对象 简单触发器 可安装的触发器
打开
编辑器文件已打开。
文档 onOpen 事件对象
表单 onOpen 事件对象
表格 onOpen 事件对象
幻灯片 onOpen 事件对象
文档
表单*
表格
幻灯片

function onOpen(e)

文档
表单
表格
安装
插件已安装。
onInstall 事件对象 文档
表单
表格
幻灯片

function onInstall(e)

修改
电子表格单元格内容已更改。
表格 onEdit 事件对象 表格

function onEdit(e)

表格
更改
工作表中的内容已修改或格式化。
表格 onChange 事件对象 表格
表单提交
Google 表单已提交。
表单 form-submit 事件对象
表格 form-submit 事件对象
表单
表格
时间驱动型(时钟)
触发器在指定时间或间隔触发。
时间驱动型事件对象 文档
表单
表格
幻灯片

当用户打开表单进行回复时,不会发生 Google 表单的打开事件,而当编辑者打开表单进行修改时,才会发生该事件。

插件中的简单触发器

简单触发器使用一组预留的 函数名称,无法使用需要授权的服务,并且会 自动启用以供使用。在某些情况下,简单触发器事件可以由 可安装的触发器来处理。

您可以通过实现具有以下预留名称之一的函数,向插件添加简单触发器:

  • 当用户打开文档、电子表格或演示文稿时,onOpen 会执行。当表单在编辑器中打开时(但不是在回复表单时),onOpen 也会执行。它仅在用户 有权修改相关文件时执行,并且最常用于创建 菜单项
  • 当用户安装插件时,onInstall 会执行。通常,onInstall 仅用于调用 onOpen;这可确保插件菜单在安装后立即显示,而无需用户刷新页面。
  • 当用户更改电子表格中的单元格值时,onEdit 会执行。此触发器不会响应单元格移动、格式设置或其他不会更改单元格值的更改而触发。

限制

插件中的简单触发器受适用于其他类型 Apps 脚本项目的简单触发器的相同 限制。设计插件时,请特别注意以下限制:

  • 如果文件以只读(查看或评论)模式打开,简单触发器不会运行。此行为会阻止填充插件菜单。
  • 在某些情况下,编辑器插件会在无授权模式下运行其 onOpenonEdit 简单触发器。如 插件授权模型中所述,此 模式会带来一些复杂性。
  • 简单触发器无法使用服务或执行其他需要授权的操作,除非插件授权模型中另有规定
  • 简单触发器的运行时间不能超过 30 秒。尽量减少在简单触发器函数中完成的处理量。
  • 简单触发器受 Apps 脚本触发器 配额限制

插件中的可安装触发器

插件可以使用 Apps 脚本 Script 服务以编程方式创建和修改可安装的触发器 。无法手动创建 插件可安装的触发器。与简单触发器不同,可安装的触发器可以使用需要授权的服务。

插件中的可安装触发器在遇到错误时不会向用户发送 错误电子邮件,因为在大多数情况下,用户无法 解决问题。因此,您应尽可能将插件设计为代表用户妥善处理错误。

插件可以使用以下可安装的触发器:

  • 当用户打开文档、电子表格或在编辑器中打开表单时(但不是在回复表单时),打开 可安装的触发器会执行。
  • 当用户更改电子表格中的单元格值时,修改 可安装的触发器会执行。此触发器不会响应格式设置或其他不会更改单元格值的更改而触发。
  • 当用户在电子表格中进行任何更改时,包括格式修改和对电子表格本身的修改(例如添加行),更改 可安装的触发器会执行。
  • 当 Google 表单回答提交时,表单提交 可安装的触发器会执行。

    表单提交触发器有两个版本:一个用于表格(收集表单回答),另一个用于 Google 表单。传递给表格表单提交触发器函数的事件对象更简单,并以简单数组的形式返回回答值。传递给表单表单提交触发器函数的 事件对象 提供更多信息,这些信息包含在 FormResponse对象中。

  • **时间驱动型触发器** (也称为时钟触发器)会在特定时间触发,或按 固定的时间间隔重复触发。

授权可安装的触发器

通常,如果开发者更新插件以使用需要额外授权的新服务,系统会在用户下次使用该插件时提示用户重新授权该插件。

不过,使用触发器的插件会遇到特殊的授权挑战。假设有一个插件使用触发器来监控表单提交:表单创建者可能会在首次使用该插件时授权该插件,然后让其运行数月或数年,而无需重新打开表单。如果插件开发者更新插件以使用需要额外授权的新服务,表单创建者将永远不会看到重新授权对话框,因为他们从未重新打开表单,并且插件将停止运行。

与常规 Apps 脚本项目中的触发器不同,插件中的触发器即使需要重新授权也会继续触发。不过,如果脚本遇到需要其没有的授权的代码行,脚本仍然会失败。为避免这种情况,请使用 ScriptApp.getAuthorizationInfo 来限制对 插件不同版本之间已更改的代码部分的访问。

以下示例展示了在触发器函数中使用的推荐结构,以避免授权陷阱。示例触发器函数响应 Google 表格插件中的表单提交事件,如果需要重新授权,则使用模板化 HTML 向插件用户发送提醒电子邮件。

Code.gs

triggers/form/Code.gs
/**
 * Responds to a form when submitted.
 * @param {event} e The Form submit event.
 */
function respondToFormSubmit(e) {
  const addonTitle = "My Add-on Title";
  const props = PropertiesService.getDocumentProperties();
  const authInfo = ScriptApp.getAuthorizationInfo(ScriptApp.AuthMode.FULL);

  // Check if the actions of the trigger requires authorization that has not
  // been granted yet; if so, warn the user via email. This check is required
  // when using triggers with add-ons to maintain functional triggers.
  if (
    authInfo.getAuthorizationStatus() === ScriptApp.AuthorizationStatus.REQUIRED
  ) {
    // Re-authorization is required. In this case, the user needs to be alerted
    // that they need to re-authorize; the normal trigger action is not
    // conducted, since it requires authorization first. Send at most one
    // "Authorization Required" email per day to avoid spamming users.
    const lastAuthEmailDate = props.getProperty("lastAuthEmailDate");
    const today = new Date().toDateString();
    if (lastAuthEmailDate !== today) {
      if (MailApp.getRemainingDailyQuota() > 0) {
        const html = HtmlService.createTemplateFromFile("AuthorizationEmail");
        html.url = authInfo.getAuthorizationUrl();
        html.addonTitle = addonTitle;
        const message = html.evaluate();
        MailApp.sendEmail(
          Session.getEffectiveUser().getEmail(),
          "Authorization Required",
          message.getContent(),
          {
            name: addonTitle,
            htmlBody: message.getContent(),
          },
        );
      }
      props.setProperty("lastAuthEmailDate", today);
    }
  } else {
    // Authorization has been granted, so continue to respond to the trigger.
    // Main trigger logic here.
  }
}

authorizationemail.html

triggers/form/AuthorizationEmail.html
<p>The Google Sheets add-on <i><?= addonTitle ?></i> is set to run automatically
    whenever a form is submitted. The add-on was recently updated and it needs you
    to re-authorize it to run on your behalf.</p>

<p>The add-on's automatic functions are temporarily disabled until you
    re-authorize it. To do so, open Google Sheets and run the add-on from the
    Add-ons menu. Alternatively, you can click this link to authorize it:</p>

<p><a href="<?= url ?>">Re-authorize the add-on.</a></p>

<p>This notification email will be sent to you at most once per day until the
    add-on is re-authorized.</p>

限制

插件中的可安装触发器受适用于其他类型 Apps 脚本 项目的可安装触发器的相同 限制

除了这些限制之外,还有一些限制专门适用于插件中的可安装触发器:

  • 每个插件对于每个用户、每个文档,只能有一种类型的触发器。例如,在给定的电子表格中,给定用户只能有一个修改触发器,但该用户也可以在同一电子表格中拥有表单提交触发器或时间驱动型触发器。有权访问同一电子表格的其他用户可以拥有自己的一组单独的触发器。
  • 插件只能为使用该插件的文件创建触发器。也就是说,在 Google 文档 A 中使用的插件无法创建触发器来监控 Google 文档 B 何时打开。
  • 时间驱动型触发器的运行频率不能超过每小时一次。
  • 当可安装的触发器运行的代码抛出异常时,插件不会自动向用户发送电子邮件。开发者需要负责检查并妥善处理失败情况。
  • 在以下任何情况下,插件触发器都会停止触发:
    • 如果用户卸载了插件,
    • 如果在文档中停用了插件(如果重新启用,触发器将再次运行),或者
    • 如果开发者取消发布插件或向插件商店提交损坏的版本。
  • 插件触发器函数会一直执行,直到遇到使用未经授权的服务的代码为止,然后停止执行。只有在插件已发布的情况下,才会出现这种情况;如果脚本的任何部分需要授权,则常规 Apps 脚本项目或未发布的插件中的同一触发器根本不会执行。
  • 可安装的触发器受 Apps 脚本触发器 配额限制