54 lines
2.2 KiB
TypeScript
54 lines
2.2 KiB
TypeScript
/**
|
|
* Booking mailer — SMTP transport for booking response emails sent from admin.
|
|
*
|
|
* Env vars (falls back to SMTP_* contact-form vars if BOOKING_* not set):
|
|
* BOOKING_SMTP_USER — SMTP username (default: SMTP_USER)
|
|
* BOOKING_SMTP_PASS — SMTP password (default: SMTP_PASS)
|
|
* BOOKING_FROM_EMAIL — Sender address (default: Quinn Bookings <booking@transquinnftw.com>)
|
|
* BOOKING_NOTIFY_EMAIL — Provider notification address (default: TransQuinnFTW@pm.me)
|
|
* SMTP_HOST — SMTP server host (default: localhost)
|
|
* SMTP_PORT — SMTP port (default: 587)
|
|
* SMTP_REQUIRE_TLS — Enforce STARTTLS; set "false" for dev (default: true)
|
|
*/
|
|
|
|
import nodemailer from 'nodemailer';
|
|
import type { Transporter } from 'nodemailer';
|
|
|
|
export const BOOKING_FROM = process.env['BOOKING_FROM_EMAIL'] ?? 'Quinn Bookings <booking@transquinnftw.com>';
|
|
export const BOOKING_NOTIFY = process.env['BOOKING_NOTIFY_EMAIL'] ?? 'TransQuinnFTW@pm.me';
|
|
|
|
const REQUIRE_TLS = process.env['SMTP_REQUIRE_TLS'] !== 'false';
|
|
|
|
let cachedTransport: Transporter | null = null;
|
|
|
|
export function getBookingTransport(): Transporter {
|
|
if (cachedTransport) return cachedTransport;
|
|
const user = process.env['BOOKING_SMTP_USER'] ?? process.env['SMTP_USER'];
|
|
const pass = process.env['BOOKING_SMTP_PASS'] ?? process.env['SMTP_PASS'] ?? '';
|
|
cachedTransport = nodemailer.createTransport({
|
|
host: process.env['SMTP_HOST'] ?? 'localhost',
|
|
port: parseInt(process.env['SMTP_PORT'] ?? '587', 10),
|
|
secure: false, // STARTTLS on 587
|
|
auth: user ? { user, pass } : undefined,
|
|
requireTLS: REQUIRE_TLS,
|
|
tls: {
|
|
rejectUnauthorized: REQUIRE_TLS,
|
|
minVersion: 'TLSv1.2' as const,
|
|
},
|
|
});
|
|
return cachedTransport;
|
|
}
|
|
|
|
export function escapeHtml(str: string): string {
|
|
return str
|
|
.replace(/&/g, '&')
|
|
.replace(/</g, '<')
|
|
.replace(/>/g, '>')
|
|
.replace(/"/g, '"')
|
|
.replace(/'/g, ''');
|
|
}
|
|
|
|
/** Replace {{key}} tokens in a template string with the values map. */
|
|
export function interpolate(template: string, vars: Record<string, string>): string {
|
|
return template.replace(/\{\{(\w+)\}\}/g, (_, key: string) => vars[key] ?? '');
|
|
}
|