用户必须授权访问其数据或代表其执行操作的脚本项目。当用户首次运行需要授权的脚本时,界面会显示一个提示,以启动授权流程。
在此流程中,界面会告知用户脚本请求哪些权限。例如,脚本可能会请求读取电子邮件或创建日历活动的权限。脚本项目会将这些单独的权限定义为 OAuth 范围。
对于大多数脚本,Apps 脚本会自动检测所需的范围。您可以随时查看脚本使用的范围。您还可以使用网址字符串在清单中明确设置范围。已发布的应用(例如插件)必须使用尽可能最小的范围。
在授权流程中,Apps 脚本会显示所需范围的人类可读说明。例如,如果脚本需要电子表格的只读权限,则清单可能包含 https://www.googleapis.com/auth/spreadsheets.readonly 范围。授权提示会要求用户允许此应用“查看您的 Google 电子表格”。
某些范围包含其他范围。例如,授权范围 https://www.googleapis.com/auth/spreadsheets 允许对电子表格进行读写操作。
对于某些界面(例如 Apps 脚本 IDE),用户会看到精细的 OAuth 权限请求页面。在此界面中,用户可以选择要授予的特定权限,而不是一次性授予所有权限。设计脚本以处理精细的 OAuth 权限。
查看范围
如需查看脚本项目所需的范围,请执行以下操作:
- 打开脚本项目。
- 点击左侧的概览图标 。
- 查看项目 OAuth 范围 下的范围。
设置明确的范围
Apps 脚本会扫描代码中的函数调用,自动确定所需的范围。虽然这足以满足大多数脚本的需求,但对于已发布的插件、Web 应用、Chat 应用以及对 Chat API 的调用,您必须直接控制范围。
Apps 脚本有时会自动分配宽泛的范围。这可能意味着您的脚本向用户请求的权限超出了所需范围。对于已发布的脚本,请将宽泛的范围替换为有限的范围集,该范围集应涵盖脚本的需求。
您可以修改脚本项目的清单文件,明确设置脚本项目使用的范围。清单字段 oauthScopes 是项目使用的范围数组。如需设置项目的范围,请执行以下操作:
- 打开脚本项目。
- 点击左侧的项目设置图标 。
- 选中在编辑器中显示“appsscript.json”清单文件复选框。
- 点击左侧的编辑器 。
- 点击左侧的
appsscript.json文件。 - 找到标记为
oauthScopes的顶层字段。如果不存在,您可以添加该字段。 - 将
oauthScopes数组的内容替换为您希望项目使用的范围。例如:{ ... "oauthScopes": [ "https://www.googleapis.com/auth/spreadsheets.readonly", "https://www.googleapis.com/auth/userinfo.email" ], ... } - 点击顶部的保存图标 。
处理精细的 OAuth 权限
精细的 OAuth 权限请求页面最初是在 Apps 脚本 IDE 中推出的,面向直接执行脚本的用户。随着时间的推移,权限请求页面将逐步推广到其他场景,例如宏、触发器和插件。如需了解详情,请参阅 Google Apps 脚本 IDE 执行中的精细 OAuth 权限请求。
通过精细的 OAuth 权限请求页面,用户可以指定要授权的各个 OAuth 范围。这样,用户就可以精细地控制与每个脚本共享哪些账号数据。例如,如果某个脚本请求电子邮件范围和日历范围的权限,用户可以选择授予日历权限,但不授予 Gmail 权限。
以下部分介绍了如何处理精细的 OAuth 权限。
自动为必要的范围请求权限
如果执行流程需要特定范围,您可以要求用户授予这些权限。您的脚本可以检查权限,并在缺少权限时自动请求。
ScriptApp 类中的以下方法可验证权限并呈现授权提示:
requireScopes(authMode, oAuthScopes):对于依赖于特定范围的 flow,请使用此方法。requireAllScopes(authMode):如果执行流程依赖于所有项目范围,请使用此方法。
示例
以下示例展示了如何调用 requireScopes() 和 requireAllScopes()。该脚本使用 Gmail、Google 表格和 Google 日历的范围。sendEmail() 函数仅需要 Gmail 和 Google 表格的权限范围,而 createEventSendEmail() 函数需要脚本使用的所有权限范围。
// This function requires the Gmail and Sheets scopes.
function sendEmail() {
// Validates that the user has granted permission for the Gmail and Sheets scopes.
// If not, the execution ends and prompts the user for authorization.
ScriptApp.requireScopes(ScriptApp.AuthMode.FULL, [
'https://mail.google.com/',
'https://www.googleapis.com/auth/spreadsheets'
]);
// Sends an email.
GmailApp.sendEmail("dana@example.com", "Subject", "Body");
Logger.log("Email sent successfully!");
// Opens a spreadsheet and sheet to track the sent email.
const ss = SpreadsheetApp.openById("abc1234567");
const sheet = ss.getSheetByName("Email Tracker")
// Gets the last row of the sheet.
const lastRow = sheet.getLastRow();
// Adds "Sent" to column E of the last row of the spreadsheet.
sheet.getRange(lastRow, 5).setValue("Sent");
Logger.log("Sheet updated successfully!");
}
// This function requires all scopes used by the script (Gmail,
// Calendar, and Sheets).
function createEventSendEmail() {
// Validates that the user has granted permission for all scopes used by the
// script. If not, the execution ends and prompts the user for authorization.
ScriptApp.requireAllScopes(ScriptApp.AuthMode.FULL);
// Creates an event.
CalendarApp.getDefaultCalendar().createEvent(
"Meeting",
new Date("November 28, 2024 10:00:00"),
new Date("November 28, 2024 11:00:00")
);
Logger.log("Calendar event created successfully!");
// Sends an email.
GmailApp.sendEmail("dana@example.com", "Subject 2", "Body 2");
Logger.log("Email sent successfully!");
// Opens a spreadsheet and sheet to track the created meeting and sent email.
const ss = SpreadsheetApp.openById("abc1234567");
const sheet = ss.getSheetByName("Email and Meeting Tracker")
// Gets the last row
const lastRow = sheet.getLastRow();
// Adds "Sent" to column E of the last row
sheet.getRange(lastRow, 5).setValue("Sent");
// Adds "Meeting created" to column F of the last row
sheet.getRange(lastRow, 6).setValue("Meeting created");
Logger.log("Sheet updated successfully!");
}
为缺失的范围创建自定义体验
您可以检索用户的权限状态,并设计自定义体验。 例如,您可以停用需要缺少权限的功能,或显示一个对话框来解释相关要求。以下方法会检索一个包含用户权限信息的对象,其中包括用户已授权的范围以及一个用于请求缺失范围的网址:
getAuthorizationInfo(authMode, oAuthScopes):检查特定范围的权限状态。getAuthorizationInfo(authMode):检查所有项目范围的权限状态。
如需从授权信息对象中获取权限详细信息,例如授权范围列表和用于请求缺失权限的网址,请使用 AuthorizationInfo 类中的方法。
示例
以下示例展示了如何使用 getAuthorizationInfo() 跳过用户未授予所需范围的功能。这样一来,其余执行流程便可继续,而不会提示缺少相应范围的授权。
// This function uses the Gmail scope and skips the email
// capabilities if the scope for Gmail hasn't been granted.
function myFunction() {
const authInfo = ScriptApp.getAuthorizationInfo(ScriptApp.AuthMode.FULL, ['https://mail.google.com/']);
if (authInfo.getAuthorizationStatus() === ScriptApp.AuthorizationStatus.NOT_REQUIRED) {
GmailApp.sendEmail("dana@example.com", "Subject", "Body");
Logger.log("Email sent successfully!");
} else {
const scopesGranted = ScriptApp.getAuthorizationInfo(ScriptApp.AuthMode.FULL).getAuthorizedScopes();
console.warn(`Authorized scopes: ${scopesGranted} not enough to send mail, skipping.`);
}
// Continue the rest of the execution flow...
}
确保触发器执行具有权限
与触发器关联的函数会自动运行,用户可能不在场,无法提供权限。建议您在安装触发器之前使用
requireScopes(authMode, oAuthScopes)。此方法会提示用户授予缺失的权限,并且不允许在未授予这些权限的情况下安装触发器。
示例
// This function requires scope Sheets.
function trackFormSubmissions(e){
// Opens a spreadsheet to track the sent email.
const ss = SpreadsheetApp.openById("abc1234567");
const sheet = ss.getSheetByName("Submission Tracker")
// Gets the last row of the sheet.
const lastRow = sheet.getLastRow();
// Adds email address of user that submitted the form
// to column E of the last row of the spreadsheet.
sheet.getRange(lastRow, 5).setValue(e.name);
Logger.log("Sheet updated successfully!");
}
function installTrigger(){
// Validates that the user has granted permissions for trigger
// installation and execution. If not, trigger doesn't get
// installed and prompts the user for authorization.
ScriptApp.requireScopes(ScriptApp.AuthMode.FULL, [
'https://www.googleapis.com/auth/script.scriptapp',
'https://www.googleapis.com/auth/spreadsheets',
'https://www.googleapis.com/auth/forms.currentonly'
]);
ScriptApp.newTrigger('trackFormSubmission')
.forForm(FormApp.getActiveForm())
.onFormSubmit()
.create();
}
OAuth 验证
某些 OAuth 范围是敏感范围,因为它们允许访问 Google 用户数据。如果您的脚本项目使用的范围允许访问用户数据,则该项目必须先通过 OAuth 客户端验证,然后才能作为 Web 应用或插件公开发布。如需了解详情,请参阅以下指南:
受限范围
除了敏感范围之外,某些范围还被归类为受限范围,并受有助于保护用户数据的额外规则的约束。如果您发布的应用使用受限范围,则必须遵守所有规范。
在发布之前,请查看受限范围的完整列表。合规应用必须遵守有关特定 API 范围的其他要求。
请尽可能避免使用受限范围,以简化审核流程。您可以为非公开应用随意使用受限范围。