import Handlebars from "handlebars"; import type { Transporter } from "nodemailer"; import nodemailer from "nodemailer"; import type Mail from "nodemailer/lib/mailer/index.js"; import type { Address } from "nodemailer/lib/mailer/index.js"; import type SMTPTransport from "nodemailer/lib/smtp-transport/index.js"; import hbs from "nodemailer-express-handlebars"; import path from "path"; import { fileURLToPath } from "url"; import { promisify } from "util"; import { db } from "../../../../database/dbclient.js"; import { settings } from "../../../../database/schema/settings.js"; import { tryCatch } from "../../../globalUtils/tryCatch.js"; import { installed } from "../../../index.js"; import { createLog } from "../../logger/logger.js"; interface HandlebarsMailOptions extends Mail.Options { template: string; context: Record; // Use a generic object for context } interface EmailData { email: string; subject: string; template: string; context: []; } export const sendEmail = async (data: any): Promise => { if (!installed) { createLog("error", "notify", "notify", "server not installed."); return; } let transporter: Transporter; let fromEmail: string | Address; const { data: settingData, error: settingError } = await tryCatch( db.select().from(settings), ); if (settingError) { return { success: false, message: "There was an error getting the settings.", settingError, }; } // get the plantToken const server = settingData.filter((n) => n.name === "server"); if ( server[0].value === "localhostx" && process.env.EMAIL_USER && process.env.EMAIL_PASSWORD ) { transporter = nodemailer.createTransport({ service: "gmail", host: "smtp.gmail.com", port: 465, auth: { user: process.env.EMAIL_USER, pass: process.env.EMAIL_PASSWORD, }, //debug: true, }); // update the from email fromEmail = process.env.EMAIL_USER; } else { // convert to the correct plant token. const plantToken = settingData.filter((s) => s.name === "plantToken"); let host = `${plantToken[0].value}-smtp.alpla.net`; const testServers = ["test1", "test2", "test3"]; if (testServers.includes(plantToken[0].value)) { host = "USMCD1-smtp.alpla.net"; } if (plantToken[0].value === "usiow2") { host = "USIOW1-smtp.alpla.net"; } transporter = nodemailer.createTransport({ host: host, port: 25, rejectUnauthorized: false, //secure: false, // auth: { // user: "alplaprod", // pass: "obelix", // }, debug: true, } as SMTPTransport.Options); // update the from email fromEmail = `donotreply@alpla.com`; } // creating the handlbar options const viewPath = path.resolve( path.dirname(fileURLToPath(import.meta.url)), "../utils/views/", ); const handlebarOptions = { viewEngine: { extname: ".hbs", //layoutsDir: path.resolve(viewPath, "layouts"), // Path to layouts directory defaultLayout: "", // Specify the default layout partialsDir: viewPath, }, viewPath: viewPath, extName: ".hbs", // File extension for Handlebars templates }; transporter.use("compile", hbs(handlebarOptions)); const mailOptions: HandlebarsMailOptions = { from: fromEmail, to: data.email, subject: data.subject, //text: "You will have a reset token here and only have 30min to click the link before it expires.", //html: emailTemplate("BlakesTest", "This is an example with css"), template: data.template, // Name of the Handlebars template (e.g., 'welcome.hbs') context: data.context, }; // now verify and send the email const sendMailPromise = promisify(transporter.sendMail).bind(transporter); try { // Send email and await the result const info = await sendMailPromise(mailOptions); createLog( "info", "notification", "system", `Email was sent to: ${data.email}`, ); return { success: true, message: "Email sent.", data: info }; } catch (err) { console.log(err); createLog( "error", "notification", "system", `Error sending Email: ${JSON.stringify(err)}`, ); return { success: false, message: "Error sending email.", error: err }; } };