everything-dev
Version:
A consolidated product package for building Module Federation apps with oRPC APIs.
134 lines (132 loc) • 5.64 kB
JavaScript
const require_runtime = require('./_virtual/_rolldown/runtime.cjs');
const require_config = require('./config.cjs');
let node_fs = require("node:fs");
let node_path = require("node:path");
let node_net = require("node:net");
//#region src/app.ts
const DEFAULT_HOST_PORT = 3e3;
const DEFAULT_API_PORT = 3001;
const DEFAULT_AUTH_PORT = 3002;
const DEFAULT_UI_PORT = 3003;
const DEFAULT_PLUGIN_PORT_START = 3010;
function detectLocalPackages(bosConfig, runtimeConfig) {
const packages = [];
const configDir = require_config.getProjectRoot();
const uiLocalPath = runtimeConfig?.ui.localPath ?? require_config.resolveLocalDevelopmentPath(bosConfig?.app.ui.development, configDir);
if (uiLocalPath && (0, node_fs.existsSync)((0, node_path.join)(uiLocalPath, "package.json"))) packages.push("ui");
const apiLocalPath = runtimeConfig?.api.localPath ?? require_config.resolveLocalDevelopmentPath(bosConfig?.app.api.development, configDir);
if (apiLocalPath && (0, node_fs.existsSync)((0, node_path.join)(apiLocalPath, "package.json"))) packages.push("api");
const hostLocalPath = runtimeConfig?.host?.localPath ?? require_config.resolveLocalDevelopmentPath(bosConfig?.app.host.development, configDir);
if (hostLocalPath && (0, node_fs.existsSync)((0, node_path.join)(hostLocalPath, "package.json"))) packages.push("host");
else if ((0, node_fs.existsSync)((0, node_path.join)(configDir, "host", "package.json"))) packages.push("host");
for (const [pluginId, pluginConfig] of Object.entries(runtimeConfig?.plugins ?? {})) {
if (pluginConfig.localPath && (0, node_fs.existsSync)((0, node_path.join)(pluginConfig.localPath, "package.json"))) packages.push(`plugin:${pluginId}`);
if (pluginConfig.ui?.localPath && (0, node_fs.existsSync)((0, node_path.join)(pluginConfig.ui.localPath, "package.json"))) packages.push(`plugin-ui:${pluginId}`);
}
const authLocalPath = runtimeConfig?.auth?.localPath ?? require_config.resolveLocalDevelopmentPath(bosConfig?.app.auth?.development, configDir);
if (authLocalPath && (0, node_fs.existsSync)((0, node_path.join)(authLocalPath, "package.json"))) packages.push("auth");
return packages;
}
function buildRuntimeConfig(bosConfig, options) {
return require_config.buildRuntimeConfig(bosConfig, require_config.getProjectRoot(), options.env ?? "development", {
hostSource: options.hostSource,
uiSource: options.uiSource,
apiSource: options.apiSource,
authSource: options.authSource,
proxy: options.proxy,
plugins: options.plugins
});
}
function probeTcpOpen(port, timeoutMs = 250) {
return new Promise((resolve) => {
const socket = (0, node_net.createConnection)({
host: "127.0.0.1",
port
});
const timer = setTimeout(() => {
socket.destroy();
resolve(false);
}, timeoutMs);
socket.once("connect", () => {
clearTimeout(timer);
socket.destroy();
resolve(true);
});
socket.once("error", () => {
clearTimeout(timer);
resolve(false);
});
});
}
async function pickAvailablePort(preferred, usedPorts) {
let port = preferred;
while (usedPorts.has(port) || await probeTcpOpen(port)) port += 1;
usedPorts.add(port);
return port;
}
function withLocalRuntimeUrl(entry, port) {
const url = `http://localhost:${port}`;
return {
...entry,
url,
entry: `${url}/mf-manifest.json`,
port
};
}
async function prepareDevelopmentRuntimeConfig(runtimeConfig, options) {
const usedPorts = /* @__PURE__ */ new Set();
const hostPort = await pickAvailablePort(options?.hostPort ?? DEFAULT_HOST_PORT, usedPorts);
const next = {
...runtimeConfig,
host: {
...runtimeConfig.host,
url: `http://localhost:${hostPort}`,
port: hostPort
},
ui: { ...runtimeConfig.ui },
api: { ...runtimeConfig.api },
auth: runtimeConfig.auth ? { ...runtimeConfig.auth } : void 0,
plugins: runtimeConfig.plugins ? { ...runtimeConfig.plugins } : void 0
};
if (next.api.source === "local" && next.api.localPath) {
const apiPort = await pickAvailablePort(next.api.port ?? DEFAULT_API_PORT, usedPorts);
next.api = withLocalRuntimeUrl(next.api, apiPort);
}
if (next.auth?.source === "local" && next.auth.localPath) {
const authPort = await pickAvailablePort(next.auth.port ?? DEFAULT_AUTH_PORT, usedPorts);
next.auth = withLocalRuntimeUrl(next.auth, authPort);
}
if (next.ui.source === "local" && next.ui.localPath) {
const uiPort = await pickAvailablePort(next.ui.port ?? DEFAULT_UI_PORT, usedPorts);
next.ui = withLocalRuntimeUrl(next.ui, uiPort);
if (options?.ssr) {
const ssrPort = await pickAvailablePort(uiPort + 1, usedPorts);
next.ui.ssrUrl = `http://localhost:${ssrPort}`;
} else next.ui.ssrUrl = void 0;
}
if (next.plugins) {
const entries = Object.entries(next.plugins).sort(([a], [b]) => a.localeCompare(b));
let pluginBasePort = DEFAULT_PLUGIN_PORT_START;
for (const [pluginId, plugin] of entries) {
if (plugin.source === "local" && plugin.localPath) {
const pluginPort = await pickAvailablePort(plugin.port ?? pluginBasePort, usedPorts);
next.plugins[pluginId] = withLocalRuntimeUrl(plugin, pluginPort);
pluginBasePort = pluginPort + 1;
}
if (plugin.ui?.source === "local" && plugin.ui.localPath) {
const uiPort = await pickAvailablePort(plugin.ui.port ?? pluginBasePort, usedPorts);
next.plugins[pluginId] = {
...next.plugins[pluginId],
ui: withLocalRuntimeUrl(plugin.ui, uiPort)
};
pluginBasePort = uiPort + 1;
}
}
}
return next;
}
//#endregion
exports.buildRuntimeConfig = buildRuntimeConfig;
exports.detectLocalPackages = detectLocalPackages;
exports.prepareDevelopmentRuntimeConfig = prepareDevelopmentRuntimeConfig;
//# sourceMappingURL=app.cjs.map