npm package: @smg-automotive/i18n-pkg
Description: A boilerplate package setup
Author: SMG Automotive
Latest version: 3.2.0

# SMG Automotive I18n

Shared i18n setup for React application

[![CircleCI](https://circleci.com/gh/smg-automotive/example-pkg/tree/main.svg?style=svg&circle-token=c183f151fea3c74453cf8dd962d31e115906a300)](https://app.circleci.com/pipelines/github/smg-automotive/i18n-pkg?branch=main)

## Usage

```
npm install @smg-automotive/i18n-pkg
```

## Setup

### 1. Create an i18n Scope
To ensure SSR safety and prevent cross-request contamination, you must create an isolated i18n scope.

**For Next.js App Router:** Create this in a **Client Component** file (e.g., `src/i18n.ts`).

```typescript
// src/i18n.ts
'use client';

import { createI18nScope } from '@smg-automotive/i18n-pkg';

// Export the Provider, Hook and Component bound to this specific scope
export const { I18nProvider, useI18n, Trans } = createI18nScope();
```

### 2. Wrap your Application
Import the `I18nProvider` **from your local file** (not the package directly) and wrap your app.

```typescript
// src/app/layout.tsx (or _app.tsx)
import { filterDictionaryScopes } from '@smg-automotive/i18n-pkg';
import { I18nProvider } from '../i18n'; // <--- Import from your setup file

// ... import dictionaries ...

export default function RootLayout({ children, params }) {
  return (
    <I18nProvider
      lngDict={filterDictionaryScopes({ ... })}
      language="de"
      onMissingTranslation={(err) => console.error(err)}
    >
      {children}
    </I18nProvider>
  );
}
```

## Usage in Components

Always import `useI18n` and `Trans` from your local setup file.

```typescript
import { useI18n, Trans } from '../i18n'; // <--- Import from your setup file

const MyComponent = () => {
  const { t } = useI18n();

  return (
    <div>
      {/* Simple translation */}
      <h1>{t('home.title')}</h1>

      {/* Rich text translation */}
      <Trans 
        i18nKey="home.welcome" 
        values={{ name: 'User' }} 
      >
        <strong>User</strong>
      </Trans>
    </div>
  );
};
```

## Server-Side Usage (Next.js)

For utility functions like `initI18nServer` (if used for API routes or metadata), you can import them directly from the package as they don't rely on React Context.

```typescript
import { initI18nServer } from '@smg-automotive/i18n-pkg';
```

To use the `t` function in the case above you need to specify before the key if the translation is common across MS24 and AS24 or specific to one universe.

```
i18n.t('specific.homeSearchForm.subtitle')
```

or

```
i18n.t('common.homeSearchForm.lastSearch')
```

In case you need a plural and a singular version for 1 translation:

In your JSON file:

```
"plural": {
            "cookies": {
                "zero": "We did not bake anything",
                "other": "We baked {{ count }} cookies",
                "one": "We baked a cookie"
            }
        }
```

In your component/page:

```
{i18n.t('index.plural', { count: 1 })}
```

- If `count = 0`, `cookies.zero` will be returned
- If `count = 1`, `cookies.one` will be returned
- If `count > 2`, `cookies.other` will be returned

## Test

To test components using your i18n setup, you should mock your local `i18n.ts` file, or simply use the real provider in tests since it's now isolated.

```typescript
// Example test setup
import { render } from '@testing-library/react';
import { I18nProvider } from '../i18n'; // Your local instance

test('renders translation', () => {
  render(
    <I18nProvider language="en" lngDict={...}>
      <MyComponent />
    </I18nProvider>
  );
  // ...
});
```

In order to test the package, you should create the following folders and file:
** mocks **>@smg-automotive>i18n-pkg.tsx
In the i18n-pkg.tsx:

```
export { useI18n, Trans } from '@smg-automotive/i18n-pkg/dist/__mocks__/index';
```

## Development

```
npm run build
```

You can link your local npm package to integrate it with any local project:

```
cd i18n-pkg
npm run build
cd email-templates
npm link ../i18n-pkg
```

## Utility Script

For linting and formatting json dictionaries the package exports the `sort-locale` npx command

Linting

```
npx sort-locales ./locales/de/dict.json ./locales/en/dict.json ...
```

Formatting:

```
npx sort-locales ./locales/de/dict.json ./locales/en/dict.json ... --fix
```