@bleedingdev/modern-js-utils 3.9.0-ultramodern.4 → 3.9.0-ultramodern.5

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.
Files changed (53) hide show
  1. package/dist/cjs/universal/index.js +5 -25
  2. package/dist/esm/universal/index.mjs +0 -2
  3. package/dist/esm-node/universal/index.mjs +0 -2
  4. package/dist/types/universal/index.d.ts +0 -2
  5. package/package.json +2 -2
  6. package/dist/cjs/universal/backend-federation-contract/build-artifact.js +0 -185
  7. package/dist/cjs/universal/backend-federation-contract/constants.js +0 -92
  8. package/dist/cjs/universal/backend-federation-contract/delivery-unit.js +0 -130
  9. package/dist/cjs/universal/backend-federation-contract/index.js +0 -137
  10. package/dist/cjs/universal/backend-federation-contract/metadata.js +0 -133
  11. package/dist/cjs/universal/backend-federation-contract/types.js +0 -18
  12. package/dist/cjs/universal/backend-federation-contract/validation-core.js +0 -85
  13. package/dist/cjs/universal/surface-resolution/env-static-provider.js +0 -318
  14. package/dist/cjs/universal/surface-resolution/index.js +0 -69
  15. package/dist/cjs/universal/surface-resolution/surface-ref.js +0 -132
  16. package/dist/cjs/universal/surface-resolution/types.js +0 -18
  17. package/dist/cjs/universal/surface-resolution/validation.js +0 -202
  18. package/dist/esm/universal/backend-federation-contract/build-artifact.mjs +0 -135
  19. package/dist/esm/universal/backend-federation-contract/constants.mjs +0 -18
  20. package/dist/esm/universal/backend-federation-contract/delivery-unit.mjs +0 -74
  21. package/dist/esm/universal/backend-federation-contract/index.mjs +0 -5
  22. package/dist/esm/universal/backend-federation-contract/metadata.mjs +0 -80
  23. package/dist/esm/universal/backend-federation-contract/types.mjs +0 -0
  24. package/dist/esm/universal/backend-federation-contract/validation-core.mjs +0 -29
  25. package/dist/esm/universal/surface-resolution/env-static-provider.mjs +0 -274
  26. package/dist/esm/universal/surface-resolution/index.mjs +0 -3
  27. package/dist/esm/universal/surface-resolution/surface-ref.mjs +0 -88
  28. package/dist/esm/universal/surface-resolution/types.mjs +0 -0
  29. package/dist/esm/universal/surface-resolution/validation.mjs +0 -155
  30. package/dist/esm-node/universal/backend-federation-contract/build-artifact.mjs +0 -136
  31. package/dist/esm-node/universal/backend-federation-contract/constants.mjs +0 -19
  32. package/dist/esm-node/universal/backend-federation-contract/delivery-unit.mjs +0 -75
  33. package/dist/esm-node/universal/backend-federation-contract/index.mjs +0 -6
  34. package/dist/esm-node/universal/backend-federation-contract/metadata.mjs +0 -81
  35. package/dist/esm-node/universal/backend-federation-contract/types.mjs +0 -1
  36. package/dist/esm-node/universal/backend-federation-contract/validation-core.mjs +0 -30
  37. package/dist/esm-node/universal/surface-resolution/env-static-provider.mjs +0 -275
  38. package/dist/esm-node/universal/surface-resolution/index.mjs +0 -4
  39. package/dist/esm-node/universal/surface-resolution/surface-ref.mjs +0 -89
  40. package/dist/esm-node/universal/surface-resolution/types.mjs +0 -1
  41. package/dist/esm-node/universal/surface-resolution/validation.mjs +0 -156
  42. package/dist/types/universal/backend-federation-contract/build-artifact.d.ts +0 -9
  43. package/dist/types/universal/backend-federation-contract/constants.d.ts +0 -14
  44. package/dist/types/universal/backend-federation-contract/delivery-unit.d.ts +0 -9
  45. package/dist/types/universal/backend-federation-contract/index.d.ts +0 -7
  46. package/dist/types/universal/backend-federation-contract/metadata.d.ts +0 -7
  47. package/dist/types/universal/backend-federation-contract/types.d.ts +0 -60
  48. package/dist/types/universal/backend-federation-contract/validation-core.d.ts +0 -8
  49. package/dist/types/universal/surface-resolution/env-static-provider.d.ts +0 -107
  50. package/dist/types/universal/surface-resolution/index.d.ts +0 -4
  51. package/dist/types/universal/surface-resolution/surface-ref.d.ts +0 -72
  52. package/dist/types/universal/surface-resolution/types.d.ts +0 -102
  53. package/dist/types/universal/surface-resolution/validation.d.ts +0 -53
