mirror of
https://github.com/facebook/docusaurus.git
synced 2025-07-26 21:18:47 +02:00
Add support for locale extensions in pages plugin
This commit is contained in:
parent
ca09f238f3
commit
fc72669528
7 changed files with 90 additions and 14 deletions
|
@ -11,6 +11,10 @@ module.exports = {
|
||||||
url: 'https://your-docusaurus-site.example.com',
|
url: 'https://your-docusaurus-site.example.com',
|
||||||
baseUrl: '/',
|
baseUrl: '/',
|
||||||
favicon: 'img/favicon.ico',
|
favicon: 'img/favicon.ico',
|
||||||
|
i18n: {
|
||||||
|
defaultLocale: 'en',
|
||||||
|
locales: ['en', 'fr'],
|
||||||
|
},
|
||||||
markdown: {
|
markdown: {
|
||||||
parseFrontMatter: async (params) => {
|
parseFrontMatter: async (params) => {
|
||||||
const result = await params.defaultParseFrontMatter(params);
|
const result = await params.defaultParseFrontMatter(params);
|
||||||
|
|
|
@ -0,0 +1,22 @@
|
||||||
|
/**
|
||||||
|
* Copyright (c) Facebook, Inc. and its affiliates.
|
||||||
|
*
|
||||||
|
* This source code is licensed under the MIT license found in the
|
||||||
|
* LICENSE file in the root directory of this source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
import React from 'react';
|
||||||
|
import Head from '@docusaurus/Head';
|
||||||
|
|
||||||
|
export default class Home extends React.Component {
|
||||||
|
render() {
|
||||||
|
return (
|
||||||
|
<div>
|
||||||
|
<Head>
|
||||||
|
<title>translated Hello</title>
|
||||||
|
</Head>
|
||||||
|
<div>translated TypeScript...</div>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
|
@ -69,7 +69,7 @@ exports[`docusaurus-plugin-content-pages loads simple pages with french translat
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"permalink": "/fr/typescript",
|
"permalink": "/fr/typescript",
|
||||||
"source": "@site/src/pages/typescript.tsx",
|
"source": "@site/src/pages/typescript.fr.tsx",
|
||||||
"type": "jsx",
|
"type": "jsx",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
|
|
@ -13,7 +13,6 @@ import {
|
||||||
aliasedSitePath,
|
aliasedSitePath,
|
||||||
docuHash,
|
docuHash,
|
||||||
getPluginI18nPath,
|
getPluginI18nPath,
|
||||||
getFolderContainingFile,
|
|
||||||
addTrailingPathSeparator,
|
addTrailingPathSeparator,
|
||||||
Globby,
|
Globby,
|
||||||
createAbsoluteFilePathMatcher,
|
createAbsoluteFilePathMatcher,
|
||||||
|
@ -22,6 +21,7 @@ import {
|
||||||
parseMarkdownFile,
|
parseMarkdownFile,
|
||||||
isUnlisted,
|
isUnlisted,
|
||||||
isDraft,
|
isDraft,
|
||||||
|
findAsyncSequential,
|
||||||
} from '@docusaurus/utils';
|
} from '@docusaurus/utils';
|
||||||
import {validatePageFrontMatter} from './frontMatter';
|
import {validatePageFrontMatter} from './frontMatter';
|
||||||
|
|
||||||
|
@ -38,6 +38,48 @@ export function getContentPathList(contentPaths: PagesContentPaths): string[] {
|
||||||
return [contentPaths.contentPathLocalized, contentPaths.contentPath];
|
return [contentPaths.contentPathLocalized, contentPaths.contentPath];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async function getLocalizedSource({
|
||||||
|
relativeSource,
|
||||||
|
contentPaths,
|
||||||
|
locale,
|
||||||
|
}: {
|
||||||
|
relativeSource: string;
|
||||||
|
contentPaths: PagesContentPaths;
|
||||||
|
locale: string;
|
||||||
|
}) {
|
||||||
|
const {name, dir, ext} = path.parse(relativeSource);
|
||||||
|
|
||||||
|
// Lookup in localized folder in priority
|
||||||
|
const possibleSources = getContentPathList(contentPaths).flatMap(
|
||||||
|
(contentPath) => [
|
||||||
|
path.join(contentPath, dir, `${name}.${locale}${ext}`),
|
||||||
|
path.join(contentPath, relativeSource),
|
||||||
|
],
|
||||||
|
);
|
||||||
|
|
||||||
|
const localizedSource = await findAsyncSequential(
|
||||||
|
possibleSources,
|
||||||
|
fs.pathExists,
|
||||||
|
);
|
||||||
|
|
||||||
|
if (!localizedSource) {
|
||||||
|
throw new Error('unexpected');
|
||||||
|
}
|
||||||
|
|
||||||
|
return localizedSource;
|
||||||
|
}
|
||||||
|
|
||||||
|
function filterLocaleExtensionFiles(
|
||||||
|
files: string[],
|
||||||
|
locales: string[],
|
||||||
|
): string[] {
|
||||||
|
const localeExtensions = locales.map((locale) => `.${locale}`);
|
||||||
|
return files.filter((file) => {
|
||||||
|
const {name} = path.parse(file);
|
||||||
|
return !localeExtensions.includes(path.extname(name));
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
const isMarkdownSource = (source: string) =>
|
const isMarkdownSource = (source: string) =>
|
||||||
source.endsWith('.md') || source.endsWith('.mdx');
|
source.endsWith('.md') || source.endsWith('.mdx');
|
||||||
|
|
||||||
|
@ -62,6 +104,14 @@ export default function pluginContentPages(
|
||||||
);
|
);
|
||||||
const dataDir = path.join(pluginDataDirRoot, options.id ?? DEFAULT_PLUGIN_ID);
|
const dataDir = path.join(pluginDataDirRoot, options.id ?? DEFAULT_PLUGIN_ID);
|
||||||
|
|
||||||
|
async function getPageFiles() {
|
||||||
|
const files = await Globby(options.include, {
|
||||||
|
cwd: contentPaths.contentPath,
|
||||||
|
ignore: options.exclude,
|
||||||
|
});
|
||||||
|
return filterLocaleExtensionFiles(files, context.i18n.locales);
|
||||||
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
name: 'docusaurus-plugin-content-pages',
|
name: 'docusaurus-plugin-content-pages',
|
||||||
|
|
||||||
|
@ -73,28 +123,21 @@ export default function pluginContentPages(
|
||||||
},
|
},
|
||||||
|
|
||||||
async loadContent() {
|
async loadContent() {
|
||||||
const {include} = options;
|
|
||||||
|
|
||||||
if (!(await fs.pathExists(contentPaths.contentPath))) {
|
if (!(await fs.pathExists(contentPaths.contentPath))) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
const {baseUrl} = siteConfig;
|
const {baseUrl} = siteConfig;
|
||||||
const pagesFiles = await Globby(include, {
|
const pagesFiles = await getPageFiles();
|
||||||
cwd: contentPaths.contentPath,
|
|
||||||
ignore: options.exclude,
|
|
||||||
});
|
|
||||||
|
|
||||||
async function processPageSourceFile(
|
async function processPageSourceFile(
|
||||||
relativeSource: string,
|
relativeSource: string,
|
||||||
): Promise<Metadata | undefined> {
|
): Promise<Metadata | undefined> {
|
||||||
// Lookup in localized folder in priority
|
const source = await getLocalizedSource({
|
||||||
const contentPath = await getFolderContainingFile(
|
|
||||||
getContentPathList(contentPaths),
|
|
||||||
relativeSource,
|
relativeSource,
|
||||||
);
|
contentPaths,
|
||||||
|
locale: context.i18n.currentLocale,
|
||||||
const source = path.join(contentPath, relativeSource);
|
});
|
||||||
const aliasedSourcePath = aliasedSitePath(source, siteDir);
|
const aliasedSourcePath = aliasedSitePath(source, siteDir);
|
||||||
const permalink = normalizeUrl([
|
const permalink = normalizeUrl([
|
||||||
baseUrl,
|
baseUrl,
|
||||||
|
|
3
website/_dogfooding/_pages tests/i18n/index.fr.md
Normal file
3
website/_dogfooding/_pages tests/i18n/index.fr.md
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
# Page i18n test
|
||||||
|
|
||||||
|
French version
|
3
website/_dogfooding/_pages tests/i18n/index.md
Normal file
3
website/_dogfooding/_pages tests/i18n/index.md
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
# Page i18n test
|
||||||
|
|
||||||
|
English version
|
|
@ -26,6 +26,7 @@ import Readme from "../README.mdx"
|
||||||
### Other tests
|
### Other tests
|
||||||
|
|
||||||
- [React 18](/tests/pages/react-18)
|
- [React 18](/tests/pages/react-18)
|
||||||
|
- [i18n](/tests/pages/i18n)
|
||||||
- [Crash test](/tests/pages/crashTest)
|
- [Crash test](/tests/pages/crashTest)
|
||||||
- [Code block tests](/tests/pages/code-block-tests)
|
- [Code block tests](/tests/pages/code-block-tests)
|
||||||
- [Link tests](/tests/pages/link-tests)
|
- [Link tests](/tests/pages/link-tests)
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue