@macrof/cli
Version:
React MicroFrontend compiler, Typescript, Webpack 5, ModuleFederation
149 lines (148 loc) • 8 kB
JavaScript
var __rest = (this && this.__rest) || function (s, e) {
var t = {};
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
t[p] = s[p];
if (s != null && typeof Object.getOwnPropertySymbols === "function")
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
t[p[i]] = s[p[i]];
}
return t;
};
require('dotenv').config();
import { container, DefinePlugin, BannerPlugin } from 'webpack';
import DynamicRemote from "../Plugins/DynamicRemotes";
import { MFConfig, Constants, Utils } from './index';
export default class {
constructor(currentPath, isShell) {
var _a;
this.mfConfig = MFConfig(currentPath);
this.isShell = isShell;
this.appId = Constants.APP_ID;
const _b = this.mfConfig, { main = Constants.DEFAULT_DEPENDENCY_CONFIG_MAIN, exports, dependencies, version, registry } = _b, otherConfig = __rest(_b, ["main", "exports", "dependencies", "version", "registry"]);
if (typeof registry !== 'undefined' && typeof this.mfConfig.registry !== 'string') {
throw new Error("typeof registry !== 'undefined' && typeof registry !== 'string'");
}
this.depURLs = {};
this.config = Object.assign(Object.assign({}, otherConfig), { filename: main, exposes: {} });
if (Array.isArray(exports)) {
const exposes = {};
Object.assign(this.config.exposes || {}, exports.reduce((acc, name) => Object.assign(acc, { [name]: name }), exposes));
}
else if (typeof this.mfConfig.exports !== 'undefined') {
throw new Error("!Array.isArray(exports) && typeof mfConfig.exports !== 'undefined'");
}
if (dependencies) {
this.collectDependencies(dependencies);
}
this.metaData = Object.assign(Object.assign({ dependencies: (_a = (typeof registry !== 'undefined' ? dependencies : this.depURLs)) !== null && _a !== void 0 ? _a : {} }, (registry ? { registry } : {})), (version ? { version } : {}));
}
collectDependencies(dependencies) {
if (typeof dependencies !== 'object') {
throw new Error("typeof dependencies !== 'object'");
}
else {
this.config.remotes = Object.entries(dependencies).reduce((previousValue, [dependency, dependencyConfig]) => {
var _a;
if (typeof this.mfConfig.registry !== 'undefined') {
if (typeof dependencyConfig !== 'string') {
throw new Error("typeof dependencyConfig !== 'string'");
}
return previousValue;
}
if (typeof dependencyConfig === 'string') {
this.depURLs[dependency] =
process.env.REACT_APP_DEV_AS_PROD !== "TRUE" &&
process.env.NODE_ENV === "development"
? Utils.getUrl(dependencyConfig)
: dependencyConfig;
return Object.assign(previousValue, { [dependency]: `${dependency}@${dependencyConfig}` });
}
else if (typeof dependencyConfig === 'object') {
let external = dependencyConfig.external;
if (!external) {
if (typeof dependencyConfig.host !== 'string') {
throw new Error("typeof dependencyConfig.host !== 'string'");
}
external = `${dependency}@${dependencyConfig.host}${/\/$/.test(dependencyConfig.host) ? '' : '/'}${(_a = dependencyConfig.main) !== null && _a !== void 0 ? _a : Constants.DEFAULT_DEPENDENCY_CONFIG_MAIN}`;
}
const remoteConfig = { external };
if (dependencyConfig.shareScope) {
remoteConfig.shareScope = dependencyConfig.shareScope;
}
if (Array.isArray(external)) {
this.depURLs[dependency] = external.map(Utils.getUrl);
}
else {
this.depURLs[dependency] = Utils.getUrl(external);
}
return Object.assign(previousValue, { [dependency]: remoteConfig });
}
else {
throw new Error("typeof dependencyConfig !=== 'string' && typeof dependencyConfig !=== 'object'");
}
}, {});
}
}
collectPlugins({ webpackConfig, context: { paths } }) {
var _a, _b, _c, _d;
let currentWebpackConfig = webpackConfig;
if (!currentWebpackConfig.output) {
currentWebpackConfig.output = {};
}
if (!currentWebpackConfig.optimization) {
currentWebpackConfig.optimization = {};
}
if (!currentWebpackConfig.plugins) {
currentWebpackConfig.plugins = [];
}
if (this.isShell) {
const htmlWebpackPlugin = currentWebpackConfig.plugins.find((plugin) => plugin.constructor.name === "HtmlWebpackPlugin");
htmlWebpackPlugin.userOptions = Object.assign(Object.assign({}, htmlWebpackPlugin.userOptions), { publicPath: paths.publicUrlOrPath, excludeChunks: [`MF${this.mfConfig.name}`] });
currentWebpackConfig.output.filename = 'static/js/bundle.[name].[id].[contenthash].js';
}
else {
currentWebpackConfig.output.publicPath = "auto";
currentWebpackConfig.output.chunkFilename = '[id].[contenthash].js';
currentWebpackConfig.optimization.chunkIds = "named";
}
currentWebpackConfig.plugins[5].options.filename = 'static/css/bundle.[name].[id].[contenthash].css';
currentWebpackConfig.optimization = {
runtimeChunk: false,
splitChunks: {
chunks() {
return false;
},
},
};
currentWebpackConfig.plugins = [
...currentWebpackConfig.plugins,
new BannerPlugin({
banner: `
window.${this.appId} = window.${this.appId} ? window.${this.appId} : {};
if (!window.${this.appId}['${this.mfConfig.name}']) window.${this.appId}['${this.mfConfig.name}'] = ${JSON.stringify(this.metaData)};`,
include: `${this.config.filename}`,
raw: true,
}),
new DefinePlugin(Object.assign({ 'process.env.APP_NAME': JSON.stringify(`${this.mfConfig.name}`), 'process.env.FPM_DEPS': JSON.stringify(`${JSON.stringify(this.metaData)}`), 'process.env.FPM_REG': JSON.stringify(this.mfConfig.registry) }, (typeof this.mfConfig.registry !== 'undefined' ? {
'process.env.FPM_MAP': JSON.stringify(`${JSON.stringify((_a = this.mfConfig.dependencies) !== null && _a !== void 0 ? _a : {})}`),
} : { 'process.env.DEP_URLS': JSON.stringify(`${JSON.stringify(this.depURLs)}`) }))),
new container.ModuleFederationPlugin(Object.assign({}, this.config)),
];
if (this.isShell) {
(_b = currentWebpackConfig.plugins) === null || _b === void 0 ? void 0 : _b.push(new DynamicRemote());
}
if (currentWebpackConfig.resolve) {
const scopePluginIndex = (_c = currentWebpackConfig.resolve.plugins) === null || _c === void 0 ? void 0 : _c.findIndex(({ constructor }) => constructor && constructor.name === 'ModuleScopePlugin');
scopePluginIndex && ((_d = currentWebpackConfig.resolve.plugins) === null || _d === void 0 ? void 0 : _d.splice(scopePluginIndex, 1));
}
return currentWebpackConfig;
}
plugins() {
return {
plugin: {
overrideWebpackConfig: this.collectPlugins.bind(this)
},
};
}
}