Vue i18n ist die Standard-Lösung für Internationalisierung (i18n) in Vue.js Anwendungen. In diesem Guide zeige ich dir, wie du Vue i18n in Vue 3, Nuxt 3 und mit verschiedenen Build-Tools einrichtest.
Was ist Vue i18n?#
Vue i18n ist ein Plugin, das von Intlify entwickelt wird und dir ermöglicht, deine Vue-Anwendung mehrsprachig zu gestalten. Es unterstützt:
- Vue 2 und Vue 3
- Composition API und Options API
- Pluralisierung
- Datums- und Zahlenformatierung
- Lazy Loading von Übersetzungen
Vue 3 i18n Installation#
Mit npm/yarn installieren#
npm install vue-i18n@9
# oder
yarn add vue-i18n@9
Basis-Setup in Vue 3#
// src/i18n/index.js
import { createI18n } from 'vue-i18n'
const messages = {
de: {
welcome: 'Willkommen',
greeting: 'Hallo, {name}!'
},
en: {
welcome: 'Welcome',
greeting: 'Hello, {name}!'
}
}
const i18n = createI18n({
locale: 'de',
fallbackLocale: 'en',
messages
})
export default i18n
// main.js
import { createApp } from 'vue'
import App from './App.vue'
import i18n from './i18n'
const app = createApp(App)
app.use(i18n)
app.mount('#app')
Vue i18n im Template verwenden#
Die $t Funktion#
<template>
<h1>{{ $t('welcome') }}</h1>
<p>{{ $t('greeting', { name: 'Max' }) }}</p>
</template>
Mit Composition API (useI18n)#
<script setup>
import { useI18n } from 'vue-i18n'
const { t, locale } = useI18n()
// Sprache wechseln
function changeLanguage(lang) {
locale.value = lang
}
</script>
<template>
<h1>{{ t('welcome') }}</h1>
<button @click="changeLanguage('en')">English</button>
<button @click="changeLanguage('de')">Deutsch</button>
</template>
Vue i18n Change Language#
Um die Sprache dynamisch zu wechseln, gibt es mehrere Ansätze:
Global#
import i18n from '@/i18n'
// Sprache ändern
i18n.global.locale.value = 'en'
In einer Komponente#
<script setup>
import { useI18n } from 'vue-i18n'
const { locale, availableLocales } = useI18n()
</script>
<template>
<select v-model="locale">
<option v-for="lang in availableLocales" :key="lang" :value="lang">
{{ lang }}
</option>
</select>
</template>
Nuxt i18n / Nuxt 3 i18n#
Für Nuxt-Projekte gibt es das offizielle @nuxtjs/i18n Modul.
Installation#
npm install @nuxtjs/i18n
Nuxt 3 Konfiguration#
// nuxt.config.ts
export default defineNuxtConfig({
modules: ['@nuxtjs/i18n'],
i18n: {
locales: [
{ code: 'de', iso: 'de-DE', file: 'de.json' },
{ code: 'en', iso: 'en-US', file: 'en.json' }
],
defaultLocale: 'de',
lazy: true,
langDir: 'locales/',
strategy: 'prefix_except_default'
}
})
Nuxt i18n mit Vue Router#
// locales/de.json
{
"home": "Startseite",
"about": "Über uns"
}
<!-- pages/index.vue -->
<script setup>
const { t } = useI18n()
const localePath = useLocalePath()
</script>
<template>
<nav>
<NuxtLink :to="localePath('/')">{{ t('home') }}</NuxtLink>
<NuxtLink :to="localePath('/about')">{{ t('about') }}</NuxtLink>
</nav>
</template>
Vue i18n mit Vite#
Vite Plugin Vue i18n#
Für bessere Performance und Build-Optimierung:
npm install @intlify/unplugin-vue-i18n
// vite.config.js
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import VueI18nPlugin from '@intlify/unplugin-vue-i18n/vite'
import { resolve } from 'path'
export default defineConfig({
plugins: [
vue(),
VueI18nPlugin({
include: resolve(__dirname, './src/locales/**')
})
]
})
Übersetze deine Vue-i18n-Dateien
@:verlinkte Keys und {benannte} Platzhalter überstehen den Hin- und Rückweg.
Übersetzungsdateien strukturieren#
Einzelne JSON-Dateien pro Sprache#
src/
locales/
de.json
en.json
fr.json
// locales/de.json
{
"nav": {
"home": "Startseite",
"products": "Produkte",
"contact": "Kontakt"
},
"auth": {
"login": "Anmelden",
"logout": "Abmelden",
"register": "Registrieren"
}
}
Lazy Loading (für große Projekte)#
// i18n/index.js
import { createI18n } from 'vue-i18n'
const i18n = createI18n({
locale: 'de',
fallbackLocale: 'en',
messages: {}
})
export async function loadLocaleMessages(locale) {
const messages = await import(`./locales/${'${locale}'}.json`)
i18n.global.setLocaleMessage(locale, messages.default)
return messages
}
export default i18n
Vue i18n Pluralisierung#
{
"items": "keine Artikel | ein Artikel | {count} Artikel"
}
<template>
<p>{{ $t('items', 0) }}</p> <!-- keine Artikel -->
<p>{{ $t('items', 1) }}</p> <!-- ein Artikel -->
<p>{{ $t('items', 5) }}</p> <!-- 5 Artikel -->
</template>
Vue i18n mit Vue Router#
Für mehrsprachige URLs:
// router/index.js
import { createRouter, createWebHistory } from 'vue-router'
import i18n from '@/i18n'
const routes = [
{
path: '/:locale',
children: [
{ path: '', name: 'home', component: () => import('@/views/Home.vue') },
{ path: 'about', name: 'about', component: () => import('@/views/About.vue') }
]
}
]
const router = createRouter({
history: createWebHistory(),
routes
})
router.beforeEach((to, from, next) => {
const locale = to.params.locale
if (locale && i18n.global.availableLocales.includes(locale)) {
i18n.global.locale.value = locale
}
next()
})
export default router
Vue i18next als Alternative#
Wenn du bereits i18next in anderen Projekten nutzt:
npm install i18next i18next-vue
import i18next from 'i18next'
import I18NextVue from 'i18next-vue'
i18next.init({
lng: 'de',
resources: {
de: { translation: { welcome: 'Willkommen' } }
}
})
app.use(I18NextVue, { i18next })
Best Practices#
1. Übersetzungsschlüssel organisieren#
{
"common": {
"save": "Speichern",
"cancel": "Abbrechen"
},
"pages": {
"home": {
"title": "Startseite"
}
}
}
2. TypeScript Support#
// i18n.d.ts
import { DefineLocaleMessage } from 'vue-i18n'
import de from './locales/de.json'
type MessageSchema = typeof de
declare module 'vue-i18n' {
export interface DefineLocaleMessage extends MessageSchema {}
}
3. SEO für mehrsprachige Seiten#
<script setup>
import { useI18n } from 'vue-i18n'
import { useHead } from '@vueuse/head'
const { t, locale } = useI18n()
useHead({
htmlAttrs: { lang: locale.value },
title: t('pages.home.title'),
link: [
{ rel: 'alternate', hreflang: 'de', href: 'https://example.com/de/' },
{ rel: 'alternate', hreflang: 'en', href: 'https://example.com/en/' }
]
})
</script>
Häufig gestellte Fragen (FAQ)#
Wie wechsle ich die Sprache in Vue i18n?#
Mit locale.value = 'en' in der Composition API oder i18n.global.locale.value = 'en' global. Beide Methoden aktualisieren die Sprache reaktiv in der gesamten Anwendung.
Was ist der Unterschied zwischen Vue i18n und i18next?#
Vue i18n ist speziell für Vue entwickelt und bietet tiefe Integration mit Vue-Features wie Composition API und Reactivity. i18next ist framework-agnostisch und kann in React, Angular oder Vanilla JS verwendet werden. Für reine Vue-Projekte ist Vue i18n die bessere Wahl.
Unterstützt Vue i18n TypeScript?#
Ja, Vue i18n bietet volle TypeScript-Unterstützung. Mit dem DefineLocaleMessage Interface kannst du typisierte Übersetzungsschlüssel definieren, die Autovervollständigung und Typprüfung ermöglichen.
Wie lade ich Übersetzungen dynamisch (Lazy Loading)?#
Mit dynamischen Imports: const messages = await import('./locales/' + locale + '.json') und dann i18n.global.setLocaleMessage(locale, messages.default). Dies reduziert die initiale Bundle-Größe erheblich.
Fazit#
Vue i18n ist die beste Wahl für Internationalisierung in Vue.js Projekten. Mit Vue 3 und der Composition API ist das Setup noch einfacher geworden. Für Nuxt-Projekte bietet @nuxtjs/i18n eine nahtlose Integration mit zusätzlichen Features wie automatischem Routing.
Beim Übersetzen deiner Vue i18n JSON-Dateien ist es wichtig, dass Platzhalter wie {name} und ICU-Format erhalten bleiben. shipglobal.dev handhabt Vue i18n Dateiformate automatisch und bewahrt alle Variablen-Syntax.
Verwandte Artikel#
- Vue i18n in JavaScript - Übersetzen außerhalb von Templates
- React i18next Placeholder Guide
- Android i18n JSON Guide