`te` returns invalid value when the given value (or "branch") is an object
sybrendotinga opened this issue · comments
Reporting a bug?
After upgrading to v9.6 we are experiencing that the te
does not recognize changes anymore.
Expected behavior
After mergeLocaleMessages
is called we expect te
to return true
, because the message now exists
Reproduction
- Load translations via an API
- Merge the message with the
mergeLocaleMessages
- The value from
te('common')
should now betrue
In this example you can see that the "Terug"-translation is loaded, via the external package.
The first true
is the te('common.action.cancel.label')
from the portal, the second false-value te('common')
.
Stackblitz: https://stackblitz.com/edit/vitejs-vite-gyzvu8?file=package.json
When downgrading to ~9.5 all values are true
.
System Info
System:
OS: macOS 14.0
CPU: (12) x64 Intel(R) Core(TM) i7-9750H CPU @ 2.60GHz
Memory: 217.91 MB / 16.00 GB
Shell: 5.9 - /bin/zsh
Binaries:
Node: 18.15.0 - ~/Library/pnpm/node
Yarn: 1.22.19 - ~/.yarn/bin/yarn
npm: 8.19.4 - ~/Documents/frontend/.../node_modules/.bin/npm
pnpm: 8.15.1 - ~/Library/pnpm/pnpm
Browsers:
Chrome: 121.0.6167.160
Safari: 17.0
npmPackages:
@vitejs/plugin-vue: ^5.0.3 => 5.0.3
@vue/eslint-config-prettier: ^8.0.0 => 8.0.0
@vue/eslint-config-typescript: ^11.0.3 => 11.0.3
@vue/test-utils: ^2.4.1 => 2.4.1
@vue/tsconfig: ^0.1.3 => 0.1.3
vite: ^5.0.12 => 5.0.12
vite-plugin-dts: ^3.7.2 => 3.7.2
vitest: ^1.2.2 => 1.2.2
vue: ^3.4.15 => 3.4.15
vue-good-table-next: ^0.2.1 => 0.2.1
vue-i18n: ^9.9.1 => 9.9.1
vue-router: ^4.2.5 => 4.2.5
vue-tsc: ^1.8.27 => 1.8.27
vue3-apexcharts: ^1.4.4 => 1.4.4
Screenshot
Additional context
Because we have a lot of translations, we load them from the API, based on a given prefix
. For example "load all translations for the employee-prefix"
We use the following setup:
- A (private) library (installed with
pnpm
) that loads translations based on aprefix
. e.g.entity.employee
- We use
mergeLocaleMessage
to merge the new translations into the existing translations:
const { data } = await axios.get<TranslationsResponse>(`${url}?prefix=${prefix}`)
for (const key in data) {
const language = key as Language // (for example `nl` or `en` or `es`)
const translations = data[language]
mergeLocaleMessage(key, translations)
}
The private library aswel as vue-i18n
is installed in the project.
I discovered that it returns false
because te('common')
is not very specific to a translation, but to a branch of translations.
Validations
- Read the Contributing Guidelines
- Read the Documentation
- Check that there isn't already an issue that reports the same bug to avoid creating a duplicate.
- Check that this is a concrete bug. For Q&A open a GitHub Discussions
Reading more about this, I've found that this works:
const translations = computed(() => tm('editor'))
const showTools = computed(() => Object.keys(translations.value).length >= 1)
But, maybe that is not the nicest solution, because it adds a lot more operations than it previously was
@kazupon It seems very related to #1602
I've added a very simple Stackblitz reproduction: https://stackblitz.com/edit/vitejs-vite-gyzvu8?file=src%2FApp.vue
te
is broken after updating to 9.6. You can install 9.5 in de stackblitz and all checks become true
again.
Thank you for your reporting!
te('common') -> false
te('common.actions') -> false
This is the result of your reproduction above, which is the correct behavior.
Until now, true was returned even if the value of the key was not translatable, i.e., not a string.
So, I've fixed in #1559
I will put this notice in te
API documentation.
Thanks!
Hi @kazupon is there an alternative? Or can one be provided? Because our applications rely on this check and therefore are now broken on this version.
@sybrendotinga
I'll give translateExistCompatible
option, a compatibility flag that will result in pre-9.6 behavior. You can specify that option to createI18n
.
We will remove that option in the next major version v10, so please migrate at some point.
That would be great, thank you. Nonetheless, we would still appreciate an alternative after that. Can vue-i18n
provide an alternaive to check if a branch exists (aka is an object)? Or should we build something like this ourself?
const translations = computed(() => tm('editor'))
const showTools = computed(() => Object.keys(translations.value).length >= 1)
vue-i18n v9 is giving us tm
for getting object or array.
https://vue-i18n.intlify.dev/guide/migration/breaking.html#translation-api-return-value
Like the code you presented, we can check if there is a branch by using computed
.