PHPackages                             tobento/service-language - 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. tobento/service-language

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

tobento/service-language
========================

Managing languages for PHP applications.

2.0(7mo ago)01754MITPHPPHP &gt;=8.4

Since Sep 28Pushed 7mo ago1 watchersCompare

[ Source](https://github.com/tobento-ch/service-language)[ Packagist](https://packagist.org/packages/tobento/service-language)[ Docs](https://www.tobento.ch)[ RSS](/packages/tobento-service-language/feed)WikiDiscussions 2.x Synced 1mo ago

READMEChangelog (9)Dependencies (2)Versions (11)Used By (4)

Language Service
================

[](#language-service)

The Language Service provides a way for managing languages for PHP applications.

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

[](#table-of-contents)

- [Getting started](#getting-started)
    - [Requirements](#requirements)
    - [Highlights](#highlights)
- [Documentation](#documentation)
    - [Language](#language)
        - [Create Language](#create-language)
        - [Language Interface](#language-interface)
    - [Languages](#languages)
        - [Create Languages](#create-languages)
        - [Get Language](#get-language)
        - [Default Language](#default-language)
        - [Current Language](#current-language)
        - [All Languages](#all-languages)
        - [Columns](#columns)
        - [Fallbacks](#fallbacks)
        - [Miscellaneous Methods](#miscellaneous-methods)
    - [Area Languages](#area-languages)
    - [Current Language Resolver](#current-language-resolver)
- [Credits](#credits)

---

Getting started
===============

[](#getting-started)

Add the latest version of the Language service project running this command.

```
composer require tobento/service-language

```

Requirements
------------

[](#requirements)

- PHP 8.4 or greater

Highlights
----------

[](#highlights)

- Framework-agnostic, will work with any project
- Decoupled design

Documentation
=============

[](#documentation)

Language
--------

[](#language)

### Create Language

[](#create-language)

Easily create a language with the provided factory:

```
use Tobento\Service\Language\LanguageFactory;
use Tobento\Service\Language\LanguageInterface;

$languageFactory = new LanguageFactory();

$language = $languageFactory->createLanguage('en');

var_dump($language instanceof LanguageInterface);
// bool(true)
```

**Parameters:**

```
use Tobento\Service\Language\LanguageFactory;

$languageFactory = new LanguageFactory();

$language = $languageFactory->createLanguage(
    locale: 'en-US',
    name: 'English',
    key: 'en-us',
    id: 1,
    iso: 'en',
    region: 'US',
    slug: 'en',
    directory: 'enUs',
    direction: 'ltr',
    area: 'frontend',
    domain: 'example.com',
    url: 'https://www.example.com',
    fallback: 'en',
    default: false,
    active: true,
    editable: true,
    order: 2,
);
```

### Language Interface

[](#language-interface)

```
use Tobento\Service\Language\LanguageFactory;
use Tobento\Service\Language\LanguageInterface;

$languageFactory = new LanguageFactory();

$language = $languageFactory->createLanguage('en-US');

var_dump($language instanceof LanguageInterface);
// bool(true)

var_dump($language->locale());
// string(5) "en-US"

var_dump($language->iso());
// string(2) "en"

var_dump($language->region());
// string(2) "US" or returns NULL if no region.

var_dump($language->name());
// string(5) "en-US"

var_dump($language->key());
// string(5) "en-us"

var_dump($language->id());
// int(0)

var_dump($language->slug());
// string(5) "en-us"

var_dump($language->directory());
// string(5) "en-us"

var_dump($language->direction());
// string(3) "ltr"

var_dump($language->area());
// string(7) "default"

var_dump($language->domain());
// NULL or returns string if has domain.

var_dump($language->url());
// NULL or returns string if has url.

var_dump($language->fallback());
// NULL or returns string if has fallback

var_dump($language->default());
// bool(false)

var_dump($language->active());
// bool(true)

var_dump($language->editable());
// bool(true)

var_dump($language->order());
// int(2)
```

Languages
---------

[](#languages)

### Create Languages

[](#create-languages)

```
use Tobento\Service\Language\LanguageFactory;
use Tobento\Service\Language\Languages;
use Tobento\Service\Language\LanguagesInterface;

$languageFactory = new LanguageFactory();

$languages = new Languages(
    $languageFactory->createLanguage(locale: 'en', default: true),
    $languageFactory->createLanguage(locale: 'de', fallback: 'en'),
    $languageFactory->createLanguage(locale: 'de-CH', fallback: 'de'),
    $languageFactory->createLanguage(locale: 'fr', fallback: 'en', active: false),
    $languageFactory->createLanguage(locale: 'it', fallback: 'de', active: false),
);

var_dump($languages instanceof LanguagesInterface);
// bool(true)
```

**Create languages from an array:**

```
use Tobento\Service\Language\LanguageFactory;
use Tobento\Service\Language\Languages;
use Tobento\Service\Language\LanguagesInterface;

$languageFactory = new LanguageFactory();

$languages = new Languages(
    ...$languageFactory->createLanguagesFromArray([
        ['locale' => 'en', 'default' => true],
        ['locale' => 'de', 'fallback' => 'en'],
        ['locale' => 'fr', 'fallback' => 'en'],
    ])
);

var_dump($languages instanceof LanguagesInterface);
// bool(true)
```

### Get Language

[](#get-language)

```
use Tobento\Service\Language\LanguageFactory;
use Tobento\Service\Language\Languages;
use Tobento\Service\Language\LanguagesInterface;
use Tobento\Service\Language\LanguageInterface;

$languageFactory = new LanguageFactory();

$languages = new Languages(
    $languageFactory->createLanguage(locale: 'en', default: true),
    $languageFactory->createLanguage(locale: 'de', fallback: 'en'),
);

$language = $languages->get('de-CH');
// supports locale, id, key or slug values (all are case-insensitive).

var_dump($language instanceof LanguageInterface);
// bool(true)

// Will return the default language as language does not exist.
var_dump($languages->get('it')->locale());
// string(2) "en"

// Without fallback
var_dump($languages->get(languageKey: 'fr', fallback: false)?->locale());
// NULL

var_dump($languages->get(languageKey: 'it', fallback: false)?->locale());
// NULL
```

**Check if a language exist:**

```
// supports locale, id, key or slug values (all are case-insensitive).

var_dump($languages->has('de-CH'));
// bool(true)

var_dump($languages->has('fr'));
// bool(false)
```

### Default Language

[](#default-language)

```
use Tobento\Service\Language\LanguageInterface;

$defaultLanguage = $languages->default();

var_dump($defaultLanguage instanceof LanguageInterface);
// bool(true)
```

### Current Language

[](#current-language)

**Set the current language:**

```
$languages->current('en');
// supports locale, id, key or slug values (all are case-insensitive).
```

> ⚠️ If the language does not exist, the default language will be set as the current language but only if none is defined.

**Get the current language:**

```
use Tobento\Service\Language\LanguageInterface;

$currentLanguage = $languages->current();

var_dump($currentLanguage instanceof LanguageInterface);
// bool(true)
```

### All Languages

[](#all-languages)

```
use Tobento\Service\Language\LanguageInterface;

$allLanguages = $languages->all();
// array

// or just
foreach($languages as $language) {}
```

### Columns

[](#columns)

Sometimes you may need only specific columns from the languages.

```
$locales = $languages->column('locale');
/*Array
(
    [0] => en
    [1] => de
    [2] => de-CH
)*/
```

**Index by language id:**

```
$locales = $languages->column('locale', 'id');
/*Array
(
    [1] => en
    [2] => de
    [3] => de-CH
)*/
```

### Fallbacks

[](#fallbacks)

**Get the fallbacks**

Returns fallbacks for all languages.

```
// by locale
$fallbacks = $languages->fallbacks();
/*Array
(
    [de] => en
    [de-CH] => de
    [fr] => en
    [it] => de
)*/

// by id:
$fallbacks = $languages->fallbacks('id');
/*Array
(
    [2] => 1
    [3] => 2
    [4] => 1
    [5] => 2
)*/

// by key:
$fallbacks = $languages->fallbacks('key');
/*Array
(
    [de] => en
    [de-ch] => de
    [fr] => en
    [it] => de
)*/

// by slug:
$fallbacks = $languages->fallbacks('slug');
/*Array
(
    [de] => en
    [de-ch] => de
    [fr] => en
    [it] => de
)*/
```

**Get the fallback language for a specific locale, id, key or slug**

If no fallback language is provided, the default language will be returned.

```
use Tobento\Service\Language\LanguageInterface;

$fallbackLanguage = $languages->getFallback('de-CH');

var_dump($fallbackLanguage instanceof LanguageInterface);
// bool(true)
```

### Miscellaneous Methods

[](#miscellaneous-methods)

**first**

```
use Tobento\Service\Language\LanguageInterface;

// returns first found active language:
var_dump($languages->first() instanceof LanguageInterface);
// bool(true) or NULL

// returns first found language:
$firstLanguage = $languages->first(activeOnly: false);
```

**filter**

Filter languages returning a new instance.

```
use Tobento\Service\Language\LanguageInterface;

$languagesNew = $languages->filter(
    fn(LanguageInterface $l): bool => $l->active()
);
```

**active**

Returns a new instance with the active or inactive languages.

```
use Tobento\Service\Language\LanguageInterface;

$activeLanguages = $languages->active();

$inactiveLanguages = $languages->active(active: false);
```

**domain**

Returns a new instance with the specified domain filtered.

```
use Tobento\Service\Language\LanguageInterface;

$chLanguages = $languages->domain('example.ch');

$undomainedLanguages = $languages->domain(null);
```

**map**

Map over each of the languages returning a new instance.

```
use Tobento\Service\Language\LanguageInterface;

$languagesNew = $languages->map(
    fn(LanguageInterface $l): LanguageInterface => $l->withName(strtoupper($l->name()))
);
```

**sort**

Sort languages returning a new instance.

```
use Tobento\Service\Language\LanguageInterface;

$languagesNew = $languages->sort(
    fn(LanguageInterface $a, LanguageInterface $b) => $a->locale()  $b->locale()
);
```

Area Languages
--------------

[](#area-languages)

**Create area languages**

```
use Tobento\Service\Language\LanguageFactory;
use Tobento\Service\Language\AreaLanguages;
use Tobento\Service\Language\AreaLanguagesInterface;
use Tobento\Service\Language\LanguagesFactoryInterface;

$languageFactory = new LanguageFactory();

$areaLanguages = new AreaLanguages(
    null, // null|LanguagesFactoryInterface
    $languageFactory->createLanguage(locale: 'en', area: 'frontend', default: true),
    $languageFactory->createLanguage(locale: 'de', area: 'frontend', fallback: 'en'),
    $languageFactory->createLanguage(locale: 'de-CH', area: 'frontend', fallback: 'de'),
    $languageFactory->createLanguage(locale: 'en', area: 'backend', default: true),
    $languageFactory->createLanguage(locale: 'de', area: 'backend', fallback: 'en'),
);

var_dump($areaLanguages instanceof AreaLanguagesInterface);
// bool(true)
```

**get / has**

```
use Tobento\Service\Language\LanguagesInterface;

$frontendLanguages = $areaLanguages->get('frontend');

var_dump($frontendLanguages instanceof LanguagesInterface);
// bool(true)

// return NULL if no languages found:
var_dump($areaLanguages->get('api'));
// NULL

var_dump($areaLanguages->has('frontend'));
// bool(true)
```

**add**

```
use Tobento\Service\Language\LanguageFactory;
use Tobento\Service\Language\Languages;
use Tobento\Service\Language\LanguagesInterface;

$factory = new LanguageFactory();

$languages = new Languages(
    $factory->createLanguage(locale: 'en', area: 'frontend', default: true),
);

$areaLanguages->add('frontend', $languages);
```

Current Language Resolver
-------------------------

[](#current-language-resolver)

You might want to use the current language resolver to set the current language. You might also write your own resolver depending on your needs such as a CurrentLanguageSessionResolver, CurrentLanguageServerRequestResolver and so on.

```
use Tobento\Service\Language\LanguageFactory;
use Tobento\Service\Language\Languages;
use Tobento\Service\Language\LanguagesInterface;
use Tobento\Service\Language\CurrentLanguageResolver;
use Tobento\Service\Language\CurrentLanguageResolverInterface;
use Tobento\Service\Language\CurrentLanguageResolverException;

$languageFactory = new LanguageFactory();

$languages = new Languages(
    $languageFactory->createLanguage('en', default: true),
    $languageFactory->createLanguage('de'),
);

$resolver = new CurrentLanguageResolver(
    currentLanguage: 'fr',
    allowFallbackToDefaultLanguage: false, // default is true
);

var_dump($resolver instanceof CurrentLanguageResolverInterface);
// bool(true)

try {
    $resolver->resolve($languages);
} catch (CurrentLanguageResolverException $e) {
    // do something
}
```

Credits
=======

[](#credits)

- [Tobias Strub](https://www.tobento.ch)
- [All Contributors](../../contributors)

###  Health Score

45

—

FairBetter than 92% of packages

Maintenance67

Regular maintenance activity

Popularity13

Limited adoption so far

Community13

Small or concentrated contributor base

Maturity74

Established project with proven stability

 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

Every ~145 days

Recently: every ~77 days

Total

11

Last Release

226d ago

Major Versions

1.x-dev → 2.02025-09-25

PHP version history (2 changes)1.0.0PHP &gt;=8.0

2.0PHP &gt;=8.4

### Community

Maintainers

![](https://www.gravatar.com/avatar/055d6a1b5c2384bb179c75ab0b55914231d898fdc4dffeb30770f81200e52206?d=identicon)[TOBENTOch](/maintainers/TOBENTOch)

---

Top Contributors

[![tobento-ch](https://avatars.githubusercontent.com/u/16684832?v=4)](https://github.com/tobento-ch "tobento-ch (23 commits)")

---

Tags

languagepackagetobentolanguage-manager

###  Code Quality

TestsPHPUnit

Static AnalysisPsalm

Type Coverage Yes

### Embed Badge

![Health badge](/badges/tobento-service-language/health.svg)

```
[![Health](https://phpackages.com/badges/tobento-service-language/health.svg)](https://phpackages.com/packages/tobento-service-language)
```

###  Alternatives

[codezero/laravel-localized-routes

A convenient way to set up, manage and use localized routes in a Laravel app.

543638.1k4](/packages/codezero-laravel-localized-routes)[gettext/languages

gettext languages with plural rules

7530.3M10](/packages/gettext-languages)[vanderlee/syllable

Text syllable splitting and hyphenation using Frank M. Liang's TeX algorithm.

124432.6k8](/packages/vanderlee-syllable)[pmochine/laravel-tongue

🎉 Finally a subdomain localization that works how you want it to work. 🌐

4158.4k](/packages/pmochine-laravel-tongue)[josiasmontag/laravel-redis-mock

This Laravel package provides a Redis mock for your tests

471.8M16](/packages/josiasmontag-laravel-redis-mock)[longman/laravel-multilang

Package to integrate multi language (multi locale) functionality in Laravel 5.x

5514.4k1](/packages/longman-laravel-multilang)

PHPackages © 2026

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