Internationalization (i18n)
Overview
Nuxt Email Renderer supports internationalization (i18n) when you have the @nuxtjs/i18n module installed in your project. This allows you to render email templates in different languages.
Prerequisites
To use i18n support in your email templates, you need to:
- Install
@nuxtjs/i18nin your Nuxt project - Configure
@nuxtjs/i18nin yournuxt.config.ts
Installation
npm install @nuxtjs/i18n
yarn add @nuxtjs/i18n
pnpm add @nuxtjs/i18n
bun add @nuxtjs/i18n
Configuration
Add @nuxtjs/i18n to your Nuxt config:
export default defineNuxtConfig({
modules: ["nuxt-email-renderer", "@nuxtjs/i18n"],
i18n: {
locales: [
{ code: "en", name: "English" },
{ code: "de", name: "Deutsch" },
{ code: "es", name: "Español" },
],
defaultLocale: "en",
vueI18n: "./i18n.config.ts",
},
});
Create your i18n configuration file. @nuxtjs/i18n v10 resolves vueI18n inside the i18n/ directory (restructureDir):
export default defineI18nConfig(() => ({
legacy: false,
locale: "en",
messages: {
en: {
welcome: "Welcome",
greeting: "Hello, {name}!",
message: "This is a test email",
button: "Click here",
},
de: {
welcome: "Willkommen",
greeting: "Hallo, {name}!",
message: "Dies ist eine Test-E-Mail",
button: "Hier klicken",
},
es: {
welcome: "Bienvenido",
greeting: "¡Hola, {name}!",
message: "Este es un correo electrónico de prueba",
button: "Haz clic aquí",
},
},
}));
nuxt.config.ts still works, and so does a plain object export without defineI18nConfig.When vueI18n is not used, locale messages can also be loaded from locales[].file or locales[].files. JSON, YAML, and YML files are supported, including multiple files per locale and files in Nuxt layers.
Using i18n in Email Templates
Once configured, you can use the $t function in your email templates just like you would in regular Vue components:
<script setup lang="ts">
const props = defineProps<{
name: string;
}>();
</script>
<template>
<EHtml>
<EHead />
<EBody>
<EContainer>
<EHeading>{{ $t("welcome") }}</EHeading>
<EText>{{ $t("greeting", { name: props.name }) }}</EText>
<EText>{{ $t("message") }}</EText>
<EButton href="https://example.com">
{{ $t("button") }}
</EButton>
</EContainer>
</EBody>
</EHtml>
</template>
Rendering with Different Locales
To render an email template in a specific locale, pass the locale option to the renderEmailComponent function:
export default defineEventHandler(async (event) => {
const body = await readBody(event);
// Render the email in German
const { html } = await renderEmailComponent(
"WelcomeEmail",
{ name: "Hans" },
{
locale: "de",
pretty: true,
},
);
// Send the email...
return { success: true };
});
How It Works
The module detects @nuxtjs/i18n and loads its configured messages during build time. It stores the messages and default locale in private runtime config, then creates a new i18n instance when rendering an email. Pass locale to renderEmailComponent to choose the email language; the renderer does not read the locale from the request event.
Nuxt Email Renderer does not add its copy of the messages to runtimeConfig.public.i18n. The @nuxtjs/i18n module continues to manage its own public config.
Limitations
- Build-time messages: Messages are loaded during build time, so dynamic message loading is not supported.
- Server-side only: i18n support only works when rendering emails on the server using
renderEmailComponent. - No composables: You cannot use
useI18n()or other i18n composables in email templates. Only the$tfunction is available in templates.
Example
Check out the i18n test fixture in the repository for a complete working example.