@module-federation/modern-js 0.0.0-next-20240521123600 → 0.0.0-next-20240523080317

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -52,15 +52,15 @@ const moduleFederationPlugin = (userConfig = {}) => ({
52
52
  const enableSSR = Boolean(modernjsConfig === null || modernjsConfig === void 0 ? void 0 : (_modernjsConfig_server = modernjsConfig.server) === null || _modernjsConfig_server === void 0 ? void 0 : _modernjsConfig_server.ssr);
53
53
  const mfConfig = await (0, import_utils2.getMFConfig)(userConfig);
54
54
  let outputDir = "";
55
- const bundlerType = useAppContext().bundlerType === "rspack" ? "rspack" : "webpack";
56
- const WebpackPluginConstructor = userConfig.webpackPluginImplementation || import_enhanced.ModuleFederationPlugin;
57
- const RspackPluginConstructor = userConfig.webpackPluginImplementation || import_rspack.ModuleFederationPlugin;
58
- const MFBundlerPlugin = bundlerType === "rspack" ? RspackPluginConstructor : WebpackPluginConstructor;
59
55
  let browserPlugin;
60
56
  let nodePlugin;
61
57
  return {
62
58
  config: () => {
63
59
  var _modernjsConfig_dev;
60
+ const bundlerType = useAppContext().bundlerType === "rspack" ? "rspack" : "webpack";
61
+ const WebpackPluginConstructor = userConfig.webpackPluginImplementation || import_enhanced.ModuleFederationPlugin;
62
+ const RspackPluginConstructor = userConfig.rspackPluginImplementation || import_rspack.ModuleFederationPlugin;
63
+ const MFBundlerPlugin = bundlerType === "rspack" ? RspackPluginConstructor : WebpackPluginConstructor;
64
64
  if (enableSSR) {
65
65
  process.env["MF_DISABLE_EMIT_STATS"] = "true";
66
66
  process.env["MF_SSR_PRJ"] = "true";
@@ -72,11 +72,15 @@ const moduleFederationPlugin = (userConfig = {}) => ({
72
72
  nodePlugin = new MFBundlerPlugin(envConfig);
73
73
  (_config_plugins = config.plugins) === null || _config_plugins === void 0 ? void 0 : _config_plugins.push(nodePlugin);
74
74
  (_config_plugins1 = config.plugins) === null || _config_plugins1 === void 0 ? void 0 : _config_plugins1.push(new import_node.StreamingTargetPlugin(envConfig));
75
+ if (isDev) {
76
+ var _config_plugins2;
77
+ (_config_plugins2 = config.plugins) === null || _config_plugins2 === void 0 ? void 0 : _config_plugins2.push(new import_node.EntryChunkTrackerPlugin());
78
+ }
75
79
  } else {
76
- var _config_output, _config_plugins2;
80
+ var _config_output, _config_plugins3;
77
81
  outputDir = ((_config_output = config.output) === null || _config_output === void 0 ? void 0 : _config_output.path) || import_path.default.resolve(process.cwd(), "dist");
78
82
  browserPlugin = new MFBundlerPlugin(envConfig);
79
- (_config_plugins2 = config.plugins) === null || _config_plugins2 === void 0 ? void 0 : _config_plugins2.push(browserPlugin);
83
+ (_config_plugins3 = config.plugins) === null || _config_plugins3 === void 0 ? void 0 : _config_plugins3.push(browserPlugin);
80
84
  }
81
85
  (0, import_utils2.patchWebpackConfig)({
82
86
  bundlerConfig: config,
@@ -116,9 +120,9 @@ const moduleFederationPlugin = (userConfig = {}) => ({
116
120
  return;
117
121
  }
118
122
  try {
119
- var _req_url, _req_url1;
123
+ var _req_url, _req_url1, _req_url2;
120
124
  const SERVER_PREFIX = `/${import_constant.MODERN_JS_SERVER_DIR}`;
121
- if (((_req_url = req.url) === null || _req_url === void 0 ? void 0 : _req_url.startsWith(SERVER_PREFIX)) || ((_req_url1 = req.url) === null || _req_url1 === void 0 ? void 0 : _req_url1.includes(".json"))) {
125
+ if (((_req_url = req.url) === null || _req_url === void 0 ? void 0 : _req_url.startsWith(SERVER_PREFIX)) || ((_req_url1 = req.url) === null || _req_url1 === void 0 ? void 0 : _req_url1.includes(".json")) && !((_req_url2 = req.url) === null || _req_url2 === void 0 ? void 0 : _req_url2.includes("hot-update"))) {
122
126
  const filepath = import_path.default.join(process.cwd(), `dist${req.url}`);
123
127
  import_utils.fs.statSync(filepath);
124
128
  res.setHeader("Access-Control-Allow-Origin", "*");
@@ -134,6 +138,14 @@ const moduleFederationPlugin = (userConfig = {}) => ({
134
138
  }
135
139
  }
136
140
  ]
141
+ },
142
+ bundlerChain(chain, { isServer }) {
143
+ if (isDev && !isServer) {
144
+ chain.externals({
145
+ "@module-federation/node/utils": "NOT_USED_IN_BROWSER",
146
+ "@module-federation/dts-plugin/server": "NOT_USED_IN_BROWSER"
147
+ });
148
+ }
137
149
  }
138
150
  },
139
151
  source: {
@@ -175,7 +187,9 @@ const moduleFederationPlugin = (userConfig = {}) => ({
175
187
  }
176
188
  plugins.unshift({
177
189
  name: SSR_PLUGIN_IDENTIFIER,
178
- options: JSON.stringify({})
190
+ options: JSON.stringify({
191
+ name: mfConfig.name
192
+ })
179
193
  });
180
194
  return {
181
195
  entrypoint,
@@ -0,0 +1,44 @@
1
+ "use strict";
2
+ var __create = Object.create;
3
+ var __defProp = Object.defineProperty;
4
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
+ var __getOwnPropNames = Object.getOwnPropertyNames;
6
+ var __getProtoOf = Object.getPrototypeOf;
7
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __export = (target, all) => {
9
+ for (var name in all)
10
+ __defProp(target, name, { get: all[name], enumerable: true });
11
+ };
12
+ var __copyProps = (to, from, except, desc) => {
13
+ if (from && typeof from === "object" || typeof from === "function") {
14
+ for (let key of __getOwnPropNames(from))
15
+ if (!__hasOwnProp.call(to, key) && key !== except)
16
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
17
+ }
18
+ return to;
19
+ };
20
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
+ // If the importer is in node compatibility mode or this is not an ESM
22
+ // file that has been converted to a CommonJS file using a Babel-
23
+ // compatible transform (i.e. "__esModule" has not been set), then set
24
+ // "default" to the CommonJS "module.exports" for node compatibility.
25
+ isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
26
+ mod
27
+ ));
28
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
+ var inject_node_fetch_exports = {};
30
+ __export(inject_node_fetch_exports, {
31
+ default: () => inject_node_fetch_default
32
+ });
33
+ module.exports = __toCommonJS(inject_node_fetch_exports);
34
+ var import_node_fetch = __toESM(require("node-fetch"));
35
+ const injectNodeFetchPlugin = () => ({
36
+ name: "inject-node-fetch-plugin",
37
+ beforeInit(args) {
38
+ if (!globalThis.fetch) {
39
+ globalThis.fetch = import_node_fetch.default;
40
+ }
41
+ return args;
42
+ }
43
+ });
44
+ var inject_node_fetch_default = injectNodeFetchPlugin;
@@ -34,6 +34,7 @@ __export(utils_exports, {
34
34
  patchWebpackConfig: () => patchWebpackConfig
35
35
  });
36
36
  module.exports = __toCommonJS(utils_exports);
37
+ var import_sdk = require("@module-federation/sdk");
37
38
  var import_path = __toESM(require("path"));
38
39
  var import_node_bundle_require = require("@modern-js/node-bundle-require");
39
40
  const defaultPath = import_path.default.resolve(process.cwd(), "module-federation.config.ts");
@@ -51,22 +52,48 @@ const patchMFConfig = (mfConfig, isServer) => {
51
52
  const runtimePlugins = [
52
53
  ...mfConfig.runtimePlugins || []
53
54
  ];
54
- const runtimePluginPath = import_path.default.resolve(__dirname, "./mfRuntimePlugins/shared-strategy.js");
55
- if (!runtimePlugins.includes(runtimePluginPath)) {
56
- runtimePlugins.push(import_path.default.resolve(__dirname, "./mfRuntimePlugins/shared-strategy.js"));
55
+ const sharedStrategyRuntimePluginPath = import_path.default.resolve(__dirname, "./mfRuntimePlugins/shared-strategy.js");
56
+ if (!runtimePlugins.includes(sharedStrategyRuntimePluginPath)) {
57
+ runtimePlugins.push(sharedStrategyRuntimePluginPath);
57
58
  }
58
59
  if (isServer) {
59
- const nodeHmrPluginPath = require.resolve("@module-federation/node/record-dynamic-remote-entry-hash-plugin");
60
- if (!runtimePlugins.includes(nodeHmrPluginPath)) {
61
- runtimePlugins.push(nodeHmrPluginPath);
60
+ const isDev = process.env.NODE_ENV === "development";
61
+ if (isDev) {
62
+ const nodeHmrPluginPath = require.resolve("@module-federation/node/record-dynamic-remote-entry-hash-plugin");
63
+ if (!runtimePlugins.includes(nodeHmrPluginPath)) {
64
+ runtimePlugins.push(nodeHmrPluginPath);
65
+ }
66
+ }
67
+ const injectNodeFetchRuntimePluginPath = import_path.default.resolve(__dirname, "./mfRuntimePlugins/inject-node-fetch.js");
68
+ if (!runtimePlugins.includes(injectNodeFetchRuntimePluginPath)) {
69
+ runtimePlugins.push(injectNodeFetchRuntimePluginPath);
62
70
  }
63
71
  }
64
72
  if (typeof mfConfig.async === "undefined") {
65
73
  mfConfig.async = true;
66
74
  }
75
+ if (!isServer) {
76
+ return {
77
+ ...mfConfig,
78
+ runtimePlugins,
79
+ dts: mfConfig.dts === false ? false : {
80
+ generateTypes: false,
81
+ consumeTypes: false,
82
+ ...typeof mfConfig.dts === "object" ? mfConfig.dts : {}
83
+ },
84
+ dev: mfConfig.dev === false ? false : {
85
+ disableHotTypesReload: true,
86
+ disableLiveReload: false,
87
+ injectWebClient: true,
88
+ ...typeof mfConfig.dev === "object" ? mfConfig.dev : {}
89
+ }
90
+ };
91
+ }
67
92
  return {
68
93
  ...mfConfig,
69
- runtimePlugins
94
+ runtimePlugins,
95
+ dts: false,
96
+ dev: false
70
97
  };
71
98
  };
72
99
  function getTargetEnvConfig(mfConfig, isServer) {
@@ -112,7 +139,7 @@ function patchWebpackConfig(options) {
112
139
  const uniqueName = mfConfig.name || (output === null || output === void 0 ? void 0 : output.uniqueName);
113
140
  const chunkFileName = output === null || output === void 0 ? void 0 : output.chunkFilename;
114
141
  if (output && typeof chunkFileName === "string" && uniqueName && !chunkFileName.includes(uniqueName)) {
115
- const suffix = `-[chunkhash].js`;
142
+ const suffix = `${(0, import_sdk.encodeName)(uniqueName)}-[chunkhash].js`;
116
143
  output.chunkFilename = chunkFileName.replace(".js", suffix);
117
144
  }
118
145
  }
@@ -31,27 +31,44 @@ __export(plugin_exports, {
31
31
  mfPluginSSR: () => mfPluginSSR
32
32
  });
33
33
  module.exports = __toCommonJS(plugin_exports);
34
- const mfPluginSSR = () => ({
34
+ const mfPluginSSR = ({ name }) => ({
35
35
  name: "@module-federation/modern-js",
36
- // eslint-disable-next-line max-lines-per-function
37
- setup: () => ({
38
- // eslint-disable-next-line max-lines-per-function
39
- async init({ context }, next) {
40
- if (typeof window !== "undefined") {
36
+ setup: () => {
37
+ let mfDevServer;
38
+ return {
39
+ async init({ context }, next) {
40
+ if (typeof window !== "undefined") {
41
+ return next({
42
+ context
43
+ });
44
+ }
45
+ const devServer = await Promise.resolve().then(() => __toESM(require("@module-federation/dts-plugin/server")));
46
+ if (name) {
47
+ mfDevServer = new devServer.ModuleFederationDevServer({
48
+ name: `${name}-server`,
49
+ remotes: [],
50
+ updateCallback: async () => {
51
+ },
52
+ remoteTypeTarPath: ""
53
+ });
54
+ }
55
+ const nodeUtils = await Promise.resolve().then(() => __toESM(require("@module-federation/node/utils")));
56
+ const shouldUpdate = await nodeUtils.revalidate();
57
+ if (shouldUpdate) {
58
+ console.log("should RELOAD", shouldUpdate);
59
+ await nodeUtils.flushChunks();
60
+ mfDevServer && mfDevServer.update({
61
+ updateKind: devServer.UpdateKind.RELOAD_PAGE,
62
+ updateMode: devServer.UpdateMode.POSITIVE,
63
+ clientName: name
64
+ });
65
+ }
41
66
  return next({
42
67
  context
43
68
  });
44
69
  }
45
- const nodeUtils = await Promise.resolve().then(() => __toESM(require("@module-federation/node/utils")));
46
- const shouldUpdate = await nodeUtils.revalidate();
47
- if (shouldUpdate) {
48
- console.log("should HMR", shouldUpdate);
49
- }
50
- return next({
51
- context
52
- });
53
- }
54
- })
70
+ };
71
+ }
55
72
  });
56
73
  // Annotate the CommonJS export names for ESM import in node:
57
74
  0 && (module.exports = {
@@ -4,7 +4,7 @@ import path from "path";
4
4
  import { fs } from "@modern-js/utils";
5
5
  import { ModuleFederationPlugin as WebpackModuleFederationPlugin, AsyncBoundaryPlugin } from "@module-federation/enhanced";
6
6
  import { ModuleFederationPlugin as RspackModuleFederationPlugin } from "@module-federation/enhanced/rspack";
7
- import { StreamingTargetPlugin } from "@module-federation/node";
7
+ import { StreamingTargetPlugin, EntryChunkTrackerPlugin } from "@module-federation/node";
8
8
  import { getMFConfig, getTargetEnvConfig, patchWebpackConfig } from "./utils";
9
9
  import { updateStatsAndManifest } from "./manifest";
10
10
  import { MODERN_JS_SERVER_DIR } from "../constant";
@@ -16,7 +16,7 @@ var moduleFederationPlugin = function() {
16
16
  name: "@modern-js/plugin-module-federation",
17
17
  setup: function() {
18
18
  var _ref = _async_to_generator(function(param) {
19
- var useConfigContext, useAppContext, _modernjsConfig_server, modernjsConfig, enableSSR, mfConfig, outputDir, bundlerType, WebpackPluginConstructor, RspackPluginConstructor, MFBundlerPlugin, browserPlugin, nodePlugin;
19
+ var useConfigContext, useAppContext, _modernjsConfig_server, modernjsConfig, enableSSR, mfConfig, outputDir, browserPlugin, nodePlugin;
20
20
  return _ts_generator(this, function(_state) {
21
21
  switch (_state.label) {
22
22
  case 0:
@@ -30,15 +30,15 @@ var moduleFederationPlugin = function() {
30
30
  case 1:
31
31
  mfConfig = _state.sent();
32
32
  outputDir = "";
33
- bundlerType = useAppContext().bundlerType === "rspack" ? "rspack" : "webpack";
34
- WebpackPluginConstructor = userConfig.webpackPluginImplementation || WebpackModuleFederationPlugin;
35
- RspackPluginConstructor = userConfig.webpackPluginImplementation || RspackModuleFederationPlugin;
36
- MFBundlerPlugin = bundlerType === "rspack" ? RspackPluginConstructor : WebpackPluginConstructor;
37
33
  return [
38
34
  2,
39
35
  {
40
36
  config: function() {
41
37
  var _modernjsConfig_dev;
38
+ var bundlerType = useAppContext().bundlerType === "rspack" ? "rspack" : "webpack";
39
+ var WebpackPluginConstructor = userConfig.webpackPluginImplementation || WebpackModuleFederationPlugin;
40
+ var RspackPluginConstructor = userConfig.rspackPluginImplementation || RspackModuleFederationPlugin;
41
+ var MFBundlerPlugin = bundlerType === "rspack" ? RspackPluginConstructor : WebpackPluginConstructor;
42
42
  if (enableSSR) {
43
43
  process.env["MF_DISABLE_EMIT_STATS"] = "true";
44
44
  process.env["MF_SSR_PRJ"] = "true";
@@ -50,11 +50,15 @@ var moduleFederationPlugin = function() {
50
50
  nodePlugin = new MFBundlerPlugin(envConfig);
51
51
  (_config_plugins = config.plugins) === null || _config_plugins === void 0 ? void 0 : _config_plugins.push(nodePlugin);
52
52
  (_config_plugins1 = config.plugins) === null || _config_plugins1 === void 0 ? void 0 : _config_plugins1.push(new StreamingTargetPlugin(envConfig));
53
+ if (isDev) {
54
+ var _config_plugins2;
55
+ (_config_plugins2 = config.plugins) === null || _config_plugins2 === void 0 ? void 0 : _config_plugins2.push(new EntryChunkTrackerPlugin());
56
+ }
53
57
  } else {
54
- var _config_output, _config_plugins2;
58
+ var _config_output, _config_plugins3;
55
59
  outputDir = ((_config_output = config.output) === null || _config_output === void 0 ? void 0 : _config_output.path) || path.resolve(process.cwd(), "dist");
56
60
  browserPlugin = new MFBundlerPlugin(envConfig);
57
- (_config_plugins2 = config.plugins) === null || _config_plugins2 === void 0 ? void 0 : _config_plugins2.push(browserPlugin);
61
+ (_config_plugins3 = config.plugins) === null || _config_plugins3 === void 0 ? void 0 : _config_plugins3.push(browserPlugin);
58
62
  }
59
63
  patchWebpackConfig({
60
64
  bundlerConfig: config,
@@ -99,9 +103,9 @@ var moduleFederationPlugin = function() {
99
103
  return;
100
104
  }
101
105
  try {
102
- var _req_url, _req_url1;
106
+ var _req_url, _req_url1, _req_url2;
103
107
  var SERVER_PREFIX = "/".concat(MODERN_JS_SERVER_DIR);
104
- if (((_req_url = req.url) === null || _req_url === void 0 ? void 0 : _req_url.startsWith(SERVER_PREFIX)) || ((_req_url1 = req.url) === null || _req_url1 === void 0 ? void 0 : _req_url1.includes(".json"))) {
108
+ if (((_req_url = req.url) === null || _req_url === void 0 ? void 0 : _req_url.startsWith(SERVER_PREFIX)) || ((_req_url1 = req.url) === null || _req_url1 === void 0 ? void 0 : _req_url1.includes(".json")) && !((_req_url2 = req.url) === null || _req_url2 === void 0 ? void 0 : _req_url2.includes("hot-update"))) {
105
109
  var filepath = path.join(process.cwd(), "dist".concat(req.url));
106
110
  fs.statSync(filepath);
107
111
  res.setHeader("Access-Control-Allow-Origin", "*");
@@ -117,6 +121,15 @@ var moduleFederationPlugin = function() {
117
121
  }
118
122
  }
119
123
  ]
124
+ },
125
+ bundlerChain: function bundlerChain(chain, param2) {
126
+ var isServer = param2.isServer;
127
+ if (isDev && !isServer) {
128
+ chain.externals({
129
+ "@module-federation/node/utils": "NOT_USED_IN_BROWSER",
130
+ "@module-federation/dts-plugin/server": "NOT_USED_IN_BROWSER"
131
+ });
132
+ }
120
133
  }
121
134
  },
122
135
  source: {
@@ -160,7 +173,9 @@ var moduleFederationPlugin = function() {
160
173
  }
161
174
  plugins.unshift({
162
175
  name: SSR_PLUGIN_IDENTIFIER,
163
- options: JSON.stringify({})
176
+ options: JSON.stringify({
177
+ name: mfConfig.name
178
+ })
164
179
  });
165
180
  return {
166
181
  entrypoint,
@@ -0,0 +1,16 @@
1
+ import nodeFetch from "node-fetch";
2
+ var injectNodeFetchPlugin = function() {
3
+ return {
4
+ name: "inject-node-fetch-plugin",
5
+ beforeInit: function beforeInit(args) {
6
+ if (!globalThis.fetch) {
7
+ globalThis.fetch = nodeFetch;
8
+ }
9
+ return args;
10
+ }
11
+ };
12
+ };
13
+ var inject_node_fetch_default = injectNodeFetchPlugin;
14
+ export {
15
+ inject_node_fetch_default as default
16
+ };
@@ -3,6 +3,7 @@ import { _ as _object_spread } from "@swc/helpers/_/_object_spread";
3
3
  import { _ as _object_spread_props } from "@swc/helpers/_/_object_spread_props";
4
4
  import { _ as _to_consumable_array } from "@swc/helpers/_/_to_consumable_array";
5
5
  import { _ as _ts_generator } from "@swc/helpers/_/_ts_generator";
6
+ import { encodeName } from "@module-federation/sdk";
6
7
  import path from "path";
7
8
  import { bundle } from "@modern-js/node-bundle-require";
8
9
  var defaultPath = path.resolve(process.cwd(), "module-federation.config.ts");
@@ -45,21 +46,44 @@ var getMFConfig = function() {
45
46
  }();
46
47
  var patchMFConfig = function(mfConfig, isServer) {
47
48
  var runtimePlugins = _to_consumable_array(mfConfig.runtimePlugins || []);
48
- var runtimePluginPath = path.resolve(__dirname, "./mfRuntimePlugins/shared-strategy.js");
49
- if (!runtimePlugins.includes(runtimePluginPath)) {
50
- runtimePlugins.push(path.resolve(__dirname, "./mfRuntimePlugins/shared-strategy.js"));
49
+ var sharedStrategyRuntimePluginPath = path.resolve(__dirname, "./mfRuntimePlugins/shared-strategy.js");
50
+ if (!runtimePlugins.includes(sharedStrategyRuntimePluginPath)) {
51
+ runtimePlugins.push(sharedStrategyRuntimePluginPath);
51
52
  }
52
53
  if (isServer) {
53
- var nodeHmrPluginPath = require.resolve("@module-federation/node/record-dynamic-remote-entry-hash-plugin");
54
- if (!runtimePlugins.includes(nodeHmrPluginPath)) {
55
- runtimePlugins.push(nodeHmrPluginPath);
54
+ var isDev = process.env.NODE_ENV === "development";
55
+ if (isDev) {
56
+ var nodeHmrPluginPath = require.resolve("@module-federation/node/record-dynamic-remote-entry-hash-plugin");
57
+ if (!runtimePlugins.includes(nodeHmrPluginPath)) {
58
+ runtimePlugins.push(nodeHmrPluginPath);
59
+ }
60
+ }
61
+ var injectNodeFetchRuntimePluginPath = path.resolve(__dirname, "./mfRuntimePlugins/inject-node-fetch.js");
62
+ if (!runtimePlugins.includes(injectNodeFetchRuntimePluginPath)) {
63
+ runtimePlugins.push(injectNodeFetchRuntimePluginPath);
56
64
  }
57
65
  }
58
66
  if (typeof mfConfig.async === "undefined") {
59
67
  mfConfig.async = true;
60
68
  }
69
+ if (!isServer) {
70
+ return _object_spread_props(_object_spread({}, mfConfig), {
71
+ runtimePlugins,
72
+ dts: mfConfig.dts === false ? false : _object_spread({
73
+ generateTypes: false,
74
+ consumeTypes: false
75
+ }, typeof mfConfig.dts === "object" ? mfConfig.dts : {}),
76
+ dev: mfConfig.dev === false ? false : _object_spread({
77
+ disableHotTypesReload: true,
78
+ disableLiveReload: false,
79
+ injectWebClient: true
80
+ }, typeof mfConfig.dev === "object" ? mfConfig.dev : {})
81
+ });
82
+ }
61
83
  return _object_spread_props(_object_spread({}, mfConfig), {
62
- runtimePlugins
84
+ runtimePlugins,
85
+ dts: false,
86
+ dev: false
63
87
  });
64
88
  };
65
89
  function getTargetEnvConfig(mfConfig, isServer) {
@@ -102,7 +126,7 @@ function patchWebpackConfig(options) {
102
126
  var uniqueName = mfConfig.name || (output === null || output === void 0 ? void 0 : output.uniqueName);
103
127
  var chunkFileName = output === null || output === void 0 ? void 0 : output.chunkFilename;
104
128
  if (output && typeof chunkFileName === "string" && uniqueName && !chunkFileName.includes(uniqueName)) {
105
- var suffix = "-[chunkhash].js";
129
+ var suffix = "".concat(encodeName(uniqueName), "-[chunkhash].js");
106
130
  output.chunkFilename = chunkFileName.replace(".js", suffix);
107
131
  }
108
132
  }
@@ -1,54 +1,88 @@
1
1
  import { _ as _async_to_generator } from "@swc/helpers/_/_async_to_generator";
2
2
  import { _ as _ts_generator } from "@swc/helpers/_/_ts_generator";
3
- var mfPluginSSR = function() {
3
+ var mfPluginSSR = function(param) {
4
+ var name = param.name;
4
5
  return {
5
6
  name: "@module-federation/modern-js",
6
- // eslint-disable-next-line max-lines-per-function
7
7
  setup: function() {
8
+ var mfDevServer;
8
9
  return {
9
- init: (
10
- // eslint-disable-next-line max-lines-per-function
11
- function init(param, next) {
12
- var context = param.context;
13
- return _async_to_generator(function() {
14
- var nodeUtils, shouldUpdate;
15
- return _ts_generator(this, function(_state) {
16
- switch (_state.label) {
17
- case 0:
18
- if (typeof window !== "undefined") {
19
- return [
20
- 2,
21
- next({
22
- context
23
- })
24
- ];
25
- }
26
- return [
27
- 4,
28
- import("@module-federation/node/utils")
29
- ];
30
- case 1:
31
- nodeUtils = _state.sent();
32
- return [
33
- 4,
34
- nodeUtils.revalidate()
35
- ];
36
- case 2:
37
- shouldUpdate = _state.sent();
38
- if (shouldUpdate) {
39
- console.log("should HMR", shouldUpdate);
40
- }
10
+ init: function init(param2, next) {
11
+ var context = param2.context;
12
+ return _async_to_generator(function() {
13
+ var devServer, nodeUtils, shouldUpdate;
14
+ return _ts_generator(this, function(_state) {
15
+ switch (_state.label) {
16
+ case 0:
17
+ if (typeof window !== "undefined") {
41
18
  return [
42
19
  2,
43
20
  next({
44
21
  context
45
22
  })
46
23
  ];
47
- }
48
- });
49
- })();
50
- }
51
- )
24
+ }
25
+ return [
26
+ 4,
27
+ import("@module-federation/dts-plugin/server")
28
+ ];
29
+ case 1:
30
+ devServer = _state.sent();
31
+ if (name) {
32
+ mfDevServer = new devServer.ModuleFederationDevServer({
33
+ name: "".concat(name, "-server"),
34
+ remotes: [],
35
+ updateCallback: /* @__PURE__ */ _async_to_generator(function() {
36
+ return _ts_generator(this, function(_state2) {
37
+ return [
38
+ 2
39
+ ];
40
+ });
41
+ }),
42
+ remoteTypeTarPath: ""
43
+ });
44
+ }
45
+ return [
46
+ 4,
47
+ import("@module-federation/node/utils")
48
+ ];
49
+ case 2:
50
+ nodeUtils = _state.sent();
51
+ return [
52
+ 4,
53
+ nodeUtils.revalidate()
54
+ ];
55
+ case 3:
56
+ shouldUpdate = _state.sent();
57
+ if (!shouldUpdate)
58
+ return [
59
+ 3,
60
+ 5
61
+ ];
62
+ console.log("should RELOAD", shouldUpdate);
63
+ return [
64
+ 4,
65
+ nodeUtils.flushChunks()
66
+ ];
67
+ case 4:
68
+ _state.sent();
69
+ mfDevServer && mfDevServer.update({
70
+ updateKind: devServer.UpdateKind.RELOAD_PAGE,
71
+ updateMode: devServer.UpdateMode.POSITIVE,
72
+ clientName: name
73
+ });
74
+ _state.label = 5;
75
+ case 5:
76
+ return [
77
+ 2,
78
+ next({
79
+ context
80
+ })
81
+ ];
82
+ }
83
+ });
84
+ })();
85
+ }
52
86
  };
53
87
  }
54
88
  };
@@ -2,7 +2,7 @@ import path from "path";
2
2
  import { fs } from "@modern-js/utils";
3
3
  import { ModuleFederationPlugin as WebpackModuleFederationPlugin, AsyncBoundaryPlugin } from "@module-federation/enhanced";
4
4
  import { ModuleFederationPlugin as RspackModuleFederationPlugin } from "@module-federation/enhanced/rspack";
5
- import { StreamingTargetPlugin } from "@module-federation/node";
5
+ import { StreamingTargetPlugin, EntryChunkTrackerPlugin } from "@module-federation/node";
6
6
  import { getMFConfig, getTargetEnvConfig, patchWebpackConfig } from "./utils";
7
7
  import { updateStatsAndManifest } from "./manifest";
8
8
  import { MODERN_JS_SERVER_DIR } from "../constant";
@@ -16,15 +16,15 @@ const moduleFederationPlugin = (userConfig = {}) => ({
16
16
  const enableSSR = Boolean(modernjsConfig === null || modernjsConfig === void 0 ? void 0 : (_modernjsConfig_server = modernjsConfig.server) === null || _modernjsConfig_server === void 0 ? void 0 : _modernjsConfig_server.ssr);
17
17
  const mfConfig = await getMFConfig(userConfig);
18
18
  let outputDir = "";
19
- const bundlerType = useAppContext().bundlerType === "rspack" ? "rspack" : "webpack";
20
- const WebpackPluginConstructor = userConfig.webpackPluginImplementation || WebpackModuleFederationPlugin;
21
- const RspackPluginConstructor = userConfig.webpackPluginImplementation || RspackModuleFederationPlugin;
22
- const MFBundlerPlugin = bundlerType === "rspack" ? RspackPluginConstructor : WebpackPluginConstructor;
23
19
  let browserPlugin;
24
20
  let nodePlugin;
25
21
  return {
26
22
  config: () => {
27
23
  var _modernjsConfig_dev;
24
+ const bundlerType = useAppContext().bundlerType === "rspack" ? "rspack" : "webpack";
25
+ const WebpackPluginConstructor = userConfig.webpackPluginImplementation || WebpackModuleFederationPlugin;
26
+ const RspackPluginConstructor = userConfig.rspackPluginImplementation || RspackModuleFederationPlugin;
27
+ const MFBundlerPlugin = bundlerType === "rspack" ? RspackPluginConstructor : WebpackPluginConstructor;
28
28
  if (enableSSR) {
29
29
  process.env["MF_DISABLE_EMIT_STATS"] = "true";
30
30
  process.env["MF_SSR_PRJ"] = "true";
@@ -36,11 +36,15 @@ const moduleFederationPlugin = (userConfig = {}) => ({
36
36
  nodePlugin = new MFBundlerPlugin(envConfig);
37
37
  (_config_plugins = config.plugins) === null || _config_plugins === void 0 ? void 0 : _config_plugins.push(nodePlugin);
38
38
  (_config_plugins1 = config.plugins) === null || _config_plugins1 === void 0 ? void 0 : _config_plugins1.push(new StreamingTargetPlugin(envConfig));
39
+ if (isDev) {
40
+ var _config_plugins2;
41
+ (_config_plugins2 = config.plugins) === null || _config_plugins2 === void 0 ? void 0 : _config_plugins2.push(new EntryChunkTrackerPlugin());
42
+ }
39
43
  } else {
40
- var _config_output, _config_plugins2;
44
+ var _config_output, _config_plugins3;
41
45
  outputDir = ((_config_output = config.output) === null || _config_output === void 0 ? void 0 : _config_output.path) || path.resolve(process.cwd(), "dist");
42
46
  browserPlugin = new MFBundlerPlugin(envConfig);
43
- (_config_plugins2 = config.plugins) === null || _config_plugins2 === void 0 ? void 0 : _config_plugins2.push(browserPlugin);
47
+ (_config_plugins3 = config.plugins) === null || _config_plugins3 === void 0 ? void 0 : _config_plugins3.push(browserPlugin);
44
48
  }
45
49
  patchWebpackConfig({
46
50
  bundlerConfig: config,
@@ -80,9 +84,9 @@ const moduleFederationPlugin = (userConfig = {}) => ({
80
84
  return;
81
85
  }
82
86
  try {
83
- var _req_url, _req_url1;
87
+ var _req_url, _req_url1, _req_url2;
84
88
  const SERVER_PREFIX = `/${MODERN_JS_SERVER_DIR}`;
85
- if (((_req_url = req.url) === null || _req_url === void 0 ? void 0 : _req_url.startsWith(SERVER_PREFIX)) || ((_req_url1 = req.url) === null || _req_url1 === void 0 ? void 0 : _req_url1.includes(".json"))) {
89
+ if (((_req_url = req.url) === null || _req_url === void 0 ? void 0 : _req_url.startsWith(SERVER_PREFIX)) || ((_req_url1 = req.url) === null || _req_url1 === void 0 ? void 0 : _req_url1.includes(".json")) && !((_req_url2 = req.url) === null || _req_url2 === void 0 ? void 0 : _req_url2.includes("hot-update"))) {
86
90
  const filepath = path.join(process.cwd(), `dist${req.url}`);
87
91
  fs.statSync(filepath);
88
92
  res.setHeader("Access-Control-Allow-Origin", "*");
@@ -98,6 +102,14 @@ const moduleFederationPlugin = (userConfig = {}) => ({
98
102
  }
99
103
  }
100
104
  ]
105
+ },
106
+ bundlerChain(chain, { isServer }) {
107
+ if (isDev && !isServer) {
108
+ chain.externals({
109
+ "@module-federation/node/utils": "NOT_USED_IN_BROWSER",
110
+ "@module-federation/dts-plugin/server": "NOT_USED_IN_BROWSER"
111
+ });
112
+ }
101
113
  }
102
114
  },
103
115
  source: {
@@ -139,7 +151,9 @@ const moduleFederationPlugin = (userConfig = {}) => ({
139
151
  }
140
152
  plugins.unshift({
141
153
  name: SSR_PLUGIN_IDENTIFIER,
142
- options: JSON.stringify({})
154
+ options: JSON.stringify({
155
+ name: mfConfig.name
156
+ })
143
157
  });
144
158
  return {
145
159
  entrypoint,
@@ -0,0 +1,14 @@
1
+ import nodeFetch from "node-fetch";
2
+ const injectNodeFetchPlugin = () => ({
3
+ name: "inject-node-fetch-plugin",
4
+ beforeInit(args) {
5
+ if (!globalThis.fetch) {
6
+ globalThis.fetch = nodeFetch;
7
+ }
8
+ return args;
9
+ }
10
+ });
11
+ var inject_node_fetch_default = injectNodeFetchPlugin;
12
+ export {
13
+ inject_node_fetch_default as default
14
+ };
@@ -1,3 +1,4 @@
1
+ import { encodeName } from "@module-federation/sdk";
1
2
  import path from "path";
2
3
  import { bundle } from "@modern-js/node-bundle-require";
3
4
  const defaultPath = path.resolve(process.cwd(), "module-federation.config.ts");
@@ -15,22 +16,48 @@ const patchMFConfig = (mfConfig, isServer) => {
15
16
  const runtimePlugins = [
16
17
  ...mfConfig.runtimePlugins || []
17
18
  ];
18
- const runtimePluginPath = path.resolve(__dirname, "./mfRuntimePlugins/shared-strategy.js");
19
- if (!runtimePlugins.includes(runtimePluginPath)) {
20
- runtimePlugins.push(path.resolve(__dirname, "./mfRuntimePlugins/shared-strategy.js"));
19
+ const sharedStrategyRuntimePluginPath = path.resolve(__dirname, "./mfRuntimePlugins/shared-strategy.js");
20
+ if (!runtimePlugins.includes(sharedStrategyRuntimePluginPath)) {
21
+ runtimePlugins.push(sharedStrategyRuntimePluginPath);
21
22
  }
22
23
  if (isServer) {
23
- const nodeHmrPluginPath = require.resolve("@module-federation/node/record-dynamic-remote-entry-hash-plugin");
24
- if (!runtimePlugins.includes(nodeHmrPluginPath)) {
25
- runtimePlugins.push(nodeHmrPluginPath);
24
+ const isDev = process.env.NODE_ENV === "development";
25
+ if (isDev) {
26
+ const nodeHmrPluginPath = require.resolve("@module-federation/node/record-dynamic-remote-entry-hash-plugin");
27
+ if (!runtimePlugins.includes(nodeHmrPluginPath)) {
28
+ runtimePlugins.push(nodeHmrPluginPath);
29
+ }
30
+ }
31
+ const injectNodeFetchRuntimePluginPath = path.resolve(__dirname, "./mfRuntimePlugins/inject-node-fetch.js");
32
+ if (!runtimePlugins.includes(injectNodeFetchRuntimePluginPath)) {
33
+ runtimePlugins.push(injectNodeFetchRuntimePluginPath);
26
34
  }
27
35
  }
28
36
  if (typeof mfConfig.async === "undefined") {
29
37
  mfConfig.async = true;
30
38
  }
39
+ if (!isServer) {
40
+ return {
41
+ ...mfConfig,
42
+ runtimePlugins,
43
+ dts: mfConfig.dts === false ? false : {
44
+ generateTypes: false,
45
+ consumeTypes: false,
46
+ ...typeof mfConfig.dts === "object" ? mfConfig.dts : {}
47
+ },
48
+ dev: mfConfig.dev === false ? false : {
49
+ disableHotTypesReload: true,
50
+ disableLiveReload: false,
51
+ injectWebClient: true,
52
+ ...typeof mfConfig.dev === "object" ? mfConfig.dev : {}
53
+ }
54
+ };
55
+ }
31
56
  return {
32
57
  ...mfConfig,
33
- runtimePlugins
58
+ runtimePlugins,
59
+ dts: false,
60
+ dev: false
34
61
  };
35
62
  };
36
63
  function getTargetEnvConfig(mfConfig, isServer) {
@@ -76,7 +103,7 @@ function patchWebpackConfig(options) {
76
103
  const uniqueName = mfConfig.name || (output === null || output === void 0 ? void 0 : output.uniqueName);
77
104
  const chunkFileName = output === null || output === void 0 ? void 0 : output.chunkFilename;
78
105
  if (output && typeof chunkFileName === "string" && uniqueName && !chunkFileName.includes(uniqueName)) {
79
- const suffix = `-[chunkhash].js`;
106
+ const suffix = `${encodeName(uniqueName)}-[chunkhash].js`;
80
107
  output.chunkFilename = chunkFileName.replace(".js", suffix);
81
108
  }
82
109
  }
@@ -1,24 +1,41 @@
1
- const mfPluginSSR = () => ({
1
+ const mfPluginSSR = ({ name }) => ({
2
2
  name: "@module-federation/modern-js",
3
- // eslint-disable-next-line max-lines-per-function
4
- setup: () => ({
5
- // eslint-disable-next-line max-lines-per-function
6
- async init({ context }, next) {
7
- if (typeof window !== "undefined") {
3
+ setup: () => {
4
+ let mfDevServer;
5
+ return {
6
+ async init({ context }, next) {
7
+ if (typeof window !== "undefined") {
8
+ return next({
9
+ context
10
+ });
11
+ }
12
+ const devServer = await import("@module-federation/dts-plugin/server");
13
+ if (name) {
14
+ mfDevServer = new devServer.ModuleFederationDevServer({
15
+ name: `${name}-server`,
16
+ remotes: [],
17
+ updateCallback: async () => {
18
+ },
19
+ remoteTypeTarPath: ""
20
+ });
21
+ }
22
+ const nodeUtils = await import("@module-federation/node/utils");
23
+ const shouldUpdate = await nodeUtils.revalidate();
24
+ if (shouldUpdate) {
25
+ console.log("should RELOAD", shouldUpdate);
26
+ await nodeUtils.flushChunks();
27
+ mfDevServer && mfDevServer.update({
28
+ updateKind: devServer.UpdateKind.RELOAD_PAGE,
29
+ updateMode: devServer.UpdateMode.POSITIVE,
30
+ clientName: name
31
+ });
32
+ }
8
33
  return next({
9
34
  context
10
35
  });
11
36
  }
12
- const nodeUtils = await import("@module-federation/node/utils");
13
- const shouldUpdate = await nodeUtils.revalidate();
14
- if (shouldUpdate) {
15
- console.log("should HMR", shouldUpdate);
16
- }
17
- return next({
18
- context
19
- });
20
- }
21
- })
37
+ };
38
+ }
22
39
  });
23
40
  export {
24
41
  mfPluginSSR
@@ -0,0 +1,3 @@
1
+ import type { FederationRuntimePlugin } from '@module-federation/enhanced/runtime';
2
+ declare const injectNodeFetchPlugin: () => FederationRuntimePlugin;
3
+ export default injectNodeFetchPlugin;
@@ -5,6 +5,18 @@ export type ConfigType<T> = T extends 'webpack' ? webpack.Configuration : T exte
5
5
  export declare const getMFConfig: (userConfig: PluginOptions) => Promise<moduleFederationPlugin.ModuleFederationPluginOptions>;
6
6
  export declare const patchMFConfig: (mfConfig: moduleFederationPlugin.ModuleFederationPluginOptions, isServer: boolean) => {
7
7
  runtimePlugins: string[];
8
+ dts: boolean | {
9
+ generateTypes: boolean | moduleFederationPlugin.DtsRemoteOptions;
10
+ consumeTypes: boolean | moduleFederationPlugin.DtsHostOptions;
11
+ tsConfigPath?: string | undefined;
12
+ extraOptions?: Record<string, any> | undefined;
13
+ implementation?: string | undefined;
14
+ };
15
+ dev: boolean | {
16
+ disableLiveReload: boolean;
17
+ disableHotTypesReload: boolean;
18
+ injectWebClient: boolean;
19
+ };
8
20
  exposes?: moduleFederationPlugin.Exposes | undefined;
9
21
  filename?: string | undefined;
10
22
  library?: moduleFederationPlugin.LibraryOptions | undefined;
@@ -16,12 +28,22 @@ export declare const patchMFConfig: (mfConfig: moduleFederationPlugin.ModuleFede
16
28
  shared?: moduleFederationPlugin.Shared | undefined;
17
29
  implementation?: string | undefined;
18
30
  manifest?: boolean | moduleFederationPlugin.PluginManifestOptions | undefined;
19
- dev?: boolean | moduleFederationPlugin.PluginDevOptions | undefined;
20
- dts?: boolean | moduleFederationPlugin.PluginDtsOptions | undefined;
21
31
  async?: boolean | moduleFederationPlugin.AsyncBoundaryOptions | undefined;
22
32
  };
23
33
  export declare function getTargetEnvConfig(mfConfig: moduleFederationPlugin.ModuleFederationPluginOptions, isServer: boolean): {
24
34
  runtimePlugins: string[];
35
+ dts: boolean | {
36
+ generateTypes: boolean | moduleFederationPlugin.DtsRemoteOptions;
37
+ consumeTypes: boolean | moduleFederationPlugin.DtsHostOptions;
38
+ tsConfigPath?: string | undefined;
39
+ extraOptions?: Record<string, any> | undefined;
40
+ implementation?: string | undefined;
41
+ };
42
+ dev: boolean | {
43
+ disableLiveReload: boolean;
44
+ disableHotTypesReload: boolean;
45
+ injectWebClient: boolean;
46
+ };
25
47
  exposes?: moduleFederationPlugin.Exposes | undefined;
26
48
  filename?: string | undefined;
27
49
  library?: moduleFederationPlugin.LibraryOptions | undefined;
@@ -33,8 +55,6 @@ export declare function getTargetEnvConfig(mfConfig: moduleFederationPlugin.Modu
33
55
  shared?: moduleFederationPlugin.Shared | undefined;
34
56
  implementation?: string | undefined;
35
57
  manifest?: boolean | moduleFederationPlugin.PluginManifestOptions | undefined;
36
- dev?: boolean | moduleFederationPlugin.PluginDevOptions | undefined;
37
- dts?: boolean | moduleFederationPlugin.PluginDtsOptions | undefined;
38
58
  async?: boolean | moduleFederationPlugin.AsyncBoundaryOptions | undefined;
39
59
  };
40
60
  export declare function patchWebpackConfig<T>(options: {
@@ -1,2 +1,4 @@
1
1
  import type { Plugin } from '@modern-js/runtime';
2
- export declare const mfPluginSSR: () => Plugin;
2
+ export declare const mfPluginSSR: ({ name }: {
3
+ name?: string | undefined;
4
+ }) => Plugin;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@module-federation/modern-js",
3
- "version": "0.0.0-next-20240521123600",
3
+ "version": "0.0.0-next-20240523080317",
4
4
  "files": [
5
5
  "dist/",
6
6
  "types.d.ts",
@@ -45,9 +45,11 @@
45
45
  "@swc/helpers": "0.5.3",
46
46
  "@modern-js/utils": "^2.49.2",
47
47
  "@modern-js/node-bundle-require": "^2.49.2",
48
- "@module-federation/sdk": "0.0.0-next-20240521123600",
49
- "@module-federation/enhanced": "0.0.0-next-20240521123600",
50
- "@module-federation/node": "0.0.0-next-20240521123600"
48
+ "node-fetch": "~3.3.0",
49
+ "@module-federation/sdk": "0.0.0-next-20240523080317",
50
+ "@module-federation/enhanced": "0.0.0-next-20240523080317",
51
+ "@module-federation/node": "0.0.0-next-20240523080317",
52
+ "@module-federation/dts-plugin": "0.0.0-next-20240523080317"
51
53
  },
52
54
  "devDependencies": {
53
55
  "@modern-js/app-tools": "^2.49.2",
@@ -55,7 +57,7 @@
55
57
  "@modern-js/runtime": "^2.49.2",
56
58
  "@modern-js/module-tools": "^2.35.0",
57
59
  "@modern-js/tsconfig": "^2.35.0",
58
- "@module-federation/manifest": "0.0.0-next-20240521123600"
60
+ "@module-federation/manifest": "0.0.0-next-20240523080317"
59
61
  },
60
62
  "peerDependencies": {
61
63
  "react": ">=17",