javascript - 如何使用 Google App 脚本根据条件发送带有 PDF 文件附件的电子邮件

标签 javascript html google-apps-script

我解决了以下问题。 使用 Google 表格的 Google 脚本服务将 PDF 文件发送给每个人。 我尝试向列表中的每个人发送一个文件。进展顺利。
然而,我在尝试制作类似的脚本时遇到了问题,但是为了将多个文件发送给 Google Sheet 列表上的不同人。每个人都有不同的文件。

例如:
John 拥有三个 PDF 文件:John_ 999901.pdf、John_ 999902.pdf 和 John_999903.pdf。
David 有两个 PDF 文件:David_ 999901.pdf 和 David_99990。
Jun有两个PDF文件:Jun_999901.pdf和Jun_999902.pdf。
最后,Michel 只有一个 PDF 文件:Michel_999901.pdf。
所有 PDF 文件均保存在 GOOGLE DRIVE 上。
This is where I save the PDF file
This is my spreadsheet
有没有办法根据列表中同名人员对应的文件名发送电子邮件?
下面是我尝试发送文件的代码

function onOpen() 
{
  var ui = SpreadsheetApp.getUi();
  ui.createMenu('メール送信')
     
      .addItem('送信', 'sendFormToAll')
      .addToUi();
}
function include(filename) {
  return HtmlService.createHtmlOutputFromFile(filename).getContent();
}
function sendFormToAll()
{
   var sheet = SpreadsheetApp.getActive().getSheetByName('Sheet1');
  
   var last_row = sheet.getDataRange().getLastRow();
  
   for(var row=2; row <= last_row; row++)
   {
     sendEmailWithAttachment(row);
     sheet.getRange(row,8).setValue("send");
   }
}

function sendPDFForm()
{
  var row = SpreadsheetApp.getActiveSheet().getActiveCell().getRow();
  sendEmailWithAttachment(row);
}

function sendEmailWithAttachment(row)
{
  var filename= '?????.pdf';// I don't know what to do at this point
  
  var file = DriveApp.getFilesByName(filename);
  
  if (!file.hasNext()) 
  {
    console.error("Could not open file "+filename);
    return;
  }
  
  var client = getClientInfo(row);
  
  var template = HtmlService
      .createTemplateFromFile('index');
  template.client = client;
  var message = template.evaluate().getContent();
  
  
  MailApp.sendEmail({
    to: client.email,
    subject: "Send File",
    htmlBody: message ,
    attachments: [file.next().getAs(MimeType.PDF)]
  });

}

function getClientInfo(row)
{
   var sheet = SpreadsheetApp.getActive().getSheetByName('Sheet1');
   
   var values = sheet.getRange(row,1,row,8).getValues();
   var rec = values[0];
  
  var client = 
      {
        name:rec[0],
        email: rec[1]
      };
  client.name = client.name;
  return client;
}
<!DOCTYPE html>
<html>
   <head>
      <base target="_top">
      <!-- CSS only -->
      <link href="https://cdn.jsdelivr.net/npm/<a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="02606d6d76717670637242372c332c31" rel="noreferrer noopener nofollow">[email protected]</a>/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-1BmE4kWBq78iYhFldvKuhfTAU6auU8tT94WrHftjDbrCEXSU1oBoqyl2QvZ6jIW3" crossorigin="anonymous">
      <script src="https://code.jquery.com/jquery-3.6.0.js" integrity="sha256-H+K7U5CnXl1h5ywQfKtSj8PCmoN9aaq30gDh27Xc0jk=" crossorigin="anonymous"></script>
      
   </head>

  
   <body>
     <div  >
     
     
      <p>Hi, <?= client.name ?>Sir </p>
      <p>I send you file . Please check it</p>
   
     
      <p>*********************************************************</p>
     
     </div>
   </body>
</html>

最佳答案

在您的脚本中,为了实现您的目标,进行以下修改怎么样?

修改点:

  • 当在循环中使用getValue时,处理成本会变高。
  • 需要添加从文件夹内的文件中搜索文件名的逻辑。
  • 当我看到您的示例电子表格时,情况 是“C”列。但当我看到你的脚本时,它是 sheet.getRange(row,8).setValue("send");。如果Situationsheet.getRange(row,8).setValue("send");相同,则要求为sheet.getRange(row ,3).setValue("发送");.但我不确定你的实际情况。因此,在此修改中,我对示例电子表格使用了 sheet.getRange(row,3).setValue("send");
  • 在您的脚本中,Sheet1 用作工作表名称。但在您的示例电子表格中,工作表名称为 Request。在此修改中,我对示例电子表格使用了 Request

当这些要点反射(reflect)到您的脚本中时,它就会变成如下所示。

修改后的脚本:

请将您的文件夹 ID 设置为 DriveApp.getFolderById("###").searchFiles(`title contains '${name}' andrashed=false` 的 ### );.

function sendFormToAll() {
  var sheet = SpreadsheetApp.getActive().getSheetByName('Request');
  var values = sheet.getRange("A2:C" + sheet.getLastRow()).getValues();
  var rangeList = values.reduce((ar, e, i) => {
    if (e[2] == "Send File") return ar;
    var [name, email] = e.map(f => f.trim());
    var files = DriveApp.getFolderById("###").searchFiles(`title contains '${name}' and trashed=false`);
    var attachments = [];
    var r = new RegExp(`^${name}[_\\d\\s]+\\.pdf\$`, "i");
    while (files.hasNext()) {
      var file = files.next();
      if (r.test(file.getName())) attachments.push(file.getBlob());
    }
    if (attachments.length == 0) {
      console.error("Could not find files related to " + name);
      return ar;
    }
    var template = HtmlService.createTemplateFromFile('index');
    template.client = { name };
    var message = template.evaluate().getContent();
    MailApp.sendEmail({ to: email, subject: "Send File", htmlBody: message, attachments });
    ar.push(`C${i + 2}`);
    return ar;
  }, []);
  if (rangeList.length == 0) return;
  sheet.getRangeList(rangeList).setValue("Send File");
}

注意:

  • 此示例脚本适用于您的示例电子表格。因此,如果您的实际电子表格的结构与示例电子表格的结构不同,则该脚本可能无法使用。所以,请小心这一点。

引用文献:

关于javascript - 如何使用 Google App 脚本根据条件发送带有 PDF 文件附件的电子邮件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/70416450/

相关文章:

javascript - onChange 按钮标签不保持其样式

javascript - 如何确定从今天到过去日期的纪元时间范围,然后确定过去时间的等量?

javascript - 无法从不同域中的页面访问 iframe 内容

javascript - Google Apps 脚本模式窗口 HTML - 链接的 href 问题

javascript - 如何将 "&amp;"更改为 & for twitter javascript 程序

javascript - 原型(prototype)js使表可调整列大小

javascript - 无法将数据从套接字发送到特定客户端

javascript - 单击播放音频链接

Javascript使用电子表格范围A1表示法从二维数组中提取子数组

datetime - 处理日期/时间和时区的奇怪时间偏移