Autor:
    Data utworzenia:2026-06-14Ostatnia aktualizacja:2026-06-30

    Nowy Intlayer v9 - Co nowego?

    Witaj w Intlayer v9! To główne wydanie (major release) stanowi ogromny krok milowy w upraszczaniu ścieżki migracji do Intlayer dzięki pakietom kompatybilności (Compat Adapter Packages) dla najpopularniejszych bibliotek i18n (takich jak react-i18next, next-intl, vue-i18n itp.) oraz wprowadza wsparcie dla bogatych struktur treści: Kolekcji (Collections) i Wariantów (Variants).

    Spis treści


    Pakiety kompatybilności (Compat Adapter Packages)

    Migracja do Intlayer z popularnych bibliotek i18n jest teraz łatwiejsza niż kiedykolwiek. Stworzyliśmy pięć pakietów kompatybilności (compat packages), które udostępniają dokładnie to samo publiczne API co standardowe biblioteki i18n, ale delegują całą pracę związaną z tłumaczeniami do Intlayer w czasie działania aplikacji (runtime).

    To samo publiczne API ze ścisłym typowaniem (Strict Typing)

    Zastępując importy, zyskujesz wszystkie zalety Intlayer (w tym bezpieczeństwo typów w czasie kompilacji - compile-time type safety - w oparciu o Twoje rzeczywiste słowniki) przy minimalnych zmianach w kodzie:

    • @intlayer/i18next
    • @intlayer/react-i18next
    • @intlayer/next-intl
    • @intlayer/react-intl
    • @intlayer/next-i18next
    • @intlayer/vue-i18n
    • @intlayer/lingui

    Na przykład, po prostu zmień:

    ts
    import { useTranslation } from "react-i18next";

    na:

    ts
    import { useTranslation } from "@intlayer/react-i18next";

    Twoje klucze będą teraz ściśle typowane (strictly typed) w oparciu o słowniki Intlayer, oferując pełne autouzupełnianie ścieżek kropkowych (dot-path) w Twoim IDE!

    Pluginy aliasów dla bundlerów (Vite, Next.js, Turbopack)

    Aby umożliwić migrację bez konieczności ręcznego przepisywania wszystkich importów, każdy pakiet adaptera kompatybilności zawiera dedykowany plugin dla bundlera (Vite lub Next.js) w podścieżce /plugin.

    Pluginy te automatycznie przepisują istniejące importy (np. react-i18next lub next-intl) na ich odpowiedniki @intlayer/* w czasie budowania (build time).

    Przykład dla Next.js (Webpack / Turbopack)

    Zamiast withIntlayer, owiń swoją konfigurację Next.js pluginem kompatybilności:

    next.config.ts
    import { createNextI18nPlugin } from "@intlayer/next-i18next/plugin";import type { NextConfig } from "next";const withIntlayer = createNextI18nPlugin();const nextConfig: NextConfig = {};export default withIntlayer(nextConfig);

    Przykład dla Vite (React, Vue, Solid, Svelte)

    vite.config.ts
    import vueI18nVitePlugin from "@intlayer/vue-i18n/plugin";export default defineConfig({  plugins: [vueI18nVitePlugin()],});

    Wspólny parser czasu działania (Mutualized Runtime Resolver)

    Wszystkie adaptery kompatybilności kierują teraz proces rozwiązywania tłumaczeń przez jeden, wysoce zoptymalizowany parser czasu działania (runtime parser): @intlayer/core/messageFormat.

    • Interpolacja wiadomości (Interpolate Message): Obsługuje standardowe szablony {{var}} (ze spacjami i ścieżkami kropkowymi), argumenty formatowane w standardzie ICU ({v, number, percent} itp.) oraz proste szablony {var}.
    • Rozwiązywanie węzłów wiadomości (Message Node Resolver): Obsługuje zagnieżdżone węzły: insert(), plural() (reguły liczby mnogiej CLDR), enu() (wyliczenia), gender(), tagi HTML, tablice oraz węzły funkcji wywoływalnych (callable functions).
    • Parser tagów tokenizowanych (Tokenized Tag Parser): Wspiera wbudowane tagi XML/HTML oraz tagi numerowane (np. <1>children</1>), aby zapewnić renderowanie bogatego tekstu (rich-text) po wyjęciu z pudełka.

    Specyfikacja funkcji: Kolekcje i Warianty

    Intlayer v9 wykracza poza statyczne obiekty klucz-wartość, umożliwiając słownikom deklarowanie dynamicznych struktur układu, które są w pełni typowane od początku do końca (end-to-end).

    1. Kolekcje (Collections)

    Zdefiniuj zarządzaną przez CMS uporządkowaną lista elementów (np. FAQ, produkty lub listy blogów):

    faq.1.content.ts
    import { t, type Dictionary } from "intlayer";export default {  key: "faq",  item: 1,  content: {    question: t({ en: "What is Intlayer?", fr: "Qu'est-ce qu'Intlayer ?" }),    answer: t({ en: "An i18n toolkit.", fr: "Une boîte à outils i18n." }),  },} satisfies Dictionary;
    faq.2.content.ts
    import { t, type Dictionary } from "intlayer";export default {  key: "faq",  item: 2,  content: {    question: t({ en: "Is it free?", fr: "Est-ce gratuit ?" }),    answer: t({ en: "Yes, open-source.", fr: "Oui, open-source." }),  },} satisfies Dictionary;

    Użycie:

    ts
    // Fetch all items as an arrayconst allFaqs = useIntlayer("faq"); // -> { question: string, answer: string }[]// Fetch a single item by indexconst faq = useIntlayer("faq", { item: 2 }); // -> { question: string, answer: string }

    2. Warianty (Variants)

    Dostarczaj testy A/B, nagłówki sezonowe, flagi funkcji (feature flags) lub niestandardowe strony docelowe (landing pages):

    Warianty tekstowe (np. testy A/B)

    hero.content.ts
    import { t, type Dictionary } from "intlayer";export default {  key: "hero-banner",  variant: "default",  content: {    control: t({ pl: "Witaj", en: "Welcome", fr: "Bienvenue" }),    black_friday: t({      pl: "Kup teraz",      en: "Shop now",      fr: "Acheter maintenant",    }),  },} satisfies Dictionary;

    Użycie:

    ts
    const banner = useIntlayer("hero-banner", { variant: "black_friday" });

    Warianty obiektowe (np. Dynamic Records)

    product.content.ts
    import { t, type Dictionary } from "intlayer";export default {  key: "product-copy",  variant: {    id: "prod_123",    category: "books",  },  content: {    title: t({ pl: "Czysty kod", en: "Clean Code", fr: "Code Propre" }),  },} satisfies Dictionary;

    Użycie:

    ts
    // Pobiera dynamicznie tylko żądany element (wymaga Suspense)const product = useIntlayer("product-copy", {  variant: { id: "prod_123", category: "books" },});

    Vite Plugin: Bundled Compiler & Proxy

    Plugin Vite intlayer() teraz łączy kompilator i proxy do routingu locale'ów bezpośrednio, więc większość projektów potrzebuje tylko jednej wtyczki w vite.config.ts:

    vite.config.ts
    import { defineConfig } from "vite";import { intlayer } from "vite-intlayer";export default defineConfig({  plugins: [intlayer()],});
    • Compiler: Aktywuje się automatycznie, gdy compiler.enabled jest ustawione na true i skonfigurowana jest ścieżka compiler.output. Nie musisz już rejestrować intlayerCompiler() osobno.
    • Proxy: Aktywuje się automatycznie w oparciu o nową opcję routing.enableProxy (domyślnie true). Podłącza middleware do wykrywania locale'ów / przekierowywania / przepisywania w developmencie, preview i produkcyjnym SSR. Nie musisz już rejestrować intlayerProxy() osobno.

    Opcja routing.enableProxy

    Nowa opcja routing.enableProxy kontroluje, czy proxy routingu lokalizacji jest podłączony. Domyślnie ma wartość true. Wyłącz to, jeśli chcesz samodzielnie obsługiwać routing lokalizacji:

    intlayer.config.ts
    import type { IntlayerConfig } from "intlayer";const config: IntlayerConfig = {  routing: {    enableProxy: false, // Domyślnie: true  },};export default config;

    Autonomiczne pluginy intlayerCompiler() i intlayerProxy() pozostają eksportowane dla zaawansowanych konfiguracji. Rejestrowanie ich razem z intlayer() jest bezpieczne — każdy plugin deduplikuje się i uruchamia się tylko raz.


    Kompilator domyślnie wyłączony

    Od Intlayer v9 kompilator jest domyślnie wyłączony (compiler.enabled ma teraz domyślnie wartość false). Aby włączyć ekstrakcję plików .content.ts w czasie budowania, ustaw compiler.enabled: true w swojej konfiguracji:

    intlayer.config.ts
    import type { IntlayerConfig } from "intlayer";const config: IntlayerConfig = {  compiler: {    enabled: true, // Domyślnie: false — wymagane do włączenia kompilatora od wersji v9    output: ({ fileName }) => `./${fileName}.content.ts`,  },};export default config;

    Gdy kompilator jest wyłączony, Intlayer pomija krok ekstrakcji w czasie budowania i opiera się na już zadeklarowanych słownikach. Włącz go tylko wtedy, gdy chcesz, aby plugin bundlera (@intlayer/swc, @intlayer/babel lub plugin Vite intlayer()) automatycznie wyodrębniał zawartość.


    React Native: importy z jednego pakietu

    W aplikacji React Native lub Expo nie musisz już żonglować pakietami react-intlayer i react-native-intlayer. Pakiet react-native-intlayer teraz ponownie eksportuje pełne API react-intlayer (hooki, narzędzia oraz podścieżki /format, /html i /markdown), a jego IntlayerProvider automatycznie stosuje polyfille React Native.

    Importuj wszystko z jednego pakietu react-native-intlayer:

    tsx
    import {  IntlayerProvider,  useIntlayer,  useLocale,} from "react-native-intlayer";
    bash
    npm install intlayer react-native-intlayer
    Importowanie z react-intlayer nadal działa, ale react-native-intlayer jest teraz zalecanym pojedynczym punktem wejścia dla React Native — jego provider zawiera polyfille, których nie posiada zorientowany na web provider react-intlayer.

    SDK CMS: używaj Intlayer jako bezgłowej bazy danych treści

    Intlayer v9 dostarcza przejrzysty, samodzielnie uwierzytelniający się SDK w @intlayer/api do programowej interakcji z CMS — pobieranie projektów, pobieranie słowników oraz wysyłanie lub aktualizowanie ich z własnego serwera, skryptów lub CI. Uwierzytelnianie (OAuth2 client_credentials) jest obsługiwane i odświeżane za Ciebie.

    SDK jest podzielony na dwa osobne importy, dzięki czemu Twój bundle zawiera tylko te domeny, których faktycznie używasz:

    1. createIntlayerCMS — lekki uwierzytelniacz przechowujący poświadczenia i zarządzany token (bez dołączania klienta domeny).
    2. dictionaryEndpoint, projectEndpoint, … — łączniki endpointów dla poszczególnych domen, każdy importowany z własnej podścieżki.
    cms.ts
    import { createIntlayerCMS } from "@intlayer/api";import { dictionaryEndpoint } from "@intlayer/api/dictionary";// Konfiguracja jest opcjonalna: poświadczenia są pobierane z INTLAYER_CLIENT_ID /// INTLAYER_CLIENT_SECRET rozwiązywanych przez `@intlayer/config/built`.const cms = createIntlayerCMS();// Odczytconst { data: dictionaries } = await dictionaryEndpoint(cms).getDictionaries();// Zapis — używaj CMS jak bazy danychawait dictionaryEndpoint(cms).pushDictionaries([myDictionary]);
    Bezpieczeństwo: poświadczenia CMS dają dostęp do zapisu Twoich treści. Twórz uwierzytelniacz wyłącznie po stronie serwera — nigdy nie wysyłaj clientId / clientSecret do przeglądarki.

    Samodzielne hostowanie (Self-Hosting)

    Intlayer v9 zapewnia pełne wsparcie dla uruchamiania własnej instancji Intlayer za pomocą jednej komendy — bez konieczności posiadania konta Intlayer Cloud.

    sh
    curl -fsSL https://intlayer.org/install.sh | sh

    Instalator pobiera docker-compose.yml i .env, automatycznie generuje wymagane sekrety i uruchamia docker compose up -d. Wszystko — panel, API, baza danych, magazyn obiektów oraz transakcyjne wiadomości e-mail — działa lokalnie w kontenerach.

    Uwzględnione serwisy

    Serwis Przeznaczenie
    app (TanStack Start) Interfejs panelu na porcie 3000
    backend (Fastify/Bun) REST API na porcie 3100
    MongoDB 7 (jednowęzłowy zestaw replik) Główna baza danych
    Redis 7 Kolejki zadań i pamięć podręczna
    MinIO Magazyn obiektów zgodny z S3 (awatary, zrzuty ekranu)
    Mailpit Lokalny odbiorca SMTP + interfejs webowy dla poczty transakcyjnej na porcie 8025

    Chromium (używany do generowania zrzutów ekranu przez Puppeteer) jest wbudowany w obraz backendu — żaden dodatkowy kontener nie jest potrzebny.


    Uwagi dotyczące migracji z wersji v8

    Jeśli aktualizujesz aplikację z wersji v8, pamiętaj, że wersja v9 nie zawiera zmian wprowadzających niekompatybilność wsteczną (breaking changes). Oto jednak kluczowe zmiany:

    • Kompilator domyślnie wyłączony: compiler.enabled ma teraz domyślnie wartość false. Jeśli polegasz na ekstrakcji plików .content.ts w czasie budowania, ustaw compiler.enabled: true w swoim intlayer.config.ts.
    • Języki i dialekty (Locales & Dialects): Jeśli używasz zewnętrznych zależności i18n, dodaj odpowiednie pluginy adapterów kompatybilności w swojej konfiguracji lub konfiguracji bundlera, aby automatycznie przepisywać importy.
    • Niestandardowe selektory (Custom Selectors): Podczas wywoływania useIntlayer, drugi parametr jest teraz zarezerwowany dla obiektu opcji zawierającego { locale, item, variant }. Jeśli wcześniej przekazywałeś bezpośrednio ciąg znaków języka (locale string), nadal możesz to robić, jednak zaleca się używanie obiektu opcji przy bardziej zaawansowanych wyborach.

    Przydatne linki