-
-
Notifications
You must be signed in to change notification settings - Fork 36
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
@intlify/vite-plugin-vue-i18n locale translation files splitting #97
Comments
Would love to have support for this! Currently, I'm having to cram all my i18n strings into one JSON file to make it work, and that route is really not scalable. |
i made for now my custom load for this. for now without dynamic import (all languages and all files are imported) // @/locales/index.js
// note: now import is not dynamic, so all language files are loaded at once
const modules = import.meta.globEager('./(sk|en)/**/*.yaml', { assert: { type: 'yaml' } })
const setValueByPath = (obj: any, path: string, value: any, splitChar = '.') => {
const a = path.split(splitChar)
let o = obj
while (a.length - 1) {
const n = a.shift()
if (isUndefined(n)) return
if (!(n in o)) o[n] = {}
o = o[n]
}
o[a[0]] = value
}
const cleanupKey = (key: string) => {
key = key.substring(2)
return key.substring(0, key.indexOf('.'))
}
const final = {}
for (const key in modules) {
const path = cleanupKey(key)
setValueByPath(final, path, modules[key].default, '/')
}
export const messages = final
// @/utils/object.js then just import messages to i18n config. field:
title: Title
body: Bodytext
button:
save: Save will be transformed to these keys under en language, for example: const { t } = useI18n({ useScope: 'global' })
t('blog.article.field.title')
t('blog.article.field.body')
t('blog.article.button.save') i think this can work with json also. |
Yeah, |
The yaml parser for Specifically, the following YAML fails to parse (checked with YAML Lint and eslint-plugin-yaml): some-messages:
- first message
- second message Therefore, I implemented parsing with js-yaml. import yaml from 'js-yaml';
/** Return value */
const entries: any = {};
// Get locale yaml file.
Object.entries(
import.meta.glob('./(en|ja)/**/*.yml', {
eager: true,
as: 'raw',
})
).forEach(module => {
/** File Path */
const path = module[0];
/** Locale */
const locale = path.slice(2, 4);
/** Key name */
const key = path.slice(5, -4).replace(/\//, '.');
/** Yaml value */
const value = yaml.load(module[1]);
if (key === 'index') {
// Set index.yml to root.
entries[locale] = { ...entries[locale], ...value };
} else {
// Otherwise, assign to child object
const entry = {};
entry[key] = value;
entries[locale] = { ...entries[locale], ...entry };
}
});
export const messages = entries; index.yml is assigned to root. It's not very clean code, but I think it will work. |
The reason was that Vite does not include a yaml parser. |
I use ts and vite import to manage all translation files. So, I can do a lots of things. //configuration/locale.ts export const defaultLocale = "en"; //locale/index.ts const autoImportedLangs: Record<string, () => Promise> = import.meta.glob( for (const path in autoImportedLangs) { export default usedLangs; install the plugin: import { createI18n } from "vue-i18n"; export default createI18n({ |
Clear and concise description of the problem
example (these files can really grow in size and be really unclear):
Suggested solution
There are to possibilities how to achieve this:
locales/en/group1/subject1.yaml
content is this:the "generated" file for en locale will be:
locales/en/group1/subject1.yaml
locales/fr/group1/subject1.yaml
Alternative
If there is any existing way how to achieve similar code spliting right now without need to implement it, please add it to documentation, because now there is nothing about it.
Additional context
I tried several ways how to structure the dirs, files and content of yaml/json files and nothing was correctly merged, always only one file worked and other were ignored.
Validations
The text was updated successfully, but these errors were encountered: