Files
nf-mail-relay/README.md
T
wmj c0b8981629 Initial commit: HTTP wrapper around the existing falah-ibaas email connector
Gives Supabase Edge Functions (and anything else outside the VPS) a real,
authenticated endpoint onto the VPS's already-working internal Postfix
relay (the same one Ghost uses in production), via the falah-ibaas
EmailConnector that was fully built but never actually deployed.

Deployed live at https://nfmailrelay.falahos.my as a Docker Swarm service
on the existing Traefik network, TLS via Let's Encrypt, shared-secret
bearer auth. Built for Nur Falah's heir notification emails.
2026-08-14 08:00:28 +08:00

2.8 KiB

nf-mail-relay

Small HTTP wrapper around the existing falah-ibaas email connector (/opt/falah-ibaas/connectors/email on the Falah OS VPS), so services that can't reach the VPS's internal Postfix relay directly — like a Supabase Edge Function running on Supabase's cloud — get a real, internet-reachable, authenticated endpoint that forwards to it.

Built for Nur Falah's heir (warith) notification emails, but generic enough to reuse for anything else that needs "send an email via the VPS's existing working mail path" without provisioning a third-party provider.

Why this exists

The VPS already has a working SMTP relay — Ghost uses it in production (mail__options__host=172.17.0.1:25, no auth, internal Docker bridge only). There's also a fully-built but never-deployed EmailConnector class at /opt/falah-ibaas/connectors/email/handler.py that wraps smtplib with proper error handling. Neither was reachable from outside the VPS. This relay is the missing piece: a thin, auth-gated HTTP front door onto that connector.

Endpoints

  • GET /health — connector status + send/error metrics
  • POST /send — send an email
    • Header: X-Relay-Secret: <shared secret>
    • Body: { "to": "...", "subject": "...", "body_text": "...", "body_html": "...", "cc": "...", "bcc": "..." }

Deploy

docker build -t nf-mail-relay:latest .

docker service create \
  --name nf_mail_relay \
  --mount type=bind,source=/opt/falah-ibaas/connectors/email,target=/opt/falah-ibaas/connectors/email,readonly \
  --network falah_traefik-net \
  --constraint node.role==manager \
  --env RELAY_SECRET=<generate with: openssl rand -hex 24> \
  --env SMTP_HOST=172.17.0.1 \
  --env SMTP_PORT=25 \
  --env SMTP_FROM=notifications@falahos.my \
  --label traefik.enable=true \
  --label 'traefik.http.routers.nfmailrelay.rule=Host(`nfmailrelay.falahos.my`)' \
  --label traefik.http.routers.nfmailrelay.entrypoints=websecure \
  --label traefik.http.routers.nfmailrelay.tls=true \
  --label traefik.http.routers.nfmailrelay.tls.certresolver=letsencrypt \
  --label traefik.http.services.nfmailrelay.loadbalancer.server.port=8091 \
  nf-mail-relay:latest

Currently deployed at https://nfmailrelay.falahos.my on the Falah OS VPS (13.140.161.244), covered by the *.falahos.my wildcard DNS — no new DNS record needed.

Security notes

  • RELAY_SECRET is never committed here — it's set as a Docker service environment variable on deploy. Rotate with docker service update --env-add RELAY_SECRET=<new value> nf_mail_relay.
  • The connector directory is bind-mounted read-only — this service cannot modify falah-ibaas.
  • No auth is used against the Postfix relay itself since it's only bound to the internal Docker bridge (172.17.0.1) — this service is the actual security boundary between the public internet and that relay.