@module-federation/enhanced
Version:
This package provides enhanced features for module federation.
217 lines (214 loc) • 8.82 kB
JavaScript
;
Object.defineProperties(exports, { __esModule: { value: true }, [Symbol.toStringTag]: { value: 'Module' } });
const require_runtime = require('../../_virtual/_rolldown/runtime.js');
const require_lib_Constants = require('../Constants.js');
const require_lib_container_ContainerExposedDependency = require('./ContainerExposedDependency.js');
const require_lib_container_runtime_utils = require('./runtime/utils.js');
let _module_federation_sdk = require("@module-federation/sdk");
let _module_federation_sdk_normalize_webpack_path = require("@module-federation/sdk/normalize-webpack-path");
let _module_federation_error_codes = require("@module-federation/error-codes");
let _module_federation_error_codes_node = require("@module-federation/error-codes/node");
//#region src/lib/container/ContainerEntryModule.ts
const makeSerializable = require((0, _module_federation_sdk_normalize_webpack_path.normalizeWebpackPath)("webpack/lib/util/makeSerializable"));
const { sources: webpackSources, AsyncDependenciesBlock, Template, Module, RuntimeGlobals } = require((0, _module_federation_sdk_normalize_webpack_path.normalizeWebpackPath)("webpack"));
const StaticExportsDependency = require((0, _module_federation_sdk_normalize_webpack_path.normalizeWebpackPath)("webpack/lib/dependencies/StaticExportsDependency"));
const EntryDependency = require((0, _module_federation_sdk_normalize_webpack_path.normalizeWebpackPath)("webpack/lib/dependencies/EntryDependency"));
const SOURCE_TYPES = new Set(["javascript"]);
var ContainerEntryModule = class ContainerEntryModule extends Module {
/**
* @param {string} name container entry name
* @param {[string, ExposeOptions][]} exposes list of exposed modules
* @param {string|string[]} shareScope name of the share scope
* @param {string} injectRuntimeEntry the path of injectRuntime file.
*/
constructor(name, exposes, shareScope, injectRuntimeEntry) {
super(require_lib_Constants.JAVASCRIPT_MODULE_TYPE_DYNAMIC, null);
this._name = name;
this._exposes = exposes;
this._shareScope = shareScope;
this._injectRuntimeEntry = injectRuntimeEntry;
}
/**
* @param {ObjectDeserializerContext} context context
* @returns {ContainerEntryModule} deserialized container entry module
*/
static deserialize(context) {
const { read } = context;
const obj = new ContainerEntryModule(read(), read(), read(), read());
obj.deserialize(context);
return obj;
}
/**
* @returns {Set<string>} types available (do not mutate)
*/
getSourceTypes() {
return SOURCE_TYPES;
}
/**
* @returns {string} a unique identifier of the module
*/
identifier() {
return `container entry (${Array.isArray(this._shareScope) ? this._shareScope.join("|") : this._shareScope}) ${JSON.stringify(this._exposes)} ${this._injectRuntimeEntry}`;
}
/**
* @param {RequestShortener} requestShortener the request shortener
* @returns {string} a user readable identifier of the module
*/
readableIdentifier(requestShortener) {
return "container entry";
}
/**
* @param {LibIdentOptions} options options
* @returns {string | null} an identifier for library inclusion
*/
libIdent(options) {
return `${this.layer ? `(${this.layer})/` : ""}webpack/container/entry/${this._name}`;
}
/**
* @param {NeedBuildContext} context context info
* @param {function((WebpackError | null)=, boolean=): void} callback callback function, returns true, if the module needs a rebuild
* @returns {void}
*/
needBuild(context, callback) {
callback(null, !this.buildMeta);
}
/**
* @param {WebpackOptions} options webpack options
* @param {Compilation} compilation the compilation
* @param {ResolverWithOptions} resolver the resolver
* @param {InputFileSystem} fs the file system
* @param {function(WebpackError): void} callback callback function
* @returns {void}
*/
build(options, compilation, resolver, fs, callback) {
this.buildMeta = {};
this.buildInfo = {
strict: true,
topLevelDeclarations: new Set([
"moduleMap",
"get",
"init"
])
};
this.buildMeta.exportsType = "namespace";
this.clearDependenciesAndBlocks();
for (const [name, options] of this._exposes) {
const block = new AsyncDependenciesBlock({ name: options.name }, { name }, options.import[options.import.length - 1]);
let idx = 0;
for (const request of options.import) {
const dep = new require_lib_container_ContainerExposedDependency.default(name, request);
dep.loc = {
name,
index: idx++
};
block.addDependency(dep);
}
this.addBlock(block);
}
this.addDependency(new StaticExportsDependency(["get", "init"], false));
this.addDependency(new EntryDependency(this._injectRuntimeEntry));
callback();
}
/**
* @param {CodeGenerationContext} context context for code generation
* @returns {CodeGenerationResult} result
*/
codeGeneration({ moduleGraph, chunkGraph, runtimeTemplate }) {
const sources = /* @__PURE__ */ new Map();
const runtimeRequirements = new Set([
RuntimeGlobals.definePropertyGetters,
RuntimeGlobals.hasOwnProperty,
RuntimeGlobals.exports
]);
const getters = [];
for (const block of this.blocks) {
const { dependencies } = block;
const modules = dependencies.map((dependency) => {
const dep = dependency;
return {
name: dep.exposedName,
module: moduleGraph.getModule(dep),
request: dep.userRequest
};
});
let str;
if (modules.some((m) => !m.module)) {
(0, _module_federation_error_codes_node.logAndReport)(_module_federation_error_codes.BUILD_001, _module_federation_error_codes.buildDescMap, {
exposeModules: modules.filter((m) => !m.module),
FEDERATION_WEBPACK_PATH: process.env["FEDERATION_WEBPACK_PATH"]
}, _module_federation_sdk.infrastructureLogger.error.bind(_module_federation_sdk.infrastructureLogger), void 0, {
bundler: { name: "webpack" },
mfConfig: {
name: this._name,
exposes: Object.fromEntries(this._exposes.map(([key, opts]) => [key, opts.import[opts.import.length - 1]]))
}
});
process.exit(1);
} else str = `return ${runtimeTemplate.blockPromise({
block,
message: "",
chunkGraph,
runtimeRequirements
})}.then(${runtimeTemplate.returningFunction(runtimeTemplate.returningFunction(`(${modules.map(({ module, request }) => runtimeTemplate.moduleRaw({
module,
chunkGraph,
request,
weak: false,
runtimeRequirements
})).join(", ")})`))});`;
getters.push(`${JSON.stringify(modules[0].name)}: ${runtimeTemplate.basicFunction("", str)}`);
}
const federationGlobal = require_lib_container_runtime_utils.getFederationGlobalScope(RuntimeGlobals || {});
const source = Template.asString([
`var moduleMap = {`,
Template.indent(getters.join(",\n")),
"};",
`var get = ${runtimeTemplate.basicFunction("module, getScope", [
`${RuntimeGlobals.currentRemoteGetScope} = getScope;`,
"getScope = (",
Template.indent([`${RuntimeGlobals.hasOwnProperty}(moduleMap, module)`, Template.indent(["? moduleMap[module]()", `: Promise.resolve().then(${runtimeTemplate.basicFunction("", "throw new Error('Module \"' + module + '\" does not exist in container.');")})`])]),
");",
`${RuntimeGlobals.currentRemoteGetScope} = undefined;`,
"return getScope;"
])};`,
`var init = ${runtimeTemplate.basicFunction("shareScope, initScope, remoteEntryInitOptions", [`return ${federationGlobal}.bundlerRuntime.initContainerEntry({${Template.indent([
`webpackRequire: ${RuntimeGlobals.require},`,
`shareScope: shareScope,`,
`initScope: initScope,`,
`remoteEntryInitOptions: remoteEntryInitOptions,`,
`shareScopeKey: ${JSON.stringify(this._shareScope)}`
])}`, "})"])};`,
"// This exports getters to disallow modifications",
`${RuntimeGlobals.definePropertyGetters}(exports, {`,
Template.indent([`get: ${runtimeTemplate.returningFunction("get")},`, `init: ${runtimeTemplate.returningFunction("init")}`]),
"});"
]);
sources.set("javascript", this.useSourceMap || this.useSimpleSourceMap ? new webpackSources.OriginalSource(source, "webpack/container-entry") : new webpackSources.RawSource(source));
return {
sources,
runtimeRequirements
};
}
/**
* @param {string=} type the source type for which the size should be estimated
* @returns {number} the estimated size of the module (must be non-zero)
*/
size(type) {
return 42;
}
/**
* @param {ObjectSerializerContext} context context
*/
serialize(context) {
const { write } = context;
write(this._name);
write(this._exposes);
write(this._shareScope);
write(this._injectRuntimeEntry);
super.serialize(context);
}
};
makeSerializable(ContainerEntryModule, "enhanced/lib/container/ContainerEntryModule");
//#endregion
exports.default = ContainerEntryModule;
//# sourceMappingURL=ContainerEntryModule.js.map