{"_id":"@brainz-digital/i18n","_rev":"2-01ed220d1d3251c3a662c9d2fe68a565","name":"@brainz-digital/i18n","dist-tags":{"latest":"0.3.0"},"versions":{"0.2.0":{"name":"@brainz-digital/i18n","version":"0.2.0","keywords":["i18n","icu","internationalization","localization","messageformat","react","translation","typescript"],"author":{"name":"brainz-digital"},"license":"MIT","_id":"@brainz-digital/i18n@0.2.0","maintainers":[{"name":"bazo","email":"martin@bazo.sk"}],"homepage":"https://github.com/brainz-digital/brainz/tree/main/i18n#readme","bugs":{"url":"https://github.com/brainz-digital/brainz/issues"},"bin":{"i18n":"dist/cli.js"},"dist":{"shasum":"d64448e8b12829da55ab60834d28cb734c16d005","tarball":"https://registry.npmjs.org/@brainz-digital/i18n/-/i18n-0.2.0.tgz","fileCount":49,"integrity":"sha512-sEYWPgU8meW+R1aLDcVY7lov8CXJaaC2yM32GoUoTFdpyIFnUZkP290AGUcjWvreRVViS5jq6Qg9CgeiONx+lg==","signatures":[{"sig":"MEUCICRVw92OhYU49gZRyjeLWxH8enzYaT6a1JLJ4WoMJZgNAiEA9oBj49Y9tUaJUZsVPIhTjDCcwbdengvg6lqCGRsTx1I=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":130263},"main":"./dist/index.js","type":"module","types":"./dist/index.d.ts","engines":{"node":">=20"},"exports":{".":{"types":"./dist/index.d.ts","import":"./dist/index.js"},"./cli":{"types":"./dist/cli.d.ts","import":"./dist/cli.js"},"./config":{"types":"./dist/config.d.ts","import":"./dist/config.js"},"./context":{"types":"./dist/context.d.ts","import":"./dist/context.js"},"./package.json":"./package.json"},"gitHead":"baefa5c8d82807a65671f7a4418be1cf2dcc5043","_npmUser":{"name":"bazo","email":"martin@bazo.sk"},"repository":{"url":"git+https://github.com/brainz-digital/brainz.git","type":"git","directory":"i18n"},"_npmVersion":"11.17.0","description":"Type-safe i18n library with ICU MessageFormat support, React context, and CLI tools","directories":{},"_nodeVersion":"26.5.0","dependencies":{"c12":"^3.3.4","ora":"^9.4.1","zod":"^4.4.3","glob":"^13.0.6","ts-morph":"^28.0.0","intl-messageformat":"^11.2.11","format-message-parse":"^6.2.4","@formatjs/icu-messageformat-parser":"^3.5.14"},"publishConfig":{"access":"public","registry":"https://registry.npmjs.org"},"_hasShrinkwrap":false,"peerDependencies":{"react":">=18"},"peerDependenciesMeta":{"react":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/i18n_0.2.0_1785414411472_0.27070206096911487","host":"s3://npm-registry-packages-npm-production"}},"0.3.0":{"name":"@brainz-digital/i18n","version":"0.3.0","description":"Type-safe i18n library with ICU MessageFormat support, React context, and CLI tools","keywords":["i18n","icu","internationalization","localization","messageformat","react","translation","typescript"],"homepage":"https://github.com/brainz-digital/brainz/tree/main/i18n#readme","bugs":{"url":"https://github.com/brainz-digital/brainz/issues"},"license":"MIT","author":{"name":"brainz-digital"},"repository":{"type":"git","url":"git+https://github.com/brainz-digital/brainz.git","directory":"i18n"},"type":"module","engines":{"node":">=20"},"main":"./dist/index.js","types":"./dist/index.d.ts","bin":{"i18n":"dist/cli.js"},"exports":{".":{"types":"./dist/index.d.ts","import":"./dist/index.js"},"./config":{"types":"./dist/config.d.ts","import":"./dist/config.js"},"./context":{"types":"./dist/context.d.ts","import":"./dist/context.js"},"./cli":{"types":"./dist/cli.d.ts","import":"./dist/cli.js"},"./package.json":"./package.json"},"dependencies":{"@formatjs/icu-messageformat-parser":"^3.5.14","c12":"^3.3.4","format-message-parse":"^6.2.4","glob":"^13.0.6","intl-messageformat":"^11.2.11","ora":"^9.4.1","ts-morph":"^28.0.0","zod":"^4.4.3"},"peerDependencies":{"react":">=18"},"peerDependenciesMeta":{"react":{"optional":true}},"publishConfig":{"access":"public","registry":"https://registry.npmjs.org"},"gitHead":"d56e7d8c7ab8bbd34069ff94540b2ae26d3ffa72","_id":"@brainz-digital/i18n@0.3.0","_nodeVersion":"26.5.0","_npmVersion":"11.17.0","dist":{"integrity":"sha512-2kTTOX+XA49wSuijZhwnHwsU+yv0dT0EcEnXCwckmIE69x9x5nLV9OPzW6q+6Q1Kj8R4Zqg/dWXczm4Fy1GSvQ==","shasum":"535e0e8483a356f3a5269f3ec2d23f4a279ecb64","tarball":"https://registry.npmjs.org/@brainz-digital/i18n/-/i18n-0.3.0.tgz","fileCount":53,"unpackedSize":137006,"signatures":[{"keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U","sig":"MEUCIG5SFnwM/eK2G4sgIFBcQSF3rEXwTvBFtfFBWJt8n4jSAiEA781pdW/kLDL0yk9OGoBIGv2pZEeeGefZEcQlOt2LaFk="}]},"_npmUser":{"name":"bazo","email":"martin@bazo.sk"},"directories":{},"maintainers":[{"name":"bazo","email":"martin@bazo.sk"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages-npm-production","tmp":"tmp/i18n_0.3.0_1785431138474_0.24547158639744837"},"_hasShrinkwrap":false}},"time":{"created":"2026-07-30T12:26:51.199Z","modified":"2026-07-30T17:05:38.798Z","0.2.0":"2026-07-30T12:26:51.630Z","0.3.0":"2026-07-30T17:05:38.652Z"},"bugs":{"url":"https://github.com/brainz-digital/brainz/issues"},"author":{"name":"brainz-digital"},"license":"MIT","homepage":"https://github.com/brainz-digital/brainz/tree/main/i18n#readme","keywords":["i18n","icu","internationalization","localization","messageformat","react","translation","typescript"],"repository":{"type":"git","url":"git+https://github.com/brainz-digital/brainz.git","directory":"i18n"},"description":"Type-safe i18n library with ICU MessageFormat support, React context, and CLI tools","maintainers":[{"name":"bazo","email":"martin@bazo.sk"}],"readme":"# @brainz-digital/i18n\n\nType-safe internationalization library with ICU MessageFormat support, React context, and CLI tools.\n\n## Features\n\n- **Type-safe translations** - Full TypeScript support with generated types\n- **ICU MessageFormat** - Support for plurals, selects, and rich formatting\n- **React integration** - Context provider and hooks for React apps\n- **CLI tools** - Extract keys, convert locales, sync with Localise.biz\n\n## Installation\n\n```bash\nnpm install @brainz-digital/i18n\n# or\nbun add @brainz-digital/i18n\n# or\npnpm add @brainz-digital/i18n\n```\n\nNo registry configuration or authentication is required — the package is published\npublicly to npm.\n\n**Requirements:** Node.js >= 20 (or Bun). The package ships compiled ESM with type\ndeclarations and is usable from any bundler or runtime that supports ES modules.\n\n`react` is an **optional** peer dependency; it is only needed if you import the\n`@brainz-digital/i18n/context` subpath.\n\n## Quick Start\n\n### 1. Create locale files\n\nCreate JSON locale files in `src/locales/`:\n\n```json\n// src/locales/en.json\n{\n\t\"greeting\": \"Hello, {name}!\",\n\t\"items.count\": \"{count, plural, one {# item} other {# items}}\"\n}\n```\n\n### 2. Configure i18n\n\nCreate `i18n.config.ts` in your project root:\n\n```ts\nimport { defineConfig } from \"@brainz-digital/i18n/config\";\n\nexport default defineConfig({\n\tsrcDir: \"./src\",\n\tlocalesDir: \"./src/locales\",\n\ttsconfig: \"tsconfig.json\",\n});\n```\n\n### 3. Convert locales to TypeScript\n\nRun the convert command to generate typed locale files:\n\n```bash\nnpx i18n convert\n```\n\nThis generates:\n\n- `src/locales/en-intl.ts` - Parsed ICU messages\n- `src/locales/types.ts` - TypeScript types for all keys\n\n### 4. Create i18n instance\n\n```ts\n// src/lib/i18n.ts\nimport { createI18n } from \"@brainz-digital/i18n\";\nimport type { Key, Keys, Locale } from \"@/locales/types\";\nimport { Locale as LocaleValues } from \"@/locales/types\";\nimport en from \"@/locales/en-intl\";\n\nexport const { translator, _, _any, isValidLang, locales } = createI18n<Keys, Locale>(\n\tLocaleValues,\n\tLocaleValues.EN,\n);\n\n// Load translations\ntranslator.add(LocaleValues.EN, en);\n\nexport type { Key, Keys, Locale };\n```\n\n### 5. Use in your app\n\n```tsx\nimport { _ } from \"@/lib/i18n\";\n\nfunction Greeting({ name }: { name: string }) {\n\treturn <h1>{_(\"greeting\", { name })}</h1>;\n}\n\nfunction ItemCount({ count }: { count: number }) {\n\treturn <span>{_(\"items.count\", { count })}</span>;\n}\n```\n\n## React Context (Optional)\n\nFor apps that need dynamic locale switching:\n\n```tsx\n// src/lib/i18n-context.ts\nimport { createI18nContext, createUseI18n } from \"@brainz-digital/i18n/context\";\nimport type { Keys, Locale } from \"@/locales/types\";\n\nexport const I18nContext = createI18nContext<Keys, Locale>();\nexport const useI18n = createUseI18n(I18nContext);\n```\n\n```tsx\n// src/providers/i18n-provider.tsx\nimport { useState, useCallback, type ReactNode } from \"react\";\nimport { I18nContext } from \"@/lib/i18n-context\";\nimport { translator } from \"@/lib/i18n\";\nimport type { Locale } from \"@/locales/types\";\n\nexport function I18nProvider({ children }: { children: ReactNode }) {\n\tconst [locale, setLocale] = useState(translator.locale);\n\n\tconst changeLocale = useCallback(async (newLocale: Locale) => {\n\t\t// Dynamically load locale if not already loaded\n\t\tif (!translator.hasLocale(newLocale)) {\n\t\t\tconst module = await import(`@/locales/${newLocale}-intl.ts`);\n\t\t\ttranslator.add(newLocale, module.default);\n\t\t}\n\t\ttranslator.changeLocale(newLocale);\n\t\tsetLocale(newLocale);\n\t}, []);\n\n\treturn (\n\t\t<I18nContext.Provider value={{ translator, locale, changeLocale }}>\n\t\t\t{children}\n\t\t</I18nContext.Provider>\n\t);\n}\n```\n\n## CLI Commands\n\n```bash\n# Convert JSON locales to TypeScript with ICU parsing\nnpx i18n convert\n\n# Extract translation keys from source code (dry-run)\nnpx i18n extract\n\n# Upload new keys to Localise.biz\nnpx i18n upload\n\n# Download translations from Localise.biz\nnpx i18n download\n\n# Import CSV files to Localise.biz\nnpx i18n import\n```\n\n## Configuration\n\nFull configuration options in `i18n.config.ts`:\n\n```ts\nimport { defineConfig } from \"@brainz-digital/i18n/config\";\n\nexport default defineConfig({\n\tsrcDir: \"./src\",\n\ttsconfig: \"tsconfig.json\",\n\tlocalesDir: \"./src/locales\",\n\ttypesPath: \"./src/locales/types.ts\",\n\n\tlocalise: {\n\t\tapiKey: process.env.LOCO_API_KEY,\n\t\tprojectId: \"your-project-id\",\n\t},\n\n\textract: {\n\t\tfunctionNames: [\"_\", \"translator.translate\"],\n\t},\n});\n```\n\n## ICU MessageFormat Examples\n\n```json\n{\n\t\"simple\": \"Hello, world!\",\n\t\"interpolation\": \"Hello, {name}!\",\n\t\"plural\": \"{count, plural, one {# item} other {# items}}\",\n\t\"select\": \"{gender, select, male {He} female {She} other {They}} liked this\",\n\t\"nested\": \"{count, plural, one {{name} has # message} other {{name} has # messages}}\",\n\t\"rich\": \"Click <link>here</link> to continue\"\n}\n```\n\n## API Reference\n\n### `createI18n<TKeys, TLocale>(localeValues, defaultLocale)`\n\nCreates an i18n instance with typed translation functions.\n\nReturns:\n\n- `translator` - The Translator instance\n- `_` - Type-safe translation function\n- `_any` - Untyped translation function (for dynamic keys)\n- `isValidLang` - Locale validator function\n- `locales` - Array of available locales\n\n### `Translator` class\n\n- `add(locale, translations)` - Add translations for a locale\n- `translate(id, data?)` - Translate a key (type-safe)\n- `translateAny(id, data?)` - Translate any key (untyped)\n- `changeLocale(locale)` - Switch current locale\n- `hasLocale(locale)` - Check if locale is loaded\n\n## License\n\nMIT\n","readmeFilename":"README.md"}