Skip to content

Commit

Permalink
website i18n refactor (#1485)
Browse files Browse the repository at this point in the history
* website i18n refactor

* fix tests

* final move
  • Loading branch information
gdams authored Feb 9, 2023
1 parent 9869ccc commit 50e5dbe
Show file tree
Hide file tree
Showing 24 changed files with 219 additions and 156 deletions.
File renamed without changes.
2 changes: 1 addition & 1 deletion content/asciidoc-pages/docs/faq/index.es.adoc
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
= Preguntas Frecuentes
= Frequently Asked Questions
:page-authors: eddumelendez, czelabueno, jdluna, raulmj, tellison, gdams

Hemos reunido unas cuantas preguntas frecuentes (FAQs) en este documento.
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
= 常见问题解答
= Frequently Asked Questions
:page-authors: zdtsw, gdams, tellison

在该文件中我们收集了一些常见问题。如果您想与我们讨论这些话题或有其他问题,最好的途径是通过以下链接
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
= First Timers Support (DRAFT)
= Eclipse Adoptium(R) First Timers Support
:page-authors: gdams, HanSolo, hendrikebbers, tellison
:description: Support with first time contributions
:keywords: adoptium documentation contribute first-time
Expand Down
2 changes: 1 addition & 1 deletion content/asciidoc-pages/docs/qvs-policy/index.de.adoc
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
= AQAvit Quality Verification Suite Policy
= AQAvit(TM) Quality Verification Suite Policy
:description: Adoptium QVS Policy
:keywords: adoptium AQAvit quality policy
:orgname: Eclipse Adoptium
Expand Down
File renamed without changes.
File renamed without changes.
File renamed without changes.
13 changes: 10 additions & 3 deletions gatsby-config.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
*/

const path = require('path')
const locales = require('./locales/i18n')

module.exports = {
siteMetadata: {
Expand Down Expand Up @@ -45,19 +46,25 @@ module.exports = {
options: {
name: 'locale',
path: path.join(__dirname, 'locales'),
ignore: ['**/*.md']
ignore: ['**/*.md', 'i18n.js']
}
},
{
resolve: 'gatsby-plugin-react-i18next',
options: {
localeJsonSourceName: 'locale',
languages: ['en', 'en-GB', 'es', 'de', 'zh-CN'],
languages: Object.keys(locales),
defaultLanguage: 'en',
i18nextOptions: {
transSupportBasicHtmlNodes: true,
transKeepBasicHtmlNodesFor: ['u', 'a']
}
},
pages: [
{
matchPath: '/:lang?/docs/:uid',
getLanguageFromPath: true
}
]
}
},
{
Expand Down
193 changes: 148 additions & 45 deletions gatsby-node.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,125 @@ const fs = require('fs')
const { pipeline } = require('stream')
const { promisify } = require('util')
const { createFilePath } = require('gatsby-source-filesystem')
const createMultilingualRedirects = require('./i18n-redirects')
const locales = require('./locales/i18n')

const { localizedSlug, findKey, removeTrailingSlash } = require('./src/util/gatsby-node-helpers')

exports.onCreatePage = ({ page, actions }) => {
const { createPage, deletePage } = actions

// Delete pages such as /about/index.de
if (page.path.includes('index')) {
return deletePage(page)
}

// First delete the incoming page that was automatically created by Gatsby
// So everything in src/pages/
// Don't do anything to the page if context has a language already set
if (page.component.includes('asciidocTemplate') && page.context.locale === 'en') {
// Grab the keys ('en' & 'de') of locales and map over them
// eslint-disable-next-line array-callback-return
Object.keys(locales).map(lang => {
if (lang !== 'en') {
// Use the values defined in "locales" to construct the path
const localizedPath = locales[lang].default
? page.path
: `${locales[lang].path}${page.path}`

let locale = 'en'

if (fs.existsSync(`./content/asciidoc-pages${page.path}index.${lang}.adoc`)) {
locale = lang
}

return createPage({
// Pass on everything from the original page
...page,
// Since page.path returns with a trailing slash (e.g. "/de/")
// We want to remove that
path: removeTrailingSlash(localizedPath),
// Pass in the locale as context to every page
// This context also gets passed to the src/components/layout file
// This should ensure that the locale is available on every page
context: {
...page.context,
locale,
language: lang,
i18n: {
...page.context.i18n,
routed: true,
originalPath: page.path,
path: removeTrailingSlash(localizedPath),
language: lang
}
}
})
}
})
} else {
deletePage(page)
}

return createPage({
// Pass on everything from the original page
...page,
// Pass in the locale as context to every page
// This context also gets passed to the src/components/layout file
// This should ensure that the locale is available on every page
context: {
...page.context
}
})
}

exports.onCreateNode = async ({ node, actions, getNode, getNodes }) => {
const { createNodeField } = actions

if (node.internal.type === 'Asciidoc') {
const fetchFilePath = getNodes().find(n => n.id === node.parent)
const name = path.basename(fetchFilePath.relativePath, '.adoc')

// Check if post.name is "index" -- because that's the file for default language
// (In this case "en")
const isDefault = name === 'index'

// Find the key that has "default: true" set (in this case it returns "en")
const defaultKey = findKey(locales, o => o.default === true)

// Files are defined with "name-with-dashes.lang.adoc"
// name returns "name-with-dashes.lang"
// So grab the lang from that string
// If it's the default language, pass the locale for that
const lang = isDefault ? defaultKey : name.split('.')[1]

createNodeField({ node, name: 'relativePath', value: fetchFilePath.relativePath })
createNodeField({ node, name: 'locale', value: lang })
createNodeField({ node, name: 'isDefault', value: isDefault })

const value = createFilePath({ node, getNode })
createNodeField({
name: 'slug',
node,
value
})
} else if (node.internal.type === 'Mdx') {
const slug = createFilePath({ node, getNode })
const date = new Date(node.frontmatter.date)
const year = date.getFullYear()
const zeroPaddedMonth = `${date.getMonth() + 1}`.padStart(2, '0')

createNodeField({
name: 'slug',
node,
value: slug
})
createNodeField({
name: 'postPath',
node,
value: `/blog/${year}/${zeroPaddedMonth}${slug}`
})
}
}

exports.createPages = async ({ graphql, actions }) => {
const { createPage } = actions
Expand All @@ -13,17 +131,17 @@ exports.createPages = async ({ graphql, actions }) => {

const asciidocResults = await graphql(`
{
allAsciidoc {
docs: allFile(filter: {sourceInstanceName: {eq: "asciidoc-pages"}}) {
edges {
node {
id
fields {
slug
}
parent {
... on File {
relativePath
absolutePath
childAsciidoc {
document {
title
}
fields {
locale
isDefault
slug
}
}
}
Expand All @@ -32,15 +150,29 @@ exports.createPages = async ({ graphql, actions }) => {
}
`)

asciidocResults.data.allAsciidoc.edges.forEach(({ node }) => {
const articleNodes = asciidocResults.data.allAsciidoc.edges
createMultilingualRedirects(actions, articleNodes, node)
// Create page for each asciidoc file
if (asciidocResults.errors) {
throw asciidocResults.errors
}

const docs = asciidocResults.data.docs.edges

docs.forEach(({ node: doc }) => {
const title = doc.childAsciidoc.document.title
const slug = doc.childAsciidoc.fields.slug

// Use the fields created in exports.onCreateNode
const locale = doc.childAsciidoc.fields.locale
const isDefault = doc.childAsciidoc.fields.isDefault

createPage({
path: node.fields.slug,
path: localizedSlug({ isDefault, locale, slug }),
component: asciidocTemplate,
context: {
id: node.id
// Pass both the "title" and "locale" to find a unique file
// Only the title would not have been sufficient as articles could have the same title
// in different languages, e.g. because an english phrase is also common in german
title,
locale
}
})
})
Expand Down Expand Up @@ -164,32 +296,3 @@ exports.createPages = async ({ graphql, actions }) => {
})
})
}

exports.onCreateNode = async ({ node, actions, getNode, loadNodeContent }) => {
const { createNodeField } = actions

if (node.internal.type === 'Asciidoc') {
const value = createFilePath({ node, getNode })
createNodeField({
name: 'slug',
node,
value
})
} else if (node.internal.type === 'Mdx') {
const slug = createFilePath({ node, getNode })
const date = new Date(node.frontmatter.date)
const year = date.getFullYear()
const zeroPaddedMonth = `${date.getMonth() + 1}`.padStart(2, '0')

createNodeField({
name: 'slug',
node,
value: slug
})
createNodeField({
name: 'postPath',
node,
value: `/blog/${year}/${zeroPaddedMonth}${slug}`
})
}
}
88 changes: 0 additions & 88 deletions i18n-redirects.js

This file was deleted.

25 changes: 25 additions & 0 deletions locales/i18n.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
// Only one item MUST have the "default: true" key

module.exports = {
en: {
default: true,
locale: 'en-US',
path: 'en'
},
'en-GB': {
locale: 'en-GB',
path: 'en-GB'
},
de: {
locale: 'de-DE',
path: 'de'
},
es: {
locale: 'es-ES',
path: 'es'
},
'zh-CN': {
locale: 'zh-CN',
path: 'zh-CN'
}
}
Loading

0 comments on commit 50e5dbe

Please sign in to comment.