<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: balavishnuvj</title>
    <description>The latest articles on DEV Community by balavishnuvj (@balavishnuvj).</description>
    <link>https://dev.to/balavishnuvj</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F344452%2F4b154ced-d1dc-453b-b568-d9cad6340d93.png</url>
      <title>DEV Community: balavishnuvj</title>
      <link>https://dev.to/balavishnuvj</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/balavishnuvj"/>
    <language>en</language>
    <item>
      <title>How to send dynamically created PDF as attachment with Amazon SES on Node JS</title>
      <dc:creator>balavishnuvj</dc:creator>
      <pubDate>Mon, 02 Mar 2020 17:46:37 +0000</pubDate>
      <link>https://dev.to/balavishnuvj/how-to-send-dynamically-created-pdf-as-attachment-with-amazon-ses-on-node-js-2l72</link>
      <guid>https://dev.to/balavishnuvj/how-to-send-dynamically-created-pdf-as-attachment-with-amazon-ses-on-node-js-2l72</guid>
      <description>&lt;p&gt;To send an email with dynamically created PDF as an attachment. There are two steps.&lt;/p&gt;

&lt;p&gt;Step 1: Dynamically create a pdf&lt;br&gt;
Step 2: Send this pdf as an attachment&lt;/p&gt;
&lt;h3&gt;
  
  
  Libraries used.
&lt;/h3&gt;


&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;npm install aws-sdk ejs nodemailer html-pdf
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;


&lt;p&gt;Why do we need all these libraries?&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.npmjs.com/package/aws-sdk"&gt;aws-sdk&lt;/a&gt; is used for sending the email.&lt;br&gt;
&lt;a href="https://www.npmjs.com/package/nodemailer"&gt;nodemailer&lt;/a&gt; is used to create an email with an attachment.&lt;br&gt;
&lt;a href="https://www.npmjs.com/package/ejs"&gt;ejs&lt;/a&gt; is the templating engine used for create dynamic HTML.&lt;br&gt;
&lt;a href="https://www.npmjs.com/package/html-pdf"&gt;html-pdf&lt;/a&gt; is used to convert HTML to pdf.&lt;/p&gt;
&lt;h3&gt;
  
  
  Step 1: Dynamically create a pdf
&lt;/h3&gt;

&lt;p&gt;Let us create a template for html.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;!-- template.ejs --!&amp;gt;

&amp;lt;!DOCTYPE html&amp;gt;

&amp;lt;html&amp;gt;
  &amp;lt;head&amp;gt;
    &amp;lt;title&amp;gt;My Table&amp;lt;/title&amp;gt;
  &amp;lt;/head&amp;gt;
  &amp;lt;body&amp;gt;
    &amp;lt;h1&amp;gt;Table&amp;lt;/h1&amp;gt;
    &amp;lt;table style="width: 100%;"&amp;gt;
      &amp;lt;tr&amp;gt;
        &amp;lt;th&amp;gt;Qty.&amp;lt;/th&amp;gt;
        &amp;lt;th&amp;gt;Unit Price&amp;lt;/th&amp;gt;
        &amp;lt;th&amp;gt;Total Cost&amp;lt;/th&amp;gt;
      &amp;lt;/tr&amp;gt;
      &amp;lt;% if (products.length) { %&amp;gt;
      &amp;lt;tr&amp;gt;
        &amp;lt;% products.forEach(function (product) { %&amp;gt;
        &amp;lt;td id="quantity"&amp;gt;&amp;lt;%= product.quantity %&amp;gt;&amp;lt;/td&amp;gt;
        &amp;lt;td id="unitPrice"&amp;gt;&amp;lt;%= product.unitPrice %&amp;gt;&amp;lt;/td&amp;gt;
        &amp;lt;td id="totalPrice"&amp;gt;&amp;lt;%= product.totalPrice %&amp;gt;&amp;lt;/td&amp;gt;
        &amp;lt;% }) %&amp;gt;
      &amp;lt;/tr&amp;gt;
      &amp;lt;% } %&amp;gt;
    &amp;lt;/table&amp;gt;
  &amp;lt;/body&amp;gt;
&amp;lt;/html&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Now let's use this template to generate the HTML. I'm not writing the file to disk. Instead, keep the file in memory and pass it on.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import ejs from 'ejs';
import htmlPdf from 'html-pdf';

export async function htmlToPdfBuffer(pathname, params) {
  const html = await ejs.renderFile(pathname, params);
  return new Promise((resolve, reject) =&amp;gt; {
    htmlPdf.create(html).toBuffer((err, buffer) =&amp;gt; {
      if (err) {
        reject(err);
      } else {
        resolve(buffer);
      }
    });
  });
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Usage would be like&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;const fileBuffer = await htmlToPdfBuffer('template.ejs', {
  products: [{ quantity: 2, unitPrice: 10, totalPrice: 20 }]
});

&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Now, &lt;code&gt;fileBuffer&lt;/code&gt; is the dynamic pdf file which has to be sent. You could use &lt;code&gt;toFile&lt;/code&gt; method of &lt;code&gt;html-pdf&lt;/code&gt; to write this to disk.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 2: Send this pdf as an attachment
&lt;/h3&gt;

&lt;p&gt;We could use &lt;code&gt;aws-sdk&lt;/code&gt;  directly for &lt;a href="https://docs.aws.amazon.com/ses/latest/DeveloperGuide/send-email-raw.html"&gt;attachments&lt;/a&gt;. You would have to do MIME encoding manually, which is a bit tedious.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;export function sendEmailWithAttachments(
  subject,
  html,
  toAddresses,
  attachments
) {
  const ses = new AWS.SES();
  const transporter = nodemailer.createTransport({
    SES: ses
  });
  const mailOptions = {
    from: "from@example.com",
    subject,
    html,
    to: toAddresses,
    attachments
  };
  transporter.sendMail(mailOptions, (err, data) =&amp;gt; {

  });
}

&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;h3&gt;
  
  
  Final usage
&lt;/h3&gt;



&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;const fileBuffer = await htmlToPdfBuffer("template.ejs", {
  products: [{ quantity: 2, unitPrice: 10, totalPrice: 20 }]
});

sendEmailWithAttachments(
  "This is test subject",
  "&amp;lt;p&amp;gt;This email contails attachment&amp;lt;/p&amp;gt;",
  ["to@example.com"],
  { filename: "attachment.pdf", content: fileBuffer }
);

&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



</description>
      <category>node</category>
      <category>aws</category>
    </item>
  </channel>
</rss>
