我有一个Google Apps脚本,我用它来批量同一个域中的电子邮件收件人。脚本基本上向他们发送包含月度报告的Google文档的链接。报告的值来自电子表格:
此脚本的最大问题是它在执行5分钟后超时。上次我试图运行它时,它从750电子邮件目标中发出了145封电子邮件。
模板选择器代码
function selectTemplate() {
var app = UiApp.createApplication().setTitle("Select Template").setHeight(400).setWidth(500);
var doclisthandler = app.createServerHandler('templateSelectionHandler');
var closeHandler = app.createServerHandler('closeSelectionHandler');
app.createDocsListDialog().showDocsPicker().addSelectionHandler(doclisthandler).addCloseHandler(closeHandler);
SpreadsheetApp.getActiveSpreadsheet().show(app);
}
/**
Function to retrieve the template ID from ScriptDb
**/
function setTemplateId(){
var db = ScriptDb.getMyDb();
/**we dont query for a specific ID because by default we only store one template so we will
always have one record
**/
var results = db.query({});
while (results.hasNext()) {
var result = results.next();
var jsonResults = Utilities.jsonStringify(result);
}
Logger.log(jsonResults);
var jsonTemplate = Utilities.jsonParse(jsonResults);
var templateId = jsonTemplate.template_id;
return templateId;
}
这是发送电子邮件的代码:
function sendEmail(){
var mySheet = SpreadsheetApp.getActiveSpreadsheet().getActiveSheet();
var range = mySheet.getDataRange();
var myRange = range.offset(1, 0, range.getNumRows()-1);
var curFeatures = range.getValues();
var curCols = new ColNumbers(curFeatures[0], COLS_KEYAPPCOLS);
var currentTime = new Date();
var payrollYear = currentTime.getYear();
var payMonth = mySheet.getSheetName();
var hours = currentTime.getHours();
var minutes = currentTime.getMinutes();
try{
//check if folder exists before you create one
var monthFolder = DocsList.getFolder("Report-" + mySheet.getSheetName() + "," + payrollYear);
}catch(e){
//create a folder to hold the current pay slips
var monthFolder = DocsList.createFolder("Report-" + mySheet.getSheetName() + "," + payrollYear);
Logger.log(monthFolder.getName());
}
myRange.getValues().forEach( function( recipient, index, data ){
var staffNumber = recipient[curCols.staffNumber];
Logger.log("staff Number " + staffNumber);
var staffName = recipient[curCols.name];
Logger.log("staffName " + staffName);
var subject = "Report - " + staffName + ", " + payMonth + "-" + payrollYear;
var emailAddress = recipient[curCols.email];
var adminAllowance = recipient[curCols.admin];
var respAllowance = recipient[curCols.resp];
var topUpAllowance = recipient[curCols.topup];
var arrears = recipient[curCols.arrears];
var overtime = recipient[curCols.overtime];
var grossPay = recipient[curCols.gross];
var paye = recipient[curCols.paye];
var mubasa = recipient[curCols.mubasa];
var loan = recipient[curCols.loan];
var rent = recipient[curCols.rent];
var nssf = recipient[curCols.nssf];
var net = recipient[curCols.net];
var totalDed = recipient[curCols.totalded];
var templateid = setTemplateId(); // get template file id
if(templateid == ""){
Browser.msgBox("No template has been selected. Please select the correct template");
return;
}
var docName = "Report details - " + staffNumber;
//if email address is not empty do all the cool stuff like sending the data
if(emailAddress != ""){
var copyDoc = DocsList.getFileById(templateid).makeCopy(docName);
copyDoc.addToFolder(monthFolder);
var docid = copyDoc.getId();
Logger.log("Document ID " + docid);
var doc = DocumentApp.openById(docid);
//set permissions for the doc
Logger.log("permission to view doc " + docid + " assigned to " + emailAddress);
doc.addViewer(emailAddress);
var docURL = doc.getUrl();
var body = doc.getActiveSection();
body.replaceText("%MONTH%", payMonth);
body.replaceText("%YEAR%", payrollYear);
body.replaceText("%STAFFNAME%", staffName);
body.replaceText("%PAYE%", paye);
body.replaceText("%OVERTIME%", overtime);
body.replaceText("%GROSS%", grossPay);
body.replaceText("%NSSF%", nssf);
body.replaceText("%MUBASA%", mubasa);
body.replaceText("%NET%", net);
body.replaceText("%ARREARS%", arrears);
body.replaceText("%TOTALDED%", totalDed);
body.replaceText("%LOAN%", loan);
body.replaceText("%RENT%", rent);
body.replaceText("%ADMIN%", adminAllowance);
body.replaceText("%RESP%", respAllowance);
body.replaceText('%TOPUP%', topUpAllowance);
//email message
doc.saveAndClose();
Logger.log("Sending email to " + emailAddress + " at " + hours + ":" + minutes);
try{
MailApp.sendEmail(emailAddress,
subject, "",
{htmlBody: message
},
attachment: docName,
name: "Report"
});
}catch(e){
Logger.log(e);
}
}else{
Logger.log("no email address found for staff member " + staffName);
}
});
}
我非常感谢有关如何优化此脚本的一些指示,以便它不会超时。
答案 0 :(得分:2)
我建议您修改脚本以一次处理75或100个项目,跟踪脚本属性(或其他位置)的位置并稍后继续处理750个项目。 这应该每5分钟左右在定时器触发器上启动。
发送所有内容后,关闭触发器并在需要时重新启动它。触发器可以通过编程方式轻松设置。