---
title: "Nuxt I18n"
description: "How to use the Nuxt OG Image module with @nuxtjs/i18n."
canonical_url: "https://nuxtseo.com/docs/og-image/integrations/i18n"
last_updated: "2026-05-09T10:30:26.904Z"
---

## Introduction

OG Image components render as [Nuxt Islands](https://nuxt.com/docs/api/components/nuxt-island) (server components), which means
`useI18n()` composables don't have automatic access to locale context or lazy-loaded messages.

This guide covers two patterns for creating localized OG images with `@nuxtjs/i18n`.

## Pattern 1: Props-based (Recommended)

The simplest approach is to resolve translations at the page level and pass them as props to your OG image component.

```vue [pages/index.vue]
<script setup lang="ts">
const { t } = useI18n()

// Pass already-translated strings as props
defineOgImage('MyOgImage', {
  title: t('og.title'),
  description: t('og.description'),
})
</script>
```

Your OG image component receives the translated strings directly:

```vue [components/OgImage/MyOgImage.vue]
<script setup lang="ts">
defineProps<{
  title: string
  description: string
}>()
</script>

<template>
  <div class="w-full h-full flex flex-col justify-center p-12 bg-white">
    <h1 class="text-6xl font-bold">
      {{ title }}
    </h1>
    <p class="text-2xl text-gray-600">
      {{ description }}
    </p>
  </div>
</template>
```

<callout color="green" icon="i-heroicons-check-circle">

This pattern is recommended because it's simple, works reliably, and keeps your OG image components reusable.

</callout>

## Pattern 2: Using useI18n with loadLocaleMessages

If you need to use `useI18n()` directly inside your OG image component (for example, to access many translation keys), you can pass the locale as a prop and use `loadLocaleMessages()` to load the messages.

```vue [pages/index.vue]
<script setup lang="ts">
const { locale } = useI18n()

// Pass locale as a prop
defineOgImage('MyOgImage', {
  locale: locale.value,
})
</script>
```

In your OG image component, load the messages for the requested locale:

```vue [components/OgImage/MyOgImage.vue]
<script setup lang="ts">
const props = defineProps<{
  locale?: string
}>()

const { t, locale, loadLocaleMessages } = useI18n()

// Load messages for the requested locale, then set it as active
if (props.locale) {
  await loadLocaleMessages(props.locale)
  locale.value = props.locale
}
</script>

<template>
  <div class="w-full h-full flex flex-col justify-center p-12 bg-white">
    <h1 class="text-6xl font-bold">
      {{ t('og.title') }}
    </h1>
    <p class="text-2xl text-gray-600">
      {{ t('og.description') }}
    </p>
  </div>
</template>
```

<callout color="blue" icon="i-heroicons-information-circle">

`@nuxtjs/i18n` provides the `loadLocaleMessages()` function. It asynchronously loads the messages for a specific locale, which is necessary because OG image components render in an isolated server context.

</callout>

## Why Direct useI18n Doesn't Work

When you use `useI18n()` in a regular page component, the i18n module:

1. Detects the locale from the URL path (e.g., `/es/about`), cookies, or headers
2. Loads the messages for that locale
3. Provides them to the composable

OG image components render as Nuxt Islands via an internal request like `/__nuxt_island/MyOgImage_abc123.json`. This request:

- Doesn't have the locale prefix in the URL
- Doesn't have the user's cookies (when fetched by social platforms)
- Doesn't have locale messages pre-loaded

This is why you need to either pass translated strings as props (Pattern 1) or explicitly load the messages (Pattern 2).

## Related Links

- [GitHub Issue #222](https://github.com/nuxt-modules/og-image/issues/222) - Original discussion about i18n support
- [nuxt-modules/i18n Discussion #3242](https://github.com/nuxt-modules/i18n/discussions/3242) - Discussion about translations in Nuxt Islands
- [@nuxtjs/i18n loadLocaleMessages](https://i18n.nuxtjs.org/docs/api/vue-i18n#loadlocalemessages) - API documentation
