# gt-react: General Translation React SDK: SPA Quickstart
URL: https://generaltranslation.com/en-US/docs/react/tutorials/quickstart-spa.mdx
---
title: SPA Quickstart
description: Add multiple languages to your single-page React app in under 10 minutes
---
By the end of this guide, your single-page React app will display content in multiple languages, with a language switcher your users can interact with.
In a single-page app, `gt-react` runs entirely in the browser — you initialize it once at startup with `initializeGTSPA()`, and you don't need a provider component.
**Prerequisites:**
- A client-side rendered React app (Vite, webpack, or similar)
- Node.js 18+
**Want automatic setup?** Run `npx gt@latest` to configure everything with the [Setup Wizard](/docs/cli/init). This guide covers manual setup.
**Server-rendered app?** If your app renders on the server, follow the [React quickstart](/docs/react) instead.
---
## Step 1: Install the packages
`gt-react` is the library that powers translations in your app. `gt` is the CLI tool that prepares your translations.
```bash
npm i gt-react
npm i -D gt
```
```bash
yarn add gt-react
yarn add --dev gt
```
```bash
bun add gt-react
bun add --dev gt
```
```bash
pnpm add gt-react
pnpm add --save-dev gt
```
---
## Step 2: Create a translation config file
Create a **`gt.config.json`** file in your project root. This tells the library which languages you support:
```json title="gt.config.json"
{
"defaultLocale": "en",
"locales": ["es", "fr", "ja"],
"files": {
"gt": {
"output": "src/_gt/[locale].json"
}
}
}
```
- **`defaultLocale`** — the language your app is written in (your source language).
- **`locales`** — the languages you want to translate into. Pick any from the [supported locales list](/docs/platform/supported-locales).
- **`files`** — tells the CLI where to save translation files. The `output` path should match the import path in your `loadTranslations` function (Step 3).
**File location:** Bundlers like Vite import translation files as modules, so they should live inside `src/`.
---
## Step 3: Create a translation loader
In an SPA, `gt-react` needs a function to load translation files in the browser at runtime. Create a `loadTranslations` file:
```ts title="src/loadTranslations.ts"
export default async function loadTranslations(locale: string) {
try {
const translations = await import(`./_gt/${locale}.json`);
return translations.default;
} catch (error) {
console.warn(`No translations found for ${locale}`);
return {};
}
}
```
This function loads JSON translation files from your `src/_gt/` directory. The CLI generates these files when you run `npx gt translate`.
---
## Step 4: Initialize the library
Call **`initializeGTSPA`** once at startup, before your app renders. It takes your config and translation loader, determines the user's locale, and loads the translations for it.
The most robust pattern is a small entry module that initializes GT first, then loads the rest of the app:
```ts title="src/index.ts"
import { initializeGTSPA } from 'gt-react';
import gtConfig from '../gt.config.json';
import loadTranslations from './loadTranslations';
await initializeGTSPA({
defaultLocale: gtConfig.defaultLocale,
locales: gtConfig.locales,
loadTranslations,
});
await import('./main'); // render the app only after GT is ready
```
```tsx title="src/main.tsx"
import { StrictMode } from 'react';
import { createRoot } from 'react-dom/client';
import App from './App';
createRoot(document.getElementById('root')!).render(
);
```
Then update the module script tag in your `index.html` to point at the new entry: change its `src` from `/src/main.tsx` to `/src/index.ts`.
`initializeGTSPA` runs once at startup — the configuration is immutable for the lifetime of the app. After it resolves, every component and hook in your app can access translations. **You don't need to wrap your app in a provider.**
**Want live translations in development?** Follow the [SPA development translations guide](/docs/react/tutorials/spa-development-translations) to add the compiler and development credentials.
---
## Step 5: Mark content for translation
Now, wrap any text you want translated with the **``** component. `` stands for "translate":
```tsx title="src/components/Welcome.tsx"
import { T } from 'gt-react';
export default function Welcome() {
return (
Welcome to my app
This content will be translated automatically.
);
}
```
You can wrap as much or as little JSX as you want inside ``. Everything inside it — text, nested elements, even formatting — gets translated as a unit.
For strings outside React components, use **`t()`**. It works at module level because `initializeGTSPA()` loads translations before the rest of your app:
```ts title="src/navigation.ts"
import { t } from 'gt-react';
export const navigation = [
{ label: t('Home'), href: '/' },
{ label: t('About'), href: '/about' },
];
```
---
## Step 6: Add a language switcher
Drop in a **``** so users can change languages:
```tsx title="src/components/Welcome.tsx"
import { T, LocaleSelector } from 'gt-react';
export default function Welcome() {
return (