【发布时间】:2020-02-25 00:24:07
【问题描述】:
我有一个带有绑定脚本的电子表格,该脚本试图识别当前对工作表进行编辑的用户,并将编辑信息附加到工作表的指定列中。
似乎用户总是必须通过打开脚本编辑器并通过“播放”按钮手动运行功能来进行初始脚本授权(即请求权限的 Google 弹出窗口)。通过自定义 UI 菜单调用该功能不起作用并引发错误:“您无权执行该操作。请请求此项目的所有者授予您访问权限。”
有没有什么方法可以以更用户友好的方式调用授权,而不需要用户打开脚本编辑器?
我认为制作菜单是重点(手动执行与 onEdit() 或 onOpened() 触发执行),但就目前而言,这种解决方法是无用的 - 如果用户有,我不需要菜单打开编辑器来实现同样的事情。
完整代码:
function onEdit(e) {
var sheet = e.source.getActiveSheet();
var labels = e.source.getRangeByName("labels");
if (labels == null) {
Logger.log("Error: couldn't find named range 'labels'!");
return;
}
var found = false;
for(var i = 1; i <= labels.getNumColumns(); i++){
if (labels.getCell(1,i).getValue() == "last edit") {
found = true;
break;
}
}
if (!found) {
Logger.log("Error: couldn't find column 'last edit'!");
return;
}
var minrow = labels.getRowIndex();
var range = sheet.getActiveRange();
var row = range.getRowIndex();
// don't track edits above the labels
if (row <= minrow) { return; }
var range_depth = range.getNumRows();
var rangeA1 = range.getA1Notation();
var timestamp = Utilities.formatDate(new Date(), "GMT+2", "YYYY-MM-dd HH:mm");
// the elegant way - requires the sheet owner and users to be on the same domain:
// var user = Session.getActiveUser().getEmail();
// the workaround - requires the user to identify themselves manually:
var user = PropertiesService.getUserProperties().getProperty("ID");
if (user == null) {
Browser.msgBox('Current user unidentified. Run the identification script via the "Edit tracking" menu (next to "Help").');
user = 'unknown';
}
for (var j = 0; j < range_depth; j++) {
sheet.getRange(row+j, i).setValue(timestamp);
sheet.getRange(row+j, i+1).setValue(user);
sheet.getRange(row+j, i+2).setValue(rangeA1);
}
SpreadsheetApp.flush();
}
function onOpen(e) {
SpreadsheetApp.getUi()
.createMenu('Edit tracking')
.addItem('Identify current user', 'showIdentify')
.addItem('Forget current user', 'showForget')
.addToUi();
}
function showIdentify() {
var ui = SpreadsheetApp.getUi();
var result = ui.prompt(
'Edit tracking',
'Please enter your name:',
ui.ButtonSet.OK_CANCEL);
var button = result.getSelectedButton();
var text = result.getResponseText();
if (button == ui.Button.OK) {
PropertiesService.getUserProperties().setProperty("ID", text);
} else {
ui.alert('Look, you\'re not dodging this, I\'ll nag you again on the next edit.');
}
}
function showForget() {
var ui = SpreadsheetApp.getUi();
PropertiesService.getUserProperties().deleteProperty("ID");
ui.alert('You\'re anonymous now.');
}
【问题讨论】:
标签: google-apps-script menu authorization cross-domain