feat(v2): add @theme-original alias to give access to pre-swizzled components (#2455)

This commit is contained in:
Yangshun Tay 2020-03-25 00:53:51 +08:00 committed by GitHub
parent c2fd6520ae
commit 27e7fa617d
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
5 changed files with 76 additions and 13 deletions

View file

@ -89,7 +89,7 @@ export async function load(
plugins.map(plugin => plugin.getThemePath && plugin.getThemePath()),
);
const userTheme = path.resolve(siteDir, THEME_PATH);
const alias = loadThemeAlias([fallbackTheme, ...pluginThemes, userTheme]);
const alias = loadThemeAlias([fallbackTheme, ...pluginThemes], [userTheme]);
// Make a fake plugin to:
// - Resolve aliased theme components

View file

@ -14,6 +14,19 @@ describe('themeAlias', () => {
const fixtures = path.join(__dirname, '__fixtures__');
const themePath = path.join(fixtures, 'theme-1');
const alias = themeAlias(themePath);
expect(alias).toEqual({
'@theme/Footer': path.join(themePath, 'Footer/index.js'),
'@theme-original/Footer': path.join(themePath, 'Footer/index.js'),
'@theme/Layout': path.join(themePath, 'Layout.js'),
'@theme-original/Layout': path.join(themePath, 'Layout.js'),
});
expect(alias).not.toEqual({});
});
test('valid themePath 1 with components without original', () => {
const fixtures = path.join(__dirname, '__fixtures__');
const themePath = path.join(fixtures, 'theme-1');
const alias = themeAlias(themePath, false);
expect(alias).toEqual({
'@theme/Footer': path.join(themePath, 'Footer/index.js'),
'@theme/Layout': path.join(themePath, 'Layout.js'),
@ -25,6 +38,19 @@ describe('themeAlias', () => {
const fixtures = path.join(__dirname, '__fixtures__');
const themePath = path.join(fixtures, 'theme-2');
const alias = themeAlias(themePath);
expect(alias).toEqual({
'@theme/Navbar': path.join(themePath, 'Navbar.js'),
'@theme-original/Navbar': path.join(themePath, 'Navbar.js'),
'@theme/Layout': path.join(themePath, 'Layout/index.js'),
'@theme-original/Layout': path.join(themePath, 'Layout/index.js'),
});
expect(alias).not.toEqual({});
});
test('valid themePath 2 with components without original', () => {
const fixtures = path.join(__dirname, '__fixtures__');
const themePath = path.join(fixtures, 'theme-2');
const alias = themeAlias(themePath, false);
expect(alias).toEqual({
'@theme/Navbar': path.join(themePath, 'Navbar.js'),
'@theme/Layout': path.join(themePath, 'Layout/index.js'),
@ -40,6 +66,14 @@ describe('themeAlias', () => {
expect(alias).toEqual({});
});
test('valid themePath with no components without original', () => {
const fixtures = path.join(__dirname, '__fixtures__');
const themePath = path.join(fixtures, 'empty-theme');
fs.ensureDirSync(themePath);
const alias = themeAlias(themePath, false);
expect(alias).toEqual({});
});
test('invalid themePath that does not exist', () => {
const fixtures = path.join(__dirname, '__fixtures__');
const themePath = path.join(fixtures, '__noExist__');

View file

@ -17,8 +17,11 @@ describe('loadThemeAlias', () => {
const alias = loadThemeAlias([theme1Path, theme2Path]);
expect(alias).toEqual({
'@theme/Footer': path.join(theme1Path, 'Footer/index.js'),
'@theme-original/Footer': path.join(theme1Path, 'Footer/index.js'),
'@theme/Navbar': path.join(theme2Path, 'Navbar.js'),
'@theme-original/Navbar': path.join(theme2Path, 'Navbar.js'),
'@theme/Layout': path.join(theme2Path, 'Layout/index.js'),
'@theme-original/Layout': path.join(theme2Path, 'Layout/index.js'),
});
expect(alias).not.toEqual({});
});

View file

@ -11,7 +11,10 @@ import path from 'path';
import {fileToPath, posixPath, normalizeUrl} from '@docusaurus/utils';
import {ThemeAlias} from '@docusaurus/types';
export function themeAlias(themePath: string): ThemeAlias {
export function themeAlias(
themePath: string,
addOriginalAlias: boolean = true,
): ThemeAlias {
if (!fs.pathExistsSync(themePath)) {
return {};
}
@ -20,15 +23,25 @@ export function themeAlias(themePath: string): ThemeAlias {
cwd: themePath,
});
const alias: ThemeAlias = {};
const aliases: ThemeAlias = {};
themeComponentFiles.forEach(relativeSource => {
const filePath = path.join(themePath, relativeSource);
const fileName = fileToPath(relativeSource);
const aliasName = posixPath(
normalizeUrl(['@theme', fileName]).replace(/\/$/, ''),
);
alias[aliasName] = filePath;
aliases[aliasName] = filePath;
if (addOriginalAlias) {
// For swizzled components to access the original.
const originalAliasName = posixPath(
normalizeUrl(['@theme-original', fileName]).replace(/\/$/, ''),
);
aliases[originalAliasName] = filePath;
}
});
return alias;
return aliases;
}

View file

@ -8,12 +8,25 @@
import {ThemeAlias} from '@docusaurus/types';
import {themeAlias} from './alias';
export function loadThemeAlias(themePaths: string[]): ThemeAlias {
return themePaths.reduce(
(alias, themePath) => ({
...alias,
...themeAlias(themePath),
}),
{},
);
export function loadThemeAlias(
themePaths: string[],
userThemePaths: string[] = [],
): ThemeAlias {
const aliases = {};
themePaths.forEach(themePath => {
const themeAliases = themeAlias(themePath);
Object.keys(themeAliases).forEach(aliasKey => {
aliases[aliasKey] = themeAliases[aliasKey];
});
});
userThemePaths.forEach(themePath => {
const userThemeAliases = themeAlias(themePath, false);
Object.keys(userThemeAliases).forEach(aliasKey => {
aliases[aliasKey] = userThemeAliases[aliasKey];
});
});
return aliases;
}