SES Mail Protector – Documentation
1. Overview
The SES Mail System is a Node.js library built on top of AWS SES (Simple Email Service). It provides:
- Email sending
- Bounce & complaint handling via AWS SNS
- Suppression list management with MongoDB
- Automatic admin notifications on issues
This package is designed for scalable transactional email systems where compliance and deliverability are critical.
Note: After installing and configuring package in your project, first thing you need to do is setup sns-handler for receiving bounce and complaints webhooks, Please follow point 7 all steps to do the same.
2. Installation
npm install ses-mail-protector
3. Environment Variables (.env)
AWS_ACCESS_KEY_ID=your-access-key
AWS_SECRET_ACCESS_KEY=your-secret-key
AWS_REGION=your-aws-region
# Can be 'mongodb' | 'sqldb'
DATABASE_TYPE=sqldb
# MongoDB Url
MONGO_DB_URL=mongodb+srv://user:pass@cluster/test
# SQL Details
SQL_DB_HOST=host-name
SQL_DB_NAME=db-name
SQL_DB_USER_NAME=user-name
SQL_DB_PASSWORD=db-password
# Can be 'mysql' | 'postgres' | 'sqlite' | 'mariadb' | 'mssql'
SQL_DB_DIALECT=mysql
ADMIN_EMAIL=admin@example.com
SES_FROM_ADDRESS=example@example.com
4. Features
- ✅ Send Emails using AWS SES
- ✅ Body size validation
- ✅ Suppression List (bounces, complaints)
- ✅ SNS Webhook Handling for delivery, bounces, complaints
- ✅ Admin Notifications on high bounce/complaint rate
5. Usage
const { sendMail } = require("ses-mail-protector");
let res = await sendMail({
to: "to-mail@example.com",
subject: "Test Email",
body: "Hello from SES!",
from: "from-mail@example.com",
});
if (res.success) {
res.send("Email sent!");
}
6. SNS Handler
const { handleSnsNotification } = require("ses-mail-protector");
app.post("/sns-handler", express.text({ type: "*/*" }), async (req, res) => {
try {
await handleSnsNotification(req.body);
res.sendStatus(200);
} catch (err) {
console.error("SNS handling error:", err);
res.sendStatus(500);
}
});
Note: Add
https://yourdomain.com/sns-handler
webhook in your AWS SES account.
7. AWS SES, SNS Webhook Setup Steps
Step 1: Create SNS Topics
- Log in to AWS Management Console and search for SNS.
- Click Topics → Create topic.
- Choose Standard topic.
- Enter a descriptive name for your topic, e.g.,
ses-bounce-topic
orses-complaint-topic
. - Click Create topic.
- Copy the Topic ARN, you will need it when configuring SES.
Step 2: Create SNS Subscriptions
- In the SNS Console, select your topic and click Create subscription.
- Protocol: Choose HTTPS.
- Endpoint: Enter your webhook URL, e.g.,
https://yourdomain.com/sns-handler
. - Click Create subscription.
- AWS will send a confirmation message to your endpoint.
- Your webhook must respond with the token from the message to confirm the subscription.
Step 3: Configure SES to Use SNS Topics
- Go to the SES Console → Domains → Verified Domains.
- Select your domain and click Notifications.
- Under Feedback Notifications:
- Bounce: Select your
ses-bounce-topic
. - Complaint: Select your
ses-complaint-topic
. - Delivery (optional): Select a delivery topic if needed.
- Bounce: Select your
- Click Save Configurations.
Step 4: Test Your Setup
- Send a test email using SES to a non-existent email to trigger a bounce.
- Send a test email to a complaining mailbox (or SES test addresses) to trigger a complaint.
- Verify that your
/sns-handler
receives the JSON payload correctly.
Step 5: Handle Subscription Confirmation (Optional)
Your webhook must handle the SubscribeURL
sent by AWS SNS upon subscription creation. Example JSON from SNS:
{
"Type": "SubscriptionConfirmation",
"MessageId": "...",
"Token": "...",
"SubscribeURL": "https://sns.aws.amazon.com/?Action=ConfirmSubscription&...",
"Timestamp": "...",
"TopicArn": "arn:aws:sns:region:account-id:topic-name",
"SignatureVersion": "1",
"Signature": "...",
"SigningCertURL": "..."
}
Your server should either:
- Visit the
SubscribeURL
automatically, or - Return HTTP 200 and confirm manually in the AWS console.
8. Example Full Flow
const express = require("express");
const { sendMail, handleSnsNotification } = require("ses-mail-protector");
const app = express();
app.use(express.json());
app.get("/sendMail", async (req, res) => {
let res = await sendMail({
to: "to-mail@example.com",
subject: "Test Email",
body: "Hello from SES!",
from: "from-mail@example.com",
});
if (res.success) {
res.send("Email sent!");
}
});
app.post("/sns-handler", express.text({ type: "*/*" }), async (req, res) => {
await handleSnsNotification(req.body);
res.sendStatus(200);
});
app.listen(3000, () => console.log("Server running on port 3000"));