我尝试用香草js函数实现一个关于Module Federation的简单示例。
目录结构:
── packages
├── home
│ ├── index.html
│ ├── package.json
│ ├── src
│ │ └── index.js
│ └── webpack.config.js
└── nav
├── index.html
├── package.json
├── src
│ ├── Header.js
│ ├── index.js
└── webpack.config.js
预期的结果是home
应用程序渲染nav
中的Header
。
nav
的Webpack配置
const HtmlWebpackPlugin = require("html-webpack-plugin");
const ModuleFederationPlugin = require("webpack/lib/container/ModuleFederationPlugin");
const deps = require("./package.json").dependencies;
module.exports = {
mode: 'development',
entry: './src/index.js',
optimization: {
minimize: false
},
resolve: {
extensions: [".js"],
},
output: {
publicPath: "http://localhost:4001/",
},
plugins: [
new ModuleFederationPlugin({
name: "nav",
filename: "remoteEntry.js",
library: {type: 'var', name: 'nav'},
exposes: {
"./Header": "./src/Header"
},
shared: {
...deps
}
}),
new HtmlWebpackPlugin({
title: 'Module Federation Example',
}),
],
}
home
的Webpack配置
const HtmlWebpackPlugin = require("html-webpack-plugin");
const ModuleFederationPlugin = require('webpack/lib/container/ModuleFederationPlugin')
const deps = require("./package.json").dependencies;
module.exports = {
mode: 'development',
entry: './src/index.js',
optimization: {
minimize: false,
},
resolve: {
extensions: [".js"],
},
output: {
publicPath: "http://localhost:4000/",
},
plugins: [
new ModuleFederationPlugin({
name: "home",
filename: "remoteEntry.js",
remotes: {
nav: "nav@http://localhost:4001/remoteEntry.js"
},
shared: {
...deps
}
}),
new HtmlWebpackPlugin({
title: 'Module Federation Example',
}),
],
}
这是标题:
export default () => {
const node = document.createElement('div');
node.innerHTML = 'Header';
node.style = 'padding: 1em; box-sizing: border-box;display: flex;background: aquamarine;font-family:sans-serif;'
return node;
}
在home
中的index.js
文件是我导入Header
的地方:
import Header from 'nav/Header';
const Greetings = () => {
const node = document.createElement('h1');
node.innerHTML = 'App Shell';
return node;
}
document.addEventListener("DOMContentLoaded", () => {
document.body.appendChild(Greetings());
document.body.appendChild(Header());
});
在构建并服务于home
应用程序的url后,我检索到这个错误:
Uncaught TypeError: __webpack_modules__[moduleId] is not a function
at __webpack_require__ (main.js:66:41)
at eval (index.js:2:68)
at ./src/index.js (main.js:19:1)
at __webpack_require__ (main.js:66:41)
at main.js:217:37
at main.js:219:12
你可以在StackBlitz中复制。
我试图在ModuleFederationPlugin中添加一个库选项library: {type: 'var', name: 'nav'},
但我不明白为什么不工作。
我希望看到nav/Header
渲染在家庭应用程序。
我找到解决办法了。
出现错误是因为我将远程模块直接导入index.js
。远程模块是异步加载的,因此它还不能用于导入,因此出现错误。
最快的解决方案是将远程模块导入bootstrap.js
文件,以确保它们可用,并将其导入index.js
index.js
import("./bootstrap");
bootstrap.js
import Header from 'nav/Header';
// other logics ...