【问题标题】:Google Sheets - Create PDF and Send Email (Different PDFs to Different Emails)Google 表格 - 创建 PDF 并发送电子邮件(不同的 PDF 到不同的电子邮件)
【发布时间】:2021-02-23 14:18:13
【问题描述】:

我有一个 Google 表格,它根据特定单元格(“仪表板”工作表中的 A24)中的运动员姓名更新信息。一旦运动员姓名更改(例如,A24 更改为不同的运动员姓名),“仪表板”工作表上的信息就会更改以反映该运动员的数据。

我有运动员姓名 (athleteList) 和运动员电子邮件 (emails) 的列表。本质上,我希望脚本循环执行以下操作:

  1. 将运动员姓名更新为运动员列表中的运动员 [i]
  2. 创建“仪表板”工作表的 PDF(现已更新为运动员 [i])
  3. 将该 PDF 的电子邮件发送给运动员[i](例如,使用他们的电子邮件,即 email[i])。

我是 Google Apps 脚本的新手,所以我希望这是有道理的......我非常接近。使用下面的代码可以正常发送电子邮件,但正在创建的 PDF 不适合接收电子邮件的人。任何援助将不胜感激。谢谢!

可编辑工作表的链接(与代码不同的 URL 和 GID):https://docs.google.com/spreadsheets/d/1Amkc1tDgLgaNxKCos95vsZEaxdyd67Xcdtfc4NEQT60/edit?usp=sharing

应用脚本代码代码:

     //Google Sheets URL Edit (Athletes Sheet Name)
     //Google Sheets URL Edit (Dashboard Sheet Name)
     //Google Sheets URL Export (Dashboard Sheet Name)
    var ss = SpreadsheetApp.openByUrl("https://docs.google.com/spreadsheets/d/1z15EwpuITPnmqPAIwHdxyV6DFDGMLBWKCxpDCQrGtBw/edit/");
    var ssAthletes = SpreadsheetApp.openByUrl("https://docs.google.com/spreadsheets/d/1z15EwpuITPnmqPAIwHdxyV6DFDGMLBWKCxpDCQrGtBw/edit/").getSheetByName("Athletes");

    var ssDashboard = SpreadsheetApp.openByUrl("https://docs.google.com/spreadsheets/d/1z15EwpuITPnmqPAIwHdxyV6DFDGMLBWKCxpDCQrGtBw/edit/").getSheetByName("Dashboard");

    var ssDashboardExport = SpreadsheetApp.openByUrl("https://docs.google.com/spreadsheets/d/1z15EwpuITPnmqPAIwHdxyV6DFDGMLBWKCxpDCQrGtBw/export?/").getSheetByName("Dashboard");

        var lastRow = ssAthletes.getLastRow()-1; //Define last Row
        var athleteList = ssAthletes.getRange(2,1,lastRow).getValues(); //get list of Athletes (Starting at row 2, column 1)
        var athleteEmails = ssAthletes.getRange(2,2,lastRow).getValues();



//THIS FUNCTION EMAILS as PDF

function emailSpreadsheetAsPDF() {
  DocumentApp.getActiveDocument();
  DriveApp.getFiles();

  // This is the link to my spreadsheet with the Form responses and the Invoice Template sheets
  // Add the link to your spreadsheet here 
  // or you can just replace the text in the link between "d/" and "/edit"
  // In my case is the text: 17I8-QDce0Nug7amrZeYTB3IYbGCGxvUj-XMt8uUUyvI
  // const ss = SpreadsheetApp.openByUrl("https://docs.google.com/spreadsheets/d/1z15EwpuITPnmqPAIwHdxyV6DFDGMLBWKCxpDCQrGtBw/edit");

  // We are going to get the email address from the cell "E2" from the "Lists" sheet
  // Change the reference of the cell or the name of the sheet if it is different
  const value = ss.getSheetByName("Lists").getRange("E2").getValue();
  const email = value.toString();

    for (var i = 0; i < athleteList.length; ++i) {
    athleteName = athleteList[i];
  }

  // Subject of the email message
  const subject = 'Your Report';

  // Email Text. You can add HTML code here - see ctrlq.org/html-mail
  const body = "Hey " + athleteName + "! Great work today. Here is your report for " + Date();

  // Again, the URL to your spreadsheet but now with "/export" at the end
  // Change it to the link of your spreadsheet, but leave the "/export"
  const url = 'https://docs.google.com/spreadsheets/d/1z15EwpuITPnmqPAIwHdxyV6DFDGMLBWKCxpDCQrGtBw/export?';

  const exportOptions =
    'exportFormat=pdf&format=pdf' + // export as pdf
    '&size=letter' + // paper size letter / You can use A4 or legal
    '&portrait=true' + // orientation portal, use false for landscape
    '&fitw=true' + // fit to page width false, to get the actual size
    '&sheetnames=false&printtitle=false' + // hide optional headers and footers
    '&pagenumbers=false&gridlines=false' + // hide page numbers and gridlines
    '&fzr=false' + // do not repeat row headers (frozen rows) on each page
    '&gid=680445839'; // the sheet's Id. Change it to your sheet ID.
  // You can find the sheet ID in the link bar. 
  // Select the sheet that you want to print and check the link,
  // the gid number of the sheet is on the end of your link.
  
  var params = {method:"GET",headers:{"authorization":"Bearer "+ ScriptApp.getOAuthToken()}};
  
  // Generate the PDF file
  var response = UrlFetchApp.fetch(url+exportOptions, params).getBlob();
  
  // Send the PDF file as an attachement 
    GmailApp.sendEmail(email, subject, body, {
      htmlBody: body,
      attachments: [{
            fileName: "Dashboard" + Date() + ".pdf",
            content: response.getBytes(),
            mimeType: "application/pdf"
        }]
    })}



