gatsby-plugin-useI18n
Internationalize your Gatsby site.
Introduction
This plugin is modified from these two awesome official themes: gatsby-theme-i18n and gatsby-theme-i18n-react-intl. Before this, I used these two themes to internationalize my Gatsby site, but I found that they can’t fully meet my needs. So I made this for my personal site and put everything I learned in this Gatsby plugin in hopes to help out anyone who may struggle with the same.
Features
- Internationalize your Gatsby site powered by react-intl.
- Creating prefixed, enriched pages for each language (including client-only pages that have a matchPath).
- Automatic redirection based on the user’s preferred language in browser.
- Adds
<link rel="alternate" />
seo tags to<head>
. - Exports useful React components and hooks.
Installation
- Install
gatsby-plugin-usei18n
and its peerDependencies:
npm install gatsby-plugin-usei18n react-intl gatsby-plugin-react-helmet react-helmet --save
or
yarn add gatsby-plugin-usei18n react-intl gatsby-plugin-react-helmet react-helmet
- Add the configuration to your
gatsby-config.js
file:
module.exports = {
plugins: [
{
resolve: `gatsby-plugin-usei18n`,
options: {
defaultLang: `en`,
configPath: require.resolve(`./i18n/config.json`),
},
},
],
}
-
Create the folder
i18n
at the root of your project and create a file calledconfig.json
in it. -
Add your locales to the config file and fill out these information:
code
: The ISO 3166-1 alpha-2 code which will be used for the path prefix, as a unique identifier (e.g. for thedefaultLang
option)hrefLang
: The IETF language tag for the<html lang="xx-XX" />
attribute. Also used for og tagsname
: The english name of the localelocalName
: The local name of the localelangDir
: The direction of language (e.g. “ltr”, “rtl”)dateFormat
: The tokens that Moment.js accepts for date formatting. This can be used for dates on GraphQL queries
Example config of English:
[
{
"code": "en",
"hrefLang": "en-US",
"name": "English",
"localName": "English",
"langDir": "ltr",
"dateFormat": "MM/DD/YYYY"
}
]
-
Create the folder named
messages
in theconfigPath
(e.g../i18n/
) and create your<locale>.json
files in it. -
Add a suffix/postfix to your MDX/YAML filenames, e.g. if you have your blogposts at
content/posts/my-title/index.mdx
you’ll need to copy that file and place it withindex.de.mdx
in the same folder.
Usage
By adding a suffix/postfix in your filenames you can define the locale that the document is in.
You can also see the example to learn more.
Plugins Options
Key | Default Value | Description |
---|---|---|
defaultLang |
en |
The locale that is your default language. For this language no prefixed routes will be created unless you set the option prefixDefault . |
prefixDefault |
false |
All routes will be prefixed, including the defaultLang |
configPath |
none | Path to the config file |
locales |
null |
A string of locales (divided by spaces) to only build a subset of the locales defined in configPath , e.g. en de |
redirect |
false |
if the value is true , / or /page-2 will be redirected to the user’s preferred language router. e.g. /en or /en/page-2 . Otherwise, the pages will render defaultLang language. |
You can pass additional options in as they’ll be forwarded to the plugin. You can query all options in GraphQL on the SiteI18n
type.
Available React components/hooks
The plugin also exports a couple of components and hooks that you could use in your project.
useLocalization
The plugin saves its information into a custom SiteI18n
graphql type which you can access via the useLocalization
hook. Furthermore, you’re able to ask for the current locale via React context.
Example:
import React from "react"
import { useLocalization } from "gatsby-plugin-usei18n"
const Example = () => {
const { locale, config, defaultLang } = useLocalization()
return (
<div>
<div>Current locale: {locale}</div>
<div>Current defaultLang: {defaultLang}</div>
<pre>{JSON.stringify(config, null, 2)}</pre>
</div>
)
}
export default Example
LangSelector
This is a component that can create a language selector.
Example:
import React from "react";
import { LangSelector, LocaleContext } from "gatsby-plugin-usei18n";
const Example = ({ pageContext }) => {
const { handleLanguage } = React.useContext(LocaleContext);
const path = pageContext.originalPath;
return (
<div>
<LangSelector
path={path}
toggleLanguage={handleLanguage}
/>
</div>
)
}
export default Example
Render HTML:
<div>
<ul>
<li>
<a href="/">English</a>
</li>
<li>
<a href="/de/">Deutsch</a>
</li>
...
</ul>
</div>
LocalizedLink
This is a wrapper around the Link
component from gatsby
and is transforming links to the correct path by accessing the current locale via React context.
Example:
import React from "react"
import { LocalizedLink as Link } from "gatsby-plugin-usei18n"
const Example = () => {
return (
<div>
<Link to="/page-2/">Link to second page</Link>
</div>
)
}
export default Example
LocalizedRouter
Provides a <Router />
from @reach/router
that prefixes the basePath
prop with the current locale.
Example:
import React from "react"
import { LocalizedRouter } from "gatsby-plugin-usei18n"
import Detail from "../components/detail"
const App = () => {
return (
<LocalizedRouter basePath="/app">
<Detail path="/:id" />
</LocalizedRouter>
)
}
export default App
MdxLink
This is a component specifically for MDX to replace the normal anchor tag. This way local links to other files are automatically localized (as it uses LocalizedLink
behind the scenes).
Example:
import React from "react"
import { MDXProvider } from "@mdx-js/react"
import { MdxLink } from "gatsby-plugin-usei18n"
const components = {
a: MdxLink,
}
const Layout = ({ children }) => {
return (
<React.Fragment>
<main>
<MDXProvider components={components}>{children}</MDXProvider>
</main>
</React.Fragment>
)
}
export default Layout
LocaleContext / LocaleProvider
You can also directly access the LocaleContext
and LocaleProvider
from the plugin.
Example:
import React from "react"
import { LocaleContext } from "gatsby-plugin-usei18n"
const Example = () => {
const locale = React.useContext(LocaleContext)
return <div>Locale: {locale}</div>
}
export default Example
Showcase
Feel free to send us PR to add your project.
License
MIT.