Trang chủSandboxTrưng bàyỨng dụngTài liệuBlog
    • EnglishTiếng Anh
      EN
    • русскийTiếng Nga
      RU
    • 日本語Tiếng Nhật
      JA
    • françaisTiếng Pháp
      FR
    • 한국어Tiếng Hàn
      KO
    • 中文Tiếng Trung
      ZH
    • españolTiếng Tây Ban Nha
      ES
    • DeutschTiếng Đức
      DE
    • العربيةTiếng Ả Rập
      AR
    • italianoTiếng Italy
      IT
    • British EnglishTiếng Anh (Anh)
      EN-GB
    • portuguêsTiếng Bồ Đào Nha
      PT
    • हिन्दीTiếng Hindi
      HI
    • TürkçeTiếng Thổ Nhĩ Kỳ
      TR
    • polskiTiếng Ba Lan
      PL
    • IndonesiaTiếng Indonesia
      ID
    • Tiếng ViệtTiếng Việt
      VI
    • українськаTiếng Ukraina
      UK
    /
    Lọc tài liệu theo framework
    Alt+←
    Tại sao Intlayer?
    Bắt đầu
    Khái niệm
    • Intlayer làm việc như thế nào
    • Cấu hình
    • TestFillBuildWatchExtractLoginPushPullConfigurationListVersionEditorLiveDebugDoc ReviewDoc TranslateSDK
    • Editor visual
    • CMS
    • Tích hợp CI/CD
    • DịchSố nhiềuLiệt kêĐiều kiệnGiới tínhChènTệpNestingMarkdownHTMLLấy hàm
    • File cho mỗi ngôn ngữ
    • Biên dịch
    • Tự động điền
    • Kiểm tra
    • Tối ưu hóa gói
    Môi trường
    • Next.js 14 và App Router
      Next.js 15
      Next.js không locale URL
      Next.js và Page Router
      Trình biên dịch
    • Tanstack Start Solid
    • Astro và React
      Astro và Svelte
      Astro và Vue
      Astro và Solid
      Astro và Preact
      Astro và Lit
      Astro và Vanilla JS
    • React Router v7
      React Router v7 (fs-routes)
      Compiler
    • Nuxt và Vue
    • Vite và Solid
    • SvelteKit
    • Vite và Preact
    • Vite và Vanilla JS
    • Vite và Lit
    • Angular 19 (Webpack)
      Analog
    • React CRA
    • React Native và Expo
    • Express.js
      NestJS
      Fastify
      Hono
      Adonis
    • Lynx và React
    Plugins
    • JSON
    • gettext (.po)
    Mở rộng VS Code
    Tác nhân
    • MCP Server
    • Kỹ năng tác nhân
    Phiên bản
    • v8
    • v7
    • v6
    Benchmark
    • Next.js
    • TanStack
    • Vue
    • Solid
    • Svelte
    Blog
    Đặt câu hỏi
    1. Documentation
    2. Môi trường
    3. Next.js
    4. Next with page router
    Ngày tạo:2024-12-07Cập nhật lần cuối:2026-05-06
    Xem mẫu ứng dụng trên GitHub

    Trang này có một mẫu ứng dụng có sẵn.

    Xem ứng dụng trưng bày

    Trang này liên kết đến bản demo trực tiếp của mẫu.

    Tham chiếu tài liệu này tới trợ lý AI yêu thích của bạn
    ChatGPT
    Claude
    DeepSeek
    Google AI mode
    Gemini
    Perplexity
    Mistral
    Grok

    Đặt câu hỏi và nhận tóm tắt tài liệu bằng cách tham chiếu trang này và nhà cung cấp AI bạn chọn

    Lịch sử phiên bản

    1. "Cập nhật cách sử dụng API useIntlayer của Solid sang truy cập thuộc tính trực tiếp"
      v8.9.04/5/2026
    2. "Thêm lệnh init"
      v7.5.930/12/2025
    3. "Chuyển hàm `withIntlayer()` thành hàm dựa trên promise"
      v5.6.06/7/2025
    4. "Khởi tạo lịch sử"
      v5.5.1029/6/2025

    Nội dung của trang này đã được dịch bằng AI.

    Xem phiên bản mới nhất của nội dung gốc bằng tiếng Anh
    Chỉnh sửa tài liệu này

    Nếu bạn có ý tưởng để cải thiện tài liệu này, vui lòng đóng góp bằng cách gửi pull request trên GitHub.

    Liên kết GitHub tới tài liệu
    Sao chép

    Sao chép Markdown của tài liệu vào bộ nhớ tạm

    Dịch trang web Next.js và Page Router của bạn bằng Intlayer | Quốc tế hóa (i18n)

    ide.intlayer.org
    intlayer-next-14-template.vercel.app

    Mục lục

    Intlayer là gì?

    Intlayer là một thư viện quốc tế hóa (i18n) mã nguồn mở, sáng tạo, được thiết kế để đơn giản hóa việc hỗ trợ đa ngôn ngữ trong các ứng dụng web hiện đại. Intlayer tích hợp liền mạch với framework Next.js mới nhất, bao gồm cả Page Router truyền thống của nó.

    Với Intlayer, bạn có thể:

    • Dễ dàng quản lý bản dịch bằng cách sử dụng các từ điển khai báo ở cấp độ component.
    • Địa phương hóa động metadata, các route và nội dung.
    • Đảm bảo hỗ trợ TypeScript với các kiểu được tự động tạo, cải thiện tính năng tự động hoàn thành và phát hiện lỗi.
    • Tận hưởng các tính năng nâng cao, như phát hiện và chuyển đổi locale động.
    Intlayer tương thích với Next.js 12, 13, 14 và 15. Nếu bạn đang sử dụng Next.js App Router, hãy tham khảo hướng dẫn App Router. Đối với Next.js 15, hãy theo dõi hướng dẫn này.

    Hướng Dẫn Từng Bước Để Cài Đặt Intlayer Trong Ứng Dụng Next.js Sử Dụng Page Router

    Bước 1: Cài Đặt Các Phụ Thuộc

    Cài đặt các gói cần thiết bằng trình quản lý gói bạn ưa thích:

    bash
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    npm install intlayer next-intlayernpx intlayer init
    • intlayer

      Gói cốt lõi cung cấp các công cụ quốc tế hóa cho quản lý cấu hình, dịch thuật, khai báo nội dung, biên dịch lại, và các lệnh CLI.

    • next-intlayer

      Gói tích hợp Intlayer với Next.js. Nó cung cấp các context provider và hook cho quốc tế hóa trong Next.js. Ngoài ra, nó bao gồm plugin Next.js để tích hợp Intlayer với Webpack hoặc Turbopack, cũng như middleware để phát hiện ngôn ngữ ưu tiên của người dùng, quản lý cookie, và xử lý chuyển hướng URL.

    Bước 2: Cấu hình Dự án của Bạn

    Tạo một tệp cấu hình để định nghĩa các ngôn ngữ được ứng dụng của bạn hỗ trợ:

    intlayer.config.ts
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    import { Locales, type IntlayerConfig } from "intlayer";
    
    const config: IntlayerConfig = {
      internationalization: {
        locales: [
          Locales.ENGLISH,
          Locales.FRENCH,
          Locales.SPANISH,
          // Thêm các ngôn ngữ khác của bạn ở đây
        ],
        defaultLocale: Locales.ENGLISH,
      },
    };
    
    export default config;
    Thông qua tệp cấu hình này, bạn có thể thiết lập các URL địa phương hóa, chuyển hướng middleware, tên cookie, vị trí và phần mở rộng của các khai báo nội dung của bạn, tắt các bản ghi Intlayer trong bảng điều khiển, và nhiều hơn nữa. Để xem danh sách đầy đủ các tham số có sẵn, hãy tham khảo tài liệu cấu hình.

    Bước 3: Tích hợp Intlayer với cấu hình Next.js

    Chỉnh sửa cấu hình Next.js của bạn để tích hợp Intlayer:

    next.config.mjs
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    import { withIntlayer } from "next-intlayer/server";/** @type {import('next').NextConfig} */const nextConfig = {  // Cấu hình Next.js hiện có của bạn};export default withIntlayer(nextConfig);
    Plugin Next.js withIntlayer() được sử dụng để tích hợp Intlayer với Next.js. Nó đảm bảo việc xây dựng các tệp khai báo nội dung và giám sát chúng trong chế độ phát triển. Nó định nghĩa các biến môi trường Intlayer trong môi trường Webpack hoặc Turbopack. Ngoài ra, nó cung cấp các bí danh để tối ưu hiệu suất và đảm bảo tương thích với các thành phần server.

    Hàm withIntlayer() là một hàm promise. Nếu bạn muốn sử dụng nó cùng với các plugin khác, bạn có thể sử dụng await. Ví dụ:

    tsx
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    const nextConfig = await withIntlayer(nextConfig);const nextConfigWithOtherPlugins = withOtherPlugins(nextConfig);export default nextConfigWithOtherPlugins;

    Bước 4: Cấu hình Middleware để Phát hiện Ngôn ngữ

    Thiết lập middleware để tự động phát hiện và xử lý ngôn ngữ ưu tiên của người dùng:

    src/middleware.ts
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    export { intlayerProxy as middleware } from "next-intlayer/middleware";
    
    export const config = {
      matcher:
        "/((?!api|static|assets|robots|sitemap|sw|service-worker|manifest|.*\\..*|_next).*)",
    };
    Điều chỉnh tham số matcher để phù hợp với các route của ứng dụng bạn. Để biết thêm chi tiết, tham khảo tài liệu Next.js về cấu hình matcher.

    Bước 5: Định nghĩa các Route Địa phương Động

    Triển khai routing động để phục vụ nội dung được địa phương hóa dựa trên ngôn ngữ của người dùng.

    1. Tạo các Trang theo Ngôn ngữ Cụ thể:

      Đổi tên file trang chính của bạn để bao gồm phân đoạn động [locale].

      bash
      Sao chép mã

      Sao chép đoạn mã vào khay nhớ tạm (clipboard)

      mv src/pages/index.tsx src/pages/[locale]/index.tsx
    2. Cập nhật _app.tsx để Xử lý Đa ngôn ngữ:

      Sửa đổi _app.tsx của bạn để bao gồm các provider của Intlayer.

      src/pages/_app.tsx
      Sao chép mã

      Sao chép đoạn mã vào khay nhớ tạm (clipboard)

      import type { FC } from "react";import type { AppProps } from "next/app";import { IntlayerClientProvider } from "next-intlayer";const App = FC<AppProps>({ Component, pageProps }) => {  const { locale } = pageProps;  return (    <IntlayerClientProvider locale={locale}>      <Component {...pageProps} />    </IntlayerClientProvider>  );}export default MyApp;
    3. Thiết Lập getStaticPaths và getStaticProps:

      Trong file [locale]/index.tsx của bạn, định nghĩa các đường dẫn và props để xử lý các locale khác nhau.

    src/pages/[locale]/index.tsx
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    import type { GetStaticPaths, GetStaticProps } from "next";
    import { getConfiguration } from "intlayer";
    
    const HomePage = () => <div>{/* Nội dung của bạn ở đây */}</div>;
    
    export const getStaticPaths: GetStaticPaths = async () => {
      const { internationalization } = getConfiguration();
      const { locales } = internationalization;
    
      const paths = locales.map((locale: string) => ({
        params: { locale },
      }));
    
      return { paths, fallback: false };
    };
    
    export const getStaticProps: GetStaticProps = async ({ params }) => {
      const locale = params?.locale;
    
      return {
        props: {
          locale,
        },
      };
    };
    
    export default HomePage;
    getStaticPaths và getStaticProps đảm bảo rằng ứng dụng của bạn sẽ xây dựng trước các trang cần thiết cho tất cả các locale trong Next.js Page Router. Cách tiếp cận này giảm thiểu tính toán khi chạy và mang lại trải nghiệm người dùng tốt hơn. Để biết thêm chi tiết, hãy tham khảo tài liệu Next.js về getStaticPaths và getStaticProps.

    Bước 6: Khai báo Nội dung của Bạn

    Tạo và quản lý các khai báo nội dung để lưu trữ các bản dịch.

    src/pages/[locale]/home.content.ts
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    import { t, type Dictionary } from "intlayer";
    
    const homeContent = {
      key: "home",
      content: {
        title: t({
          en: "Welcome to My Website",
          fr: "Bienvenue sur mon site Web",
          es: "Bienvenido a mi sitio web",
        }),
        description: t({
          en: "Bắt đầu bằng cách chỉnh sửa trang này.",
          fr: "Commencez par éditer cette page.",
          es: "Comience por editar esta página.",
        }),
      },
    } satisfies Dictionary;
    
    export default homeContent;

    Để biết thêm thông tin về cách khai báo nội dung, hãy tham khảo hướng dẫn khai báo nội dung.

    Bước 7: Sử dụng Nội dung trong Mã của Bạn

    Truy cập các từ điển nội dung của bạn trong toàn bộ ứng dụng để hiển thị nội dung đã được dịch.

    src/pages/[locale]/index.tsx
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    import type { FC } from "react";
    import { useIntlayer } from "next-intlayer";
    import { ComponentExample } from "@components/ComponentExample";
    
    const HomePage: FC = () => {
      const content = useIntlayer("home");
    
      return (
        <div>
          <h1>{content.title}</h1>
          <p>{content.description}</p>
          <ComponentExample />
          {/* Các thành phần bổ sung */}
        </div>
      );
    };
    
    // ... Phần còn lại của mã, bao gồm getStaticPaths và getStaticProps
    
    export default HomePage;
    src/components/ComponentExample.tsx
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    import type { FC } from "react";
    import { useIntlayer } from "next-intlayer";
    
    export const ComponentExample: FC = () => {
      const content = useIntlayer("component-example"); // Đảm bảo bạn có khai báo nội dung tương ứng
    
      return (
        <div>
          <h2>{content.title}</h2>
          <p>{content.content}</p>
        </div>
      );
    };
    Khi sử dụng bản dịch trong các thuộc tính string (ví dụ: alt, title, href, aria-label), hãy gọi
    giá trị của hàm như sau:
    html
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    <img src="{content.image.src.value}" alt="{content.image.value}" /><img src="{content.image.src.toString()}" alt="{content.image.toString()}" /><img src="{String(content.image.src)}" alt="{String(content.image)}" />
    Để tìm hiểu thêm về hook useIntlayer, hãy tham khảo tài liệu.

    (Tùy chọn) Bước 8: Quốc tế hóa metadata của bạn

    Trong trường hợp bạn muốn quốc tế hóa metadata, chẳng hạn như tiêu đề của trang, bạn có thể sử dụng hàm getStaticProps do Next.js Page Router cung cấp. Bên trong, bạn có thể lấy nội dung từ hàm getIntlayer để dịch metadata của bạn.

    src/pages/[locale]/metadata.content.ts
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    import { type Dictionary, t } from "intlayer";
    import { type Metadata } from "next";
    
    const metadataContent = {
      key: "page-metadata",
      content: {
        title: t({
          en: "Create Next App",
          fr: "Créer une application Next.js",
          es: "Crear una aplicación Next.js",
        }),
        description: t({
          en: "Generated by create next app",
          fr: "Généré par create next app",
          es: "Generado por create next app",
        }),
      },
    } satisfies Dictionary<Metadata>;
    
    export default metadataContent;
    src/pages/[locale]/index.tsx
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    import { GetStaticPaths, GetStaticProps } from "next";
    import { getIntlayer, getMultilingualUrls } from "intlayer";
    import { useIntlayer } from "next-intlayer";
    import Head from "next/head";
    import type { FC } from "react";
    
    interface HomePageProps {
      locale: string;
      metadata: {
        title: string;
        description: string;
      };
      multilingualUrls: Record<string, string>;
    }
    
    const HomePage: FC<HomePageProps> = ({
      metadata,
      multilingualUrls,
      locale,
    }) => {
      const content = useIntlayer("page");
    
      return (
        <div>
          <Head>
            <title>{metadata.title}</title>
            <meta name="description" content={metadata.description} />
            {/* Tạo các thẻ hreflang cho SEO */}
            {Object.entries(multilingualUrls).map(([lang, url]) => (
              <link key={lang} rel="alternate" hrefLang={lang} href={url} />
            ))}
            <link rel="canonical" href={multilingualUrls[locale]} />
          </Head>
    
          {/* Nội dung trang */}
          <main>{/* Nội dung trang của bạn ở đây */}</main>
        </div>
      );
    };
    
    export const getStaticProps: GetStaticProps<HomePageProps> = async ({
      params,
    }) => {
      const locale = params?.locale as string;
    
      const metadata = getIntlayer("page-metadata", locale);
    
      /**
       * Tạo một đối tượng chứa tất cả các url cho mỗi locale.
       *
       * Ví dụ:
       * ```ts
       *  getMultilingualUrls('/about');
       *
       *  // Trả về
       *  // {
       *  //   en: '/about',
       *  //   fr: '/fr/about',
       *  //   es: '/es/about',
       *  // }
       * ```
       */
      const multilingualUrls = getMultilingualUrls("/");
    
      return {
        props: {
          locale,
          metadata,
          multilingualUrls,
        },
      };
    };
    
    export default HomePage;
    
    // ... Phần còn lại của code bao gồm getStaticPaths

    // ... Phần còn lại của code bao gồm getStaticPaths

    Lưu ý rằng hàm getIntlayer được nhập từ next-intlayer trả về nội dung của bạn được bao bọc trong một IntlayerNode, cho phép tích hợp với trình soạn thảo trực quan. Ngược lại, hàm getIntlayer được nhập từ intlayer trả về nội dung của bạn trực tiếp mà không có thuộc tính bổ sung.

    Ngoài ra, bạn có thể sử dụng hàm getTranslation để khai báo metadata của bạn. Tuy nhiên, việc sử dụng các tệp khai báo nội dung được khuyến nghị để tự động hóa việc dịch metadata và ngoại hóa nội dung vào một thời điểm nào đó.

    src/pages/[locale]/index.tsx
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    import { GetStaticPaths, GetStaticProps } from "next";
    import { getTranslation, getMultilingualUrls } from "intlayer";
    import { useIntlayer } from "next-intlayer";
    import Head from "next/head";
    import type { FC } from "react";
    
    type Metadata = {
      title: string;
      description: string;
    };
    
    interface HomePageProps {
      locale: string;
      metadata: Metadata;
      multilingualUrls: Record<string, string>;
    }
    
    const HomePage: FC<HomePageProps> = ({
      metadata,
      multilingualUrls,
      locale,
    }) => {
      const content = useIntlayer("page");
    
      return (
        <div>
          <Head>
            <title>{metadata.title}</title>
            <meta name="description" content={metadata.description} />
            {/* Tạo các thẻ hreflang cho SEO */}
            {Object.entries(multilingualUrls).map(([lang, url]) => (
              <link key={lang} rel="alternate" hrefLang={lang} href={url} />
            ))}
            <link rel="canonical" href={multilingualUrls[locale]} />
          </Head>
    
          {/* Nội dung trang */}
          <main>{/* Nội dung trang của bạn ở đây */}</main>
        </div>
      );
    };
    
    export const getStaticProps: GetStaticProps<HomePageProps> = async ({
      params,
    }) => {
      const locale = params?.locale as string;
      const t = (content: Record<string, string>) =>
        getTranslation(content, locale);
    
      const metadata: Metadata = {
        title: t({
          en: "My title",
          fr: "Mon titre",
          es: "Mi título",
        }),
        description: t({
          en: "My description",
          fr: "Ma description",
          es: "Mi descripción",
        }),
      };
    
      const multilingualUrls = getMultilingualUrls("/");
    
      return {
        props: {
          locale,
          metadata,
          multilingualUrls,
        },
      };
    };
    
    export default HomePage;
    
    // ... Phần còn lại của mã bao gồm getStaticPaths
    Tìm hiểu thêm về tối ưu hóa metadata trong tài liệu chính thức của Next.js.

    (Tùy chọn) Bước 9: Thay đổi ngôn ngữ nội dung của bạn

    Để thay đổi ngôn ngữ nội dung trong Next.js, cách được khuyến nghị là sử dụng component Link để chuyển hướng người dùng đến trang được địa phương hóa phù hợp. Component Link cho phép tải trước trang, giúp tránh tải lại toàn bộ trang.

    src/components/LanguageSwitcher.tsx
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    import {
      Locales,
      getHTMLTextDir,
      getLocaleName,
      getLocalizedUrl,
    } from "intlayer";
    import { useLocalePageRouter } from "next-intlayer";
    import { type FC } from "react";
    import Link from "next/link";
    
    const LocaleSwitcher: FC = () => {
      const { locale, pathWithoutLocale, availableLocales } = useLocalePageRouter();
    
      return (
        <div>
          <button popoverTarget="localePopover">{getLocaleName(locale)}</button>
          <div id="localePopover" popover="auto">
            {availableLocales.map((localeItem) => (
              <Link
                href={getLocalizedUrl(pathWithoutLocale, localeItem)}
                hrefLang={localeItem}
                key={localeItem}
                aria-current={locale === localeItem ? "page" : undefined}
                onClick={() => setLocale(localeItem)}
              >
                <span>
                  {/* Ngôn ngữ địa phương - ví dụ: FR */}
                  {localeItem}
                </span>
                <span>
                  {/* Ngôn ngữ trong chính ngôn ngữ đó - ví dụ: Français */}
                  {getLocaleName(localeItem, locale)}
                </span>
                <span dir={getHTMLTextDir(localeItem)} lang={localeItem}>
                  {/* Ngôn ngữ trong Locale hiện tại - ví dụ: Francés với locale hiện tại được đặt thành Locales.SPANISH */}
                  {getLocaleName(localeItem)}
                </span>
                <span dir="ltr" lang={Locales.ENGLISH}>
                  {/* Ngôn ngữ bằng tiếng Anh - ví dụ: French */}
                  {getLocaleName(localeItem, Locales.ENGLISH)}
                </span>
              </Link>
            ))}
          </div>
        </div>
      );
    };
    Một cách thay thế là sử dụng hàm setLocale được cung cấp bởi hook useLocale. Hàm này sẽ không cho phép tải trước trang và sẽ tải lại trang.
    Trong trường hợp này, không sử dụng chuyển hướng với router.push, chỉ có mã phía server của bạn sẽ thay đổi locale của nội dung.
    src/components/LocaleSwitcher.tsx
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    "use client";import { useRouter } from "next/navigation";import { useLocale } from "next-intlayer";import { getLocalizedUrl } from "intlayer";// ... Phần còn lại của mãconst router = useRouter();const { setLocale } = useLocale({  onLocaleChange: (locale) => {    router.push(getLocalizedUrl(pathWithoutLocale, locale));  },});return (  <button onClick={() => setLocale(Locales.FRENCH)}>    Chuyển sang tiếng Pháp  </button>);
    API useLocalePageRouter giống với useLocale. Để tìm hiểu thêm về hook useLocale, hãy tham khảo tài liệu.

    Tham khảo tài liệu:

    • hook getLocaleName
    • hook getLocalizedUrl
    • hook getHTMLTextDir
    • thuộc tính hrefLang
    • thuộc tính lang
    • thuộc tính dir
    • thuộc tính aria-current

    (Tùy chọn) Bước 10: Tạo một Thành phần Link Đa ngôn ngữ

    Để đảm bảo rằng điều hướng trong ứng dụng của bạn tôn trọng locale hiện tại, bạn có thể tạo một thành phần Link tùy chỉnh. Thành phần này tự động thêm tiền tố ngôn ngữ hiện tại vào các URL nội bộ, ví dụ, khi một người dùng nói tiếng Pháp nhấp vào liên kết đến trang "About", họ sẽ được chuyển hướng đến /fr/about thay vì /about.

    Hành vi này hữu ích vì một số lý do:

    • SEO và Trải nghiệm Người dùng: URL đa ngôn ngữ giúp các công cụ tìm kiếm lập chỉ mục chính xác các trang theo ngôn ngữ cụ thể và cung cấp nội dung cho người dùng theo ngôn ngữ ưu tiên của họ.
    • Tính nhất quán: Bằng cách sử dụng liên kết đa ngôn ngữ trong toàn bộ ứng dụng của bạn, bạn đảm bảo rằng điều hướng luôn nằm trong locale hiện tại, ngăn chặn việc chuyển đổi ngôn ngữ không mong muốn.
    • Dễ bảo trì: Tập trung logic đa ngôn ngữ vào một thành phần duy nhất giúp đơn giản hóa việc quản lý URL, làm cho codebase của bạn dễ bảo trì và mở rộng khi ứng dụng phát triển.

    Dưới đây là triển khai của một thành phần Link đa ngôn ngữ bằng TypeScript:

    src/components/Link.tsx
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    "use client";
    
    import { getLocalizedUrl } from "intlayer";
    import NextLink, { type LinkProps as NextLinkProps } from "next/link";
    import { useLocale } from "next-intlayer";
    import { forwardRef, PropsWithChildren, type ForwardedRef } from "react";
    
    /**
     * Hàm tiện ích để kiểm tra xem một URL có phải là liên kết ngoài hay không.
     * Nếu URL bắt đầu bằng http:// hoặc https://, nó được coi là liên kết ngoài.
     */
    export const checkIsExternalLink = (href?: string): boolean =>
      /^https?:\/\//.test(href ?? "");
    
    /**
     * Một thành phần Link tùy chỉnh điều chỉnh thuộc tính href dựa trên locale hiện tại.
     * Đối với các liên kết nội bộ, nó sử dụng `getLocalizedUrl` để thêm tiền tố locale vào URL (ví dụ: /fr/about).
     * Điều này đảm bảo điều hướng luôn nằm trong cùng ngữ cảnh locale.
     */
    export const Link = forwardRef<
      HTMLAnchorElement,
      PropsWithChildren<NextLinkProps>
    >(({ href, children, ...props }, ref: ForwardedRef<HTMLAnchorElement>) => {
      const { locale } = useLocale();
      const isExternalLink = checkIsExternalLink(href.toString());
    
      // Nếu liên kết là nội bộ và href hợp lệ được cung cấp, lấy URL đã được địa phương hóa.
      const hrefI18n: NextLinkProps["href"] =
        href && !isExternalLink ? getLocalizedUrl(href.toString(), locale) : href;
    
      return (
        <NextLink href={hrefI18n} ref={ref} {...props}>
          {children}
        </NextLink>
      );
    });
    
    Link.displayName = "Link";

    Cách Hoạt Động

    • Phát hiện Liên kết Ngoài: Hàm trợ giúp checkIsExternalLink xác định xem một URL có phải là liên kết ngoài hay không. Các liên kết ngoài được giữ nguyên vì chúng không cần được địa phương hóa.

    • Lấy Ngôn ngữ Hiện tại: // Hook useLocale cung cấp locale hiện tại (ví dụ: fr cho tiếng Pháp).

    • Địa phương hóa URL: Đối với các liên kết nội bộ (tức là không phải liên kết ngoài), getLocalizedUrl được sử dụng để tự động thêm tiền tố locale hiện tại vào URL. Điều này có nghĩa là nếu người dùng của bạn đang ở chế độ tiếng Pháp, việc truyền /about làm href sẽ chuyển thành /fr/about.

    • Trả về Liên kết: Component trả về một phần tử <a> với URL đã được địa phương hóa, đảm bảo điều hướng nhất quán với locale.

    Bằng cách tích hợp component Link này trong toàn bộ ứng dụng của bạn, bạn duy trì trải nghiệm người dùng nhất quán và nhận biết ngôn ngữ đồng thời cải thiện SEO và khả năng sử dụng.

    (Tùy chọn) Bước 11: Tối ưu kích thước bundle của bạn

    Khi sử dụng next-intlayer, các từ điển được bao gồm trong bundle cho mỗi trang theo mặc định. Để tối ưu kích thước bundle, Intlayer cung cấp một plugin SWC tùy chọn thay thế thông minh các lệnh gọi useIntlayer bằng cách sử dụng macro. Điều này đảm bảo các từ điển chỉ được bao gồm trong bundle của những trang thực sự sử dụng chúng.

    Để kích hoạt tối ưu hóa này, hãy cài đặt gói @intlayer/swc. Khi đã cài đặt, next-intlayer sẽ tự động phát hiện và sử dụng plugin:

    bash
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    npm install @intlayer/swc --save-dev
    Lưu ý: Tối ưu hóa này chỉ có sẵn cho Next.js 13 trở lên.
    Lưu ý: Gói này không được cài đặt mặc định vì các plugin SWC vẫn đang trong giai đoạn thử nghiệm trên Next.js. Điều này có thể thay đổi trong tương lai.

    Cấu hình TypeScript

    Intlayer sử dụng module augmentation để tận dụng lợi ích của TypeScript và làm cho codebase của bạn mạnh mẽ hơn.

    Tự động hoàn thành

    Lỗi dịch thuật

    Đảm bảo cấu hình TypeScript của bạn bao gồm các kiểu được tạo tự động.

    tsconfig.json
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    {  // ... Các cấu hình TypeScript hiện có của bạn  "include": [    // ... Các cấu hình TypeScript hiện có của bạn    ".intlayer/**/*.ts", // Bao gồm các kiểu được tạo tự động  ],}

    Cấu hình Git

    Để giữ cho kho lưu trữ của bạn sạch sẽ và tránh việc commit các file được tạo tự động, bạn nên bỏ qua các file do Intlayer tạo ra.

    Thêm các dòng sau vào file .gitignore của bạn:

    .gitignore
    Sao chép mã

    Sao chép đoạn mã vào khay nhớ tạm (clipboard)

    # Bỏ qua các file được tạo bởi Intlayer.intlayer

    Tiện ích mở rộng VS Code

    Để cải thiện trải nghiệm phát triển với Intlayer, bạn có thể cài đặt Tiện ích mở rộng Intlayer cho VS Code chính thức.

    Cài đặt từ VS Code Marketplace

    Tiện ích mở rộng này cung cấp:

    • Tự động hoàn thành cho các khóa dịch.
    • Phát hiện lỗi thời gian thực cho các bản dịch bị thiếu.
    • Xem trước nội dung dịch ngay trong dòng.
    • Hành động nhanh để dễ dàng tạo và cập nhật các bản dịch.

    Để biết thêm chi tiết về cách sử dụng tiện ích mở rộng, hãy tham khảo tài liệu Tiện ích mở rộng Intlayer cho VS Code.

    Tài nguyên bổ sung

    • Tài liệu Intlayer: Kho GitHub
    • Hướng dẫn Từ điển: Từ điển
    • Tài liệu Cấu hình: Hướng dẫn Cấu hình

    Bằng cách làm theo hướng dẫn này, bạn có thể tích hợp hiệu quả Intlayer vào ứng dụng Next.js của mình sử dụng Page Router, cho phép hỗ trợ quốc tế hóa mạnh mẽ và có khả năng mở rộng cho các dự án web của bạn.

    Tiến xa hơn

    Để đi xa hơn, bạn có thể triển khai trình chỉnh sửa trực quan hoặc tách nội dung của bạn ra bên ngoài bằng cách sử dụng CMS.

    Next.js không locale URL
    Trình biên dịch
    Alt+→

    Trong trang này

      Các cuộc thảo luận là ẩn danh và được xem xét thường xuyên để giải quyết các vấn đề phổ biến. Hãy thoải mái chia sẻ ý tưởng tính năng, phản hồi về tài liệu hoặc bất cứ điều gì liên quan đến Intlayer, chúng tôi sử dụng thông tin này để định hình lộ trình và cải thiện sản phẩm.

      npm install intlayer next-intlayernpx intlayer init
      import { withIntlayer } from "next-intlayer/server";/** @type {import('next').NextConfig} */const nextConfig = {  // Cấu hình Next.js hiện có của bạn};export default withIntlayer(nextConfig);
      const nextConfig = await withIntlayer(nextConfig);const nextConfigWithOtherPlugins = withOtherPlugins(nextConfig);export default nextConfigWithOtherPlugins;
      mv src/pages/index.tsx src/pages/[locale]/index.tsx
      import type { FC } from "react";import type { AppProps } from "next/app";import { IntlayerClientProvider } from "next-intlayer";const App = FC<AppProps>({ Component, pageProps }) => {  const { locale } = pageProps;  return (    <IntlayerClientProvider locale={locale}>      <Component {...pageProps} />    </IntlayerClientProvider>  );}export default MyApp;
      <img src="{content.image.src.value}" alt="{content.image.value}" /><img src="{content.image.src.toString()}" alt="{content.image.toString()}" /><img src="{String(content.image.src)}" alt="{String(content.image)}" />
      "use client";import { useRouter } from "next/navigation";import { useLocale } from "next-intlayer";import { getLocalizedUrl } from "intlayer";// ... Phần còn lại của mãconst router = useRouter();const { setLocale } = useLocale({  onLocaleChange: (locale) => {    router.push(getLocalizedUrl(pathWithoutLocale, locale));  },});return (  <button onClick={() => setLocale(Locales.FRENCH)}>    Chuyển sang tiếng Pháp  </button>);
      npm install @intlayer/swc --save-dev
      {  // ... Các cấu hình TypeScript hiện có của bạn  "include": [    // ... Các cấu hình TypeScript hiện có của bạn    ".intlayer/**/*.ts", // Bao gồm các kiểu được tạo tự động  ],}
      # Bỏ qua các file được tạo bởi Intlayer.intlayer