Skip to content

Commit

Permalink
feat: migrate document plugin
Browse files Browse the repository at this point in the history
  • Loading branch information
caohuilin committed Dec 12, 2024
1 parent 950a386 commit 52447ce
Show file tree
Hide file tree
Showing 6 changed files with 98 additions and 78 deletions.
1 change: 0 additions & 1 deletion packages/runtime/plugin-runtime/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -221,7 +221,6 @@
},
"devDependencies": {
"@modern-js/app-tools": "workspace:*",
"@modern-js/core": "workspace:*",
"@remix-run/web-fetch": "^4.1.3",
"@rsbuild/core": "1.1.9",
"@scripts/build": "workspace:*",
Expand Down
2 changes: 1 addition & 1 deletion packages/runtime/plugin-runtime/src/cli/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ export const runtimePlugin = (params?: {
ssrPlugin(),
routerPlugin(),
statePlugin(),
documentPlugin() as any,
documentPlugin(),
],
setup: api => {
api.checkEntryPoint(({ path, entry }) => {
Expand Down
91 changes: 45 additions & 46 deletions packages/runtime/plugin-runtime/src/document/cli/index.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import path from 'path';
import type {
AppTools,
CliPlugin,
CliPluginFuture,
NormalizedConfig,
} from '@modern-js/app-tools';
import type { Entrypoint } from '@modern-js/types/cli';
Expand Down Expand Up @@ -64,7 +64,7 @@ export const getDocumenByEntryName = function (
return docFile || undefined;
};

export const documentPlugin = (): CliPlugin<AppTools> => ({
export const documentPlugin = (): CliPluginFuture<AppTools<'shared'>> => ({
name: '@modern-js/plugin-document',

pre: ['@modern-js/plugin-analyze'],
Expand Down Expand Up @@ -92,7 +92,7 @@ export const documentPlugin = (): CliPlugin<AppTools> => ({
templateParameters: Record<string, unknown>,
) => {
const { entrypoints, internalDirectory, appDirectory } =
api.useAppContext();
api.getAppContext();
// search the document.[tsx|jsx|js|ts] under entry
const documentFilePath = getDocumenByEntryName(
entrypoints,
Expand All @@ -105,10 +105,10 @@ export const documentPlugin = (): CliPlugin<AppTools> => ({
}

return async ({ htmlWebpackPlugin }: { [option: string]: any }) => {
const config = api.useResolvedConfigContext();
const config = api.getNormalizedConfig();

const documentParams = getDocParams({
config,
config: config as NormalizedConfig<AppTools>,
entryName,
templateParameters,
});
Expand Down Expand Up @@ -186,7 +186,7 @@ export const documentPlugin = (): CliPlugin<AppTools> => ({

debug("entry %s's document jsx rendered html: %o", entryName, html);
// htmlWebpackPlugin.tags
const { partialsByEntrypoint } = api.useAppContext();
const { partialsByEntrypoint } = api.getAppContext();
const scripts = [
htmlWebpackPlugin.tags.headTags
.filter((item: any) => item.tagName === 'script')
Expand Down Expand Up @@ -300,52 +300,51 @@ export const documentPlugin = (): CliPlugin<AppTools> => ({
return finalHtml;
};
};
return {
config: () => {
const userConfig = api.useConfigContext();

if (userConfig.tools?.htmlPlugin === false) {
return {};
}
api.config(() => {
const userConfig = api.getConfig();

return {
tools: {
htmlPlugin: (options, entry) => {
// just for reuse the baseParames calculate by builder:
// https://github.com/web-infra-dev/modern.js/blob/1abb452a87ae1adbcf8da47d62c05da39cbe4d69/packages/builder/builder-webpack-provider/src/plugins/html.ts#L69-L103
const hackParameters: Record<string, unknown> =
typeof options?.templateParameters === 'function'
? options?.templateParameters(
{} as any,
{} as any,
{} as any,
{} as any,
)
: { ...options?.templateParameters };
if (userConfig.tools?.htmlPlugin === false) {
return {};
}

const templateContent = documentEntry(
entry.entryName,
// options,
hackParameters,
);
return {
tools: {
htmlPlugin: (options, entry) => {
// just for reuse the baseParames calculate by builder:
// https://github.com/web-infra-dev/modern.js/blob/1abb452a87ae1adbcf8da47d62c05da39cbe4d69/packages/builder/builder-webpack-provider/src/plugins/html.ts#L69-L103
const hackParameters: Record<string, unknown> =
typeof options?.templateParameters === 'function'
? options?.templateParameters(
{} as any,
{} as any,
{} as any,
{} as any,
)
: { ...options?.templateParameters };

const documentHtmlOptions = templateContent
? {
templateContent,
// Note: the behavior of inject/modify tags in afterTemplateExecution hook will not take effect
inject: false,
}
: {};
const templateContent = documentEntry(
entry.entryName,
// options,
hackParameters,
);

return {
...options,
...documentHtmlOptions,
};
},
const documentHtmlOptions = templateContent
? {
templateContent,
// Note: the behavior of inject/modify tags in afterTemplateExecution hook will not take effect
inject: false,
}
: {};

return {
...options,
...documentHtmlOptions,
};
},
};
},
};
},
};
});
},
});

Expand Down
2 changes: 1 addition & 1 deletion packages/runtime/plugin-runtime/src/state/cli/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { createRuntimeExportsUtils, getEntryOptions } from '@modern-js/utils';

const PLUGIN_IDENTIFIER = 'state';

export const statePlugin = (): CliPluginFuture<AppTools> => ({
export const statePlugin = (): CliPluginFuture<AppTools<'shared'>> => ({
name: '@modern-js/plugin-state',

required: ['@modern-js/runtime'],
Expand Down
77 changes: 51 additions & 26 deletions packages/runtime/plugin-runtime/tests/document/cli.test.tsx
Original file line number Diff line number Diff line change
@@ -1,46 +1,70 @@
import { existsSync } from 'fs';
import path from 'path';
import { type CliPlugin, type IAppContext, manager } from '@modern-js/core';
import {
type CLIPluginAPI,
type Plugin,
createPluginManager,
} from '@modern-js/plugin-v2';
import { createContext, initPluginAPI } from '@modern-js/plugin-v2/cli';

import type {
AppTools,
AppToolsContext,
AppToolsHooks,
} from '@modern-js/app-tools';
import { getBundleEntry } from '../../../../solutions/app-tools/src/plugins/analyze/getBundleEntry';
import { documentPlugin, getDocumenByEntryName } from '../../src/document/cli';

describe('plugin runtime cli', () => {
const main = manager.clone().usePlugin(documentPlugin as CliPlugin);
let runner: any;

let pluginAPI: CLIPluginAPI<AppTools>;
const setup = async ({ appDirectory }: { appDirectory: string }) => {
const pluginManager = createPluginManager();
pluginManager.addPlugins([documentPlugin() as Plugin]);
const plugins = pluginManager.getPlugins();
const context = await createContext<AppTools>({
appContext: {
appDirectory,
plugins,
} as any,
config: {},
normalizedConfig: { plugins: [] } as any,
});
pluginAPI = initPluginAPI<AppTools>({
context,
pluginManager,
});
context.pluginAPI = pluginAPI;
for (const plugin of plugins) {
await plugin.setup(pluginAPI);
}
};
beforeAll(async () => {
runner = await main.init();
await setup({ appDirectory: path.join(__dirname, './feature') });
});

it('plugin is defined', () => {
expect(documentPlugin).toBeDefined();
});

it('plugin-document cli config is defined', async () => {
const config = await runner.config();
const hooks = pluginAPI.getHooks();
const config = await hooks.config.call();
expect(config.find((item: any) => item.tools)).toBeTruthy();
expect(config.find((item: any) => item.tools.htmlPlugin)).toBeTruthy();
});

it('plugin-document htmlPlugin can return the right', async () => {
const mockAPI = {
useAppContext: jest.fn((): any => ({
internalDirectory: path.join(__dirname, './feature'),
appDirectory: path.join(__dirname, './feature'),
entrypoints: [
{
entryName: 'main',
absoluteEntryDir: path.join(__dirname, './feature'),
},
],
})),
};
const cloned = manager.clone(mockAPI);
cloned.usePlugin(documentPlugin as CliPlugin);
const runner2 = await cloned.init();
const config = await runner2.config();

pluginAPI.updateAppContext({
internalDirectory: path.join(__dirname, './feature'),
appDirectory: path.join(__dirname, './feature'),
entrypoints: [
{
entryName: 'main',
absoluteEntryDir: path.join(__dirname, './feature'),
},
],
});
const hooks = pluginAPI.getHooks();
const config = await hooks.config.call();
const { htmlPlugin } = (
config.find((item: any) => item.tools.htmlPlugin)! as any
).tools;
Expand Down Expand Up @@ -77,12 +101,13 @@ describe('plugin runtime cli', () => {
).toBeTruthy();
});
it('when user config set empty entries and disableDefaultEntries true, should get the ', async () => {
const hooks: any = pluginAPI.getHooks();
const entries = await getBundleEntry(
runner,
hooks,
{
internalDirectory: path.join(__dirname, './feature'),
appDirectory: path.join(__dirname, './feature'),
} as IAppContext,
} as AppToolsContext<'shared'>,
{
source: {
disableDefaultEntries: true,
Expand Down
3 changes: 0 additions & 3 deletions pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

0 comments on commit 52447ce

Please sign in to comment.