Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/pink-rings-reply.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@module-federation/runtime-core': patch
---

fix(runtime): preload filter loaded resources
19 changes: 14 additions & 5 deletions packages/modernjs/src/cli/configPlugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ import {
getMFConfig,
patchMFConfig,
addMyTypes2Ignored,
isWebTarget,
skipByTarget,
} from './utils';

export function setEnv(enableSSR: boolean) {
Expand Down Expand Up @@ -34,21 +36,26 @@ export const moduleFederationConfigPlugin = (
const enableSSR =
userConfig.userConfig?.ssr ?? Boolean(modernjsConfig?.server?.ssr);

api.modifyBundlerChain((chain, { isServer }) => {
api.modifyBundlerChain((chain) => {
const target = chain.get('target');
if (skipByTarget(target)) {
return;
}
const isWeb = isWebTarget(target);
// @ts-expect-error chain type is not correct
addMyTypes2Ignored(chain, isServer ? ssrConfig : csrConfig);
addMyTypes2Ignored(chain, !isWeb ? ssrConfig : csrConfig);

const targetMFConfig = isServer ? ssrConfig : csrConfig;
const targetMFConfig = !isWeb ? ssrConfig : csrConfig;
patchMFConfig(
targetMFConfig,
isServer,
!isWeb,
userConfig.remoteIpStrategy || 'ipv4',
);

patchBundlerConfig({
// @ts-expect-error chain type is not correct
chain,
isServer,
isServer: !isWeb,
modernjsConfig,
mfConfig,
enableSSR,
Expand Down Expand Up @@ -107,3 +114,5 @@ export const moduleFederationConfigPlugin = (
});

export default moduleFederationConfigPlugin;

export { isWebTarget, skipByTarget };
14 changes: 9 additions & 5 deletions packages/modernjs/src/cli/ssrPlugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import { updateStatsAndManifest } from './manifest';
import { isDev } from './constant';
import { MODERN_JS_SERVER_DIR } from '../constant';
import logger from './logger';
import { isWebTarget } from './utils';
import { isWebTarget, skipByTarget } from './utils';

export function setEnv() {
process.env['MF_DISABLE_EMIT_STATS'] = 'true';
Expand Down Expand Up @@ -48,15 +48,19 @@ export const moduleFederationSSRPlugin = (
});
return { entrypoint, plugins };
});
api.modifyBundlerChain((chain, { isServer }) => {
api.modifyBundlerChain((chain) => {
const target = chain.get('target');
if (skipByTarget(target)) {
return;
}
const bundlerType =
api.getAppContext().bundlerType === 'rspack' ? 'rspack' : 'webpack';
const MFPlugin =
bundlerType === 'webpack'
? ModuleFederationPlugin
: RspackModuleFederationPlugin;

const isWeb = isWebTarget(chain.get('target'));
const isWeb = isWebTarget(target);

if (!isWeb) {
if (!chain.plugins.has(CHAIN_MF_PLUGIN_ID)) {
Expand All @@ -79,13 +83,13 @@ export const moduleFederationSSRPlugin = (
}
}

if (isDev && !isServer) {
if (isDev && isWeb) {
chain.externals({
'@module-federation/node/utils': 'NOT_USED_IN_BROWSER',
});
}

if (isServer) {
if (!isWeb) {
ssrOutputPath =
chain.output.get('path') ||
path.resolve(process.cwd(), `dist/${MODERN_JS_SERVER_DIR}`);
Expand Down
10 changes: 10 additions & 0 deletions packages/modernjs/src/cli/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -389,3 +389,13 @@ export const isWebTarget = (target: string[] | string) => {
}
return false;
};

export const skipByTarget = (target: string[] | string) => {
const IGNORE_TARGET = 'webworker';
if (Array.isArray(target)) {
return target.includes(IGNORE_TARGET);
} else if (typeof target === 'string') {
return target === IGNORE_TARGET;
}
return false;
};
5 changes: 4 additions & 1 deletion packages/modernjs/src/runtime/index.ts
Original file line number Diff line number Diff line change
@@ -1,2 +1,5 @@
export * from '@module-federation/enhanced/runtime';
export { createRemoteSSRComponent } from './createRemoteSSRComponent';
export {
createRemoteSSRComponent,
collectSSRAssets,
} from './createRemoteSSRComponent';
20 changes: 17 additions & 3 deletions packages/runtime-core/src/plugins/generate-preload-assets.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import {
ProviderModuleInfo,
isManifestProvider,
getResourceUrl,
isBrowserEnv,
} from '@module-federation/sdk';
import {
EntryAssets,
Expand Down Expand Up @@ -101,6 +102,12 @@ function traverseModuleInfo(
}
}

const isExisted = (type: 'link' | 'script', url: string) => {
return document.querySelector(
`${type}[${type === 'link' ? 'href' : 'src'}="${url}"]`,
);
};

// eslint-disable-next-line max-lines-per-function
export function generatePreloadAssets(
origin: FederationHost,
Expand Down Expand Up @@ -290,16 +297,16 @@ export function generatePreloadAssets(
}

const needPreloadJsAssets = jsAssets.filter(
(asset) => !loadedSharedJsAssets.has(asset),
(asset) => !loadedSharedJsAssets.has(asset) && !isExisted('script', asset),
);
const needPreloadCssAssets = cssAssets.filter(
(asset) => !loadedSharedCssAssets.has(asset),
(asset) => !loadedSharedCssAssets.has(asset) && !isExisted('link', asset),
);

return {
cssAssets: needPreloadCssAssets,
jsAssetsWithoutEntry: needPreloadJsAssets,
entryAssets,
entryAssets: entryAssets.filter((entry) => !isExisted('script', entry.url)),
};
}

Expand All @@ -316,6 +323,13 @@ export const generatePreloadAssetsPlugin: () => FederationRuntimePlugin =
globalSnapshot,
remoteSnapshot,
} = args;
if (!isBrowserEnv()) {
return {
cssAssets: [],
jsAssetsWithoutEntry: [],
entryAssets: [],
};
}

if (isRemoteInfoWithEntry(remote) && isPureRemoteEntry(remote)) {
return {
Expand Down