//THIS FUNCTION EMAILS MULTIPLE PEOPLE as PDF -- WORK IN PROGRESS!!!

function emailSpreadsheetAsPDFMulti() {
  DocumentApp.getActiveDocument();
  DriveApp.getFiles();

  // This is the link to my spreadsheet with the Form responses and the Invoice Template sheets
  // Add the link to your spreadsheet here 
  // or you can just replace the text in the link between "d/" and "/edit"
  // In my case is the text: 17I8-QDce0Nug7amrZeYTB3IYbGCGxvUj-XMt8uUUyvI
  // const ss = SpreadsheetApp.openByUrl("https://docs.google.com/spreadsheets/d/1z15EwpuITPnmqPAIwHdxyV6DFDGMLBWKCxpDCQrGtBw/edit");

  // We are going to get the email address from the cell "E2" from the "Lists" sheet
  // Change the reference of the cell or the name of the sheet if it is different
  const emails = ss.getSheetByName("Athletes").getRange(2,2,lastRow).getValues();
  const emailsString = emails.toString();

 // for (var i = 0; i < athleteList.length; ++i) {
 //  athleteName = athleteList[i];
 // }

  for (var i = 0; i < emails.length; ++i) {
    athleteEmail = emails[i];
    athleteName = athleteList[i];
  }

  // Again, the URL to your spreadsheet but now with "/export" at the end
  // Change it to the link of your spreadsheet, but leave the "/export"
  const url = 'https://docs.google.com/spreadsheets/d/1z15EwpuITPnmqPAIwHdxyV6DFDGMLBWKCxpDCQrGtBw/export?';

  const exportOptions =
    'exportFormat=pdf&format=pdf' + // export as pdf
    '&size=letter' + // paper size letter / You can use A4 or legal
    '&portrait=true' + // orientation portal, use false for landscape
    '&fitw=true' + // fit to page width false, to get the actual size
    '&sheetnames=false&printtitle=false' + // hide optional headers and footers
    '&pagenumbers=false&gridlines=false' + // hide page numbers and gridlines
    '&fzr=false' + // do not repeat row headers (frozen rows) on each page
    '&gid=680445839'; // the sheet's Id. Change it to your sheet ID.
  // You can find the sheet ID in the link bar. 
  // Select the sheet that you want to print and check the link,
  // the gid number of the sheet is on the end of your link.
  


// Cycle through athletes

  for (var i = 0; i < athleteList.length; i++) {
    var output = [];
    ssDashboard.getRange('A24').setValue(athleteList[i][0]);
    output.push([athleteList[i][0]]);
    Utilities.sleep(10000);
    
  

 // Generate the PDF file
var params = {method:"GET",headers:{"authorization":"Bearer "+ ScriptApp.getOAuthToken()}};
var response = UrlFetchApp.fetch(url+exportOptions, params).getBlob();

// Subject of the email message
  const subject = 'Report'

  var athletename = athleteList[i][0];

  // Email Text. You can add HTML code here - see ctrlq.org/html-mail
  const body = "Hey " + athletename + "! Great work today. Here is your report for " + Date();

console.log(output);
console.log(response);
console.log(body);
console.log(athletename);
console.log(emails[i]);

// Send the PDF file as an attachement 
    GmailApp.sendEmail(emails[i], subject, body, {
      htmlBody: body,
      attachments: [{
            fileName: "Dashboard" + Date() + ".pdf",
            content: response.getBytes(),
            mimeType: "application/pdf"
    }]
    })}}'''

【问题讨论】:

  • 尝试检查您的代码中是否存在冗余或不必要的行,例如 DocumentApp.getActiveDocument(); DriveApp.getFiles(); 或重复函数。尽可能简单。然后增加更多的复杂性。
  • 请与您正在使用的工作表的虚拟数据共享一个可编辑的副本。
  • 这是一个可编辑的副本:docs.google.com/spreadsheets/d/… 感谢您的 cmets。大部分重复是由于我在 Google Apps 脚本世界中处于起步阶段 - 我基本上从不同领域复制/粘贴了一些代码,并且一直在玩弄这些代码段的作用。希望随着我的深入了解,我能够将其精简为必要的组件。

标签: email pdf google-apps-script google-sheets


【解决方案1】:

我想你几乎明白了。我就是这样做的。 请不要忘记更新电子表格的 ID

function updateInfo(){

 // I get the emails from the Athletes sheet, hope is ok, otherwise you can point in to another range
  var athleteSheet = SpreadsheetApp.getActive().getSheetByName("Athletes");  
  var athleteList = athleteSheet.getRange("A2:B"+athleteSheet.getLastRow()).getValues();
 
  for (i=0;i<athleteList.length;i++){
    var name = athleteList[i][0];
    var email = athleteList[i][1];
    SpreadsheetApp.getActive().getSheetByName("Dashboard").getRange("A24").setValue(name);
    SpreadsheetApp.flush(); // this is important for the changes in the spreadsheet to take place
    sendInfo(name, email); // then I send the emails
  }
}

现在我使用了与您的功能非常相似的功能并发送文件

function sendInfo(name, email){
   // change the id (this is the id of my file, a copy of yours)
    var ss = SpreadsheetApp.openById('1uftGO8ACoQTE8LtjURjIG2g5G-x3B-taIobVxzvJA2E'); 
    var sheet = ss.getSheetByName("Dashboard");
    var ssId = ss.getId();

    // export url
    var url = 'https://docs.google.com/spreadsheets/d/'+ ssId +'/export?'
      + 'exportFormat=pdf&format=pdf'
      + '&size=letter'                           // paper size legal / letter / A4
      + '&portrait=true'                     // orientation, false for landscape
      + '&fitw=true'                        // fit to page width, false for actual size
      + '&sheetnames=false&printtitle=false' // hide optional headers and footers
      + '&pagenumbers=false&gridlines=false' // hide page numbers and gridlines
      + '&fzr=false'                         // do not repeat row headers (frozen rows) on each page
      + '&gid='+sheet.getSheetId();    // the sheet's Id
  
    var headers = { 
       'Authorization': 'Bearer ' +  ScriptApp.getOAuthToken()
    }

  // request export url
    var response = UrlFetchApp.fetch(url, { headers: headers });
    var blob = response.getBlob();
    const subject = 'Your Report';
    const body = "Sent via Generate Dashboard Report from Google Form and print/email it";
 
    GmailApp.sendEmail(email, subject, body, {
        htmlBody: body,
        attachments: [{
              fileName: "Dashboard.pdf",
              content: blob.getBytes(),
              mimeType: "application/pdf"
          }]
      });

    DriveApp.createFile(blob.setName(name+".pdf"))

}

顺便说一句,您在这些电子表格上做得很好。

【讨论】:

  • 塞巴斯蒂安,非常感谢!这非常有效。你是最好的。我阅读了 .flush,现在明白了为什么它如此重要。
  • 我不知道如何通过该网站向您发送消息。显然,我不能在 5 分钟后编辑评论?以前从未见过。无论如何,你介意给我发一封电子邮件(adam.virgile@gmail.com)吗?如果您提供咨询和/或教学服务,我想与您一起探讨。
  • 我的荣幸亚当!我很想谈一谈。我已经写信给你了! (sebastianlaclau@gmail.com)
猜你喜欢
  • 1970-01-01
  • 2018-11-06
  • 2011-08-20
  • 1970-01-01
  • 1970-01-01
  • 2015-10-30
  • 2011-11-08
  • 2014-09-14
  • 1970-01-01
相关资源
最近更新 更多