Search code examples
angularfirebasegoogle-cloud-platformgoogle-cloud-functionsnodemailer

Nodemailer sends email but no email body/message is displayed


I have been bouncing around a bunch of different tutorials, the docs and on here but can't find the solution. And I know I'm missing a small piece of the puzzle.

I have built a contact form & email sender using Nodemailer, Angular & Firebase (Store - to hold email data & Functions - to trigger send on email DB being populated).

  • Now when the user fills out the form on the front end and Submits it I can see the form is populated with the relevant values and I receive a success message from my subscription.
  • The email is sent and I can see it in my Firestore DB emulator with all the relevant model fields populated.
  • Also the email is sent and I receive it my inbox but only with the emailFrom, emailTo & subject fields. I simply have "This message has no content" in the body of the email.
  • I would like to have the firstName, lastName, phone, email(form user email address) and the message body from the text field.

I assume my mailOptions config is incorrect. Unsure if I need to add html pre tags, if I need to encode/decode it, json it, etc.

import * as functions from "firebase-functions";

const admin = require("firebase-admin");
const nodemailer = require("nodemailer");
admin.initializeApp();

require('dotenv').config();

exports.sendMail = functions.firestore.document("emails/{emailId}")
    .onCreate((snap: any, context: any) => {
        const email = snap.data();
        functions.logger.log("Email Information: ", email);
        const mailTransport = nodemailer.createTransport({
            host: "smtp.gmail.com",
            port: 465, 
            secure: true, 
            service: "gmail",
            auth: {
                user: "realEmailAddress@gmail.com",
                pass: "realPassword",
            },
    });

    const mailOptions = {
        from: email.email,
        to: "dave.smith@company.co.uk",
        firstName: email.firstName,
        lastName: email.lastName,
        phone: email.phone,
        subject: email.subject,
        message: email.message,
    };

    return mailTransport.sendMail(mailOptions).then(() => {
        return console.log("Email sent");
    }).catch((error: any) => {
        return console.log("Error sending email", error);
    });
});

Firebase Logger

12:37:56
I
function[us-central1-sendMail]
{
  "firstName": "Homer ",
  "lastName": "Simpson",
  "seqNo": 1,
  "phone": "07788 44 55 66",
  "subject": "My subject is - Hi this is Homer ",
  "message": "Email Information: ",
  "email": "homer@simpson.com",
  "severity": "INFO"
}

Firestore DB email

enter image description here


Solution

  • Have a look at the possible fields of an NodeMailer email message object: Including elements like firstName, lastName or phone cannot work.

    You have to either use the text or the html elements by passing them a string corresponding to the desired body content. For example:

    Using text:

    const mailOptions = {
        from: email.email,
        to: "dave.smith@company.co.uk",
        subject: email.subject,
        text: `firstName:  ${email.firstName} - lastName: ${email.lastName}` 
    };
    

    Using html:

    const mailOptions = {
        from: email.email,
        to: "dave.smith@company.co.uk",
        subject: email.subject,
        html: `<b>Title</b><br/><br/>firstName:  ${email.firstName} <br/><br/> lastName: ${email.lastName}`
    };