# General Translation Knowledge Base: Come si migra da next-intl a gt-next?
URL: https://generaltranslation.com/it/kb/migrate-from-next-intl.mdx
Docs index: https://generaltranslation.com/llms.txt
Description: Sostituisci il plugin, il middleware e il provider di next-intl con quelli di gt-next, replica la sua impostazione del prefisso dell'impostazione regionale e carica messages/en.json come dizionario gt-next, così i messaggi ICU e le traduzioni esistenti continuano a funzionare. Mappa gli eventuali pathname localizzati prima di eliminare il routing di next-intl, poi sposta i testi inline in `<T>` una route alla volta.
Category: Internazionalizzazione
Last updated: 2026-11-11
Authors: Kevin Wu
Published: 2026-11-11

next-intl e gt-next localizzano entrambi le app Next.js basate su App Router, con route prefissate dall'impostazione regionale e Componenti server, quindi la struttura dell&#39;app cambia pochissimo. I tuoi messaggi next-intl sono già in ICU MessageFormat, lo stesso formato usato dai dizionari gt-next. Puoi quindi mantenere `messages/en.json` e i cataloghi tradotti durante il passaggio di libreria, e poi spostare i testi inline in [`<T>`](/docs/react/reference/components/t) con i tuoi tempi.

Se i tuoi cataloghi funzionano e l&#39;unico problema è la lentezza nel produrre le traduzioni, forse non ti serve migrare. Se resti su next-intl, la CLI `gt` traduce i suoi cataloghi in-place. (Vedi [next-intl vs. gt-next](/kb/next-intl-vs-gt-next).)

## Qual è la corrispondenza tra le API di next-intl e quelle di gt-next?

