Minimalistic translate (i18n) library for Preact
Bundle size: ~1KB
Live example: Sandbox
Minimal requirements: Preact 10.0.0
Add the .npmrc
file to your project root if you are using GitHub Package Registry
registry=https://npm.pkg.github.com
Using Yarn:
yarn add @denysvuika/preact-translate
Using NPM:
npm i @denysvuika/preact-translate
You should wrap your application with the TranslateProvider
component:
import { TranslateProvider } from '@denysvuika/preact-translate';
export default function App() {
return (
<TranslateProvider>
<MainComponent />
</TranslateProvider>
);
}
Create an assets/en.json
file with the following content:
{
"title": "Hello",
"subtitle": "World"
}
Create a second file assets/ua.json
to be able to switch between different resources.
{
"title": "[ua] Hello",
"subtitle": "[ua] World"
}
You can now use the TranslateContext
in your components to access the translation API and data:
import { useContext } from 'preact/hooks';
import { TranslateContext } from '@denysvuika/preact-translate';
export default function MainComponent() {
const { setLang, t, lang } = useContext(TranslateContext);
return (
<div>
<div>Lang: {lang}</div>
<div>{t('title')}</div>
<div>{t('subtitle')}</div>
<div>
<button onClick={() => setLang('en')}>EN</button>
<button onClick={() => setLang('ua')}>UA</button>
</div>
</div>
);
}
For the EN
locale you should see:
Lang: en
Hello
World
For the UA
locale you should see:
Lang: ua
[ua] Hello
[ua] World
The language loading performs on demand.
The en.json
gets loaded and cached only when first requested by your application.
By default, the assets
folder is used to fetch locales.
You can change it via the TranslateProvider.root
property:
import { TranslateProvider } from '@denysvuika/preact-translate';
export default function App() {
return (
<TranslateProvider root="i18n">
<MainComponent />
</TranslateProvider>
);
}
You can use runtime string substitution when translating text
{
"hello": "Hello, {name}"
}
Then in the JSX:
<div>{t('hello', { name: 'Bob' })}</div>
The library supports complex objects with nested levels.
Put the following in the en.json
file:
{
"messages": {
"errors": {
"404": "Sorry, not found"
}
}
}
Then in the JSX use:
<div>{t('messages.errors.404')}</div>
You can also use composite strings like the following:
{
"messages.errors.404": "Sorry, not found"
}
You can set the default language to use with the application by assigning the TranslateProvider.lang
property.
<TranslateProvider lang="ua">
<Application />
</TranslateProvider>
Please note that in this case provider is going to load and cache two locales at startup:
en.json
(as a fallback) and ua.json
(as an active lang).
You can use TranslateProvider.translations
property to provide a custom translation data from the code.
That helps with unit testing as well.
const data = {
en: {
messages: {
404: 'Not found'
}
}
};
<TranslateProvider translations={data}>
<Application />
</TranslateProvider>;
Note that the TranslateProvider
is not going to fetch translation files for the en
locale,
and will use your custom data instead.