Home > OS >  Send email of specific cells as PDF
Send email of specific cells as PDF

Time:07-31

I've successfully learnt through this site how to send a sheet as a PDF attached via google sheets. What I'd now like to do is slightly expand that a bit.

I want to select a constant specific range that will export, along with the last added row within a column range.

J1:S1 to export every time. then the newest row from J2:S2 onwards.

I like to have these two ranges combined, with the constant range (J1:S1) always being on top.

I'm not entirely sure if this is possible as a PDF or if it may need to be a HTML table. I can work with either atm.

I really not sure where to start here, so would appreciate suggestions.

Thank you!

enter image description here

In the example above, the titles remain on every email / PDF. But each newest edition to the rows below is added to the PDF. So in the example above the row with the 2's would be added.

var ss = SpreadsheetApp.getActiveSpreadsheet();

function sendReport() {
  var sheetTabNameToGet = "Form response master";
  var range = "J1:S1";
  var pdfBlob = exportRangeToPDf(range, sheetTabNameToGet);
  var message = {
    to: "[email protected]",
    subject: "Monthly sales report",
    body: "Hi team,\n\nPlease find the monthly report attached.\n\nThank you,\nBob",
    name: "Bob",
    attachments: [pdfBlob.setName("Monthly sales report")]
  }
  MailApp.sendEmail(message);
}


function exportRangeToPDf(range, sheetTabNameToGet) {
  var blob,exportUrl,options,pdfFile,response,sheetTabId,ssID,url_base;
  ssID = ss.getId();
  sh = ss.getSheetByName(sheetTabNameToGet);
  sheetTabId = sh.getSheetId();
  url_base = ss.getUrl().replace(/edit$/,'');
  exportUrl = url_base   'export?exportFormat=pdf&format=pdf'  
    
    '&gid='   sheetTabId   '&id='   ssID  
      '&range='   range   
        '&size=A4'       // paper size
          '&portrait=false'     // orientation, false for landscape
            '&fitw=true'         // fit to width, false for actual size
              '&sheetnames=true&printtitle=false&pagenumbers=true'   //hide optional headers and footers
                '&gridlines=false'   // hide gridlines
                  '&fzr=false';       // do not repeat row headers (frozen rows) on each page
  
  options = {
    headers: {
      'Authorization': 'Bearer '    ScriptApp.getOAuthToken(),
    }
  }
  options.muteHttpExceptions = true;//Make sure this is always set
  response = UrlFetchApp.fetch(exportUrl, options);
  if (response.getResponseCode() !== 200) {
    console.log("Error exporting Sheet to PDF!  Response Code: "   response.getResponseCode());
    return;
    
  }  
  blob = response.getBlob();
  return blob;
}

CodePudding user response:

If the last response is always a last row, you can remove all the rows between the header and the last row, export the sheet in PDF, send it, and restore the sheet back:

function main() {
  var ss = SpreadsheetApp.getActiveSpreadsheet();
  var sh = ss.getSheetByName("Form response master");

  var formula = sh.getRange('a1').getFormula();    // take the formula from A1
  var data = sh.getDataRange().getDisplayValues(); // get data from the original table
  var table = [data.shift(), data.pop()];          // make the new table from first and last row

  sh.clearContents()                               // clear the sheet
    .getRange(1,1,table.length,table[0].length)
    .setValues(table);                             // put the new table on the sheet

  sendReport(get_blob_PDF(ss, sh));                // make PDF and send it
  sh.clearContents().getRange('a1')
   .setFormula(formula);                           // restore the sheet
}

function get_blob_PDF(ss, sh) {
  SpreadsheetApp.flush(); // update the Sheet
  var ssID = ss.getId();
  var shID = sh.getSheetId();
  var url_base = ss.getUrl().replace(/edit$/,'');
  var exportUrl = url_base   'export?exportFormat=pdf&format=pdf'  
    '&gid='   shID   '&id='   ssID  
    '&size=A4'           // paper size
    '&portrait=false'    // orientation, false for landscape
    '&fitw=true'         // fit to width, false for actual size
    '&sheetnames=true&printtitle=false&pagenumbers=true'   //hide optional headers and footers
    '&gridlines=false'   // hide gridlines
    '&fzr=false';        // do not repeat row headers (frozen rows) on each page
  
  var options = {headers: {'Authorization': 'Bearer '    ScriptApp.getOAuthToken()}}
  options.muteHttpExceptions = true; // Make sure this is always set

  var response = UrlFetchApp.fetch(exportUrl, options);
  if (response.getResponseCode() !== 200) {
    console.log("Error exporting Sheet to PDF!  Response Code: "   response.getResponseCode());
    return;  
  }

  return response.getBlob();
}

function sendReport(pdfBlob) {
  var message = {
    to: "[email protected]",
    subject: "Monthly sales report",
    body: "Hi team,\n\nPlease find the monthly report attached.\n\nThank you,\nBob",
    name: "Bob",
    attachments: [pdfBlob.setName("Monthly sales report")]
  }
  MailApp.sendEmail(message);
}

In your particular case the problem was that your sheet 'Form response master' is made via the array formula in cell 'A1'. It makes the code a little bit weird.

It does the job but, yeah, it's likely a script that takes a response object from the trigger onFormSubmit(e) would be more efficient.

Update

If there is email address in cell 'C2' you can take it if you replace the line:

sendReport(get_blob_PDF(ss, sh));

with:

var address = table[1][2]; // get the address from 'C2'
sendReport(get_blob_PDF(ss, sh), address);

And use the address in the function sendReport() if you change these lines:

function sendReport(pdfBlob) {
  var message = {
    to: "[email protected]",

this way:

function sendReport(pdfBlob, address) {
  var message = {
    to: address,
  • Related