EmailSender extensibility
Implement a script-based email provider by registering `runtime.scriptable.emailEngine.SendEmail`.
What this is
Use this extensibility point to have The Wallet Crew send emails through a provider under tenant control. This is a script-level integration. It keeps The Wallet Crew templates and rendering logic, while delegating the final “send” to dedicated API calls.
This design separates rendering from delivery. That makes the email layer easier to test and easier to swap. It also keeps culture handling explicit, because the caller decides which cultures exist and how templates are resolved.
How SendEmail works
The platform calls runtime.scriptable.emailEngine.SendEmail when it needs to send an email and the email provider is set to script. The function receives the recipient address, the template name, a data payload, and the list of supported cultures.
The last parameter, buildEmail, is a callback supplied by the platform. The provider implementation calls it to obtain the final rendered content. That callback returns an object with a Subject and a Body. Once that payload is available, the script is responsible for sending it.
Reference implementation (signature)
/**
* @typedef {Object} EmailData
* @property {string} Subject - Rendered subject line.
* @property {string} Body - Rendered body content.
*/
/**
* Send an email using the provided template name and data.
* The caller supplies the supported cultures and a callback
* to build the rendered email content.
*
* @param {string} recipient - Target email address.
* @param {string} emailTemplate - Template name to render.
* @param {Object.<string, any>} data - Template data passed to the script.
* @param {string[]} cultures - Available culture names from the culture provider.
* @param {(templateName: string) => Promise<EmailData>} buildEmail
* Callback that returns the final rendered email content.
*
* @returns {Promise<void>}
*/
async function sendEmail(recipient, emailTemplate, data, cultures, buildEmail){
// call any API to send email
}
export default function(context) {
context.register('runtime.scriptable.emailEngine', {
SendEmail: sendEmail
})
}SendEmail runs in the same runtime as any other custom connector script, so fetch, getSecret, and the rest of the approved globals are available for the actual delivery call. See Custom connectors → Runtime constraints for the full list and the 5-second execution limit that applies here as well.
Enable the script email provider
Switching to the script email provider is a configuration change. It tells The Wallet Crew to call the tenant SendEmail implementation for outgoing emails.
Template and culture notes
Email templates are loaded from the paths listed under resources. Keep this aligned with where the HTML templates live, because the rendering callback uses those templates.
Culture handling is part of the contract. The platform passes a cultures array, but the provider implementation decides how to use it. In practice, most setups either pick a single culture per recipient or fall back to a default culture when no specific template exists.
Troubleshooting
If emails stop sending after enabling the script provider, start by confirming that /server/emails.yml is valid YAML and saved in the right tenant. Then confirm the script is actually registered under runtime.scriptable.emailEngine and exports SendEmail.
For provider-side errors, log the template name and culture choices, but avoid logging full rendered bodies. Email content can contain personal data.
FAQ
Last updated

