Quick Start
SvelteKit
This page demonstrates the minimal setup of Intor in a SvelteKit project.
Installation
This example is based on the SvelteKit minimal template.
For details, see: SvelteKit 。
Install Intor:
npm install intoryarn add intorpnpm add intorbun add intor
After installation, update vite.config.ts to ensure Intor is bundled correctly in SSR.
export default defineConfig({ plugins: [sveltekit()], ssr: { noExternal: ["intor"] }, // Ensure Intor is bundled for SSR });
Project Structure
index.jsonUindex.jsonU+layout.server.tsU+layout.svelteM+page.svelteMintor-config.tsUapp.d.tsMapp.htmlMhooks.server.tsU
Integration Steps
♯1 Messages
Create a messages directory in your project, and add a subdirectory for each locale.
Each locale provides an index.json file.
index.jsonUindex.jsonU
{ "hello": "Hello, {name}", "rich": "A <tag>text</tag>." }
{ "hello": "Bonjour, {name}", "rich": "Un <tag>texte</tag>." }
♯2 Config
Create an i18n/ directory under src/lib/, and add an intor-config.ts file inside it.
This example uses the most basic translation loading approach by defining messages directly in the config.
For more details, see: Message Loading
intor-config.tsU
import { defineIntorConfig } from "intor"; import EN from "../../../messages/en/index.json"; import FR from "../../../messages/fr/index.json"; export const intorConfig = defineIntorConfig({ defaultLocale: "en", supportedLocales: ["en", "fr"], messages: { en: EN, fr: FR, }, });
♯3 Initialization
- Create
hooks.server.tsundersrc/to integrate Intor into the request flow.
hooks.server.tsU
import { createIntorHandler } from "intor/svelte-kit"; import { intorConfig } from "$lib/i18n/intor-config"; export const handle = createIntorHandler(intorConfig);
- Update
app.d.tsto extend the required type definitions.
app.d.tsM
import type { InboundContext } from "intor"; declare global { namespace App { interface Locals { intor: InboundContext; } } } export {};
- Update
app.htmlto add a placeholder for the document language attribute.
app.htmlM
// ... <html lang="%lang%"> // ...
- Create
+layout.server.tsundersrc/routes/and callintor()to initialize the translation system during SSR.
+layout.server.tsU
import { intor } from "intor/server"; import { intorConfig } from "$lib/i18n/intor-config"; export const load = async ({ locals, fetch }) => { const intorValue = await intor(intorConfig, locals.intor.locale, { fetch }); return { intorValue }; };
- Update
+layout.svelteand wrap the application withIntorProvider.
+layout.svelteM
<script lang="ts"> import favicon from "$lib/assets/favicon.svg"; import { IntorProvider } from "intor/svelte"; let { children, data } = $props(); </script> <svelte:head> <link rel="icon" href={favicon} /> </svelte:head> <IntorProvider value={data.intorValue}> {@render children()} </IntorProvider>
Usage Example
Use useTranslator to access translation capabilities:
t: returns the resolved texttRich: renders structured messages with semantic tags
Use useNavigation to access navigation capabilities:
goto: handles navigation and locale switching
+page.svelteM
<script lang="ts"> import { useTranslator } from "intor/svelte"; import { useNavigation } from "intor/svelte-kit"; const { t, tRich } = useTranslator(); const { goto } = useNavigation(); </script> <p>{$t("hello", { name: "Intor" })}</p> <p>{@html $tRich("rich", { tag: (children) => `<b>${children}</b>` })}</p> <button onclick={() => goto("/", { locale: "en" })}>English</button> <button onclick={() => goto("/", { locale: "fr" })}>French</button>
Server-side
On the server side, the same translation capabilities can be accessed via getTranslator().
This can be used for metadata generation, API routes, or other server-only execution environments.
+layout.server.tsM
import { getTranslator } from "intor/server"; // ... const { t } = await getTranslator(intorConfig, { locale: locals.intor.locale, });