Lightweight SMTP sink built with Bun. Accepts incoming mail (SMTP), stores messages in SQLite, and exposes an HTTP JSON API for inspection.
- SMTP server: EHLO/HELO, MAIL FROM, RCPT TO, DATA, RSET, NOOP, QUIT
- SQLite storage of full RFC822 message + parsed headers
- HTTP JSON API for listing, reading, marking read, and deleting
- Configurable ports, size limits, and DB path
bun install
bun run dev- SMTP: 127.0.0.1:2525
- HTTP: 127.0.0.1:3000
Override where the DB file is written (default is ./mail.db):
DB_PATH=/absolute/path/mail.db bun run devpython3 - <<'PY'
import socket, time
s=socket.socket(); s.connect(('127.0.0.1',2525))
s.recv(4096)
for line in [
'HELO test\r\n',
'MAIL FROM:<alice@example.com>\r\n',
'RCPT TO:<bob@example.com>\r\n',
'DATA\r\n',
'Subject: Hello\r\n',
'\r\n',
'Body here.\r\n',
'.\r\n',
'QUIT\r\n']:
s.sendall(line.encode()); time.sleep(0.05)
try: print(s.recv(4096).decode(), end='')
except: pass
s.close()
PYList messages:
curl -s http://127.0.0.1:3000/api/messages | jq .SMTP_HOST(default127.0.0.1)SMTP_PORT(default2525)HTTP_HOST(default127.0.0.1)HTTP_PORT(default3000)MAX_MESSAGE_SIZE(default10485760)DB_PATH(defaultmail.db)CORS_ORIGIN(default*)
See openapi.json.
Endpoints:
- GET
/api/messages(optional?q=...) - GET
/api/messages/:id - POST
/api/messages/:id/readbody:{ "read": true } - DELETE
/api/messages/:id - DELETE
/api/messages
Build and run:
docker build -t bun-mail-server .
docker run --rm \
-p 3000:3000 -p 2525:2525 \
-v $(pwd)/data:/data \
-e DB_PATH=/data/mail.db \
--name bun-mail bun-mail-serverBind the DB to a host path (example):
sudo mkdir -p /home/homelab/databinds/mailtester
docker run --rm \
-p 3000:3000 -p 2525:2525 \
-v /home/homelab/databinds/mailtester:/data \
-e DB_PATH=/data/mail.db \
--name bun-mail bun-mail-serverENV overrides inside container (defaults shown):
docker run --rm \
-e SMTP_HOST=0.0.0.0 -e SMTP_PORT=2525 \
-e HTTP_HOST=0.0.0.0 -e HTTP_PORT=3000 \
-e DB_PATH=/data/mail.db -e MAX_MESSAGE_SIZE=10485760 \
-p 3000:3000 -p 2525:2525 -v $(pwd)/data:/data \
bun-mail-serverservices:
mail:
image: bun-mail-server
container_name: bun-mail
ports:
- "3000:3000"
- "2525:2525"
environment:
DB_PATH: /data/mail.db
volumes:
- ./data:/dataSee plan.md.