@saykit/react
v0.11.0
Published
React integration for saykit, i18n hooks and components
Maintainers
Readme
@saykit/react
React integration for SayKit.
A <Say> component for rendering translated content in server and client components, a <SayProvider> and useSay() for client trees, and a withSay and getSay() that mirror them on the server.
Install
pnpm add @saykit/react saykitYou will also need a SayKit build-tool plugin (unplugin-saykit or babel-plugin-saykit) and a saykit.config.ts with @saykit/transform-jsx in the bucket. The lazy () => import(...) catalogues below need unplugin-saykit or babel-plugin-saykit with catalogues: 'module'; Babel's default inline mode only handles static imports.
Usage
import { createCatalogue, createStore } from 'saykit';
export const catalogue = createCatalogue({
en: () => import('./locales/en.po'),
fr: () => import('./locales/fr.po'),
});
const initial = catalogue.match(navigator.languages);
await catalogue.load(initial);
export const store = createStore(catalogue, initial);
export type Locale = (typeof catalogue.locales)[number];import { Say } from '@saykit/react';
import { SayProvider, useSay } from '@saykit/react/client';
import { type Locale, store } from './i18n.js';
function Cart({ name, items }: { name: string; items: string[] }) {
return (
<p>
<Say>Hello, {name}!</Say>{' '}
<Say.Plural
_={items.length}
_0="Your cart is empty."
one="You have 1 item."
other={<>You have {items.length} items.</>}
/>
</p>
);
}
function LocalePicker() {
const say = useSay();
return (
<select value={say.locale} onChange={(event) => store.set(event.target.value as Locale)}>
<option value="en">English</option>
<option value="fr">Français</option>
</select>
);
}
export function App() {
return (
<SayProvider store={store}>
<LocalePicker />
<Cart name="Ada" items={[]} />
</SayProvider>
);
}Elements inside a message survive translation as numbered tags: <Say>Read the <a href="/docs">docs</a></Say> extracts as Read the <0>docs</0>.
