从Google电子表格发送带有脚本的电子邮件-Need Loop

时间:2018-10-12 20:36:32

标签: javascript loops google-apps-script google-sheets

我有一个电子表格,其中包含不同日期的不同事件。

每个活动都有一名讲师和一名主持人。

该脚本经过编程,可以在安排每个事件的前一天向教师和协调员发送提醒。

问题在于,每天有多个活动由同一位辅导员但不同的指导员参加。

该电子邮件目前每天发送一封电子邮件,无论是多少天或多个主持人。

我需要它每行发送一封电子邮件,但在确定必要的循环时遇到了麻烦。我将不胜感激。这是我的脚本:

   function SGIDReminder() {
  //get the spreadsheet object
  var spreadsheet = SpreadsheetApp.getActiveSpreadsheet();
  //set the first sheet as active
  SpreadsheetApp.setActiveSheet(spreadsheet.getSheets()[0]);
  //fetch this sheet
  var sheet = spreadsheet.getActiveSheet();

  //figure out what the last row is
  var lastRow = sheet.getLastRow();

  //the rows are indexed starting at 1; first row is header row so start with 2
  var startRow = 2;

  //grab column 13; it contains the reminder days left
  var range = sheet.getRange(2,13,lastRow-startRow+1, 1);
  var numRows = range.getNumRows();
  var reminder_send_values = range.getValues();

  //grab column for name of reminder
  range = sheet.getRange(2,4,lastRow-startRow+1, 1);
  var course_values = range.getValues();

  //grab column for location
  range = sheet.getRange(2,3,lastRow-startRow+1, 1);
  var location_values = range.getValues();

  //grab column for time
  range = sheet.getRange(2,2,lastRow-startRow+1, 1);
  var time_values = range.getValues();

  //grab column for email
  range = sheet.getRange(2,10,lastRow-startRow+1, 1);
  var email_values = range.getValues();

  //grab column for instructor email
  range = sheet.getRange(2,7,lastRow-startRow+1, 1);
  var instructor_email_values = range.getValues();

  var warning_count = 0;
  var msg = "";

  //Loop over the reminder_send values
  //changed time to hour to avoid message formatting and date addition javascript wanted to add
  for (var i = 0; i <= numRows - 1; i++) {
    var reminder_send = reminder_send_values[i][0];
    if(reminder_send == 1) {
      //if it is 1, do something with the data
      var course = course_values[i][0];
      var location = location_values[i][0];
      var hour = time_values[i][0];
      var email =  email_values[i][0];
      var instructor = instructor_email_values[i][0];
      msg = msg + "Reminder: You have an SGID scheduled tomorrow  at "+hour+" in "+location+" for "+course+".\n Please remind students to bring a smartphone or web capable device with them to class.";
      warning_count++;
    }
  }
  //cc instructor - but could bcc or add other emails, from cte, reply to Gregg
  if(warning_count) {
    MailApp.sendEmail(email, "SGID Reminder Message", msg,
                      {bcc: "myemail@miamioh.edu", cc: instructor, name: "CTE", replyTo: "coordinator@miamioh.edu"});
   }                      
};

1 个答案:

答案 0 :(得分:0)

这不是一揽子解决方案,但说明了您可以做什么。

要发送多个电子邮件,您需要为每种需要电子邮件的案例收集电子邮件。通常,这是使用Object中的ArrayArray或可能的Object完成的(例如,捆绑多个信息)。

可能值得仅向每位讲师发送一封电子邮件,其中包含他们所拥有的所有事件的列表,而向每位辅导员发送一封电子邮件,其中包含其所拥有的所有事件的列表。

此示例使用一个对象来保存instructorfacilitator信息,以便在电子表格数据循环之外进行电子邮件处理。每个相关的电子邮件都用作对象键,其值是事件信息的数组。

const data = sheet.getDataRange().getValues();
const headers = data.shift();
const reminderColText = "Reminder Days Left", // Title of the header col
      compareCol = headers.indexOf(reminderColText),
      // If the row & column intersection has this value, an email is sent for the row's data
      sendIfDays = 1;
if (compareCol === -1)
  throw new Error("Did not find the header column titled '" + reminderColText + "'")

// Prune the sheet's data to only that which we care about.
const events = data.filter(function (row) { return row[compareCol] === sendIfDays; });

const infoIndices = { eventName: 0, // Event name in Col A
                      eventTime: 1,
                      eventLoc: 3, // Event location in Col D
                      instructorEmail: 4,
                      facilitatorEmail: 5 };
const emailInfo = { instructors: {}, facilitators: {} };
events.forEach(function (row) {
  var ins = row[infoIndices.instructorEmail],
      fac = row[infoIndices.facilitatorEmail],
      name = row[infoIndices.eventName],
      time = row[infoIndices.eventTime],
      loc = row[infoIndices.eventLoc];

  // Create an Array for each instructor / facilitator email
  if (!emailInfo.instructors[ins])
    emailInfo.instructors[ins] = [];
  if (!emailInfo.facilitators[fac])
    emailInfo.facilitators[fac] = [];

  // Add the event data to the relevant array
  var eData = { name: name, time: time, loc: loc };
  emailInfo.instructors[ins].push(eData);
  emailInfo.facilitators[fac].push(eData);
});

// Send emails based on the collected information.
[ {r: emailInfo.instructors,  f: getFormattedInstructorMessage_},
  {r: emailInfo.facilitators, f: getFormattedFacilitatorMessage_} 
].forEach( function (o) {
  var formatFunc = o.f;
  for (var email in o.r) {
    var recipientName = getNameFromEmailSomehow_(email);
    var msg = formatFunc(recipientName, o.r[email]);
    MailApp.sendEmail(email, "Subject", msg);
  }
});

以上假设您还编写了一些后台功能:

  • 功能getNameFromEmailSomehow_,用于将电子邮件转换为名称(例如LDAP查询,或者您已经在该行中写下了讲师/主持人的姓名,并将其包含在eData
  • 两个格式化功能getFormattedInstructorMessage_getFormattedFaciliatorMessage_,用于接收收件人名称和该日即将发生的所有事件的列表,并使用对象列表制作电子邮件文本。您可以返回HTML(并使用MailApp.sendEmail的其他版本),也可以仅返回纯文本。

一个绝对原始的示例格式化程序:

function basicFormattedMessage_(to, events) {
  var msg = "Hello " + to + ",\n";
  msg += "You have " + events.length + " events tomorrow:\n";
  events.forEach(function (e) {
    msg += "\nName: " + e.name;
    msg += "\nTime: " + e.time;
    msg += "\nRoom: " + e.loc;
    msg += "\n";
  });
  return msg;
}