Node.js7 min read

Sending Emails with Nodemailer

Send emails from Node.js using Nodemailer. Learn SMTP configuration, templates, and attachments.

Sarah Chen
December 19, 2025
0.0k0

Sending Emails with Nodemailer

Nodemailer is the standard for sending emails from Node.js.

Setup

```bash npm install nodemailer ```

Basic Configuration

```javascript const nodemailer = require('nodemailer');

const transporter = nodemailer.createTransport({ host: 'smtp.gmail.com', port: 587, secure: false, // true for 465, false for other ports auth: { user: process.env.EMAIL_USER, pass: process.env.EMAIL_PASS // App password, not regular password } }); ```

Send Basic Email

```javascript async function sendEmail() { const info = await transporter.sendMail({ from: '"My App" <noreply@myapp.com>', to: 'user@example.com', subject: 'Hello!', text: 'Plain text version', html: '<h1>Hello!</h1><p>This is HTML content.</p>' }); console.log('Message sent:', info.messageId); } ```

Multiple Recipients

```javascript await transporter.sendMail({ from: '"My App" <noreply@myapp.com>', to: 'user1@example.com, user2@example.com', cc: 'cc@example.com', bcc: 'bcc@example.com', subject: 'Team Update', html: '<p>Hello team!</p>' }); ```

Attachments

```javascript await transporter.sendMail({ from: '"My App" <noreply@myapp.com>', to: 'user@example.com', subject: 'Report', text: 'Please find the report attached.', attachments: [ { filename: 'report.pdf', path: './reports/monthly.pdf' }, { filename: 'image.png', content: Buffer.from('...'), // Or file buffer }, { filename: 'data.json', content: JSON.stringify({ data: 'value' }) } ] }); ```

HTML Templates

```javascript function welcomeEmail(name) { return ` <!DOCTYPE html> <html> <head> <style> .container { font-family: Arial, sans-serif; padding: 20px; } .header { color: #333; } .button { background: #007bff; color: white; padding: 10px 20px; text-decoration: none; border-radius: 5px; } </style> </head> <body> <div class="container"> <h1 class="header">Welcome, ${name}!</h1> <p>Thanks for signing up.</p> <a href="https://myapp.com/verify" class="button">Verify Email</a> </div> </body> </html> `; }

await transporter.sendMail({ to: 'user@example.com', subject: 'Welcome!', html: welcomeEmail('Alice') }); ```

Email Service Class

```javascript class EmailService { constructor() { this.transporter = nodemailer.createTransport({ host: process.env.SMTP_HOST, port: process.env.SMTP_PORT, auth: { user: process.env.SMTP_USER, pass: process.env.SMTP_PASS } }); } async send(to, subject, html) { return this.transporter.sendMail({ from: process.env.FROM_EMAIL, to, subject, html }); } async sendWelcome(user) { return this.send( user.email, 'Welcome!', welcomeEmail(user.name) ); } async sendPasswordReset(email, resetUrl) { return this.send( email, 'Password Reset', `<p>Click <a href="${resetUrl}">here</a> to reset your password.</p>` ); } }

module.exports = new EmailService(); ```

Testing with Ethereal

```javascript // For development - catches emails without sending async function createTestAccount() { const testAccount = await nodemailer.createTestAccount(); return nodemailer.createTransport({ host: 'smtp.ethereal.email', port: 587, auth: { user: testAccount.user, pass: testAccount.pass } }); }

const info = await transporter.sendMail({...}); console.log('Preview URL:', nodemailer.getTestMessageUrl(info)); ```

Key Takeaway

Nodemailer sends emails via SMTP. Configure with your email provider's settings, use app passwords for Gmail. Create reusable templates and a service class for clean code. Use Ethereal for testing.

#Node.js#Email#Nodemailer#Intermediate