| next-intl                                                                          | gt-next                                                                                                                                                                                                                                                                       |
| ---------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `defineRouting({ locales, defaultLocale })`                                        | `defaultLocale` e `locales` in `gt.config.json`                                                                                                                                                                                                                               |
| `createNextIntlPlugin()` in `next.config.ts`                                       | [`withGTConfig`](/docs/react/nextjs/config) da `gt-next/config`                                                                                                                                                                                                               |
| `createMiddleware(routing)` in `proxy.ts`                                          | [`createNextMiddleware`](/docs/react/nextjs/reference/functions/create-next-middleware) da `gt-next/middleware`                                                                                                                                                               |
| `localePrefix: 'as-needed'` / `'always'`                                           | `prefixDefaultLocale: false` (valore predefinito) / `true`                                                                                                                                                                                                                    |
| `getRequestConfig` in `i18n/request.ts`                                            | Un file `getLocale.ts` nella radice che legge `next/root-params`, più l&#39;opzione `dictionary`                                                                                                                                                                              |
| `NextIntlClientProvider`                                                           | [`GTProvider`](/docs/react/reference/components/gt-provider) in `app/[locale]/layout.tsx`                                                                                                                                                                                     |
| `useTranslations('ns')`                                                            | [`useTranslations`](/docs/react/reference/hooks/use-translations)`('ns')` da `gt-next`                                                                                                                                                                                        |
| `await getTranslations('ns')`                                                      | `await` [`getTranslations`](/docs/react/nextjs/reference/functions/get-translations)`('ns')` da `gt-next/server`                                                                                                                                                              |
| `t.rich` e `t.markup`                                                              | [`<T>`](/docs/react/reference/components/t) che racchiude direttamente il JSX                                                                                                                                                                                                 |
| `useFormatter` / `getFormatter`                                                    | [`<Num>`](/docs/react/reference/components/num), [`<Currency>`](/docs/react/reference/components/currency), [`<DateTime>`](/docs/react/reference/components/datetime) e [`<RelativeTime>`](/docs/react/reference/components/relative-time), oppure argomenti ICU nei messaggi |
| [`useLocale` / `getLocale`](https://next-intl.dev/docs/usage/configuration#locale) | [`useLocale`](/docs/react/reference/hooks/use-locale) / [`getLocale`](/docs/react/nextjs/reference/functions/get-locale)                                                                                                                                                      |
| `setRequestLocale(locale)`                                                         | Non necessario per pagine e layout con `getLocale.ts`; [`registerLocale`](/docs/react/nextjs/reference/functions/register-locale) per i gestori di route e le route di immagini                                                                                               |
| `Link` da `createNavigation`                                                       | [`Link`](/docs/react/nextjs/link) da `gt-next/link`                                                                                                                                                                                                                           |
| `useRouter` / `getPathname` / `redirect`                                           | Le API native di Next.js insieme a [`useLocalizeHref`](/docs/react/nextjs/reference/hooks/use-localize-href) o [`getLocalizeHref`](/docs/react/nextjs/reference/functions/get-localize-href)                                                                                  |
| Cookie `NEXT_LOCALE`                                                               | `generaltranslation.locale`, rinominabile tramite `headersAndCookies.localeCookieName`                                                                                                                                                                                        |

## Passaggio 1: Sostituisci il plugin e mantieni i tuoi messaggi

Installa `gt-next` e la CLI `gt`, poi elenca le tue lingue in `gt.config.json`. Fai puntare `withGTConfig` al tuo catalogo di origine esistente e replica la struttura degli URL di next-intl:

```ts title="next.config.ts"
import type { NextConfig } from 'next';
import { withGTConfig } from 'gt-next/config';

const nextConfig: NextConfig = {};

export default withGTConfig(nextConfig, {
  dictionary: './messages/en.json',
  prefixDefaultLocale: true, // valore predefinito di next-intl, localePrefix: 'always'
  headersAndCookies: { localeCookieName: 'NEXT_LOCALE' }, // conserva la lingua dei visitatori abituali
});
```

Ometti `prefixDefaultLocale` se hai usato `localePrefix: 'as-needed'`. Imposta le opzioni di routing in `withGTConfig` e non solo nel middleware, perché il componente `<Link>` di gt-next le legge da lì.

Questo esempio copre i prefissi del locale standard, come `/de/about`. Se la tua chiamata a `defineRouting` personalizza le route, trasferisci ogni personalizzazione prima che il Passaggio 2 la elimini:

* **Pathname localizzati** (`pathnames`, come `/de/ueber-uns`): mappa ciascuno con l&#39;opzione [`pathConfig`](/docs/react/nextjs/reference/functions/create-next-middleware#path-config) di gt-next, che accetta la stessa struttura: un percorso condiviso e un percorso localizzato per ogni impostazione regionale.
* **Prefissi personalizzati, routing basato su dominio o `localePrefix: 'never'`:** gt-next non ha un equivalente diretto. Stabilisci i nuovi URL e aggiungi reindirizzamenti permanenti da quelli vecchi prima di rimuovere il routing di next-intl.

Per continuare a servire le traduzioni già revisionate, aggiungi un file `loadDictionary.ts` nella radice del progetto. gt-next lo rileva automaticamente:

```ts title="loadDictionary.ts"
export default async function loadDictionary(locale: string) {
  try {
    return (await import(`./messages/${locale}.json`)).default;
  } catch {
    return {}; // una nuova impostazione regionale senza catalogo utilizza le traduzioni di General Translation
  }
}
```

Le voci in questi file hanno la precedenza. Per qualsiasi chiave assente da un catalogo viene renderizzata la traduzione di General Translation. Se `gt.config.json` elenca già questi cataloghi in `files`, rimuovi quella voce: ora gt-next li carica come dizionari e ogni stringa deve avere un&#39;unica fonte di traduzione.

## Passaggio 2: Sostituisci il middleware, il layout e la config della richiesta

Sostituisci il middleware di next-intl in `proxy.ts` (`middleware.ts` in Next.js 15 e versioni precedenti):

```ts title="proxy.ts"
import { createNextMiddleware } from 'gt-next/middleware';

export default createNextMiddleware();

export const config = {
  matcher: ['/((?!api|static|.*\\..*|_next).*)'],
};
```

Dopo aver mappato le route, elimina `i18n/request.ts` e `i18n/routing.ts`. Al loro posto, aggiungi un file `getLocale.ts` nella radice, in modo che pagine e layout possano essere renderizzati staticamente senza `setRequestLocale`:

```ts title="getLocale.ts"
import { locale } from 'next/root-params';

export default async function getLocale() {
  return await locale();
}
```

`next/root-params` richiede Next.js 15.5 o versioni successive; per le versioni dalla 15.2 alla 15.4, consulta la [guida al middleware](/docs/react/nextjs/app-router-middleware#root-locale). Poi sostituisci il provider nel layout dell&#39;impostazione regionale:

```tsx title="app/[locale]/layout.tsx"
import { GTProvider, getLocales } from 'gt-next';
import { getLocale } from 'gt-next/server';

export function generateStaticParams() {
  return getLocales().map((locale) => ({ locale }));
}

export default async function LocaleLayout({ children }: { children: React.ReactNode }) {
  return (
    <html lang={await getLocale()}>
      <body>
        <GTProvider>{children}</GTProvider>
      </body>
    </html>
  );
}
```

Per impostazione predefinita, se il segmento di impostazione regionale non è supportato, gt-next ripiega su `defaultLocale`. Per restituire un 404, come fa il controllo `hasLocale` di next-intl, verifica il segmento con [`isLocaleSupported`](/docs/react/nextjs/reference/functions/is-locale-supported) e chiama `notFound()`.

## Passaggio 3: Modificare le importazioni

Una volta caricato il catalogo come dizionario, nella maggior parte dei componenti basta cambiare la riga di importazione:

```tsx
// Prima
import { useTranslations } from 'next-intl';
import { getTranslations } from 'next-intl/server';
import { Link } from '@/i18n/navigation';

// Dopo
import { useTranslations } from 'gt-next';
import { getTranslations } from 'gt-next/server';
import Link from 'gt-next/link';
```

`t('heading')`, i namespace, i segnaposto `{name}` e i messaggi ICU `plural` e `select` funzionano senza modifiche, anche in `generateMetadata`. Tre pattern richiedono interventi:

* **`t.rich` e `t.markup`.** La funzione [`t()`](/docs/react/reference/hooks/use-translations) di gt-next restituisce una stringa. Sposta il testo ricco inline all&#39;interno di [`<T>`](/docs/react/reference/components/t), usando elementi reali.
* **`t.raw` con array.** gt-next non dispone di `t.raw` e interpreta un array del dizionario solo come un messaggio con le relative opzioni. Ristruttura gli elenchi come oggetti annidati e leggili con [`t.obj()`](/docs/react/guides/translating-with-dictionaries#objects) oppure una chiave alla volta.
* **Chiavi mancanti.** next-intl registra un errore e renderizza un fallback; gt-next invece solleva un&#39;eccezione, quindi verifica dove viene usata una chiave prima di eliminarla dal catalogo.

Poi esegui [`npx gt validate`](/docs/cli/reference/commands/validate) per individuare le voci che non sono ICU valido e [`npx gt translate --dictionary ./messages/en.json`](/docs/cli/reference/commands/translate) per generare le traduzioni delle chiavi mancanti nei tuoi cataloghi e di eventuali nuove impostazioni regionali. La CLI rileva automaticamente un dizionario solo se si chiama `dictionary.json`, `.ts` o `.js` e si trova nella radice del progetto o in `src/`: passa quindi `--dictionary ./messages/en.json` a entrambi i comandi, sia in locale sia in CI, finché continui a usare il catalogo:

```bash
npx gt validate --dictionary ./messages/en.json
npx gt translate --dictionary ./messages/en.json
```

## Passaggio 4: Sposta i testi inline, una route alla volta

Le chiavi continuano a funzionare, quindi puoi anche fermarti qui. Se vuoi tenere i testi accanto al JSX che li renderizza, spostali in [`<T>`](/docs/react/reference/components/t) una route alla volta, partendo dai messaggi `t.rich`:

```tsx
// Prima: "terms": "By continuing you accept the <link>terms</link>."
t.rich('terms', { link: (chunks) => <a href="/terms">{chunks}</a> });

// Dopo
<T>
  By continuing you accept the <a href="/terms">terms</a>.
</T>
```

Nei Componenti server asincroni, usa [`getGT`](/docs/react/nextjs/reference/functions/get-gt) per le semplici stringhe. Lo stesso comando [`npx gt translate`](/docs/cli/reference/commands/translate) genera nuove traduzioni per i testi che sposti inline, usando il JSX circostante come contesto. I revisori possono correggerle nella [Dashboard](/docs/platform/dashboard/guides/reviewing-translations), mentre il Glossario di un [gruppo di contesto](/docs/platform/dashboard/guides/defining-context-for-translations) mantiene coerente la tua terminologia. Elimina ogni chiave dai tuoi cataloghi non appena nessuna parte del codice la usa più.

## Passaggio 5: Rimuovere next-intl

Quando la ricerca di `next-intl` non restituisce più alcun risultato, rimuovi la dipendenza e `createNextIntlPlugin`, quindi testa una build di produzione in ogni impostazione regionale. Poi aggiungi [`npx gt translate`](/docs/cli/reference/commands/translate) alla tua build o alla [CI](/kb/translations-in-ci), così i nuovi testi vengono rilasciati già tradotti, con `--dictionary ./messages/en.json` se hai mantenuto il catalogo.

## Domande frequenti

### I miei URL cambieranno?

No, per i prefissi standard del locale, a patto di replicare l&#39;impostazione di next-intl: `localePrefix: 'as-needed'` corrisponde al comportamento predefinito di gt-next, mentre `'always'` corrisponde a `prefixDefaultLocale: true`. Anche gt-next utilizza un segmento `app/[locale]`. I pathname localizzati richiedono una mappatura `pathConfig` esplicita, mentre i prefissi personalizzati e il routing basato sui domini non hanno un equivalente diretto in gt-next: configura quindi dei reindirizzamenti per questi URL e verifica ogni route prima di rimuovere il routing di next-intl.

### Perderò le traduzioni esistenti?

No. Carica i tuoi cataloghi next-intl con [`loadDictionary`](/docs/react/reference/functions/load-dictionary) e verranno renderizzati come prima. General Translation traduce solo le chiavi mancanti, oltre ai testi che in seguito sposterai inline in [`<T>`](/docs/react/reference/components/t).

### gt-next supporta il rendering statico?

Sì. Aggiungi un file `getLocale.ts` nella radice del progetto e `generateStaticParams`. (Vedi [Generazione di Siti Statici](/docs/react/nextjs/app-router-static-site-generation).)

### gt-next è gratuito?

gt-next è distribuito con licenza MIT e renderizza le traduzioni incluse nel bundle senza bisogno di un account. La generazione delle traduzioni con General Translation prevede una [tariffazione a consumo](https://generaltranslation.com/pricing).

## Punti chiave

* Sostituisci il plugin, il middleware, la config della richiesta e il provider di next-intl con `withGTConfig`, [`createNextMiddleware`](/docs/react/nextjs/reference/functions/create-next-middleware), `getLocale.ts` e [`GTProvider`](/docs/react/reference/components/gt-provider).
* Mantieni `messages/en.json` come dizionario di gt-next e carica i cataloghi tradotti tramite [`loadDictionary`](/docs/react/reference/functions/load-dictionary); i messaggi ICU funzionano senza modifiche.
* Allinea `localePrefix` con `prefixDefaultLocale` e mantieni il cookie `NEXT_LOCALE`, in modo che gli URL standard per impostazione regionale e le preferenze salvate continuino a funzionare; mappa i pathname localizzati con `pathConfig` prima di rimuovere il routing di next-intl.
* Riscrivi `t.rich` con [`<T>`](/docs/react/reference/components/t), quindi sposta gli altri testi inline una route alla volta.

## Related questions

- [Alternative a next-intl: gt-next vs. next-intl](https://generaltranslation.com/it/kb/next-intl-vs-gt-next.mdx): next-intl renderizza le traduzioni che fornisci in un catalogo di messaggi per ciascuna lingua. Anche gt-next renderizza le traduzioni, ma in più General Translation le genera a partire dai testi scritti inline nel tuo JSX. Entrambi sono rilasciati con licenza MIT e supportano l'App Router e i Componenti server. Se i tuoi cataloghi next-intl funzionano già, puoi mantenerli e usare General Translation per tradurli senza alcuna migrazione.
- [Come si aggiunge l'i18n a un'app Next.js con App Router?](https://generaltranslation.com/it/kb/add-i18n-to-nextjs.mdx): Inizia con gt init per configurare General Translation in un progetto App Router supportato, poi contrassegna il contenuto di origine, genera le traduzioni e verifica il cambio di lingua. gt-next mantiene i testi nel JSX insieme al contesto di traduzione; la CLI, l'editor della Dashboard e Locadex si occupano di generazione, revisione e aggiornamenti continui. Questa guida mostra anche la configurazione esplicita con file locali.
- [Come si configura la SEO per un'app Next.js multilingue?](https://generaltranslation.com/it/kb/multilingual-nextjs-seo.mdx): Assegna a ogni lingua un proprio URL con prefisso, come /en/about e /es/about, quindi pubblica html lang, un canonical autoreferenziale, alternative hreflang con x-default, un titolo e una descrizione tradotti e una voce nella mappa del sito per ogni lingua pubblicata. Contrassegna con noindex le versioni non pubblicate. gt-next di General Translation instrada ogni lingua verso il proprio URL e traduce i titoli con getGT.
- [Reindirizzamenti per lingua e SEO: URL, cookie o Accept-Language?](https://generaltranslation.com/it/kb/locale-routing-seo.mdx): Lascia che sia l'URL a stabilire la lingua di ogni pagina che vuoi far indicizzare, perché Googlebot non invia alcuna intestazione Accept-Language ed esegue la scansione soprattutto da indirizzi statunitensi. Usa la scelta salvata in un cookie e, in subordine, Accept-Language solo per decidere verso quale pagina reindirizzare una radice neutra come /, con un reindirizzamento temporaneo 302 o 307.
- [Come mantengo le traduzioni aggiornate a ogni distribuzione?](https://generaltranslation.com/it/kb/translations-in-ci.mdx): Esegui la traduzione come passaggio della pipeline prima di ogni build di produzione, così i nuovi testi vengono rilasciati già tradotti insieme alla distribuzione che li introduce. La CLI gt di General Translation lo fa con npx gt translate, usando una chiave API e un ID progetto archiviati come segreti CI.

## Previous and next questions

- Previous question: [Quali strumenti di traduzione fanno pagare in base all'utilizzo anziché per postazione?](https://generaltranslation.com/it/kb/translation-pricing-without-seat-fees.mdx)
- Next question: [Come si migra da react-i18next a gt-react?](https://generaltranslation.com/it/kb/migrate-from-react-i18next.mdx)

## Sitemap

See the [Knowledge Base sitemap](https://generaltranslation.com/it/kb/sitemap.md) for every article.
