@bleedingdev/modern-js-app-tools-extensions 3.9.0-ultramodern.2 → 3.9.0-ultramodern.21
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.
- package/dist/cjs/backend-federation-build/codegen.js +267 -0
- package/dist/cjs/backend-federation-build/config.js +239 -0
- package/dist/cjs/backend-federation-build/emit.js +154 -0
- package/dist/cjs/backend-federation-build/index.js +53 -0
- package/dist/cjs/build-config/build-environment.js +129 -0
- package/dist/cjs/build-config/precompress/plugin.js +124 -0
- package/dist/cjs/build-config/precompress/types.js +18 -0
- package/dist/cjs/build-config/public.js +43 -0
- package/dist/cjs/build-config/remote-address.js +58 -0
- package/dist/cjs/cloudflare/artifacts.js +8 -19
- package/dist/cjs/cloudflare/constants.js +1 -1
- package/dist/cjs/cloudflare/delivery-unit.js +23 -42
- package/dist/cjs/cloudflare/index.js +10 -2
- package/dist/cjs/cloudflare/worker-manifest.js +13 -4
- package/dist/cjs/cloudflare/wrangler-config.js +35 -7
- package/dist/cjs/cloudflare-builder.js +252 -75
- package/dist/cjs/cloudflare-output-contract.js +69 -3
- package/dist/cjs/cloudflare-output-verifier/identity.js +29 -27
- package/dist/cjs/cloudflare-output-verifier/index.js +10 -0
- package/dist/cjs/cloudflare-output-verifier/manifest.js +46 -0
- package/dist/cjs/cloudflare-output-verifier/mutation-policy.js +7 -1
- package/dist/cjs/cloudflare-output-verifier/worker-bundles.js +14 -6
- package/dist/cjs/config.js +34 -1
- package/dist/cjs/deploy-output/npmAliases.js +251 -0
- package/dist/cjs/deploy-output/plugin.js +97 -0
- package/dist/cjs/deploy-output/public-assets.js +146 -0
- package/dist/cjs/deploy-output/target.js +104 -0
- package/dist/cjs/deploy-output/trace-files.js +90 -0
- package/dist/cjs/native-type-checker.js +193 -0
- package/dist/cjs/policy-defaults.js +101 -0
- package/dist/cjs/release-envelope/framework-output.js +153 -79
- package/dist/cjs/release-envelope/index.js +10 -4
- package/dist/cjs/release-envelope/plugin.js +18 -13
- package/dist/cjs/release-identity.js +5 -6
- package/dist/cjs/runtime-package-resolution.js +118 -0
- package/dist/cjs/templates/cloudflare-entry.001-bootstrap-security.mjs +0 -3
- package/dist/cjs/templates/cloudflare-entry.002-assets-routes.mjs +1 -1
- package/dist/cjs/templates/cloudflare-entry.004-rendering-css.mjs +5 -1
- package/dist/cjs/templates/cloudflare-entry.005-worker-dispatch.mjs +98 -10
- package/dist/cjs/templates/cloudflare-entry.006-fetch-handler.mjs +9 -2
- package/dist/cjs/templates/cloudflare-worker-route-data.mjs +1069 -0
- package/dist/esm/backend-federation-build/codegen.mjs +216 -0
- package/dist/esm/backend-federation-build/config.mjs +163 -0
- package/dist/esm/backend-federation-build/emit.mjs +103 -0
- package/dist/esm/backend-federation-build/index.mjs +1 -0
- package/dist/esm/build-config/build-environment.mjs +88 -0
- package/dist/esm/build-config/precompress/plugin.mjs +76 -0
- package/dist/esm/build-config/precompress/types.mjs +0 -0
- package/dist/esm/build-config/public.mjs +1 -0
- package/dist/esm/build-config/remote-address.mjs +20 -0
- package/dist/esm/cloudflare/artifacts.mjs +8 -19
- package/dist/esm/cloudflare/constants.mjs +1 -1
- package/dist/esm/cloudflare/delivery-unit.mjs +17 -36
- package/dist/esm/cloudflare/index.mjs +10 -2
- package/dist/esm/cloudflare/worker-manifest.mjs +13 -4
- package/dist/esm/cloudflare/wrangler-config.mjs +35 -7
- package/dist/esm/cloudflare-builder.mjs +246 -75
- package/dist/esm/cloudflare-output-contract.mjs +59 -2
- package/dist/esm/cloudflare-output-verifier/identity.mjs +27 -25
- package/dist/esm/cloudflare-output-verifier/index.mjs +10 -0
- package/dist/esm/cloudflare-output-verifier/manifest.mjs +46 -0
- package/dist/esm/cloudflare-output-verifier/mutation-policy.mjs +7 -1
- package/dist/esm/cloudflare-output-verifier/worker-bundles.mjs +15 -7
- package/dist/esm/config.mjs +3 -0
- package/dist/esm/deploy-output/npmAliases.mjs +199 -0
- package/dist/esm/deploy-output/plugin.mjs +46 -0
- package/dist/esm/deploy-output/public-assets.mjs +82 -0
- package/dist/esm/deploy-output/target.mjs +57 -0
- package/dist/esm/deploy-output/trace-files.mjs +38 -0
- package/dist/esm/native-type-checker.mjs +142 -0
- package/dist/esm/policy-defaults.mjs +45 -0
- package/dist/esm/release-envelope/framework-output.mjs +130 -56
- package/dist/esm/release-envelope/index.mjs +10 -4
- package/dist/esm/release-envelope/plugin.mjs +18 -13
- package/dist/esm/release-identity.mjs +5 -6
- package/dist/esm/runtime-package-resolution.mjs +60 -0
- package/dist/esm/templates/cloudflare-entry.001-bootstrap-security.mjs +0 -3
- package/dist/esm/templates/cloudflare-entry.002-assets-routes.mjs +1 -1
- package/dist/esm/templates/cloudflare-entry.004-rendering-css.mjs +5 -1
- package/dist/esm/templates/cloudflare-entry.005-worker-dispatch.mjs +98 -10
- package/dist/esm/templates/cloudflare-entry.006-fetch-handler.mjs +9 -2
- package/dist/esm/templates/cloudflare-worker-route-data.mjs +1069 -0
- package/dist/esm-node/backend-federation-build/codegen.mjs +217 -0
- package/dist/esm-node/backend-federation-build/config.mjs +164 -0
- package/dist/esm-node/backend-federation-build/emit.mjs +104 -0
- package/dist/esm-node/backend-federation-build/index.mjs +2 -0
- package/dist/esm-node/build-config/build-environment.mjs +89 -0
- package/dist/esm-node/build-config/precompress/plugin.mjs +77 -0
- package/dist/esm-node/build-config/precompress/types.mjs +1 -0
- package/dist/esm-node/build-config/public.mjs +2 -0
- package/dist/esm-node/build-config/remote-address.mjs +21 -0
- package/dist/esm-node/cloudflare/artifacts.mjs +8 -19
- package/dist/esm-node/cloudflare/constants.mjs +1 -1
- package/dist/esm-node/cloudflare/delivery-unit.mjs +17 -36
- package/dist/esm-node/cloudflare/index.mjs +10 -2
- package/dist/esm-node/cloudflare/worker-manifest.mjs +13 -4
- package/dist/esm-node/cloudflare/wrangler-config.mjs +35 -7
- package/dist/esm-node/cloudflare-builder.mjs +246 -75
- package/dist/esm-node/cloudflare-output-contract.mjs +59 -2
- package/dist/esm-node/cloudflare-output-verifier/identity.mjs +27 -25
- package/dist/esm-node/cloudflare-output-verifier/index.mjs +10 -0
- package/dist/esm-node/cloudflare-output-verifier/manifest.mjs +46 -0
- package/dist/esm-node/cloudflare-output-verifier/mutation-policy.mjs +7 -1
- package/dist/esm-node/cloudflare-output-verifier/worker-bundles.mjs +15 -7
- package/dist/esm-node/config.mjs +3 -0
- package/dist/esm-node/deploy-output/npmAliases.mjs +200 -0
- package/dist/esm-node/deploy-output/plugin.mjs +49 -0
- package/dist/esm-node/deploy-output/public-assets.mjs +83 -0
- package/dist/esm-node/deploy-output/target.mjs +58 -0
- package/dist/esm-node/deploy-output/trace-files.mjs +39 -0
- package/dist/esm-node/native-type-checker.mjs +143 -0
- package/dist/esm-node/policy-defaults.mjs +46 -0
- package/dist/esm-node/release-envelope/framework-output.mjs +130 -56
- package/dist/esm-node/release-envelope/index.mjs +10 -4
- package/dist/esm-node/release-envelope/plugin.mjs +18 -13
- package/dist/esm-node/release-identity.mjs +5 -6
- package/dist/esm-node/runtime-package-resolution.mjs +61 -0
- package/dist/esm-node/templates/cloudflare-entry.001-bootstrap-security.mjs +0 -3
- package/dist/esm-node/templates/cloudflare-entry.002-assets-routes.mjs +1 -1
- package/dist/esm-node/templates/cloudflare-entry.004-rendering-css.mjs +5 -1
- package/dist/esm-node/templates/cloudflare-entry.005-worker-dispatch.mjs +98 -10
- package/dist/esm-node/templates/cloudflare-entry.006-fetch-handler.mjs +9 -2
- package/dist/esm-node/templates/cloudflare-worker-route-data.mjs +1069 -0
- package/dist/types/backend-federation-build/codegen.d.ts +116 -0
- package/dist/types/backend-federation-build/config.d.ts +121 -0
- package/dist/types/backend-federation-build/emit.d.ts +21 -0
- package/dist/types/backend-federation-build/index.d.ts +2 -0
- package/dist/types/build-config/build-environment.d.ts +14 -0
- package/dist/types/build-config/precompress/plugin.d.ts +4 -0
- package/dist/types/build-config/precompress/types.d.ts +19 -0
- package/dist/types/build-config/public.d.ts +2 -0
- package/dist/types/build-config/remote-address.d.ts +3 -0
- package/dist/types/cloudflare/artifacts.d.ts +7 -6
- package/dist/types/cloudflare/constants.d.ts +1 -1
- package/dist/types/cloudflare/delivery-unit.d.ts +3 -3
- package/dist/types/cloudflare/worker-manifest.d.ts +2 -2
- package/dist/types/cloudflare/wrangler-config.d.ts +6 -0
- package/dist/types/cloudflare-builder.d.ts +49 -9
- package/dist/types/cloudflare-output-contract.d.ts +4 -1
- package/dist/types/cloudflare-output-verifier/identity.d.ts +1 -1
- package/dist/types/cloudflare-output-verifier/worker-bundles.d.ts +2 -2
- package/dist/types/config.d.ts +29 -1
- package/dist/types/deploy-output/npmAliases.d.ts +14 -0
- package/dist/types/deploy-output/plugin.d.ts +35 -0
- package/dist/types/deploy-output/public-assets.d.ts +51 -0
- package/dist/types/deploy-output/target.d.ts +29 -0
- package/dist/types/deploy-output/trace-files.d.ts +17 -0
- package/dist/types/native-type-checker.d.ts +15 -0
- package/dist/types/policy-defaults.d.ts +46 -0
- package/dist/types/precompress/LICENSE +20 -0
- package/dist/types/precompress/index.d.ts +76 -0
- package/dist/types/release-envelope/framework-output.d.ts +8 -3
- package/dist/types/release-envelope/plugin.d.ts +7 -7
- package/dist/types/runtime-package-resolution.d.ts +28 -0
- package/dist/types/templates/cloudflare-worker-route-data.d.mts +14 -0
- package/package.json +97 -15
- package/src/backend-federation-build/codegen.ts +254 -0
- package/src/backend-federation-build/config.ts +492 -0
- package/src/backend-federation-build/emit.ts +213 -0
- package/src/backend-federation-build/index.ts +2 -0
- package/src/build-config/build-environment.ts +160 -0
- package/src/build-config/precompress/plugin.ts +140 -0
- package/src/build-config/precompress/types.ts +26 -0
- package/src/build-config/public.ts +5 -0
- package/src/build-config/remote-address.ts +33 -0
- package/src/cloudflare/artifacts.ts +22 -43
- package/src/cloudflare/constants.ts +1 -1
- package/src/cloudflare/delivery-unit.ts +42 -53
- package/src/cloudflare/index.ts +24 -11
- package/src/cloudflare/worker-manifest.ts +20 -3
- package/src/cloudflare/wrangler-config.ts +86 -10
- package/src/cloudflare-builder.ts +475 -151
- package/src/cloudflare-output-contract.ts +70 -0
- package/src/cloudflare-output-verifier/identity.ts +5 -1
- package/src/cloudflare-output-verifier/index.ts +20 -0
- package/src/cloudflare-output-verifier/manifest.ts +77 -0
- package/src/cloudflare-output-verifier/mutation-policy.ts +11 -1
- package/src/cloudflare-output-verifier/worker-bundles.ts +32 -14
- package/src/config.ts +34 -6
- package/src/deploy-output/npmAliases.ts +382 -0
- package/src/deploy-output/plugin.ts +86 -0
- package/src/deploy-output/public-assets.ts +224 -0
- package/src/deploy-output/target.ts +106 -0
- package/src/deploy-output/trace-files.ts +67 -0
- package/src/native-type-checker.ts +183 -0
- package/src/policy-defaults.ts +127 -0
- package/src/release-envelope/framework-output.ts +346 -94
- package/src/release-envelope/index.ts +26 -5
- package/src/release-envelope/plugin.ts +43 -40
- package/src/release-identity.ts +13 -2
- package/src/runtime-package-resolution.ts +115 -0
- package/src/templates/cloudflare-entry.001-bootstrap-security.mjs +0 -3
- package/src/templates/cloudflare-entry.002-assets-routes.mjs +1 -1
- package/src/templates/cloudflare-entry.004-rendering-css.mjs +5 -1
- package/src/templates/cloudflare-entry.005-worker-dispatch.mjs +98 -10
- package/src/templates/cloudflare-entry.006-fetch-handler.mjs +9 -2
- package/src/templates/cloudflare-worker-route-data.mjs +1069 -0
- package/dist/cjs/templates/cloudflare-worker-fs-promises.mjs +0 -11
- package/dist/cjs/templates/cloudflare-worker-loadable-server.mjs +0 -281
- package/dist/cjs/templates/cloudflare-worker-mf-ssr-runtime-plugin.mjs +0 -14
- package/dist/cjs/templates/cloudflare-worker-path.mjs +0 -98
- package/dist/esm/templates/cloudflare-worker-fs-promises.mjs +0 -11
- package/dist/esm/templates/cloudflare-worker-loadable-server.mjs +0 -281
- package/dist/esm/templates/cloudflare-worker-mf-ssr-runtime-plugin.mjs +0 -14
- package/dist/esm/templates/cloudflare-worker-path.mjs +0 -98
- package/dist/esm-node/templates/cloudflare-worker-fs-promises.mjs +0 -11
- package/dist/esm-node/templates/cloudflare-worker-loadable-server.mjs +0 -281
- package/dist/esm-node/templates/cloudflare-worker-mf-ssr-runtime-plugin.mjs +0 -14
- package/dist/esm-node/templates/cloudflare-worker-path.mjs +0 -98
- package/dist/types/templates/cloudflare-worker-fs-promises.d.mts +0 -5
- package/dist/types/templates/cloudflare-worker-loadable-server.d.mts +0 -48
- package/dist/types/templates/cloudflare-worker-mf-ssr-runtime-plugin.d.mts +0 -13
- package/dist/types/templates/cloudflare-worker-path.d.mts +0 -21
- package/src/templates/cloudflare-worker-fs-promises.mjs +0 -11
- package/src/templates/cloudflare-worker-loadable-server.mjs +0 -281
- package/src/templates/cloudflare-worker-mf-ssr-runtime-plugin.mjs +0 -14
- package/src/templates/cloudflare-worker-path.mjs +0 -98
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
const __rslib_import_meta_url__ = /*#__PURE__*/ function() {
|
|
3
|
+
return "u" < typeof document ? new (require('url'.replace('', ''))).URL('file:' + __filename).href : document.currentScript && document.currentScript.src || new URL('main.js', document.baseURI).href;
|
|
4
|
+
}();
|
|
5
|
+
var __webpack_require__ = {};
|
|
6
|
+
(()=>{
|
|
7
|
+
__webpack_require__.d = (exports1, getters, values)=>{
|
|
8
|
+
var define = (defs, kind)=>{
|
|
9
|
+
for(var key in defs)if (__webpack_require__.o(defs, key) && !__webpack_require__.o(exports1, key)) Object.defineProperty(exports1, key, {
|
|
10
|
+
enumerable: true,
|
|
11
|
+
[kind]: defs[key]
|
|
12
|
+
});
|
|
13
|
+
};
|
|
14
|
+
define(getters, "get");
|
|
15
|
+
define(values, "value");
|
|
16
|
+
};
|
|
17
|
+
})();
|
|
18
|
+
(()=>{
|
|
19
|
+
__webpack_require__.o = (obj, prop)=>Object.prototype.hasOwnProperty.call(obj, prop);
|
|
20
|
+
})();
|
|
21
|
+
(()=>{
|
|
22
|
+
__webpack_require__.r = (exports1)=>{
|
|
23
|
+
if ("u" > typeof Symbol && Symbol.toStringTag) Object.defineProperty(exports1, Symbol.toStringTag, {
|
|
24
|
+
value: 'Module'
|
|
25
|
+
});
|
|
26
|
+
Object.defineProperty(exports1, '__esModule', {
|
|
27
|
+
value: true
|
|
28
|
+
});
|
|
29
|
+
};
|
|
30
|
+
})();
|
|
31
|
+
var __webpack_exports__ = {};
|
|
32
|
+
__webpack_require__.r(__webpack_exports__);
|
|
33
|
+
__webpack_require__.d(__webpack_exports__, {
|
|
34
|
+
POLICY_DEFAULTS_PLUGIN_NAME: ()=>POLICY_DEFAULTS_PLUGIN_NAME,
|
|
35
|
+
RENDERER_EXTENSIONS_PACKAGE: ()=>RENDERER_EXTENSIONS_PACKAGE,
|
|
36
|
+
RENDERER_EXTENSIONS_PLUGIN_NAME: ()=>RENDERER_EXTENSIONS_PLUGIN_NAME,
|
|
37
|
+
SERVER_EXTENSIONS_PLUGIN_NAME: ()=>SERVER_EXTENSIONS_PLUGIN_NAME,
|
|
38
|
+
applyPolicyDefaults: ()=>applyPolicyDefaults,
|
|
39
|
+
createPolicyDefaultsPlugin: ()=>createPolicyDefaultsPlugin
|
|
40
|
+
});
|
|
41
|
+
const external_runtime_package_resolution_js_namespaceObject = require("./runtime-package-resolution.js");
|
|
42
|
+
const RENDERER_EXTENSIONS_PACKAGE = '@modern-js/runtime-renderer-extensions';
|
|
43
|
+
const RENDERER_EXTENSIONS_PLUGIN_NAME = 'rendererHead';
|
|
44
|
+
const SERVER_EXTENSIONS_PLUGIN_NAME = '@modern-js/app-tools/server-plugin';
|
|
45
|
+
const POLICY_DEFAULTS_PLUGIN_NAME = '@modern-js/ultramodern-policy-defaults';
|
|
46
|
+
const applyPolicyDefaults = (api, options = {})=>{
|
|
47
|
+
if (false !== options.rendererExtensions) {
|
|
48
|
+
api._internalRuntimePlugins(({ entrypoint, plugins })=>{
|
|
49
|
+
if (!plugins.some((plugin)=>plugin.path === RENDERER_EXTENSIONS_PACKAGE)) plugins.push({
|
|
50
|
+
name: RENDERER_EXTENSIONS_PLUGIN_NAME,
|
|
51
|
+
path: RENDERER_EXTENSIONS_PACKAGE,
|
|
52
|
+
config: {}
|
|
53
|
+
});
|
|
54
|
+
return {
|
|
55
|
+
entrypoint,
|
|
56
|
+
plugins
|
|
57
|
+
};
|
|
58
|
+
});
|
|
59
|
+
const moduleDirectories = (0, external_runtime_package_resolution_js_namespaceObject.collectRuntimePackageModuleDirectories)([
|
|
60
|
+
RENDERER_EXTENSIONS_PACKAGE
|
|
61
|
+
], __rslib_import_meta_url__);
|
|
62
|
+
if (moduleDirectories.length > 0) api.modifyResolvedConfig((config)=>({
|
|
63
|
+
...config,
|
|
64
|
+
builderPlugins: [
|
|
65
|
+
...config.builderPlugins ?? [],
|
|
66
|
+
(0, external_runtime_package_resolution_js_namespaceObject.createRuntimePackageResolutionPlugin)(moduleDirectories)
|
|
67
|
+
]
|
|
68
|
+
}));
|
|
69
|
+
}
|
|
70
|
+
if (false !== options.serverExtensions) api._internalServerPlugins(({ plugins })=>{
|
|
71
|
+
if (!plugins.some((plugin)=>plugin.name === SERVER_EXTENSIONS_PLUGIN_NAME)) plugins.push({
|
|
72
|
+
name: SERVER_EXTENSIONS_PLUGIN_NAME
|
|
73
|
+
});
|
|
74
|
+
return {
|
|
75
|
+
plugins
|
|
76
|
+
};
|
|
77
|
+
});
|
|
78
|
+
};
|
|
79
|
+
const createPolicyDefaultsPlugin = (options = {})=>({
|
|
80
|
+
name: POLICY_DEFAULTS_PLUGIN_NAME,
|
|
81
|
+
setup (api) {
|
|
82
|
+
applyPolicyDefaults(api, options);
|
|
83
|
+
}
|
|
84
|
+
});
|
|
85
|
+
exports.POLICY_DEFAULTS_PLUGIN_NAME = __webpack_exports__.POLICY_DEFAULTS_PLUGIN_NAME;
|
|
86
|
+
exports.RENDERER_EXTENSIONS_PACKAGE = __webpack_exports__.RENDERER_EXTENSIONS_PACKAGE;
|
|
87
|
+
exports.RENDERER_EXTENSIONS_PLUGIN_NAME = __webpack_exports__.RENDERER_EXTENSIONS_PLUGIN_NAME;
|
|
88
|
+
exports.SERVER_EXTENSIONS_PLUGIN_NAME = __webpack_exports__.SERVER_EXTENSIONS_PLUGIN_NAME;
|
|
89
|
+
exports.applyPolicyDefaults = __webpack_exports__.applyPolicyDefaults;
|
|
90
|
+
exports.createPolicyDefaultsPlugin = __webpack_exports__.createPolicyDefaultsPlugin;
|
|
91
|
+
for(var __rspack_i in __webpack_exports__)if (-1 === [
|
|
92
|
+
"POLICY_DEFAULTS_PLUGIN_NAME",
|
|
93
|
+
"RENDERER_EXTENSIONS_PACKAGE",
|
|
94
|
+
"RENDERER_EXTENSIONS_PLUGIN_NAME",
|
|
95
|
+
"SERVER_EXTENSIONS_PLUGIN_NAME",
|
|
96
|
+
"applyPolicyDefaults",
|
|
97
|
+
"createPolicyDefaultsPlugin"
|
|
98
|
+
].indexOf(__rspack_i)) exports[__rspack_i] = __webpack_exports__[__rspack_i];
|
|
99
|
+
Object.defineProperty(exports, '__esModule', {
|
|
100
|
+
value: true
|
|
101
|
+
});
|
|
@@ -53,7 +53,7 @@ const promises_namespaceObject = require("node:fs/promises");
|
|
|
53
53
|
var promises_default = /*#__PURE__*/ __webpack_require__.n(promises_namespaceObject);
|
|
54
54
|
const external_node_path_namespaceObject = require("node:path");
|
|
55
55
|
var external_node_path_default = /*#__PURE__*/ __webpack_require__.n(external_node_path_namespaceObject);
|
|
56
|
-
const
|
|
56
|
+
const backend_federation_contracts_namespaceObject = require("@modern-js/backend-federation-contracts");
|
|
57
57
|
const external_index_js_namespaceObject = require("./index.js");
|
|
58
58
|
const MICROVERTICAL_RELEASE_ENVELOPE_PATH = 'release/microvertical-release-envelope.json';
|
|
59
59
|
const MICROVERTICAL_RELEASE_IDENTITY_CARRIERS_PATH = 'release/microvertical-release-identity-carriers.json';
|
|
@@ -61,6 +61,21 @@ const MICROVERTICAL_RELEASE_IDENTITY_CARRIERS_KIND = 'ultramodern-release-identi
|
|
|
61
61
|
const MICROVERTICAL_RELEASE_IDENTITY_CARRIERS_SCHEMA_VERSION = 1;
|
|
62
62
|
const COMPILED_MODULE_PATTERN = /\.(?:c|m)?js$/u;
|
|
63
63
|
const EFFECT_BFF_WORKER_PATTERN = /^worker\/__modern_bff_effect\.(?:c|m)?js$/u;
|
|
64
|
+
const EFFECT_BFF_WORKER_SUPPORT_PATTERN = /^worker\/__modern_worker_(?:runtime|shared)_*\.(?:c|m)?js$/u;
|
|
65
|
+
const isEffectBffWorkerArtifact = (logicalPath)=>EFFECT_BFF_WORKER_PATTERN.test(logicalPath) || EFFECT_BFF_WORKER_SUPPORT_PATTERN.test(logicalPath);
|
|
66
|
+
const CRAWLER_POLICY_PATH = 'public/robots.txt';
|
|
67
|
+
const isPublicMetadataPath = (logicalPath)=>'public/_headers' === logicalPath || /^public\/\.well-known\/[^/]+\.json$/u.test(logicalPath);
|
|
68
|
+
const PUBLIC_BUILD_ARTIFACT_PATH = `public/${backend_federation_contracts_namespaceObject.ULTRAMODERN_BUILD_ARTIFACT_FILE}`;
|
|
69
|
+
const DECLARED_PUBLIC_ASSET_RUNTIME = 'public-asset';
|
|
70
|
+
const resolveDeclaredPublicAssets = (files, declaredPublicAssets, target)=>{
|
|
71
|
+
const staged = new Set(files);
|
|
72
|
+
const declared = new Set();
|
|
73
|
+
for (const logicalPath of declaredPublicAssets){
|
|
74
|
+
if (!logicalPath.startsWith('public/') || !staged.has(logicalPath)) throw new Error(`[ultramodern-release-envelope] final ${target} staging has no declared public asset file ${JSON.stringify(logicalPath)}.`);
|
|
75
|
+
declared.add(logicalPath);
|
|
76
|
+
}
|
|
77
|
+
return declared;
|
|
78
|
+
};
|
|
64
79
|
const isRecord = (value)=>'object' == typeof value && null !== value && !Array.isArray(value);
|
|
65
80
|
const flattenStrings = (value)=>'string' == typeof value ? [
|
|
66
81
|
value
|
|
@@ -73,6 +88,46 @@ const collectNestedStrings = (value, key)=>{
|
|
|
73
88
|
...collectNestedStrings(entryValue, key)
|
|
74
89
|
]);
|
|
75
90
|
};
|
|
91
|
+
const emptyProducerRouteModules = async (distDirectory, files, manifest, manifestLogicalPath)=>{
|
|
92
|
+
if (!isRecord(manifest) || !Array.isArray(manifest.exposes) || 0 !== manifest.exposes.length || !Array.isArray(manifest.remotes) || 0 !== manifest.remotes.length || !isRecord(manifest.metaData) || !isRecord(manifest.metaData.remoteEntry) || '' !== manifest.metaData.remoteEntry.name || '' !== manifest.metaData.remoteEntry.path || 'global' !== manifest.metaData.remoteEntry.type) return [];
|
|
93
|
+
const publicPath = manifest.metaData.publicPath;
|
|
94
|
+
const safeReference = (value)=>'string' == typeof value && value.length > 0 && !/[\\\\%?#\s]/u.test(value) && !value.split('/').some((segment)=>'.' === segment || '..' === segment);
|
|
95
|
+
if (!safeReference(publicPath)) return [];
|
|
96
|
+
const absoluteBase = /^https?:\/\//u.test(publicPath);
|
|
97
|
+
if ('auto' !== publicPath && (!publicPath.endsWith('/') || !absoluteBase && (!publicPath.startsWith('/') || publicPath.startsWith('//')))) return [];
|
|
98
|
+
if (absoluteBase) {
|
|
99
|
+
const base = new URL(publicPath);
|
|
100
|
+
if (base.username || base.password || base.href !== publicPath) return [];
|
|
101
|
+
}
|
|
102
|
+
const directory = external_node_path_default().posix.dirname(manifestLogicalPath);
|
|
103
|
+
const routesManifest = await readJson(external_node_path_default().join(distDirectory, directory, 'routes-manifest.json'));
|
|
104
|
+
if (!isRecord(routesManifest) || !isRecord(routesManifest.routeAssets)) return [];
|
|
105
|
+
const modules = new Set();
|
|
106
|
+
for (const route of Object.values(routesManifest.routeAssets)){
|
|
107
|
+
if (!isRecord(route) || !Array.isArray(route.assets)) return [];
|
|
108
|
+
for (const reference of route.assets){
|
|
109
|
+
if (!safeReference(reference) || reference.startsWith('//')) return [];
|
|
110
|
+
let relative = reference;
|
|
111
|
+
if (/^https?:\/\//u.test(reference)) {
|
|
112
|
+
if (!absoluteBase || !reference.startsWith(publicPath)) return [];
|
|
113
|
+
relative = reference.slice(publicPath.length);
|
|
114
|
+
} else if (reference.startsWith('/')) {
|
|
115
|
+
const prefix = 'auto' === publicPath ? '/' : absoluteBase ? new URL(publicPath).pathname : publicPath;
|
|
116
|
+
if (!reference.startsWith(prefix)) return [];
|
|
117
|
+
relative = reference.slice(prefix.length);
|
|
118
|
+
}
|
|
119
|
+
if (!/^(?:static|html|public)\/[^:]+$/u.test(relative) || relative.includes('//')) return [];
|
|
120
|
+
const logicalPath = external_node_path_default().posix.join(directory, relative);
|
|
121
|
+
if (!files.includes(logicalPath)) return [];
|
|
122
|
+
const assetStat = await promises_default().lstat(external_node_path_default().join(distDirectory, logicalPath));
|
|
123
|
+
if (!assetStat.isFile()) return [];
|
|
124
|
+
if (COMPILED_MODULE_PATTERN.test(logicalPath)) modules.add(logicalPath);
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
return [
|
|
128
|
+
...modules
|
|
129
|
+
];
|
|
130
|
+
};
|
|
76
131
|
const manifestReferencedClientModules = async (distDirectory, files, manifestLogicalPath = 'mf-manifest.json')=>{
|
|
77
132
|
const manifest = await readJson(external_node_path_default().join(distDirectory, manifestLogicalPath));
|
|
78
133
|
const references = [
|
|
@@ -82,9 +137,10 @@ const manifestReferencedClientModules = async (distDirectory, files, manifestLog
|
|
|
82
137
|
...collectNestedStrings(manifest, 'async')
|
|
83
138
|
];
|
|
84
139
|
const normalizedReferences = new Set(references.filter((value)=>'string' == typeof value).map((value)=>value.replace(/^https?:\/\/[^/]+/u, '')).map((value)=>value.replace(/^\/+/u, '')));
|
|
85
|
-
|
|
140
|
+
const modules = files.filter((logicalPath)=>COMPILED_MODULE_PATTERN.test(logicalPath) && [
|
|
86
141
|
...normalizedReferences
|
|
87
142
|
].some((reference)=>reference === logicalPath || reference.endsWith(`/${logicalPath}`) || logicalPath.endsWith(`/${reference}`)));
|
|
143
|
+
return modules.length > 0 ? modules : emptyProducerRouteModules(distDirectory, files, manifest, manifestLogicalPath);
|
|
88
144
|
};
|
|
89
145
|
const routeReferencedSsrModules = async (distDirectory, files, target, routeSpecLogicalPath = 'route.json')=>{
|
|
90
146
|
const routeSpec = await readJson(external_node_path_default().join(distDirectory, routeSpecLogicalPath));
|
|
@@ -134,11 +190,14 @@ const writeReleaseEnvelope = async (artifactRoot, envelope)=>{
|
|
|
134
190
|
if (!envelopePath) throw new Error('[ultramodern-release-envelope] could not resolve release envelope path.');
|
|
135
191
|
await promises_default().writeFile(envelopePath, `${(0, external_index_js_namespaceObject.canonicalSerializeMicroVerticalReleaseEnvelope)(envelope)}\n`);
|
|
136
192
|
};
|
|
137
|
-
const readBuildArtifact = async (distDirectory)=>{
|
|
138
|
-
const artifactPath = external_node_path_default().join(distDirectory,
|
|
193
|
+
const readBuildArtifact = async (distDirectory, requirePromotable = true)=>{
|
|
194
|
+
const artifactPath = external_node_path_default().join(distDirectory, backend_federation_contracts_namespaceObject.ULTRAMODERN_BUILD_ARTIFACT_FILE);
|
|
139
195
|
const artifact = await readJson(artifactPath);
|
|
140
|
-
if (!(0,
|
|
141
|
-
if ('workspace' === artifact.deliveryUnit.sourceRevision)
|
|
196
|
+
if (!(0, backend_federation_contracts_namespaceObject.isUltramodernBuildArtifact)(artifact)) throw new Error(`[ultramodern-release-envelope] ${backend_federation_contracts_namespaceObject.ULTRAMODERN_BUILD_ARTIFACT_FILE} is missing or invalid.`);
|
|
197
|
+
if ('workspace' === artifact.deliveryUnit.sourceRevision) {
|
|
198
|
+
if (!requirePromotable) return;
|
|
199
|
+
throw new Error('[ultramodern-release-envelope] sourceRevision "workspace" cannot produce a promotable envelope.');
|
|
200
|
+
}
|
|
142
201
|
return artifact;
|
|
143
202
|
};
|
|
144
203
|
const assertIdentityBlock = (value, identity, location, includeReleaseVersion)=>{
|
|
@@ -154,7 +213,7 @@ const assertIdentityBlock = (value, identity, location, includeReleaseVersion)=>
|
|
|
154
213
|
for (const [field, expectedValue] of Object.entries(expected))if (value[field] !== expectedValue) throw new Error(`[ultramodern-release-envelope] ${location}.${field} must match ${expectedValue}; received ${String(value[field])}.`);
|
|
155
214
|
};
|
|
156
215
|
const readBackendManifest = async (distDirectory, identity)=>{
|
|
157
|
-
const manifest = await readJson(external_node_path_default().join(distDirectory,
|
|
216
|
+
const manifest = await readJson(external_node_path_default().join(distDirectory, backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE));
|
|
158
217
|
if (!isRecord(manifest) || !isRecord(manifest.backendFederation)) throw new Error('[ultramodern-release-envelope] backend federation manifest is missing backendFederation metadata.');
|
|
159
218
|
assertIdentityBlock(manifest.backendFederation.deliveryUnit, identity, 'backendFederation.deliveryUnit', true);
|
|
160
219
|
const versionBoundary = manifest.backendFederation.versionBoundary;
|
|
@@ -207,7 +266,7 @@ const releaseArtifact = (logicalPath, runtime)=>({
|
|
|
207
266
|
const writeReleaseIdentityCarrierMetadata = async (artifactRoot, identity, carrierPaths)=>{
|
|
208
267
|
const surfacesByPath = new Map();
|
|
209
268
|
for (const [surface, logicalPaths] of Object.entries(carrierPaths)){
|
|
210
|
-
if (0 === logicalPaths.length) throw new Error(`[ultramodern-release-envelope] ${surface} has no declared release-identity carrier artifact.`);
|
|
269
|
+
if (0 === logicalPaths.length && 'ssr' !== surface && 'uiClient' !== surface) throw new Error(`[ultramodern-release-envelope] ${surface} has no declared release-identity carrier artifact.`);
|
|
211
270
|
for (const logicalPath of logicalPaths){
|
|
212
271
|
const surfaces = surfacesByPath.get(logicalPath) ?? new Set();
|
|
213
272
|
surfaces.add(surface);
|
|
@@ -247,12 +306,12 @@ const writeReleaseIdentityCarrierMetadata = async (artifactRoot, identity, carri
|
|
|
247
306
|
}, null, 2)}\n`);
|
|
248
307
|
return releaseArtifact(MICROVERTICAL_RELEASE_IDENTITY_CARRIERS_PATH, 'release-identity-metadata');
|
|
249
308
|
};
|
|
250
|
-
const createReleaseArtifactInputs = async (distDirectory, identity, target)=>{
|
|
309
|
+
const createReleaseArtifactInputs = async (distDirectory, identity, target, apiOnly)=>{
|
|
251
310
|
const files = await collectFiles(distDirectory);
|
|
252
|
-
if ('node' === target && files.some(
|
|
311
|
+
if ('node' === target && files.some(isEffectBffWorkerArtifact)) throw new Error('[ultramodern-release-envelope] Node target conflicts with a Cloudflare Effect API/BFF worker artifact; resolve the canonical deploy target instead of emitting a Node envelope for Cloudflare output.');
|
|
253
312
|
const uiClientPaths = files.filter((logicalPath)=>{
|
|
254
313
|
const topLevel = logicalPath.split('/')[0];
|
|
255
|
-
return 'static' === topLevel || 'html' === topLevel || 'public' === topLevel || [
|
|
314
|
+
return 'static' === topLevel || 'html' === topLevel || 'public' === topLevel && logicalPath !== CRAWLER_POLICY_PATH && !isPublicMetadataPath(logicalPath) || [
|
|
256
315
|
'index.html',
|
|
257
316
|
'mf-manifest.json',
|
|
258
317
|
'mf-stats.json',
|
|
@@ -261,16 +320,17 @@ const createReleaseArtifactInputs = async (distDirectory, identity, target)=>{
|
|
|
261
320
|
'loadable-stats.json'
|
|
262
321
|
].includes(logicalPath);
|
|
263
322
|
});
|
|
264
|
-
const ssrPaths = 'node' === target ? files.filter((logicalPath)=>logicalPath.startsWith('bundles/') && COMPILED_MODULE_PATTERN.test(logicalPath)) : files.filter((logicalPath)=>logicalPath.startsWith('worker/') && COMPILED_MODULE_PATTERN.test(logicalPath) && !
|
|
323
|
+
const ssrPaths = 'node' === target ? files.filter((logicalPath)=>logicalPath.startsWith('bundles/') && COMPILED_MODULE_PATTERN.test(logicalPath)) : files.filter((logicalPath)=>logicalPath.startsWith('worker/') && COMPILED_MODULE_PATTERN.test(logicalPath) && !isEffectBffWorkerArtifact(logicalPath));
|
|
265
324
|
const nodeApiEntryPaths = files.filter((logicalPath)=>logicalPath.startsWith('api/') && COMPILED_MODULE_PATTERN.test(logicalPath));
|
|
266
|
-
const apiBackendPaths = 'node' === target ? files.filter((logicalPath)=>(logicalPath.startsWith('api/') || logicalPath.startsWith('shared/')) && COMPILED_MODULE_PATTERN.test(logicalPath)) : files.filter(
|
|
267
|
-
if (
|
|
268
|
-
if (0 ===
|
|
269
|
-
if (
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
325
|
+
const apiBackendPaths = 'node' === target ? files.filter((logicalPath)=>(logicalPath.startsWith('api/') || logicalPath.startsWith('shared/')) && COMPILED_MODULE_PATTERN.test(logicalPath)) : files.filter(isEffectBffWorkerArtifact);
|
|
326
|
+
if (apiOnly && (uiClientPaths.length > 0 || ssrPaths.length > 0)) throw new Error('[ultramodern-release-envelope] API-only MicroVertical emitted an undeclared UI/client or SSR surface.');
|
|
327
|
+
if (!apiOnly && 0 === uiClientPaths.length) throw new Error(`[ultramodern-release-envelope] ${target} full-stack MicroVertical has no UI/client artifacts.`);
|
|
328
|
+
if (!apiOnly && 0 === ssrPaths.length) throw new Error(`[ultramodern-release-envelope] ${target} full-stack MicroVertical has no ${'node' === target ? 'Node' : 'workerd'} SSR artifacts.`);
|
|
329
|
+
if ('node' === target && 0 === nodeApiEntryPaths.length || 'cloudflare' === target && !files.some((logicalPath)=>EFFECT_BFF_WORKER_PATTERN.test(logicalPath)) || 0 === apiBackendPaths.length) throw new Error(`[ultramodern-release-envelope] ${target} MicroVertical has no actual ${'node' === target ? 'compiled Node Effect API artifact' : 'Effect API/BFF worker artifact'}.`);
|
|
330
|
+
const clientExecutionPaths = apiOnly ? [] : await manifestReferencedClientModules(distDirectory, files);
|
|
331
|
+
if (!apiOnly && 0 === clientExecutionPaths.length) throw new Error('[ultramodern-release-envelope] UI/client manifest references no compiled execution module.');
|
|
332
|
+
const ssrExecutionPaths = apiOnly ? [] : await routeReferencedSsrModules(distDirectory, files, target);
|
|
333
|
+
if (!apiOnly && 0 === ssrExecutionPaths.length) throw new Error(`[ultramodern-release-envelope] route manifest references no emitted ${'node' === target ? 'Node' : 'Cloudflare'} SSR execution module.`);
|
|
274
334
|
const runtimeByPath = new Map();
|
|
275
335
|
const add = (paths, runtime)=>{
|
|
276
336
|
for (const logicalPath of paths){
|
|
@@ -280,13 +340,15 @@ const createReleaseArtifactInputs = async (distDirectory, identity, target)=>{
|
|
|
280
340
|
}
|
|
281
341
|
};
|
|
282
342
|
add(uiClientPaths, 'browser');
|
|
343
|
+
add(files.filter((logicalPath)=>logicalPath === CRAWLER_POLICY_PATH), 'crawler-policy');
|
|
344
|
+
add(files.filter(isPublicMetadataPath), 'public-metadata');
|
|
283
345
|
add(ssrPaths, 'node' === target ? 'nodejs' : 'workerd');
|
|
284
346
|
add(apiBackendPaths, 'node' === target ? 'nodejs' : 'workerd-effect');
|
|
285
347
|
add([
|
|
286
|
-
|
|
348
|
+
backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE
|
|
287
349
|
], 'module-federation-manifest');
|
|
288
350
|
add([
|
|
289
|
-
|
|
351
|
+
backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE
|
|
290
352
|
], 'node' === target ? 'nodejs' : 'commonjs-module');
|
|
291
353
|
const surfaces = {
|
|
292
354
|
uiClient: [
|
|
@@ -299,8 +361,8 @@ const createReleaseArtifactInputs = async (distDirectory, identity, target)=>{
|
|
|
299
361
|
...apiBackendPaths
|
|
300
362
|
].sort((left, right)=>left.localeCompare(right)),
|
|
301
363
|
backendFederation: {
|
|
302
|
-
manifest:
|
|
303
|
-
container:
|
|
364
|
+
manifest: backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE,
|
|
365
|
+
container: backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE
|
|
304
366
|
}
|
|
305
367
|
};
|
|
306
368
|
const artifacts = [
|
|
@@ -309,8 +371,8 @@ const createReleaseArtifactInputs = async (distDirectory, identity, target)=>{
|
|
|
309
371
|
const identityCarrierMetadata = await writeReleaseIdentityCarrierMetadata(distDirectory, identity, {
|
|
310
372
|
apiBackend: apiBackendPaths,
|
|
311
373
|
backendFederation: [
|
|
312
|
-
|
|
313
|
-
|
|
374
|
+
backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE,
|
|
375
|
+
backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE
|
|
314
376
|
],
|
|
315
377
|
ssr: [
|
|
316
378
|
...new Set([
|
|
@@ -336,17 +398,17 @@ const pathExists = async (filePath)=>{
|
|
|
336
398
|
return false;
|
|
337
399
|
}
|
|
338
400
|
};
|
|
339
|
-
const emitFrameworkMicroVerticalReleaseEnvelope = async ({ apiOnly, distDirectory, target })=>{
|
|
340
|
-
|
|
341
|
-
const
|
|
342
|
-
const backendContainerPath = external_node_path_default().join(distDirectory, universal_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE);
|
|
401
|
+
const emitFrameworkMicroVerticalReleaseEnvelope = async ({ apiOnly, distDirectory, requirePromotable = true, target })=>{
|
|
402
|
+
const backendManifestPath = external_node_path_default().join(distDirectory, backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE);
|
|
403
|
+
const backendContainerPath = external_node_path_default().join(distDirectory, backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE);
|
|
343
404
|
const [hasBackendManifest, hasBackendContainer] = await Promise.all([
|
|
344
405
|
pathExists(backendManifestPath),
|
|
345
406
|
pathExists(backendContainerPath)
|
|
346
407
|
]);
|
|
347
|
-
if (!hasBackendManifest && !hasBackendContainer) return;
|
|
348
|
-
if (!hasBackendManifest || !hasBackendContainer) throw new Error('[ultramodern-release-envelope]
|
|
349
|
-
const buildArtifact = await readBuildArtifact(distDirectory);
|
|
408
|
+
if (!hasBackendManifest && !hasBackendContainer && !apiOnly) return;
|
|
409
|
+
if (!hasBackendManifest || !hasBackendContainer) throw new Error('[ultramodern-release-envelope] MicroVertical backend federation manifest and container must be emitted together.');
|
|
410
|
+
const buildArtifact = await readBuildArtifact(distDirectory, requirePromotable);
|
|
411
|
+
if (!buildArtifact) return;
|
|
350
412
|
const identity = {
|
|
351
413
|
unitId: buildArtifact.deliveryUnit.unitId,
|
|
352
414
|
buildMarker: buildArtifact.deliveryUnit.buildMarker,
|
|
@@ -354,7 +416,7 @@ const emitFrameworkMicroVerticalReleaseEnvelope = async ({ apiOnly, distDirector
|
|
|
354
416
|
releaseVersion: buildArtifact.deliveryUnit.version
|
|
355
417
|
};
|
|
356
418
|
await readBackendManifest(distDirectory, identity);
|
|
357
|
-
const { artifacts, surfaces } = await createReleaseArtifactInputs(distDirectory, identity, target);
|
|
419
|
+
const { artifacts, surfaces } = await createReleaseArtifactInputs(distDirectory, identity, target, apiOnly);
|
|
358
420
|
const envelope = await (0, external_index_js_namespaceObject.createMicroVerticalReleaseEnvelope)({
|
|
359
421
|
artifactRoot: distDirectory,
|
|
360
422
|
target,
|
|
@@ -385,19 +447,16 @@ const readFrameworkMicroVerticalReleaseEnvelope = async ({ artifactRoot, expecte
|
|
|
385
447
|
});
|
|
386
448
|
};
|
|
387
449
|
const verifyBuildOutputReleaseEnvelope = async (distDirectory, expectedTarget)=>{
|
|
388
|
-
const [hasEnvelope, hasBuildArtifact
|
|
450
|
+
const [hasEnvelope, hasBuildArtifact] = await Promise.all([
|
|
389
451
|
pathExists(external_node_path_default().join(distDirectory, MICROVERTICAL_RELEASE_ENVELOPE_PATH)),
|
|
390
|
-
pathExists(external_node_path_default().join(distDirectory,
|
|
391
|
-
pathExists(external_node_path_default().join(distDirectory, universal_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE)),
|
|
392
|
-
pathExists(external_node_path_default().join(distDirectory, universal_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE))
|
|
452
|
+
pathExists(external_node_path_default().join(distDirectory, backend_federation_contracts_namespaceObject.ULTRAMODERN_BUILD_ARTIFACT_FILE))
|
|
393
453
|
]);
|
|
394
|
-
const isFullStackMicroVertical = hasBuildArtifact && (hasBackendManifest || hasBackendEntry);
|
|
395
454
|
return readFrameworkMicroVerticalReleaseEnvelope({
|
|
396
455
|
artifactRoot: distDirectory,
|
|
397
456
|
...expectedTarget ? {
|
|
398
457
|
expectedTarget
|
|
399
458
|
} : {},
|
|
400
|
-
required: hasEnvelope ||
|
|
459
|
+
required: hasEnvelope || hasBuildArtifact
|
|
401
460
|
});
|
|
402
461
|
};
|
|
403
462
|
const verifyNodeReleaseEnvelopeStaging = async ({ outputDirectory })=>readFrameworkMicroVerticalReleaseEnvelope({
|
|
@@ -405,21 +464,22 @@ const verifyNodeReleaseEnvelopeStaging = async ({ outputDirectory })=>readFramew
|
|
|
405
464
|
expectedTarget: 'node',
|
|
406
465
|
required: true
|
|
407
466
|
});
|
|
408
|
-
const createNodeStagedReleaseArtifactInputs = async (outputDirectory, identity)=>{
|
|
467
|
+
const createNodeStagedReleaseArtifactInputs = async (outputDirectory, identity, apiOnly, declaredPublicAssets)=>{
|
|
409
468
|
const files = await collectFiles(outputDirectory);
|
|
469
|
+
const declaredPublicAssetPaths = resolveDeclaredPublicAssets(files, declaredPublicAssets, 'Node');
|
|
410
470
|
for (const requiredPath of [
|
|
411
471
|
'index.js',
|
|
412
472
|
'package.json',
|
|
413
|
-
|
|
414
|
-
|
|
473
|
+
backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE,
|
|
474
|
+
backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE
|
|
415
475
|
])if (!files.includes(requiredPath)) throw new Error(`[ultramodern-release-envelope] final Node staging is missing ${requiredPath}.`);
|
|
416
476
|
const backendFederationPaths = new Set([
|
|
417
|
-
|
|
418
|
-
|
|
477
|
+
backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE,
|
|
478
|
+
backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE
|
|
419
479
|
]);
|
|
420
480
|
const uiClientPaths = files.filter((logicalPath)=>{
|
|
421
481
|
const topLevel = logicalPath.split('/')[0];
|
|
422
|
-
return 'static' === topLevel || 'html' === topLevel || 'public' === topLevel || [
|
|
482
|
+
return 'static' === topLevel || 'html' === topLevel || 'public' === topLevel && logicalPath !== CRAWLER_POLICY_PATH && !isPublicMetadataPath(logicalPath) && !declaredPublicAssetPaths.has(logicalPath) || [
|
|
423
483
|
'index.html',
|
|
424
484
|
'mf-manifest.json',
|
|
425
485
|
'mf-stats.json',
|
|
@@ -430,6 +490,7 @@ const createNodeStagedReleaseArtifactInputs = async (outputDirectory, identity)=
|
|
|
430
490
|
});
|
|
431
491
|
const ssrPaths = files.filter((logicalPath)=>'index.js' === logicalPath || logicalPath.startsWith('bundles/') && COMPILED_MODULE_PATTERN.test(logicalPath));
|
|
432
492
|
const apiBackendPaths = files.filter((logicalPath)=>(logicalPath.startsWith('api/') || logicalPath.startsWith('shared/')) && COMPILED_MODULE_PATTERN.test(logicalPath));
|
|
493
|
+
if (apiOnly && (uiClientPaths.length > 0 || ssrPaths.some((path)=>'index.js' !== path))) throw new Error('[ultramodern-release-envelope] final API-only Node staging contains an undeclared UI/client or SSR surface.');
|
|
433
494
|
for (const [surface, paths] of [
|
|
434
495
|
[
|
|
435
496
|
'UI/client',
|
|
@@ -437,32 +498,35 @@ const createNodeStagedReleaseArtifactInputs = async (outputDirectory, identity)=
|
|
|
437
498
|
],
|
|
438
499
|
[
|
|
439
500
|
'Node SSR',
|
|
440
|
-
ssrPaths
|
|
501
|
+
apiOnly ? [] : ssrPaths
|
|
441
502
|
],
|
|
442
503
|
[
|
|
443
504
|
'Node API/backend',
|
|
444
505
|
apiBackendPaths
|
|
445
506
|
]
|
|
446
|
-
])if (0 === paths.length) throw new Error(`[ultramodern-release-envelope] final Node staging has no ${surface} artifacts.`);
|
|
447
|
-
const clientExecutionPaths = await manifestReferencedClientModules(outputDirectory, files);
|
|
448
|
-
const ssrExecutionPaths = await routeReferencedSsrModules(outputDirectory, files, 'node');
|
|
449
|
-
if (0 === clientExecutionPaths.length || 0 === ssrExecutionPaths.length) throw new Error('[ultramodern-release-envelope] final Node manifests must reference emitted UI/client and SSR execution modules.');
|
|
507
|
+
])if (0 === paths.length && (!apiOnly || 'Node API/backend' === surface)) throw new Error(`[ultramodern-release-envelope] final Node staging has no ${surface} artifacts.`);
|
|
508
|
+
const clientExecutionPaths = apiOnly ? [] : await manifestReferencedClientModules(outputDirectory, files);
|
|
509
|
+
const ssrExecutionPaths = apiOnly ? [] : await routeReferencedSsrModules(outputDirectory, files, 'node');
|
|
510
|
+
if (!apiOnly && (0 === clientExecutionPaths.length || 0 === ssrExecutionPaths.length)) throw new Error('[ultramodern-release-envelope] final Node manifests must reference emitted UI/client and SSR execution modules.');
|
|
450
511
|
const runtimeByPath = new Map(files.filter((logicalPath)=>!backendFederationPaths.has(logicalPath)).map((logicalPath)=>[
|
|
451
512
|
logicalPath,
|
|
452
513
|
'nodejs-deployment'
|
|
453
514
|
]));
|
|
454
515
|
for (const logicalPath of uiClientPaths)runtimeByPath.set(logicalPath, 'browser');
|
|
455
|
-
for (const logicalPath of
|
|
516
|
+
for (const logicalPath of declaredPublicAssetPaths)runtimeByPath.set(logicalPath, DECLARED_PUBLIC_ASSET_RUNTIME);
|
|
517
|
+
if (files.includes(CRAWLER_POLICY_PATH)) runtimeByPath.set(CRAWLER_POLICY_PATH, 'crawler-policy');
|
|
518
|
+
for (const logicalPath of files.filter(isPublicMetadataPath))runtimeByPath.set(logicalPath, 'public-metadata');
|
|
519
|
+
for (const logicalPath of apiOnly ? [] : ssrPaths)runtimeByPath.set(logicalPath, 'nodejs');
|
|
456
520
|
for (const logicalPath of apiBackendPaths)runtimeByPath.set(logicalPath, 'nodejs');
|
|
457
|
-
runtimeByPath.set(
|
|
458
|
-
runtimeByPath.set(
|
|
521
|
+
runtimeByPath.set(backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE, 'module-federation-manifest');
|
|
522
|
+
runtimeByPath.set(backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE, 'nodejs');
|
|
459
523
|
const identityCarrierMetadata = await writeReleaseIdentityCarrierMetadata(outputDirectory, identity, {
|
|
460
524
|
apiBackend: apiBackendPaths,
|
|
461
525
|
backendFederation: [
|
|
462
|
-
|
|
463
|
-
|
|
526
|
+
backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE,
|
|
527
|
+
backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE
|
|
464
528
|
],
|
|
465
|
-
ssr: [
|
|
529
|
+
ssr: apiOnly ? [] : [
|
|
466
530
|
...new Set([
|
|
467
531
|
...ssrExecutionPaths,
|
|
468
532
|
...ssrPaths.filter((logicalPath)=>'index.js' !== logicalPath)
|
|
@@ -481,23 +545,23 @@ const createNodeStagedReleaseArtifactInputs = async (outputDirectory, identity)=
|
|
|
481
545
|
uiClient: [
|
|
482
546
|
...uiClientPaths
|
|
483
547
|
].sort((left, right)=>left.localeCompare(right)),
|
|
484
|
-
ssr: [
|
|
548
|
+
ssr: apiOnly ? [] : [
|
|
485
549
|
...ssrPaths
|
|
486
550
|
].sort((left, right)=>left.localeCompare(right)),
|
|
487
551
|
apiBackend: [
|
|
488
552
|
...apiBackendPaths
|
|
489
553
|
].sort((left, right)=>left.localeCompare(right)),
|
|
490
554
|
backendFederation: {
|
|
491
|
-
manifest:
|
|
492
|
-
container:
|
|
555
|
+
manifest: backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE,
|
|
556
|
+
container: backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE
|
|
493
557
|
}
|
|
494
558
|
}
|
|
495
559
|
};
|
|
496
560
|
};
|
|
497
|
-
const emitNodeStagedReleaseEnvelope = async ({ distDirectory, outputDirectory })=>{
|
|
561
|
+
const emitNodeStagedReleaseEnvelope = async ({ declaredPublicAssets = [], distDirectory, outputDirectory })=>{
|
|
498
562
|
const source = await verifyBuildOutputReleaseEnvelope(distDirectory, 'node');
|
|
499
563
|
if (!source) return;
|
|
500
|
-
const { artifacts, surfaces } = await createNodeStagedReleaseArtifactInputs(outputDirectory, source.identity);
|
|
564
|
+
const { artifacts, surfaces } = await createNodeStagedReleaseArtifactInputs(outputDirectory, source.identity, 0 === source.surfaces.uiClient.length, declaredPublicAssets);
|
|
501
565
|
const staged = await (0, external_index_js_namespaceObject.createMicroVerticalReleaseEnvelope)({
|
|
502
566
|
artifactRoot: outputDirectory,
|
|
503
567
|
target: 'node',
|
|
@@ -515,21 +579,26 @@ const stageCloudflareReleaseEnvelope = async ({ distDirectory, outputDirectory }
|
|
|
515
579
|
if (await pathExists(stagedEnvelopePath)) throw new Error('[ultramodern-release-envelope] Cloudflare staging contains a stale envelope before final output generation.');
|
|
516
580
|
return source;
|
|
517
581
|
};
|
|
518
|
-
const createCloudflareStagedReleaseArtifactInputs = async (outputDirectory, identity)=>{
|
|
582
|
+
const createCloudflareStagedReleaseArtifactInputs = async (outputDirectory, identity, apiOnly, declaredPublicAssets)=>{
|
|
519
583
|
const files = await collectFiles(outputDirectory);
|
|
584
|
+
const declaredPublicAssetPaths = resolveDeclaredPublicAssets(files, declaredPublicAssets, 'Cloudflare');
|
|
520
585
|
for (const requiredPath of [
|
|
521
586
|
'server/index.mjs',
|
|
522
587
|
'server/modern-worker-manifest.json',
|
|
523
588
|
'wrangler.json',
|
|
524
589
|
'package.json',
|
|
525
|
-
|
|
590
|
+
...apiOnly ? [] : [
|
|
591
|
+
'worker/package.json'
|
|
592
|
+
]
|
|
526
593
|
])if (!files.includes(requiredPath)) throw new Error(`[ultramodern-release-envelope] final Cloudflare staging is missing ${requiredPath}.`);
|
|
527
594
|
if (files.some((logicalPath)=>'public/release' === logicalPath || logicalPath.startsWith('public/release/'))) throw new Error('[ultramodern-release-envelope] final Cloudflare envelope must remain private and cannot be staged under public/release.');
|
|
528
|
-
const backendManifestPath = `public/${
|
|
529
|
-
const backendContainerPath = `public/${
|
|
530
|
-
const apiBackendPaths = files.filter(
|
|
531
|
-
|
|
532
|
-
const
|
|
595
|
+
const backendManifestPath = `public/${backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_MANIFEST_FILE}`;
|
|
596
|
+
const backendContainerPath = `public/${backend_federation_contracts_namespaceObject.BACKEND_FEDERATION_REMOTE_ENTRY_FILE}`;
|
|
597
|
+
const apiBackendPaths = files.filter(isEffectBffWorkerArtifact);
|
|
598
|
+
if (!files.some((logicalPath)=>EFFECT_BFF_WORKER_PATTERN.test(logicalPath))) throw new Error('[ultramodern-release-envelope] final Cloudflare staging has no actual Effect API/BFF worker artifact.');
|
|
599
|
+
const ssrPaths = files.filter((logicalPath)=>(logicalPath.startsWith('server/') || logicalPath.startsWith('worker/')) && COMPILED_MODULE_PATTERN.test(logicalPath) && !isEffectBffWorkerArtifact(logicalPath));
|
|
600
|
+
const uiClientPaths = files.filter((logicalPath)=>logicalPath.startsWith('public/') && logicalPath !== CRAWLER_POLICY_PATH && !isPublicMetadataPath(logicalPath) && !declaredPublicAssetPaths.has(logicalPath) && logicalPath !== PUBLIC_BUILD_ARTIFACT_PATH && logicalPath !== backendManifestPath && logicalPath !== backendContainerPath);
|
|
601
|
+
if (apiOnly && (uiClientPaths.length > 0 || ssrPaths.some((path)=>'server/index.mjs' !== path))) throw new Error('[ultramodern-release-envelope] final API-only Cloudflare staging contains an undeclared UI/client or SSR surface.');
|
|
533
602
|
for (const [surface, paths] of [
|
|
534
603
|
[
|
|
535
604
|
'UI/client',
|
|
@@ -537,27 +606,32 @@ const createCloudflareStagedReleaseArtifactInputs = async (outputDirectory, iden
|
|
|
537
606
|
],
|
|
538
607
|
[
|
|
539
608
|
'Cloudflare SSR',
|
|
540
|
-
ssrPaths
|
|
609
|
+
apiOnly ? [] : ssrPaths
|
|
541
610
|
],
|
|
542
611
|
[
|
|
543
612
|
'Cloudflare API/backend',
|
|
544
613
|
apiBackendPaths
|
|
545
614
|
]
|
|
546
|
-
])if (0 === paths.length) throw new Error(`[ultramodern-release-envelope] final Cloudflare staging has no ${surface} artifacts.`);
|
|
615
|
+
])if (0 === paths.length && (!apiOnly || 'Cloudflare API/backend' === surface)) throw new Error(`[ultramodern-release-envelope] final Cloudflare staging has no ${surface} artifacts.`);
|
|
547
616
|
for (const logicalPath of [
|
|
548
617
|
backendManifestPath,
|
|
549
618
|
backendContainerPath
|
|
550
619
|
])if (!files.includes(logicalPath)) throw new Error(`[ultramodern-release-envelope] final Cloudflare staging is missing ${logicalPath}.`);
|
|
551
|
-
const clientExecutionPaths = await manifestReferencedClientModules(outputDirectory, files, 'public/mf-manifest.json');
|
|
552
|
-
const ssrExecutionPaths = await routeReferencedSsrModules(outputDirectory, files, 'cloudflare', 'server/route.json');
|
|
553
|
-
if (0 === clientExecutionPaths.length || 0 === ssrExecutionPaths.length) throw new Error('[ultramodern-release-envelope] final Cloudflare manifests must reference emitted UI/client and SSR execution modules.');
|
|
620
|
+
const clientExecutionPaths = apiOnly ? [] : await manifestReferencedClientModules(outputDirectory, files, 'public/mf-manifest.json');
|
|
621
|
+
const ssrExecutionPaths = apiOnly ? [] : await routeReferencedSsrModules(outputDirectory, files, 'cloudflare', 'server/route.json');
|
|
622
|
+
if (!apiOnly && (0 === clientExecutionPaths.length || 0 === ssrExecutionPaths.length)) throw new Error('[ultramodern-release-envelope] final Cloudflare manifests must reference emitted UI/client and SSR execution modules.');
|
|
554
623
|
const runtimeByPath = new Map();
|
|
555
624
|
for (const logicalPath of files)runtimeByPath.set(logicalPath, 'cloudflare-deployment');
|
|
556
625
|
const add = (paths, runtime)=>{
|
|
557
626
|
for (const logicalPath of paths)runtimeByPath.set(logicalPath, runtime);
|
|
558
627
|
};
|
|
559
628
|
add(uiClientPaths, 'browser');
|
|
560
|
-
add(
|
|
629
|
+
add([
|
|
630
|
+
...declaredPublicAssetPaths
|
|
631
|
+
], DECLARED_PUBLIC_ASSET_RUNTIME);
|
|
632
|
+
if (files.includes(CRAWLER_POLICY_PATH)) runtimeByPath.set(CRAWLER_POLICY_PATH, 'crawler-policy');
|
|
633
|
+
add(files.filter(isPublicMetadataPath), 'public-metadata');
|
|
634
|
+
add(apiOnly ? [] : ssrPaths, 'workerd');
|
|
561
635
|
add(apiBackendPaths, 'workerd-effect');
|
|
562
636
|
add([
|
|
563
637
|
backendManifestPath
|
|
@@ -571,7 +645,7 @@ const createCloudflareStagedReleaseArtifactInputs = async (outputDirectory, iden
|
|
|
571
645
|
backendManifestPath,
|
|
572
646
|
backendContainerPath
|
|
573
647
|
],
|
|
574
|
-
ssr: [
|
|
648
|
+
ssr: apiOnly ? [] : [
|
|
575
649
|
...new Set([
|
|
576
650
|
...ssrExecutionPaths,
|
|
577
651
|
...ssrPaths.filter((logicalPath)=>logicalPath.startsWith('worker/'))
|
|
@@ -590,7 +664,7 @@ const createCloudflareStagedReleaseArtifactInputs = async (outputDirectory, iden
|
|
|
590
664
|
uiClient: [
|
|
591
665
|
...uiClientPaths
|
|
592
666
|
].sort((left, right)=>left.localeCompare(right)),
|
|
593
|
-
ssr: [
|
|
667
|
+
ssr: apiOnly ? [] : [
|
|
594
668
|
...ssrPaths
|
|
595
669
|
].sort((left, right)=>left.localeCompare(right)),
|
|
596
670
|
apiBackend: [
|
|
@@ -603,10 +677,10 @@ const createCloudflareStagedReleaseArtifactInputs = async (outputDirectory, iden
|
|
|
603
677
|
}
|
|
604
678
|
};
|
|
605
679
|
};
|
|
606
|
-
const emitCloudflareStagedReleaseEnvelope = async ({ distDirectory, outputDirectory })=>{
|
|
680
|
+
const emitCloudflareStagedReleaseEnvelope = async ({ declaredPublicAssets = [], distDirectory, outputDirectory })=>{
|
|
607
681
|
const source = await verifyBuildOutputReleaseEnvelope(distDirectory, 'cloudflare');
|
|
608
682
|
if (!source) return;
|
|
609
|
-
const { artifacts, surfaces } = await createCloudflareStagedReleaseArtifactInputs(outputDirectory, source.identity);
|
|
683
|
+
const { artifacts, surfaces } = await createCloudflareStagedReleaseArtifactInputs(outputDirectory, source.identity, 0 === source.surfaces.uiClient.length, declaredPublicAssets);
|
|
610
684
|
const staged = await (0, external_index_js_namespaceObject.createMicroVerticalReleaseEnvelope)({
|
|
611
685
|
artifactRoot: outputDirectory,
|
|
612
686
|
target: 'cloudflare',
|
|
@@ -232,7 +232,7 @@ const assertUniqueSortedArtifacts = (artifacts, location)=>{
|
|
|
232
232
|
if (paths.some((logicalPath, index)=>logicalPath !== sorted[index])) throw new Error(`${location} must be sorted by logicalPath.`);
|
|
233
233
|
};
|
|
234
234
|
const assertSurfacePaths = (value, location)=>{
|
|
235
|
-
if (!Array.isArray(value)
|
|
235
|
+
if (!Array.isArray(value)) throw new Error(`${location} must be an array of artifact paths.`);
|
|
236
236
|
const paths = value.map((item, index)=>assertNormalizedLogicalPath(item, `${location}[${index}]`));
|
|
237
237
|
const sorted = [
|
|
238
238
|
...paths
|
|
@@ -254,10 +254,16 @@ const assertSurfaces = (value)=>{
|
|
|
254
254
|
'manifest',
|
|
255
255
|
'container'
|
|
256
256
|
], 'surfaces.backendFederation');
|
|
257
|
+
const uiClient = assertSurfacePaths(surfaces.uiClient, 'surfaces.uiClient');
|
|
258
|
+
const ssr = assertSurfacePaths(surfaces.ssr, 'surfaces.ssr');
|
|
259
|
+
const apiBackend = assertSurfacePaths(surfaces.apiBackend, 'surfaces.apiBackend');
|
|
260
|
+
if (uiClient.length > 0 && 0 === ssr.length) throw new Error('surfaces.ssr must contain at least one artifact path when UI/client is declared.');
|
|
261
|
+
if (ssr.length > 0 && 0 === uiClient.length) throw new Error('surfaces.uiClient must contain at least one artifact path when SSR is declared.');
|
|
262
|
+
if (0 === apiBackend.length) throw new Error('surfaces.apiBackend must contain at least one artifact path.');
|
|
257
263
|
return {
|
|
258
|
-
uiClient
|
|
259
|
-
ssr
|
|
260
|
-
apiBackend
|
|
264
|
+
uiClient,
|
|
265
|
+
ssr,
|
|
266
|
+
apiBackend,
|
|
261
267
|
backendFederation: {
|
|
262
268
|
manifest: assertNormalizedLogicalPath(backendFederation.manifest, 'surfaces.backendFederation.manifest'),
|
|
263
269
|
container: assertNormalizedLogicalPath(backendFederation.container, 'surfaces.backendFederation.container')
|