PHPackages                             bermudaphp/polyglot - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Localization &amp; i18n](/categories/localization)
4. /
5. bermudaphp/polyglot

ActiveLibrary[Localization &amp; i18n](/categories/localization)

bermudaphp/polyglot
===================

A powerful, flexible internationalization (i18n) and localization (l10n) library for PHP 8.4+ applications with support for ICU message formatting, pluralization, caching, and more.

v1.0(11mo ago)01MITPHPPHP ^8.4CI passing

Since May 21Pushed 11mo ago1 watchersCompare

[ Source](https://github.com/bermudaphp/polyglot)[ Packagist](https://packagist.org/packages/bermudaphp/polyglot)[ RSS](/packages/bermudaphp-polyglot/feed)WikiDiscussions master Synced 1mo ago

READMEChangelog (1)Dependencies (6)Versions (2)Used By (0)

Polyglot
========

[](#polyglot)

[![PHP Version Require](https://camo.githubusercontent.com/753314ba401f35f744e19dd23ff49b5a76b15f5faa86b230814bfddccdad88d7/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f7068702d253345253344382e342d627269676874677265656e2e737667)](https://php.net/)[![GitHub Tests](https://camo.githubusercontent.com/684ddcfaab16e5bf5a22484a935d50fdce52bc87b6f8d0b1e9ee302efaa9af4a/68747470733a2f2f696d672e736869656c64732e696f2f6769746875622f616374696f6e732f776f726b666c6f772f7374617475732f6265726d7564617068702f706f6c79676c6f742f74657374732e796d6c3f6272616e63683d6d6173746572266c6162656c3d7465737473)](https://github.com/bermudaphp/polyglot/actions/workflows/tests.yml)[![Code Coverage](https://camo.githubusercontent.com/dcd1558bb815e88e28fa332b09bd9148a4588a231ee1fbe6fca78bfa497aeba9/68747470733a2f2f696d672e736869656c64732e696f2f656e64706f696e743f75726c3d68747470733a2f2f676973742e67697468756275736572636f6e74656e742e636f6d2f5368656c616d6b6f66662f66613330623765303336303737303633666265643735366530316139313933342f7261772f706f6c79676c6f742d636f7665726167652e6a736f6e)](https://github.com/bermudaphp/polyglot/actions/workflows/tests.yml)[![Latest Version on Packagist](https://camo.githubusercontent.com/81dfa95711ec6c4a5faa32da8b4d3f027fe3805674458975d2000dc91ca59a2e/68747470733a2f2f696d672e736869656c64732e696f2f7061636b61676973742f762f6265726d7564617068702f706f6c79676c6f742e737667)](https://packagist.org/packages/bermudaphp/polyglot)[![License: MIT](https://camo.githubusercontent.com/fdf2982b9f5d7489dcf44570e714e3a15fce6253e0cc6b5aa61a075aac2ff71b/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f4c6963656e73652d4d49542d79656c6c6f772e737667)](https://github.com/bermudaphp/polyglot/blob/master/LICENSE)

Polyglot is a powerful, flexible internationalization (i18n) and localization (l10n) library for PHP 8.4+ applications with support for ICU message formatting, pluralization, caching, and more.

[Read documentation in Russian (Документация на русском)](README.RU.md)

Table of Contents
-----------------

[](#table-of-contents)

- [Installation](#installation)
- [Basic Usage](#basic-usage)
- [Key Concepts](#key-concepts)
- [Creating a Translator](#creating-a-translator)
- [Locales](#locales)
- [Translation Files](#translation-files)
- [Pluralization](#pluralization)
- [ICU Message Format](#icu-message-format)
    - [Parameter Substitution](#parameter-substitution)
    - [Number Formatting](#number-formatting)
    - [Date Formatting](#date-formatting)
    - [Plural Formatting](#plural-formatting)
    - [Select Formatting](#select-formatting)
    - [Nested Formatting](#nested-formatting)
- [Message Builders](#message-builders)
    - [ICU Message Builder](#icu-message-builder)
    - [Plural Builder](#plural-builder)
    - [Select Builder](#select-builder)
- [Caching](#caching)
- [Locale Detection](#locale-detection)
- [PSR-15 Middleware](#psr-15-middleware)
- [License](#license)

Installation
------------

[](#installation)

```
composer require bermudaphp/polyglot
```

Basic Usage
-----------

[](#basic-usage)

```
// Create an I18n instance using the factory
$i18n = I18nFactory::create('/path/to/translations', 'en', 'en');

// Basic translation
echo $i18n->translate('welcome'); // "Welcome!"

// Translation with parameters
echo $i18n->translate('greeting', ['name' => 'John']); // "Hello, John!"

// Translation with pluralization
echo $i18n->translatePlural('items', 1); // "You have 1 item"
echo $i18n->translatePlural('items', 5); // "You have 5 items"

// Shorthand methods
echo $i18n->t('welcome');
echo $i18n->tp('items', 3);

// Change locale
$i18n->setLocale('fr');
echo $i18n->t('welcome'); // "Bienvenue !"
```

Key Concepts
------------

[](#key-concepts)

Polyglot uses several core concepts:

- **Locale**: Identifies a specific language and region (e.g., 'en\_US', 'fr\_FR')
- **Domain**: Groups related translations (e.g., 'messages', 'errors', 'admin')
- **Translation Key**: Unique identifier for a translatable string
- **Fallback Locale**: Used when a translation is missing in the primary locale
- **Plurality**: Different forms of words based on quantity (e.g., "1 item" vs "5 items")
- **ICU Format**: International Components for Unicode message format for complex translations

Creating a Translator
---------------------

[](#creating-a-translator)

The simplest way to create a translator is using the factory:

```
use Bermuda\Polyglot\I18nFactory;

$i18n = I18nFactory::create(
    resourcesPath: '/path/to/translations',
    defaultLocale: 'en',
    fallbackLocale: 'en',
    availableLocales: ['en', 'fr', 'de', 'es'],
    cache: null // Optional cache implementation
);
```

For more control, you can create components manually:

```
use Bermuda\Polyglot\Translator;
use Bermuda\Polyglot\Loader\PhpArrayMessageLoader;
use Bermuda\Polyglot\Formatter\IcuMessageFormatter;
use Bermuda\Polyglot\PluralRule\CldrPluralRuleProvider;
use Bermuda\Polyglot\Cache\InMemoryCache;

// Create loaders
$loader = new PhpArrayMessageLoader('/path/to/translations');

// Create formatters
$formatter = new IcuMessageFormatter(new CldrPluralRuleProvider());

// Create plural rule provider
$pluralRuleProvider = new CldrPluralRuleProvider();

// Create cache (optional)
$cache = new InMemoryCache();

// Create translator
$translator = new Translator(
    locale: 'en',
    fallbackLocale: 'en',
    loader: $loader,
    formatter: $formatter,
    pluralRuleProvider: $pluralRuleProvider,
    cache: $cache
);

// Create I18n instance
$i18n = new I18n($translator);
```

Locales
-------

[](#locales)

Polyglot provides multiple ways to handle locale codes:

1. As simple strings ('en', 'en\_US', 'fr\_FR')
2. Using the `LocaleEnum` typed enum
3. Using the `Locale` value object

### LocaleEnum

[](#localeenum)

```
use Bermuda\Polyglot\LocaleEnum;

$locale = LocaleEnum::ENGLISH_US;
$i18n->setLocale($locale);

// Get language code
$language = $locale->getLanguageCode(); // 'en'

// Get region code
$region = $locale->getRegionCode(); // 'US'

// Create from string
$locale = LocaleEnum::fromString('en-US'); // Handles both 'en-US' and 'en_US' formats
```

### Locale Value Object

[](#locale-value-object)

```
use Bermuda\Polyglot\Locale;

$locale = new Locale('en_US');

// Access components
echo $locale->language; // 'en'
echo $locale->region;   // 'US'
echo $locale->variant;  // null

// Convert to string
echo $locale; // 'en_US'

// Get fallbacks
$fallbacks = $locale->getFallbacks(); // ['en']
```

Translation Files
-----------------

[](#translation-files)

Polyglot supports multiple formats for translation files:

### PHP Array Files

[](#php-array-files)

```
// /path/to/translations/en/messages.php
return [
    'welcome' => 'Welcome!',
    'greeting' => 'Hello, {name}!',
    'items' => [
        'one' => 'You have 1 item',
        'other' => 'You have {count} items'
    ],
    'user' => [
        'greeting' => 'Welcome back, {name}!',
        'profile' => [
            'title' => 'User Profile'
        ]
    ]
];
```

### JSON Files

[](#json-files)

```
{
    "welcome": "Welcome!",
    "greeting": "Hello, {name}!",
    "items": {
        "one": "You have 1 item",
        "other": "You have {count} items"
    },
    "user": {
        "greeting": "Welcome back, {name}!",
        "profile": {
            "title": "User Profile"
        }
    }
}
```

### Accessing Nested Keys

[](#accessing-nested-keys)

Nested keys can be accessed using dot notation:

```
echo $i18n->t('user.profile.title'); // "User Profile"
```

Pluralization
-------------

[](#pluralization)

Polyglot provides robust support for pluralization based on the CLDR (Common Locale Data Repository) rules:

```
// Translation file
return [
    'items' => [
        'one' => 'You have 1 item',
        'other' => 'You have {count} items'
    ],
    'apples' => [
        'one' => '{count} apple',
        'few' => '{count} apples', // For languages like Russian, Polish
        'many' => '{count} apples', // For languages like Russian, Polish
        'other' => '{count} apples'
    ]
];

// Usage
echo $i18n->translatePlural('items', 1); // "You have 1 item"
echo $i18n->translatePlural('items', 5); // "You have 5 items"

// With parameters
echo $i18n->translatePlural('items', 5, ['color' => 'red']); // "You have 5 red items"
```

ICU Message Format
------------------

[](#icu-message-format)

Polyglot supports the ICU (International Components for Unicode) message format, a powerful standard for handling translations with variables, pluralization, and more.

### Parameter Substitution

[](#parameter-substitution)

```
// Translation
'greeting' => 'Hello, {name}!'

// Usage
echo $i18n->t('greeting', ['name' => 'John']); // "Hello, John!"
```

### Number Formatting

[](#number-formatting)

```
// Translation
'price' => 'Price: {amount, number, currency}'

// Usage
echo $i18n->t('price', ['amount' => 1234.56]); // "Price: $1,234.56" (in en-US)
```

### Date Formatting

[](#date-formatting)

```
// Translation
'today' => 'Today is {date, date, medium}'

// Usage
echo $i18n->t('today', ['date' => new DateTime()]); // "Today is Jan 1, 2023"
```

### Plural Formatting

[](#plural-formatting)

```
// Translation
'items' => '{count, plural, one{# item} other{# items}}'

// Usage
echo $i18n->t('items', ['count' => 1]); // "1 item"
echo $i18n->t('items', ['count' => 5]); // "5 items"
```

### Select Formatting

[](#select-formatting)

```
// Translation
'gender' => '{gender, select, male{He} female{She} other{They}} will attend.'

// Usage
echo $i18n->t('gender', ['gender' => 'female']); // "She will attend."
```

### Nested Formatting

[](#nested-formatting)

```
// Translation
'nested' => '{gender, select, male{He has {count, plural, one{# apple} other{# apples}}} female{She has {count, plural, one{# apple} other{# apples}}} other{They have {count, plural, one{# apple} other{# apples}}}}'

// Usage
echo $i18n->t('nested', ['gender' => 'female', 'count' => 3]); // "She has 3 apples"
```

Message Builders
----------------

[](#message-builders)

Polyglot provides a set of builders to programmatically create ICU message templates.

### ICU Message Builder

[](#icu-message-builder)

```
use Bermuda\Polyglot\Generator\IcuMessage;

// Create a message builder for a specific locale
$builder = IcuMessage::for('en');

// Create a simple message with placeholders
$message = $builder->message('Hello, {name}!');

// Create a gender-specific message
$gender = IcuMessage::gender(
    'gender',
    'He will attend', // male
    'She will attend', // female
    'They will attend' // other
);
```

### Plural Builder

[](#plural-builder)

```
use Bermuda\Polyglot\Generator\IcuMessage;

// Create a plural builder for English
$pluralBuilder = IcuMessage::plural('count', 'en');

// Add cases manually
$pluralBuilder
    ->when('one', 'You have # item')
    ->when('other', 'You have # items');

// Get the ICU message
$icuMessage = $pluralBuilder->build();
// Result: "{count, plural, one{You have # item} other{You have # items}}"

// Using withInflections for common plurals
$builder = IcuMessage::plural('count', 'en')
    ->withInflections('You have # item', [
        'one' => '',
        'other' => 's'
    ]);

// For languages with more complex pluralization (e.g., Russian)
$builder = IcuMessage::plural('count', 'ru')
    ->withInflections('У вас # товар', [
        'one' => '',
        'few' => 'а',
        'many' => 'ов'
    ]);
```

### Select Builder

[](#select-builder)

```
use Bermuda\Polyglot\Generator\IcuMessage;

// Create a select builder
$selectBuilder = IcuMessage::select('role');

// Add cases
$selectBuilder
    ->when('admin', 'You have full access')
    ->when('manager', 'You have limited access')
    ->otherwise('You have basic access');

// Get the ICU message
$icuMessage = $selectBuilder->build();
// Result: "{role, select, admin{You have full access} manager{You have limited access} other{You have basic access}}"

// Using with nested plural
$builder = IcuMessage::select('gender')
    ->when('male', function($b) {
        return $b->plural('count', 'en')
            ->when('one', 'He has # apple')
            ->when('other', 'He has # apples');
    })
    ->when('female', function($b) {
        return $b->plural('count', 'en')
            ->when('one', 'She has # apple')
            ->when('other', 'She has # apples');
    });
```

Caching
-------

[](#caching)

Polyglot supports caching of loaded translations to improve performance:

```
use Bermuda\Polyglot\Cache\PsrCacheAdapter;
use Symfony\Component\Cache\Adapter\FilesystemAdapter;

// Create a PSR-16 compatible cache
$psr16Cache = new \Symfony\Component\Cache\Psr16Cache(
    new FilesystemAdapter()
);

// Create a cache adapter
$cache = new PsrCacheAdapter($psr16Cache);

// Use with I18n factory
$i18n = I18nFactory::create(
    resourcesPath: '/path/to/translations',
    defaultLocale: 'en',
    fallbackLocale: 'en',
    cache: $cache
);
```

Also included is an `InMemoryCache` for simple use cases:

```
use Bermuda\Polyglot\Cache\InMemoryCache;

$cache = new InMemoryCache();
```

Locale Detection
----------------

[](#locale-detection)

Polyglot can automatically detect the user's preferred locale:

```
use Bermuda\Polyglot\Detector\HttpAcceptLanguageDetector;
use Bermuda\Polyglot\Detector\QueryLocaleDetector;
use Bermuda\Polyglot\Detector\PathLocaleDetector;
use Bermuda\Polyglot\Detector\LocaleDetectorChain;

// Available locales
$availableLocales = ['en', 'fr', 'de', 'es'];

// Create detectors
$httpDetector = new HttpAcceptLanguageDetector($availableLocales);
$queryDetector = new QueryLocaleDetector($availableLocales, 'locale');
$pathDetector = new PathLocaleDetector($availableLocales);

// Create a chain of detectors (checked in order)
$detector = new LocaleDetectorChain([
    $pathDetector,    // First check URL path (/en/page)
    $queryDetector,   // Then check query param (?locale=en)
    $httpDetector     // Finally check Accept-Language header
]);

// Use with I18n
$i18n = new I18n($translator, $detector);

// Detect and set locale
$i18n->detectAndSetLocale('en'); // 'en' is the default if no locale is detected
```

PSR-15 Middleware
-----------------

[](#psr-15-middleware)

Polyglot includes a PSR-15 middleware for detecting the locale from HTTP requests:

```
use Bermuda\Polyglot\I18nMiddleware;

// Create middleware
$middleware = I18nFactory::createMiddleware($i18n, 'en');

// Add to your middleware stack
$app->pipe($middleware);
```

The middleware:

1. Detects the locale from the request
2. Sets it in the I18n instance
3. Adds the locale as a request attribute
4. Passes control to the next middleware

License
-------

[](#license)

The Polyglot library is open-sourced software licensed under the [MIT license](LICENSE).

###  Health Score

30

—

LowBetter than 64% of packages

Maintenance50

Moderate activity, may be stable

Popularity1

Limited adoption so far

Community7

Small or concentrated contributor base

Maturity54

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Unknown

Total

1

Last Release

359d ago

### Community

Maintainers

![](https://avatars.githubusercontent.com/u/20490712?v=4)[Andrey Shelamkoff](/maintainers/Shelamkoff)[@Shelamkoff](https://github.com/Shelamkoff)

---

Top Contributors

[![Shelamkoff](https://avatars.githubusercontent.com/u/20490712?v=4)](https://github.com/Shelamkoff "Shelamkoff (49 commits)")

---

Tags

i18nicuinternationalizationintllocalizationphp84translationintllocalizationinternationalizationi18nl10npluralicutranslation

###  Code Quality

TestsPHPUnit

Static AnalysisPHPStan

Type Coverage Yes

### Embed Badge

![Health badge](/badges/bermudaphp-polyglot/health.svg)

```
[![Health](https://phpackages.com/badges/bermudaphp-polyglot/health.svg)](https://phpackages.com/packages/bermudaphp-polyglot)
```

###  Alternatives

[symfony/intl

Provides access to the localization data of the ICU library

2.6k199.8M1.1k](/packages/symfony-intl)[gettext/languages

gettext languages with plural rules

7530.3M11](/packages/gettext-languages)[aplus/language

Aplus Framework Language Library

2351.7M15](/packages/aplus-language)[aura/intl

The Aura Intl package provides internationalization tools, specifically message translation.

898.3M4](/packages/aura-intl)[delight-im/i18n

Internationalization and localization for PHP

625.2k3](/packages/delight-im-i18n)[jrmajor/fluent

Fluent localization system for PHP

2716.9k5](/packages/jrmajor-fluent)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