@@ -1,19 +0,0 @@
1
- import "node:module";
2
- const BACKEND_FEDERATION_EFFECT_EXPOSE = './effect-api';
3
- const BACKEND_FEDERATION_MANIFEST_FILE = 'backend-mf-manifest.json';
4
- const BACKEND_FEDERATION_REMOTE_ENTRY_FILE = 'backendRemoteEntry.cjs';
5
- const BACKEND_FEDERATION_CONTRACT_VERSION = 'microvertical-server-effect-v1';
6
- const BACKEND_FEDERATION_NODE_ADAPTER_VERSION = 'backend-mf-effect-v1';
7
- const DELIVERY_UNIT_SCHEMA_VERSION = 1;
8
- const DELIVERY_UNIT_KIND = 'microvertical-delivery-unit';
9
- const DELIVERY_UNIT_DEPLOY_PROFILE = 'cloudflare-ssr-mf-effect-v1';
10
- const DELIVERY_UNIT_IDENTITY_FIELDS = [
11
- 'unitId',
12
- 'buildMarker',
13
- 'sourceRevision'
14
- ];
15
- const ULTRAMODERN_BUILD_ARTIFACT_FILE = 'ultramodern-build.json';
16
- const ULTRAMODERN_BUILD_ARTIFACT_PATH = `shared/${ULTRAMODERN_BUILD_ARTIFACT_FILE}`;
17
- const ULTRAMODERN_BUILD_MODULE_FILE = 'ultramodern-build.ts';
18
- const ULTRAMODERN_BUILD_MODULE_PATH = `shared/${ULTRAMODERN_BUILD_MODULE_FILE}`;
19
- export { BACKEND_FEDERATION_CONTRACT_VERSION, BACKEND_FEDERATION_EFFECT_EXPOSE, BACKEND_FEDERATION_MANIFEST_FILE, BACKEND_FEDERATION_NODE_ADAPTER_VERSION, BACKEND_FEDERATION_REMOTE_ENTRY_FILE, DELIVERY_UNIT_DEPLOY_PROFILE, DELIVERY_UNIT_IDENTITY_FIELDS, DELIVERY_UNIT_KIND, DELIVERY_UNIT_SCHEMA_VERSION, ULTRAMODERN_BUILD_ARTIFACT_FILE, ULTRAMODERN_BUILD_ARTIFACT_PATH, ULTRAMODERN_BUILD_MODULE_FILE, ULTRAMODERN_BUILD_MODULE_PATH };
@@ -1,75 +0,0 @@
1
- import "node:module";
2
- import { DELIVERY_UNIT_DEPLOY_PROFILE, DELIVERY_UNIT_IDENTITY_FIELDS, DELIVERY_UNIT_KIND, DELIVERY_UNIT_SCHEMA_VERSION } from "./constants.mjs";
3
- import { addError, isRecord, nonEmptyString, validationResult } from "./validation-core.mjs";
4
- const deliveryUnitIdentityFieldValue = (value, field, options = {})=>{
5
- if (!isRecord(value)) return;
6
- if ('buildMarker' === field && options.allowBuildAlias) return nonEmptyString(value.buildMarker) ?? nonEmptyString(value.build);
7
- return nonEmptyString(value[field]);
8
- };
9
- const validateDeliveryUnitIdentity = (value, options = {})=>{
10
- const path = options.path ?? 'deliveryUnit';
11
- const errors = [];
12
- if (!isRecord(value)) {
13
- addError(errors, path, 'must be an object.');
14
- return validationResult(errors);
15
- }
16
- for (const field of DELIVERY_UNIT_IDENTITY_FIELDS)if (!deliveryUnitIdentityFieldValue(value, field, options)) addError(errors, `${path}.${field}`, 'must be a non-empty string.');
17
- return validationResult(errors);
18
- };
19
- const validateDeliveryUnitContractBlock = (value, options = {})=>{
20
- const path = options.path ?? 'deliveryUnit';
21
- const errors = [
22
- ...validateDeliveryUnitIdentity(value, options).errors
23
- ];
24
- if (!isRecord(value)) return validationResult(errors);
25
- if (value.schemaVersion !== DELIVERY_UNIT_SCHEMA_VERSION) addError(errors, `${path}.schemaVersion`, `must be ${DELIVERY_UNIT_SCHEMA_VERSION}.`);
26
- if (value.kind !== DELIVERY_UNIT_KIND) addError(errors, `${path}.kind`, `must be "${DELIVERY_UNIT_KIND}".`);
27
- if (!nonEmptyString(value.packageName)) addError(errors, `${path}.packageName`, 'must be a non-empty string.');
28
- if (!nonEmptyString(value.version)) addError(errors, `${path}.version`, 'must be a non-empty string.');
29
- return validationResult(errors);
30
- };
31
- const validateDeliveryUnitRecord = (value, options = {})=>{
32
- const path = options.path ?? 'deliveryUnit';
33
- const errors = [
34
- ...validateDeliveryUnitContractBlock(value, {
35
- ...options,
36
- path
37
- }).errors
38
- ];
39
- if (!isRecord(value)) return validationResult(errors);
40
- if (!nonEmptyString(value.appId)) addError(errors, `${path}.appId`, 'must be a non-empty string.');
41
- if (value.deployProfile !== DELIVERY_UNIT_DEPLOY_PROFILE) addError(errors, `${path}.deployProfile`, `must be "${DELIVERY_UNIT_DEPLOY_PROFILE}".`);
42
- return validationResult(errors);
43
- };
44
- const validateDeliveryUnitBoundaryIdentity = (value, path)=>{
45
- const errors = [];
46
- if (!isRecord(value)) {
47
- addError(errors, path, 'must be an object.');
48
- return errors;
49
- }
50
- for (const field of DELIVERY_UNIT_IDENTITY_FIELDS)if (!deliveryUnitIdentityFieldValue(value, field)) addError(errors, `${path}.${field}`, 'must be a non-empty string.');
51
- return errors;
52
- };
53
- const deliveryUnitContractBlock = (record)=>({
54
- schemaVersion: record.schemaVersion,
55
- kind: record.kind,
56
- unitId: record.unitId,
57
- packageName: record.packageName,
58
- version: record.version,
59
- buildMarker: record.buildMarker,
60
- sourceRevision: record.sourceRevision
61
- });
62
- const toDeliveryUnitIdentity = (value)=>{
63
- const unitId = deliveryUnitIdentityFieldValue(value, 'unitId');
64
- const buildMarker = deliveryUnitIdentityFieldValue(value, 'buildMarker', {
65
- allowBuildAlias: true
66
- });
67
- const sourceRevision = deliveryUnitIdentityFieldValue(value, 'sourceRevision');
68
- if (!unitId || !buildMarker || !sourceRevision) return;
69
- return {
70
- unitId,
71
- buildMarker,
72
- sourceRevision
73
- };
74
- };
75
- export { deliveryUnitContractBlock, deliveryUnitIdentityFieldValue, toDeliveryUnitIdentity, validateDeliveryUnitBoundaryIdentity, validateDeliveryUnitContractBlock, validateDeliveryUnitIdentity, validateDeliveryUnitRecord };
@@ -1,6 +0,0 @@
1
- import "node:module";
2
- export { createUltramodernBuildArtifact, isUltramodernBuildArtifact, stampUltramodernBuildArtifactIdentity, stampUltramodernBuildArtifactSourceRevision, validateUltramodernBuildArtifact } from "./build-artifact.mjs";
3
- export { BACKEND_FEDERATION_CONTRACT_VERSION, BACKEND_FEDERATION_EFFECT_EXPOSE, BACKEND_FEDERATION_MANIFEST_FILE, BACKEND_FEDERATION_NODE_ADAPTER_VERSION, BACKEND_FEDERATION_REMOTE_ENTRY_FILE, DELIVERY_UNIT_DEPLOY_PROFILE, DELIVERY_UNIT_IDENTITY_FIELDS, DELIVERY_UNIT_KIND, DELIVERY_UNIT_SCHEMA_VERSION, ULTRAMODERN_BUILD_ARTIFACT_FILE, ULTRAMODERN_BUILD_ARTIFACT_PATH, ULTRAMODERN_BUILD_MODULE_FILE, ULTRAMODERN_BUILD_MODULE_PATH } from "./constants.mjs";
4
- export { deliveryUnitContractBlock, deliveryUnitIdentityFieldValue, toDeliveryUnitIdentity, validateDeliveryUnitContractBlock, validateDeliveryUnitIdentity, validateDeliveryUnitRecord } from "./delivery-unit.mjs";
5
- export { backendFederationExposeNames, backendFederationMetadata, backendFederationVersionBoundary, toBackendFederationExposeNames, validateBackendFederationManifest, validateBackendFederationMetadata } from "./metadata.mjs";
6
- export { formatBackendFederationValidationErrors, nonEmptyString } from "./validation-core.mjs";
@@ -1,81 +0,0 @@
1
- import "node:module";
2
- import { BACKEND_FEDERATION_CONTRACT_VERSION, BACKEND_FEDERATION_EFFECT_EXPOSE, BACKEND_FEDERATION_NODE_ADAPTER_VERSION, DELIVERY_UNIT_IDENTITY_FIELDS, DELIVERY_UNIT_SCHEMA_VERSION } from "./constants.mjs";
3
- import { deliveryUnitIdentityFieldValue, validateDeliveryUnitBoundaryIdentity, validateDeliveryUnitContractBlock } from "./delivery-unit.mjs";
4
- import { addError, isRecord, nonEmptyString, recordField, validateVersionField, validationResult } from "./validation-core.mjs";
5
- const toBackendFederationExposeNames = (value)=>{
6
- const names = [];
7
- if (Array.isArray(value)) for (const expose of value){
8
- const name = nonEmptyString(expose) ?? (isRecord(expose) ? nonEmptyString(expose.name) : void 0);
9
- if (name) names.push(name);
10
- }
11
- else if (isRecord(value)) names.push(...Object.keys(value).filter((name)=>name.length > 0));
12
- return Array.from(new Set(names));
13
- };
14
- const backendFederationExposeNames = (value)=>{
15
- if (!isRecord(value)) return [];
16
- const exposes = toBackendFederationExposeNames(value.exposes);
17
- const expose = nonEmptyString(value.expose);
18
- return Array.from(new Set([
19
- ...exposes,
20
- ...expose ? [
21
- expose
22
- ] : []
23
- ]));
24
- };
25
- const backendFederationMetadata = (value)=>isRecord(value) ? recordField(value, 'backendFederation') : void 0;
26
- const backendFederationVersionBoundary = (value)=>recordField(backendFederationMetadata(value), 'versionBoundary');
27
- const validateBackendFederationMetadata = (value, options = {})=>{
28
- const path = options.path ?? 'backendFederation';
29
- const errors = [];
30
- if (!isRecord(value)) {
31
- addError(errors, path, 'must be an object.');
32
- return validationResult(errors);
33
- }
34
- if (options.requireEffectRuntime && 'effect' !== value.runtimeFramework) addError(errors, `${path}.runtimeFramework`, 'must be "effect".');
35
- if (options.requireEffectRuntime && true !== value.strictEffectApproach) addError(errors, `${path}.strictEffectApproach`, 'must be true.');
36
- validateVersionField(errors, value, 'contractVersion', options.expectedContractVersion ?? BACKEND_FEDERATION_CONTRACT_VERSION, path, options.requireVersionFields ?? false);
37
- validateVersionField(errors, value, 'nodeAdapterVersion', options.expectedNodeAdapterVersion ?? BACKEND_FEDERATION_NODE_ADAPTER_VERSION, path, options.requireVersionFields ?? false);
38
- if (options.requireEffectExpose && !backendFederationExposeNames(value).includes(BACKEND_FEDERATION_EFFECT_EXPOSE)) addError(errors, `${path}.expose`, `must include "${BACKEND_FEDERATION_EFFECT_EXPOSE}".`);
39
- if (options.validateDeliveryUnit ?? true) {
40
- const deliveryUnit = recordField(value, 'deliveryUnit');
41
- if (deliveryUnit) errors.push(...validateDeliveryUnitContractBlock(deliveryUnit, {
42
- path: `${path}.deliveryUnit`
43
- }).errors);
44
- const versionBoundary = recordField(value, 'versionBoundary');
45
- const versionBoundaryDeliveryUnit = recordField(versionBoundary, 'deliveryUnit');
46
- if (versionBoundaryDeliveryUnit) errors.push(...validateDeliveryUnitBoundaryIdentity(versionBoundaryDeliveryUnit, `${path}.versionBoundary.deliveryUnit`));
47
- if (deliveryUnit && versionBoundaryDeliveryUnit) for (const field of DELIVERY_UNIT_IDENTITY_FIELDS){
48
- const deliveryUnitValue = deliveryUnitIdentityFieldValue(deliveryUnit, field);
49
- const versionBoundaryDeliveryUnitValue = deliveryUnitIdentityFieldValue(versionBoundaryDeliveryUnit, field);
50
- if (deliveryUnitValue && versionBoundaryDeliveryUnitValue && deliveryUnitValue !== versionBoundaryDeliveryUnitValue) addError(errors, `${path}.versionBoundary.deliveryUnit.${field}`, `must match ${path}.deliveryUnit.${field}.`);
51
- }
52
- }
53
- return validationResult(errors);
54
- };
55
- const validateBackendFederationManifest = (value, options = {})=>{
56
- const path = options.path ?? 'manifest';
57
- const errors = [];
58
- if (!isRecord(value)) {
59
- addError(errors, path, 'must be an object.');
60
- return validationResult(errors);
61
- }
62
- if (void 0 !== value.schemaVersion && value.schemaVersion !== DELIVERY_UNIT_SCHEMA_VERSION) addError(errors, `${path}.schemaVersion`, `must be ${DELIVERY_UNIT_SCHEMA_VERSION}.`);
63
- const metadata = backendFederationMetadata(value);
64
- if (metadata) errors.push(...validateBackendFederationMetadata(metadata, {
65
- ...options,
66
- path: `${path}.backendFederation`,
67
- requireEffectExpose: false
68
- }).errors);
69
- else if (options.requireBackendFederation ?? true) addError(errors, `${path}.backendFederation`, 'must be an object.');
70
- if (options.requireEffectExpose) {
71
- const topLevelExposeNames = toBackendFederationExposeNames(value.exposes);
72
- const metadataExposeNames = backendFederationExposeNames(metadata);
73
- const exposeNames = new Set([
74
- ...topLevelExposeNames,
75
- ...metadataExposeNames
76
- ]);
77
- if (!exposeNames.has(BACKEND_FEDERATION_EFFECT_EXPOSE)) addError(errors, `${path}.exposes`, `must include "${BACKEND_FEDERATION_EFFECT_EXPOSE}".`);
78
- }
79
- return validationResult(errors);
80
- };
81
- export { backendFederationExposeNames, backendFederationMetadata, backendFederationVersionBoundary, toBackendFederationExposeNames, validateBackendFederationManifest, validateBackendFederationMetadata };
@@ -1 +0,0 @@
1
- import "node:module";
@@ -1,30 +0,0 @@
1
- import "node:module";
2
- const isRecord = (value)=>'object' == typeof value && null !== value && !Array.isArray(value);
3
- const nonEmptyString = (value)=>'string' == typeof value && value.trim().length > 0 ? value : void 0;
4
- const validationResult = (errors)=>({
5
- ok: 0 === errors.length,
6
- errors
7
- });
8
- const addError = (errors, path, message)=>{
9
- errors.push({
10
- path,
11
- message
12
- });
13
- };
14
- const recordField = (value, field)=>{
15
- const fieldValue = value?.[field];
16
- return isRecord(fieldValue) ? fieldValue : void 0;
17
- };
18
- const formatBackendFederationValidationErrors = (errors)=>errors.map((error)=>`${error.path}: ${error.message}`).join('; ');
19
- const validateVersionField = (errors, record, field, expected, path, required)=>{
20
- const compatibility = recordField(record, 'compatibility');
21
- const executionSurfaces = recordField(record, 'executionSurfaces');
22
- const nodeSurface = recordField(executionSurfaces, 'node');
23
- const actual = nonEmptyString(record[field]) ?? nonEmptyString(compatibility?.[field]) ?? ('nodeAdapterVersion' === field ? nonEmptyString(nodeSurface?.adapterVersion) : void 0);
24
- if (!actual) {
25
- if (required) addError(errors, `${path}.${field}`, 'must be a non-empty string.');
26
- return;
27
- }
28
- if (false !== expected && actual !== expected) addError(errors, `${path}.${field}`, `must be "${expected}".`);
29
- };
30
- export { addError, formatBackendFederationValidationErrors, isRecord, nonEmptyString, recordField, validateVersionField, validationResult };
@@ -1,275 +0,0 @@
1
- import "node:module";
2
- import { formatSurfaceRef } from "./surface-ref.mjs";
3
- import { createDiscoveryError, validateResolvedDeliveryUnit } from "./validation.mjs";
4
- const DEFAULT_LOCAL_ENVIRONMENTS = [
5
- 'development',
6
- 'local'
7
- ];
8
- const ENV_STATIC_PROVIDER_NAME = 'env-static';
9
- function trimTrailingSlashes(value) {
10
- return value.replace(/\/+$/u, '');
11
- }
12
- function envValue(env, name) {
13
- const value = env[name]?.trim();
14
- return void 0 !== value && value.length > 0 ? value : void 0;
15
- }
16
- function stripMfNamePrefix(value, mfName) {
17
- return value.startsWith(`${mfName}@`) ? value.slice(mfName.length + 1) : value;
18
- }
19
- function createEnvContext(env, allowLocalFallback) {
20
- return {
21
- env,
22
- allowLocalFallback,
23
- cloudflareDeployEnabled: 'cloudflare' === env.MODERNJS_DEPLOY,
24
- workersDevSubdomain: envValue(env, 'ULTRAMODERN_CLOUDFLARE_WORKERS_DEV_SUBDOMAIN'),
25
- requireCloudflarePublicUrls: 'true' === env.ULTRAMODERN_CLOUDFLARE_REQUIRE_PUBLIC_URLS
26
- };
27
- }
28
- function resolveBaseUrl(context, unit) {
29
- const publicUrlEnv = `ULTRAMODERN_PUBLIC_URL_${unit.envSegment}`;
30
- const configuredPublicUrl = envValue(context.env, publicUrlEnv);
31
- if (void 0 !== configuredPublicUrl) return {
32
- ok: true,
33
- baseUrl: trimTrailingSlashes(configuredPublicUrl)
34
- };
35
- if (context.cloudflareDeployEnabled && void 0 !== context.workersDevSubdomain && void 0 !== unit.workerName) return {
36
- ok: true,
37
- baseUrl: `https://${unit.workerName}.${context.workersDevSubdomain}.workers.dev`
38
- };
39
- if (context.cloudflareDeployEnabled && context.requireCloudflarePublicUrls) return {
40
- ok: false,
41
- reason: `Cloudflare deploy requires ${publicUrlEnv} (or a configured manifest env / ULTRAMODERN_CLOUDFLARE_WORKERS_DEV_SUBDOMAIN with a worker name)`,
42
- details: {
43
- publicUrlEnv
44
- }
45
- };
46
- if (void 0 !== unit.port && context.allowLocalFallback) return {
47
- ok: true,
48
- baseUrl: `http://localhost:${unit.port}`
49
- };
50
- if (void 0 !== unit.port) return {
51
- ok: false,
52
- reason: `No base URL available: set ${publicUrlEnv} (localhost fallback is disabled outside designated local environments)`,
53
- details: {
54
- publicUrlEnv
55
- }
56
- };
57
- return {
58
- ok: false,
59
- reason: `No base URL available: set ${publicUrlEnv} or configure a localhost port`,
60
- details: {
61
- publicUrlEnv
62
- }
63
- };
64
- }
65
- function resolveBrowserMfManifest(context, unit) {
66
- const manifestEnv = `VERTICAL_${unit.envSegment}_MF_MANIFEST`;
67
- const configuredManifest = envValue(context.env, manifestEnv);
68
- if (void 0 !== configuredManifest) return {
69
- ok: true,
70
- location: {
71
- platform: 'browser-mf-manifest',
72
- manifestUrl: stripMfNamePrefix(configuredManifest, unit.mfName)
73
- }
74
- };
75
- const base = resolveBaseUrl(context, unit);
76
- if (!base.ok) return {
77
- ok: false,
78
- reason: `browser-mf-manifest unavailable (${manifestEnv} unset; ${base.reason})`,
79
- details: {
80
- manifestEnv,
81
- ...base.details
82
- }
83
- };
84
- return {
85
- ok: true,
86
- location: {
87
- platform: 'browser-mf-manifest',
88
- manifestUrl: `${base.baseUrl}/mf-manifest.json`
89
- }
90
- };
91
- }
92
- function resolveNodeMfManifest(context, unit) {
93
- const manifestEnv = `VERTICAL_${unit.envSegment}_BACKEND_MF_MANIFEST`;
94
- const configuredManifest = envValue(context.env, manifestEnv);
95
- if (void 0 !== configuredManifest) return {
96
- ok: true,
97
- location: {
98
- platform: 'node-mf-manifest',
99
- manifestRef: configuredManifest
100
- }
101
- };
102
- if (void 0 !== unit.port && context.allowLocalFallback) return {
103
- ok: true,
104
- location: {
105
- platform: 'node-mf-manifest',
106
- manifestRef: `http://localhost:${unit.port}/backend-mf-manifest.json`
107
- }
108
- };
109
- if (void 0 !== unit.port) return {
110
- ok: false,
111
- reason: `node-mf-manifest unavailable: set ${manifestEnv} (localhost fallback is disabled outside designated local environments)`,
112
- details: {
113
- manifestEnv
114
- }
115
- };
116
- return {
117
- ok: false,
118
- reason: `node-mf-manifest unavailable: set ${manifestEnv} or configure a localhost port`,
119
- details: {
120
- manifestEnv
121
- }
122
- };
123
- }
124
- function resolveHttpApi(context, unit, config) {
125
- const base = resolveBaseUrl(context, unit);
126
- if (!base.ok) return {
127
- ok: false,
128
- reason: `http-api unavailable (${base.reason})`,
129
- details: base.details
130
- };
131
- return {
132
- ok: true,
133
- location: {
134
- platform: 'http-api',
135
- baseUrl: base.baseUrl,
136
- prefix: config.prefix
137
- }
138
- };
139
- }
140
- function resolveCloudflareServiceBinding(config) {
141
- if (0 === config.serviceBinding.length) return {
142
- ok: false,
143
- reason: 'cloudflare-service-binding unavailable: empty serviceBinding'
144
- };
145
- return {
146
- ok: true,
147
- location: {
148
- platform: 'cloudflare-service-binding',
149
- serviceBinding: config.serviceBinding,
150
- ...void 0 === config.dispatchNamespace ? {} : {
151
- dispatchNamespace: config.dispatchNamespace
152
- }
153
- }
154
- };
155
- }
156
- function resolveSurfaceLocations(context, unit, surface) {
157
- const outcomes = [];
158
- if (surface.platforms.browserMfManifest) outcomes.push(resolveBrowserMfManifest(context, unit));
159
- if (surface.platforms.nodeMfManifest) outcomes.push(resolveNodeMfManifest(context, unit));
160
- if (void 0 !== surface.platforms.httpApi) outcomes.push(resolveHttpApi(context, unit, surface.platforms.httpApi));
161
- if (void 0 !== surface.platforms.cloudflareServiceBinding) outcomes.push(resolveCloudflareServiceBinding(surface.platforms.cloudflareServiceBinding));
162
- const failure = outcomes.find((outcome)=>!outcome.ok);
163
- if (void 0 !== failure && !failure.ok) return {
164
- ok: false,
165
- reason: `surface ${surface.surfaceId}: ${failure.reason}`,
166
- details: failure.details
167
- };
168
- const locations = outcomes.flatMap((outcome)=>outcome.ok ? [
169
- outcome.location
170
- ] : []);
171
- if (0 === locations.length) return {
172
- ok: false,
173
- reason: `surface ${surface.surfaceId} declares no platform locations`
174
- };
175
- return {
176
- ok: true,
177
- surface: {
178
- surfaceId: surface.surfaceId,
179
- kind: surface.kind,
180
- locations
181
- }
182
- };
183
- }
184
- function createEnvStaticSurfaceResolutionProvider(options) {
185
- const env = options.env ?? {};
186
- const localEnvironments = new Set(options.localEnvironments ?? DEFAULT_LOCAL_ENVIRONMENTS);
187
- const identityVerification = options.identityVerification ?? 'static-trust';
188
- const unitsById = new Map(options.units.map((unit)=>[
189
- unit.unitId,
190
- unit
191
- ]));
192
- return {
193
- name: ENV_STATIC_PROVIDER_NAME,
194
- resolve (ref, environment) {
195
- const refString = formatSurfaceRef(ref);
196
- const unit = unitsById.get(ref.unitId);
197
- if (void 0 === unit) return {
198
- ok: false,
199
- error: createDiscoveryError('unknown-unit', refString, `No statically configured delivery unit ${ref.unitId}.`, {
200
- environment,
201
- knownUnits: [
202
- ...unitsById.keys()
203
- ]
204
- })
205
- };
206
- if (!unit.surfaces.some((surface)=>surface.surfaceId === ref.surfaceId)) return {
207
- ok: false,
208
- error: createDiscoveryError('unknown-surface', refString, `Unit ${unit.unitId} does not declare surface ${ref.surfaceId}.`, {
209
- environment,
210
- availableSurfaces: unit.surfaces.map((surface)=>surface.surfaceId)
211
- })
212
- };
213
- let effectiveUnit = unit;
214
- if (void 0 !== ref.major) {
215
- const majorConfig = (unit.majors ?? []).find((candidate)=>candidate.major === ref.major);
216
- if (void 0 === majorConfig) return {
217
- ok: false,
218
- error: createDiscoveryError('major-not-published', refString, `Unit ${unit.unitId} has no materialization for external major v${ref.major}.`, {
219
- environment,
220
- publishedMajors: (unit.majors ?? []).map((candidate)=>candidate.major)
221
- })
222
- };
223
- effectiveUnit = {
224
- ...unit,
225
- envSegment: majorConfig.envSegment ?? `${unit.envSegment}_V${majorConfig.major}`,
226
- port: majorConfig.port,
227
- workerName: majorConfig.workerName
228
- };
229
- }
230
- const context = createEnvContext(env, localEnvironments.has(environment));
231
- const surfaces = [];
232
- for (const surfaceConfig of unit.surfaces){
233
- const resolved = resolveSurfaceLocations(context, effectiveUnit, surfaceConfig);
234
- if (!resolved.ok) return {
235
- ok: false,
236
- error: createDiscoveryError('provider-unavailable', refString, `env-static provider cannot assemble a complete record for ${unit.unitId}: ${resolved.reason}.`, {
237
- environment,
238
- ...resolved.details
239
- })
240
- };
241
- surfaces.push(void 0 === ref.major ? resolved.surface : {
242
- ...resolved.surface,
243
- servedMajor: ref.major
244
- });
245
- }
246
- const record = {
247
- unitId: unit.unitId,
248
- buildMarker: unit.buildMarker,
249
- sourceRevision: unit.sourceRevision,
250
- baselineCohortId: unit.baselineCohortId,
251
- surfaces,
252
- compatibility: {
253
- status: 'compatible',
254
- baselineCohortId: unit.baselineCohortId,
255
- ...'static-trust' === identityVerification ? {
256
- reason: 'static-identity-unverified'
257
- } : {}
258
- }
259
- };
260
- const validation = validateResolvedDeliveryUnit(record);
261
- if (!validation.ok) return {
262
- ok: false,
263
- error: createDiscoveryError('provider-unavailable', refString, `env-static provider assembled an invalid record for ${unit.unitId}.`, {
264
- environment,
265
- issues: validation.issues
266
- })
267
- };
268
- return {
269
- ok: true,
270
- unit: record
271
- };
272
- }
273
- };
274
- }
275
- export { DEFAULT_LOCAL_ENVIRONMENTS, ENV_STATIC_PROVIDER_NAME, createEnvStaticSurfaceResolutionProvider };
@@ -1,4 +0,0 @@
1
- import "node:module";
2
- export { DEFAULT_LOCAL_ENVIRONMENTS, ENV_STATIC_PROVIDER_NAME, createEnvStaticSurfaceResolutionProvider } from "./env-static-provider.mjs";
3
- export { formatSurfaceRef, parseSurfaceRef, validateSurfaceRef } from "./surface-ref.mjs";
4
- export { createDiscoveryError, matchDeliveryUnitIdentity, selectResolvedSurface, validateResolvedDeliveryUnit } from "./validation.mjs";
@@ -1,89 +0,0 @@
1
- import "node:module";
2
- const SEGMENT_PATTERN = /^[A-Za-z0-9._-]+$/;
3
- const MAJOR_PATTERN = /^v[1-9][0-9]*$/;
4
- function parseSurfaceRef(input) {
5
- if ('' === input) return {
6
- ok: false,
7
- error: {
8
- code: 'empty'
9
- }
10
- };
11
- const hashCount = countChar(input, '#');
12
- if (0 === hashCount) return {
13
- ok: false,
14
- error: {
15
- code: 'missing-surface-separator'
16
- }
17
- };
18
- if (hashCount > 1) return {
19
- ok: false,
20
- error: {
21
- code: 'multiple-surface-separators'
22
- }
23
- };
24
- const hashIndex = input.indexOf('#');
25
- const unitPart = input.slice(0, hashIndex);
26
- const rest = input.slice(hashIndex + 1);
27
- const atIndex = rest.indexOf('@');
28
- const surfaceId = -1 === atIndex ? rest : rest.slice(0, atIndex);
29
- const ref = {
30
- unitId: unitPart,
31
- surfaceId
32
- };
33
- if (-1 !== atIndex) {
34
- const majorPart = rest.slice(atIndex + 1);
35
- if ('' === majorPart) return {
36
- ok: false,
37
- error: {
38
- code: 'empty-major'
39
- }
40
- };
41
- if (!MAJOR_PATTERN.test(majorPart)) return {
42
- ok: false,
43
- error: {
44
- code: 'invalid-major',
45
- value: majorPart
46
- }
47
- };
48
- ref.major = Number(majorPart.slice(1));
49
- }
50
- const error = validateSurfaceRef(ref);
51
- return void 0 === error ? {
52
- ok: true,
53
- ref
54
- } : {
55
- ok: false,
56
- error
57
- };
58
- }
59
- function formatSurfaceRef(ref) {
60
- const error = validateSurfaceRef(ref);
61
- if (void 0 !== error) throw new TypeError(`Cannot format invalid SurfaceRef: ${error.code}.`);
62
- const base = `${ref.unitId}#${ref.surfaceId}`;
63
- return void 0 === ref.major ? base : `${base}@v${ref.major}`;
64
- }
65
- function validateSurfaceRef(ref) {
66
- if ('' === ref.unitId) return {
67
- code: 'empty-unit-id'
68
- };
69
- for (const segment of ref.unitId.split('/'))if (!SEGMENT_PATTERN.test(segment)) return {
70
- code: 'invalid-unit-id',
71
- segment
72
- };
73
- if ('' === ref.surfaceId) return {
74
- code: 'empty-surface-id'
75
- };
76
- if (!SEGMENT_PATTERN.test(ref.surfaceId)) return {
77
- code: 'invalid-surface-id'
78
- };
79
- if (void 0 !== ref.major && (!Number.isSafeInteger(ref.major) || ref.major < 1)) return {
80
- code: 'invalid-major',
81
- value: String(ref.major)
82
- };
83
- }
84
- function countChar(input, char) {
85
- let count = 0;
86
- for (const current of input)if (current === char) count += 1;
87
- return count;
88
- }
89
- export { formatSurfaceRef, parseSurfaceRef, validateSurfaceRef };
@@ -1 +0,0 @@
1
- import "node:module";