@burojs/config 0.2.0 → 0.4.0

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/index.js CHANGED
@@ -1,557 +1,499 @@
1
- import { parseDocument } from 'yaml';
2
-
3
- // src/parse.ts
4
- var RESERVED_KEYS = /* @__PURE__ */ new Set(["__proto__", "prototype", "constructor"]);
5
- var FORBIDDEN_VALUE_CATEGORIES = /* @__PURE__ */ new Map([
6
- ["action", "action"],
7
- ["actions", "action"],
8
- ["provider", "provider"],
9
- ["providers", "provider"],
10
- ["mapper", "mapper"],
11
- ["mappers", "mapper"],
12
- ["service", "service"],
13
- ["services", "service"],
14
- ["credential", "credential"],
15
- ["credentials", "credential"],
16
- ["schema", "schema"],
17
- ["schemas", "schema"],
18
- ["component", "component"],
19
- ["components", "component"],
20
- ["attachment", "attachment"],
21
- ["attachments", "attachment"],
22
- ["validator", "validator"],
23
- ["validators", "validator"]
1
+ import { parseDocument } from "yaml";
2
+ //#region src/parse.ts
3
+ const RESERVED_KEYS = new Set([
4
+ "__proto__",
5
+ "prototype",
6
+ "constructor"
7
+ ]);
8
+ const FORBIDDEN_VALUE_CATEGORIES = new Map([
9
+ ["action", "action"],
10
+ ["actions", "action"],
11
+ ["provider", "provider"],
12
+ ["providers", "provider"],
13
+ ["mapper", "mapper"],
14
+ ["mappers", "mapper"],
15
+ ["service", "service"],
16
+ ["services", "service"],
17
+ ["credential", "credential"],
18
+ ["credentials", "credential"],
19
+ ["schema", "schema"],
20
+ ["schemas", "schema"],
21
+ ["component", "component"],
22
+ ["components", "component"],
23
+ ["attachment", "attachment"],
24
+ ["attachments", "attachment"],
25
+ ["validator", "validator"],
26
+ ["validators", "validator"]
27
+ ]);
28
+ const LAYER_KEYS = new Set([
29
+ "id",
30
+ "priority",
31
+ "defaultNamespace",
32
+ "revision",
33
+ "declarations",
34
+ "transforms"
35
+ ]);
36
+ const DECLARATION_KEYS = new Set([
37
+ "kind",
38
+ "ref",
39
+ "schemaVersion",
40
+ "value"
41
+ ]);
42
+ const TRANSFORM_KEYS = new Set([
43
+ "id",
44
+ "scope",
45
+ "select",
46
+ "operation"
24
47
  ]);
25
- var LAYER_KEYS = /* @__PURE__ */ new Set([
26
- "id",
27
- "priority",
28
- "defaultNamespace",
29
- "revision",
30
- "declarations",
31
- "transforms"
48
+ const SELECTOR_KEYS = new Set([
49
+ "kinds",
50
+ "namespaces",
51
+ "layers",
52
+ "refs",
53
+ "excludeRefs",
54
+ "tags"
32
55
  ]);
33
- var DECLARATION_KEYS = /* @__PURE__ */ new Set(["kind", "ref", "schemaVersion", "value"]);
34
- var TRANSFORM_KEYS = /* @__PURE__ */ new Set(["id", "scope", "select", "operation"]);
35
- var SELECTOR_KEYS = /* @__PURE__ */ new Set(["kinds", "namespaces", "layers", "refs", "excludeRefs", "tags"]);
36
- var OPERATION_KEYS = {
37
- merge: /* @__PURE__ */ new Set(["op", "value"]),
38
- replace: /* @__PURE__ */ new Set(["op", "value", "ifMissing"]),
39
- disable: /* @__PURE__ */ new Set(["op", "reason"]),
40
- delete: /* @__PURE__ */ new Set(["op"])
56
+ const OPERATION_KEYS = {
57
+ merge: new Set(["op", "value"]),
58
+ replace: new Set([
59
+ "op",
60
+ "value",
61
+ "ifMissing"
62
+ ]),
63
+ disable: new Set(["op", "reason"]),
64
+ delete: new Set(["op"])
41
65
  };
42
- var ATTACHMENT_TAG = "@burojs/core/trusted-attachment";
66
+ const ATTACHMENT_TAG = "@burojs/core/trusted-attachment";
43
67
  var Diagnostics = class {
44
- constructor(limit) {
45
- this.limit = limit;
46
- }
47
- limit;
48
- values = [];
49
- limited = false;
50
- add(code) {
51
- if (this.limited) return;
52
- if (this.values.length + 1 < this.limit) {
53
- this.values.push(Object.freeze({ code, message: messageFor(code) }));
54
- return;
55
- }
56
- this.limited = true;
57
- this.values.push(
58
- Object.freeze({
59
- code: "source.diagnostic-limit",
60
- message: messageFor("source.diagnostic-limit")
61
- })
62
- );
63
- }
68
+ limit;
69
+ values = [];
70
+ limited = false;
71
+ constructor(limit) {
72
+ this.limit = limit;
73
+ }
74
+ add(code) {
75
+ if (this.limited) return;
76
+ if (this.values.length + 1 < this.limit) {
77
+ this.values.push(Object.freeze({
78
+ code,
79
+ message: messageFor(code)
80
+ }));
81
+ return;
82
+ }
83
+ this.limited = true;
84
+ this.values.push(Object.freeze({
85
+ code: "source.diagnostic-limit",
86
+ message: messageFor("source.diagnostic-limit")
87
+ }));
88
+ }
64
89
  };
65
90
  function messageFor(code) {
66
- switch (code) {
67
- case "source.invalid-json":
68
- return "The source is not valid JSON.";
69
- case "source.invalid-yaml":
70
- return "The source is not valid YAML.";
71
- case "source.invalid-policy":
72
- return "The source policy is invalid.";
73
- case "source.byte-limit":
74
- return "The source exceeds its byte limit.";
75
- case "source.declaration-limit":
76
- return "The source exceeds its declaration limit.";
77
- case "source.depth-limit":
78
- return "The source exceeds its nesting-depth limit.";
79
- case "source.string-limit":
80
- return "The source contains an overlong string.";
81
- case "source.diagnostic-limit":
82
- return "Additional source diagnostics were omitted.";
83
- case "source.unknown-key":
84
- return "The source contains an unknown key.";
85
- case "source.reserved-key":
86
- return "The source contains a reserved key.";
87
- case "source.accessor":
88
- return "The source must use data properties.";
89
- case "source.cyclic-value":
90
- return "The source must not contain cyclic values.";
91
- case "source.invalid-layer":
92
- return "The source layer is invalid.";
93
- case "source.invalid-declaration":
94
- return "The source declaration is invalid.";
95
- case "source.invalid-transform":
96
- return "The source transform is invalid.";
97
- case "source.forbidden-kind":
98
- return "The source requests a forbidden declaration kind.";
99
- case "source.forbidden-namespace":
100
- return "The source requests a forbidden namespace.";
101
- case "source.forbidden-transform-op":
102
- return "The source requests a forbidden transform operation.";
103
- case "source.forbidden-transform-scope":
104
- return "The source requests a forbidden transform scope.";
105
- case "source.forbidden-capability":
106
- return "The source requests a forbidden capability.";
107
- case "source.forbidden-action":
108
- return "The source requests a forbidden action binding.";
109
- case "source.forbidden-provider":
110
- return "The source requests a forbidden provider binding.";
111
- case "source.forbidden-mapper":
112
- return "The source requests a forbidden mapper binding.";
113
- case "source.forbidden-service":
114
- return "The source requests a forbidden service value.";
115
- case "source.forbidden-credential":
116
- return "The source requests a forbidden credential value.";
117
- case "source.forbidden-schema":
118
- return "The source requests a forbidden schema value.";
119
- case "source.forbidden-component":
120
- return "The source requests a forbidden component value.";
121
- case "source.forbidden-attachment":
122
- return "The source requests a forbidden attachment value.";
123
- case "source.forbidden-validator":
124
- return "The source requests a forbidden validator value.";
125
- default:
126
- return "The source is invalid.";
127
- }
91
+ switch (code) {
92
+ case "source.invalid-json": return "The source is not valid JSON.";
93
+ case "source.invalid-yaml": return "The source is not valid YAML.";
94
+ case "source.invalid-policy": return "The source policy is invalid.";
95
+ case "source.byte-limit": return "The source exceeds its byte limit.";
96
+ case "source.declaration-limit": return "The source exceeds its declaration limit.";
97
+ case "source.depth-limit": return "The source exceeds its nesting-depth limit.";
98
+ case "source.string-limit": return "The source contains an overlong string.";
99
+ case "source.diagnostic-limit": return "Additional source diagnostics were omitted.";
100
+ case "source.unknown-key": return "The source contains an unknown key.";
101
+ case "source.reserved-key": return "The source contains a reserved key.";
102
+ case "source.accessor": return "The source must use data properties.";
103
+ case "source.cyclic-value": return "The source must not contain cyclic values.";
104
+ case "source.invalid-layer": return "The source layer is invalid.";
105
+ case "source.invalid-declaration": return "The source declaration is invalid.";
106
+ case "source.invalid-transform": return "The source transform is invalid.";
107
+ case "source.forbidden-kind": return "The source requests a forbidden declaration kind.";
108
+ case "source.forbidden-namespace": return "The source requests a forbidden namespace.";
109
+ case "source.forbidden-transform-op": return "The source requests a forbidden transform operation.";
110
+ case "source.forbidden-transform-scope": return "The source requests a forbidden transform scope.";
111
+ case "source.forbidden-capability": return "The source requests a forbidden capability.";
112
+ case "source.forbidden-action": return "The source requests a forbidden action binding.";
113
+ case "source.forbidden-provider": return "The source requests a forbidden provider binding.";
114
+ case "source.forbidden-mapper": return "The source requests a forbidden mapper binding.";
115
+ case "source.forbidden-service": return "The source requests a forbidden service value.";
116
+ case "source.forbidden-credential": return "The source requests a forbidden credential value.";
117
+ case "source.forbidden-schema": return "The source requests a forbidden schema value.";
118
+ case "source.forbidden-component": return "The source requests a forbidden component value.";
119
+ case "source.forbidden-attachment": return "The source requests a forbidden attachment value.";
120
+ case "source.forbidden-validator": return "The source requests a forbidden validator value.";
121
+ default: return "The source is invalid.";
122
+ }
128
123
  }
129
124
  function validLimits(limits) {
130
- return Object.values(limits).every((value) => Number.isSafeInteger(value) && value > 0);
125
+ return Object.values(limits).every((value) => Number.isSafeInteger(value) && value > 0);
131
126
  }
132
127
  function validCapabilities(value) {
133
- return value !== null && typeof value === "object" && !Array.isArray(value) && Object.values(value).every(
134
- (capabilities) => Array.isArray(capabilities) && capabilities.every((capability) => typeof capability === "string")
135
- );
128
+ return value !== null && typeof value === "object" && !Array.isArray(value) && Object.values(value).every((capabilities) => Array.isArray(capabilities) && capabilities.every((capability) => typeof capability === "string"));
136
129
  }
137
130
  function validPolicy(policy) {
138
- return policy !== null && typeof policy === "object" && Array.isArray(policy.allowedKinds) && Array.isArray(policy.allowedNamespaces) && Array.isArray(policy.allowedTransformOps) && (policy.maxTransformScope === "layer" || policy.maxTransformScope === "namespace" || policy.maxTransformScope === "application") && validCapabilities(policy.allowedCapabilities) && validLimits(policy.limits);
131
+ return policy !== null && typeof policy === "object" && Array.isArray(policy.allowedKinds) && Array.isArray(policy.allowedNamespaces) && Array.isArray(policy.allowedTransformOps) && (policy.maxTransformScope === "layer" || policy.maxTransformScope === "namespace" || policy.maxTransformScope === "application") && validCapabilities(policy.allowedCapabilities) && validLimits(policy.limits);
139
132
  }
140
133
  function failure(diagnostics) {
141
- return { ok: false, diagnostics: Object.freeze(diagnostics.values) };
134
+ return {
135
+ ok: false,
136
+ diagnostics: Object.freeze(diagnostics.values)
137
+ };
142
138
  }
143
139
  function plainObject(value) {
144
- if (value === null || typeof value !== "object" || Array.isArray(value)) return false;
145
- const prototype = Object.getPrototypeOf(value);
146
- return prototype === Object.prototype || prototype === null;
140
+ if (value === null || typeof value !== "object" || Array.isArray(value)) return false;
141
+ const prototype = Object.getPrototypeOf(value);
142
+ return prototype === Object.prototype || prototype === null;
147
143
  }
148
144
  function ownData(value, key) {
149
- const descriptor = Object.getOwnPropertyDescriptor(value, key);
150
- return descriptor !== void 0 && "value" in descriptor ? descriptor.value : void 0;
145
+ const descriptor = Object.getOwnPropertyDescriptor(value, key);
146
+ return descriptor !== void 0 && "value" in descriptor ? descriptor.value : void 0;
151
147
  }
152
148
  function hasData(value, key) {
153
- const descriptor = Object.getOwnPropertyDescriptor(value, key);
154
- return descriptor !== void 0 && "value" in descriptor;
149
+ const descriptor = Object.getOwnPropertyDescriptor(value, key);
150
+ return descriptor !== void 0 && "value" in descriptor;
155
151
  }
156
152
  function clonePortable(value, limits, diagnostics) {
157
- const ancestors = /* @__PURE__ */ new WeakSet();
158
- function copy(current, depth) {
159
- if (depth > limits.maxDepth) {
160
- diagnostics.add("source.depth-limit");
161
- return null;
162
- }
163
- if (current === null || typeof current === "boolean" || typeof current === "number")
164
- return current;
165
- if (typeof current === "string") {
166
- if ([...current].length > limits.maxStringLength) diagnostics.add("source.string-limit");
167
- return current;
168
- }
169
- if (typeof current !== "object") {
170
- diagnostics.add("source.invalid-layer");
171
- return null;
172
- }
173
- if (ancestors.has(current)) {
174
- diagnostics.add("source.cyclic-value");
175
- return null;
176
- }
177
- ancestors.add(current);
178
- if (Array.isArray(current)) {
179
- const output2 = [];
180
- for (const key of Reflect.ownKeys(current)) {
181
- if (typeof key !== "string" || key !== "length" && !/^(0|[1-9]\d*)$/u.test(key)) {
182
- diagnostics.add("source.invalid-layer");
183
- continue;
184
- }
185
- if (key === "length") continue;
186
- if (!hasData(current, key)) diagnostics.add("source.accessor");
187
- }
188
- const length = ownData(current, "length");
189
- const arrayLength = typeof length === "number" && Number.isSafeInteger(length) && length >= 0 ? length : void 0;
190
- if (arrayLength === void 0) diagnostics.add("source.invalid-layer");
191
- else
192
- for (let index = 0; index < arrayLength; index += 1) {
193
- if (!hasData(current, String(index))) diagnostics.add("source.accessor");
194
- output2.push(copy(ownData(current, String(index)), depth + 1));
195
- }
196
- ancestors.delete(current);
197
- return Object.freeze(output2);
198
- }
199
- if (!plainObject(current)) diagnostics.add("source.invalid-layer");
200
- const output = /* @__PURE__ */ Object.create(null);
201
- for (const key of Reflect.ownKeys(current)) {
202
- if (typeof key !== "string") {
203
- diagnostics.add("source.invalid-layer");
204
- continue;
205
- }
206
- if (RESERVED_KEYS.has(key)) diagnostics.add("source.reserved-key");
207
- if ([...key].length > limits.maxStringLength) diagnostics.add("source.string-limit");
208
- if (!hasData(current, key)) {
209
- diagnostics.add("source.accessor");
210
- continue;
211
- }
212
- output[key] = copy(ownData(current, key), depth + 1);
213
- }
214
- ancestors.delete(current);
215
- return Object.freeze(output);
216
- }
217
- return copy(value, 0);
153
+ const ancestors = new WeakSet();
154
+ function copy(current, depth) {
155
+ if (depth > limits.maxDepth) {
156
+ diagnostics.add("source.depth-limit");
157
+ return null;
158
+ }
159
+ if (current === null || typeof current === "boolean" || typeof current === "number") return current;
160
+ if (typeof current === "string") {
161
+ if ([...current].length > limits.maxStringLength) diagnostics.add("source.string-limit");
162
+ return current;
163
+ }
164
+ if (typeof current !== "object") {
165
+ diagnostics.add("source.invalid-layer");
166
+ return null;
167
+ }
168
+ if (ancestors.has(current)) {
169
+ diagnostics.add("source.cyclic-value");
170
+ return null;
171
+ }
172
+ ancestors.add(current);
173
+ if (Array.isArray(current)) {
174
+ const output = [];
175
+ for (const key of Reflect.ownKeys(current)) {
176
+ if (typeof key !== "string" || key !== "length" && !/^(0|[1-9]\d*)$/u.test(key)) {
177
+ diagnostics.add("source.invalid-layer");
178
+ continue;
179
+ }
180
+ if (key === "length") continue;
181
+ if (!hasData(current, key)) diagnostics.add("source.accessor");
182
+ }
183
+ const length = ownData(current, "length");
184
+ const arrayLength = typeof length === "number" && Number.isSafeInteger(length) && length >= 0 ? length : void 0;
185
+ if (arrayLength === void 0) diagnostics.add("source.invalid-layer");
186
+ else for (let index = 0; index < arrayLength; index += 1) {
187
+ if (!hasData(current, String(index))) diagnostics.add("source.accessor");
188
+ output.push(copy(ownData(current, String(index)), depth + 1));
189
+ }
190
+ ancestors.delete(current);
191
+ return Object.freeze(output);
192
+ }
193
+ if (!plainObject(current)) diagnostics.add("source.invalid-layer");
194
+ const output = Object.create(null);
195
+ for (const key of Reflect.ownKeys(current)) {
196
+ if (typeof key !== "string") {
197
+ diagnostics.add("source.invalid-layer");
198
+ continue;
199
+ }
200
+ if (RESERVED_KEYS.has(key)) diagnostics.add("source.reserved-key");
201
+ if ([...key].length > limits.maxStringLength) diagnostics.add("source.string-limit");
202
+ if (!hasData(current, key)) {
203
+ diagnostics.add("source.accessor");
204
+ continue;
205
+ }
206
+ output[key] = copy(ownData(current, key), depth + 1);
207
+ }
208
+ ancestors.delete(current);
209
+ return Object.freeze(output);
210
+ }
211
+ return copy(value, 0);
218
212
  }
219
213
  function unknownKeys(value, allowed, diagnostics) {
220
- for (const key of Object.keys(value))
221
- if (!allowed.has(key)) diagnostics.add("source.unknown-key");
214
+ for (const key of Object.keys(value)) if (!allowed.has(key)) diagnostics.add("source.unknown-key");
222
215
  }
223
216
  function allowedNamespace(value, policy, diagnostics) {
224
- if (typeof value !== "string" || !policy.allowedNamespaces.includes(value)) {
225
- diagnostics.add("source.forbidden-namespace");
226
- return false;
227
- }
228
- return true;
217
+ if (typeof value !== "string" || !policy.allowedNamespaces.includes(value)) {
218
+ diagnostics.add("source.forbidden-namespace");
219
+ return false;
220
+ }
221
+ return true;
229
222
  }
230
223
  function namespaceFor(ref, defaultNamespace, diagnostics) {
231
- if (typeof ref === "string") {
232
- const separator = ref.indexOf(":");
233
- return separator === -1 ? defaultNamespace : ref.slice(0, separator);
234
- }
235
- if (!plainObject(ref) || !hasData(ref, "id")) {
236
- diagnostics.add("source.invalid-declaration");
237
- return void 0;
238
- }
239
- for (const key of Object.keys(ref))
240
- if (key !== "id" && key !== "namespace") diagnostics.add("source.unknown-key");
241
- const namespace = hasData(ref, "namespace") ? ownData(ref, "namespace") : defaultNamespace;
242
- if (typeof namespace !== "string") diagnostics.add("source.invalid-declaration");
243
- return typeof namespace === "string" ? namespace : void 0;
224
+ if (typeof ref === "string") {
225
+ const separator = ref.indexOf(":");
226
+ return separator === -1 ? defaultNamespace : ref.slice(0, separator);
227
+ }
228
+ if (!plainObject(ref) || !hasData(ref, "id")) {
229
+ diagnostics.add("source.invalid-declaration");
230
+ return;
231
+ }
232
+ for (const key of Object.keys(ref)) if (key !== "id" && key !== "namespace") diagnostics.add("source.unknown-key");
233
+ const namespace = hasData(ref, "namespace") ? ownData(ref, "namespace") : defaultNamespace;
234
+ if (typeof namespace !== "string") diagnostics.add("source.invalid-declaration");
235
+ return typeof namespace === "string" ? namespace : void 0;
244
236
  }
245
237
  function validateValue(value, kind, policy, diagnostics) {
246
- if (value === null || typeof value !== "object") return;
247
- if (Array.isArray(value)) {
248
- for (const item of value) validateValue(item, kind, policy, diagnostics);
249
- return;
250
- }
251
- if (!plainObject(value)) return;
252
- if (value.$buro === ATTACHMENT_TAG) {
253
- const capability = ownData(value, "capability");
254
- if (typeof capability !== "string" || !policy.allowedCapabilities[kind]?.includes(capability)) {
255
- diagnostics.add("source.forbidden-capability");
256
- }
257
- }
258
- for (const key of Object.keys(value)) {
259
- const category = FORBIDDEN_VALUE_CATEGORIES.get(key);
260
- if (category !== void 0) diagnostics.add(`source.forbidden-${category}`);
261
- validateValue(ownData(value, key), kind, policy, diagnostics);
262
- }
238
+ if (value === null || typeof value !== "object") return;
239
+ if (Array.isArray(value)) {
240
+ for (const item of value) validateValue(item, kind, policy, diagnostics);
241
+ return;
242
+ }
243
+ if (!plainObject(value)) return;
244
+ if (value.$buro === ATTACHMENT_TAG) {
245
+ const capability = ownData(value, "capability");
246
+ if (typeof capability !== "string" || !policy.allowedCapabilities[kind]?.includes(capability)) diagnostics.add("source.forbidden-capability");
247
+ }
248
+ for (const key of Object.keys(value)) {
249
+ const category = FORBIDDEN_VALUE_CATEGORIES.get(key);
250
+ if (category !== void 0) diagnostics.add(`source.forbidden-${category}`);
251
+ validateValue(ownData(value, key), kind, policy, diagnostics);
252
+ }
263
253
  }
264
254
  function scopeRank(scope) {
265
- return scope === "layer" ? 0 : scope === "namespace" ? 1 : 2;
255
+ return scope === "layer" ? 0 : scope === "namespace" ? 1 : 2;
266
256
  }
267
257
  function transformOperation(value) {
268
- if (!plainObject(value)) return void 0;
269
- const operation = ownData(value, "op");
270
- return operation === "merge" || operation === "replace" || operation === "disable" || operation === "delete" ? operation : void 0;
258
+ if (!plainObject(value)) return void 0;
259
+ const operation = ownData(value, "op");
260
+ return operation === "merge" || operation === "replace" || operation === "disable" || operation === "delete" ? operation : void 0;
271
261
  }
272
262
  function validateSelectorRefs(value, defaultNamespace, policy, diagnostics) {
273
- if (value === void 0) return;
274
- if (!Array.isArray(value)) {
275
- diagnostics.add("source.invalid-transform");
276
- return;
277
- }
278
- for (const ref of value) {
279
- const namespace = namespaceFor(ref, defaultNamespace, diagnostics);
280
- if (namespace !== void 0) allowedNamespace(namespace, policy, diagnostics);
281
- }
263
+ if (value === void 0) return;
264
+ if (!Array.isArray(value)) {
265
+ diagnostics.add("source.invalid-transform");
266
+ return;
267
+ }
268
+ for (const ref of value) {
269
+ const namespace = namespaceFor(ref, defaultNamespace, diagnostics);
270
+ if (namespace !== void 0) allowedNamespace(namespace, policy, diagnostics);
271
+ }
282
272
  }
283
273
  function validateTransforms(value, defaultNamespace, policy, diagnostics) {
284
- if (value === void 0) return;
285
- if (!Array.isArray(value)) {
286
- diagnostics.add("source.invalid-transform");
287
- return;
288
- }
289
- for (const transform of value) {
290
- if (!plainObject(transform)) {
291
- diagnostics.add("source.invalid-transform");
292
- continue;
293
- }
294
- unknownKeys(transform, TRANSFORM_KEYS, diagnostics);
295
- const scope = ownData(transform, "scope") ?? "layer";
296
- if (scope !== "layer" && scope !== "application") diagnostics.add("source.invalid-transform");
297
- else if (scopeRank(scope) > scopeRank(policy.maxTransformScope))
298
- diagnostics.add("source.forbidden-transform-scope");
299
- const select = ownData(transform, "select");
300
- if (!plainObject(select)) diagnostics.add("source.invalid-transform");
301
- else {
302
- unknownKeys(select, SELECTOR_KEYS, diagnostics);
303
- const selectedKinds = ownData(select, "kinds");
304
- if (selectedKinds !== void 0) {
305
- if (!Array.isArray(selectedKinds)) diagnostics.add("source.invalid-transform");
306
- else
307
- for (const kind of selectedKinds) {
308
- if (typeof kind !== "string") diagnostics.add("source.invalid-transform");
309
- else if (!policy.allowedKinds.includes(kind)) diagnostics.add("source.forbidden-kind");
310
- }
311
- }
312
- const selectedNamespaces = ownData(select, "namespaces");
313
- if (selectedNamespaces !== void 0) {
314
- if (!Array.isArray(selectedNamespaces)) diagnostics.add("source.invalid-transform");
315
- else
316
- for (const namespace of selectedNamespaces)
317
- allowedNamespace(namespace, policy, diagnostics);
318
- }
319
- validateSelectorRefs(ownData(select, "refs"), defaultNamespace, policy, diagnostics);
320
- validateSelectorRefs(ownData(select, "excludeRefs"), defaultNamespace, policy, diagnostics);
321
- }
322
- const operation = ownData(transform, "operation");
323
- const op = transformOperation(operation);
324
- const rawOp = plainObject(operation) ? ownData(operation, "op") : void 0;
325
- if (typeof rawOp === "string" && op === void 0)
326
- diagnostics.add("source.forbidden-transform-op");
327
- else if (op === void 0) diagnostics.add("source.invalid-transform");
328
- else {
329
- if (!policy.allowedTransformOps.includes(op))
330
- diagnostics.add("source.forbidden-transform-op");
331
- if (plainObject(operation)) {
332
- unknownKeys(operation, OPERATION_KEYS[op], diagnostics);
333
- if (hasData(operation, "value"))
334
- validateValue(ownData(operation, "value"), "", policy, diagnostics);
335
- }
336
- }
337
- }
274
+ if (value === void 0) return;
275
+ if (!Array.isArray(value)) {
276
+ diagnostics.add("source.invalid-transform");
277
+ return;
278
+ }
279
+ for (const transform of value) {
280
+ if (!plainObject(transform)) {
281
+ diagnostics.add("source.invalid-transform");
282
+ continue;
283
+ }
284
+ unknownKeys(transform, TRANSFORM_KEYS, diagnostics);
285
+ const scope = ownData(transform, "scope") ?? "layer";
286
+ if (scope !== "layer" && scope !== "application") diagnostics.add("source.invalid-transform");
287
+ else if (scopeRank(scope) > scopeRank(policy.maxTransformScope)) diagnostics.add("source.forbidden-transform-scope");
288
+ const select = ownData(transform, "select");
289
+ if (!plainObject(select)) diagnostics.add("source.invalid-transform");
290
+ else {
291
+ unknownKeys(select, SELECTOR_KEYS, diagnostics);
292
+ const selectedKinds = ownData(select, "kinds");
293
+ if (selectedKinds !== void 0) {
294
+ if (!Array.isArray(selectedKinds)) diagnostics.add("source.invalid-transform");
295
+ else for (const kind of selectedKinds) if (typeof kind !== "string") diagnostics.add("source.invalid-transform");
296
+ else if (!policy.allowedKinds.includes(kind)) diagnostics.add("source.forbidden-kind");
297
+ }
298
+ const selectedNamespaces = ownData(select, "namespaces");
299
+ if (selectedNamespaces !== void 0) {
300
+ if (!Array.isArray(selectedNamespaces)) diagnostics.add("source.invalid-transform");
301
+ else for (const namespace of selectedNamespaces) allowedNamespace(namespace, policy, diagnostics);
302
+ }
303
+ validateSelectorRefs(ownData(select, "refs"), defaultNamespace, policy, diagnostics);
304
+ validateSelectorRefs(ownData(select, "excludeRefs"), defaultNamespace, policy, diagnostics);
305
+ }
306
+ const operation = ownData(transform, "operation");
307
+ const op = transformOperation(operation);
308
+ if (typeof (plainObject(operation) ? ownData(operation, "op") : void 0) === "string" && op === void 0) diagnostics.add("source.forbidden-transform-op");
309
+ else if (op === void 0) diagnostics.add("source.invalid-transform");
310
+ else {
311
+ if (!policy.allowedTransformOps.includes(op)) diagnostics.add("source.forbidden-transform-op");
312
+ if (plainObject(operation)) {
313
+ unknownKeys(operation, OPERATION_KEYS[op], diagnostics);
314
+ if (hasData(operation, "value")) validateValue(ownData(operation, "value"), "", policy, diagnostics);
315
+ }
316
+ }
317
+ }
338
318
  }
339
319
  function validateLayerValue(value, policy) {
340
- if (!validPolicy(policy)) {
341
- return {
342
- ok: false,
343
- diagnostics: Object.freeze([
344
- Object.freeze({
345
- code: "source.invalid-policy",
346
- message: messageFor("source.invalid-policy")
347
- })
348
- ])
349
- };
350
- }
351
- const diagnostics = new Diagnostics(policy.limits.maxDiagnostics);
352
- const cloned = clonePortable(value, policy.limits, diagnostics);
353
- if (diagnostics.values.length > 0) return failure(diagnostics);
354
- if (!plainObject(cloned)) {
355
- diagnostics.add("source.invalid-layer");
356
- return failure(diagnostics);
357
- }
358
- unknownKeys(cloned, LAYER_KEYS, diagnostics);
359
- const id = ownData(cloned, "id");
360
- const priority = ownData(cloned, "priority");
361
- const declarations = ownData(cloned, "declarations");
362
- if (typeof id !== "string" || !Number.isSafeInteger(priority) || !Array.isArray(declarations)) {
363
- diagnostics.add("source.invalid-layer");
364
- return failure(diagnostics);
365
- }
366
- if (declarations.length > policy.limits.maxDeclarations)
367
- diagnostics.add("source.declaration-limit");
368
- const rawDefaultNamespace = ownData(cloned, "defaultNamespace");
369
- const defaultNamespace = rawDefaultNamespace === void 0 ? "default" : rawDefaultNamespace;
370
- if (typeof defaultNamespace !== "string") diagnostics.add("source.invalid-layer");
371
- else allowedNamespace(defaultNamespace, policy, diagnostics);
372
- for (const declaration of declarations) {
373
- if (!plainObject(declaration)) {
374
- diagnostics.add("source.invalid-declaration");
375
- continue;
376
- }
377
- unknownKeys(declaration, DECLARATION_KEYS, diagnostics);
378
- const kind = ownData(declaration, "kind");
379
- if (typeof kind !== "string") diagnostics.add("source.invalid-declaration");
380
- else if (!policy.allowedKinds.includes(kind)) diagnostics.add("source.forbidden-kind");
381
- const namespace = namespaceFor(
382
- ownData(declaration, "ref"),
383
- typeof defaultNamespace === "string" ? defaultNamespace : "default",
384
- diagnostics
385
- );
386
- if (namespace !== void 0) allowedNamespace(namespace, policy, diagnostics);
387
- if (!Number.isSafeInteger(ownData(declaration, "schemaVersion")) || !hasData(declaration, "value")) {
388
- diagnostics.add("source.invalid-declaration");
389
- }
390
- if (typeof kind === "string" && hasData(declaration, "value")) {
391
- validateValue(ownData(declaration, "value"), kind, policy, diagnostics);
392
- }
393
- }
394
- validateTransforms(
395
- ownData(cloned, "transforms"),
396
- typeof defaultNamespace === "string" ? defaultNamespace : "default",
397
- policy,
398
- diagnostics
399
- );
400
- if (diagnostics.values.length > 0) return failure(diagnostics);
401
- return { ok: true, value: cloned };
320
+ if (!validPolicy(policy)) return {
321
+ ok: false,
322
+ diagnostics: Object.freeze([Object.freeze({
323
+ code: "source.invalid-policy",
324
+ message: messageFor("source.invalid-policy")
325
+ })])
326
+ };
327
+ const diagnostics = new Diagnostics(policy.limits.maxDiagnostics);
328
+ const cloned = clonePortable(value, policy.limits, diagnostics);
329
+ if (diagnostics.values.length > 0) return failure(diagnostics);
330
+ if (!plainObject(cloned)) {
331
+ diagnostics.add("source.invalid-layer");
332
+ return failure(diagnostics);
333
+ }
334
+ unknownKeys(cloned, LAYER_KEYS, diagnostics);
335
+ const id = ownData(cloned, "id");
336
+ const priority = ownData(cloned, "priority");
337
+ const declarations = ownData(cloned, "declarations");
338
+ if (typeof id !== "string" || !Number.isSafeInteger(priority) || !Array.isArray(declarations)) {
339
+ diagnostics.add("source.invalid-layer");
340
+ return failure(diagnostics);
341
+ }
342
+ if (declarations.length > policy.limits.maxDeclarations) diagnostics.add("source.declaration-limit");
343
+ const rawDefaultNamespace = ownData(cloned, "defaultNamespace");
344
+ const defaultNamespace = rawDefaultNamespace === void 0 ? "default" : rawDefaultNamespace;
345
+ if (typeof defaultNamespace !== "string") diagnostics.add("source.invalid-layer");
346
+ else allowedNamespace(defaultNamespace, policy, diagnostics);
347
+ for (const declaration of declarations) {
348
+ if (!plainObject(declaration)) {
349
+ diagnostics.add("source.invalid-declaration");
350
+ continue;
351
+ }
352
+ unknownKeys(declaration, DECLARATION_KEYS, diagnostics);
353
+ const kind = ownData(declaration, "kind");
354
+ if (typeof kind !== "string") diagnostics.add("source.invalid-declaration");
355
+ else if (!policy.allowedKinds.includes(kind)) diagnostics.add("source.forbidden-kind");
356
+ const namespace = namespaceFor(ownData(declaration, "ref"), typeof defaultNamespace === "string" ? defaultNamespace : "default", diagnostics);
357
+ if (namespace !== void 0) allowedNamespace(namespace, policy, diagnostics);
358
+ if (!Number.isSafeInteger(ownData(declaration, "schemaVersion")) || !hasData(declaration, "value")) diagnostics.add("source.invalid-declaration");
359
+ if (typeof kind === "string" && hasData(declaration, "value")) validateValue(ownData(declaration, "value"), kind, policy, diagnostics);
360
+ }
361
+ validateTransforms(ownData(cloned, "transforms"), typeof defaultNamespace === "string" ? defaultNamespace : "default", policy, diagnostics);
362
+ if (diagnostics.values.length > 0) return failure(diagnostics);
363
+ return {
364
+ ok: true,
365
+ value: cloned
366
+ };
402
367
  }
403
368
  function byteLength(value) {
404
- return new TextEncoder().encode(value).byteLength;
369
+ return new TextEncoder().encode(value).byteLength;
405
370
  }
406
371
  function parseSource(source, policy, format) {
407
- if (!validPolicy(policy)) return validateLayerValue(null, policy);
408
- const diagnostics = new Diagnostics(policy.limits.maxDiagnostics);
409
- if (byteLength(source) > policy.limits.maxBytes) {
410
- diagnostics.add("source.byte-limit");
411
- return failure(diagnostics);
412
- }
413
- try {
414
- if (format === "json") return validateLayerValue(JSON.parse(source), policy);
415
- const document = parseDocument(source, { prettyErrors: false, strict: true, uniqueKeys: true });
416
- if (document.errors.length > 0) {
417
- diagnostics.add("source.invalid-yaml");
418
- return failure(diagnostics);
419
- }
420
- return validateLayerValue(document.toJS({ maxAliasCount: 0 }), policy);
421
- } catch {
422
- diagnostics.add(format === "json" ? "source.invalid-json" : "source.invalid-yaml");
423
- return failure(diagnostics);
424
- }
372
+ if (!validPolicy(policy)) return validateLayerValue(null, policy);
373
+ const diagnostics = new Diagnostics(policy.limits.maxDiagnostics);
374
+ if (byteLength(source) > policy.limits.maxBytes) {
375
+ diagnostics.add("source.byte-limit");
376
+ return failure(diagnostics);
377
+ }
378
+ try {
379
+ if (format === "json") return validateLayerValue(JSON.parse(source), policy);
380
+ const document = parseDocument(source, {
381
+ prettyErrors: false,
382
+ strict: true,
383
+ uniqueKeys: true
384
+ });
385
+ if (document.errors.length > 0) {
386
+ diagnostics.add("source.invalid-yaml");
387
+ return failure(diagnostics);
388
+ }
389
+ return validateLayerValue(document.toJS({ maxAliasCount: 0 }), policy);
390
+ } catch {
391
+ diagnostics.add(format === "json" ? "source.invalid-json" : "source.invalid-yaml");
392
+ return failure(diagnostics);
393
+ }
425
394
  }
426
395
  function parseJsonLayer(source, policy) {
427
- return parseSource(source, policy, "json");
396
+ return parseSource(source, policy, "json");
428
397
  }
429
398
  function parseYamlLayer(source, policy) {
430
- return parseSource(source, policy, "yaml");
399
+ return parseSource(source, policy, "yaml");
431
400
  }
432
-
433
- // src/adapter.ts
401
+ //#endregion
402
+ //#region src/adapter.ts
434
403
  function diagnostic(code, message) {
435
- return Object.freeze({ code, message });
404
+ return Object.freeze({
405
+ code,
406
+ message
407
+ });
436
408
  }
437
409
  function diagnosticLimit(policy) {
438
- const candidate = policy?.limits?.maxDiagnostics;
439
- return typeof candidate === "number" && Number.isSafeInteger(candidate) && candidate > 0 ? candidate : 1;
410
+ const candidate = policy?.limits?.maxDiagnostics;
411
+ return typeof candidate === "number" && Number.isSafeInteger(candidate) && candidate > 0 ? candidate : 1;
440
412
  }
441
413
  function frozenPolicy(policy) {
442
- const capabilities = /* @__PURE__ */ Object.create(null);
443
- for (const [kind, values] of Object.entries(policy.allowedCapabilities)) {
444
- capabilities[kind] = Object.freeze([...values]);
445
- }
446
- const limits = Object.freeze({ ...policy.limits });
447
- return Object.freeze({
448
- allowedKinds: Object.freeze([...policy.allowedKinds]),
449
- allowedNamespaces: Object.freeze([...policy.allowedNamespaces]),
450
- allowedTransformOps: Object.freeze([...policy.allowedTransformOps]),
451
- maxTransformScope: policy.maxTransformScope,
452
- allowedCapabilities: Object.freeze(capabilities),
453
- limits
454
- });
414
+ const capabilities = Object.create(null);
415
+ for (const [kind, values] of Object.entries(policy.allowedCapabilities)) capabilities[kind] = Object.freeze([...values]);
416
+ const limits = Object.freeze({ ...policy.limits });
417
+ return Object.freeze({
418
+ allowedKinds: Object.freeze([...policy.allowedKinds]),
419
+ allowedNamespaces: Object.freeze([...policy.allowedNamespaces]),
420
+ allowedTransformOps: Object.freeze([...policy.allowedTransformOps]),
421
+ maxTransformScope: policy.maxTransformScope,
422
+ allowedCapabilities: Object.freeze(capabilities),
423
+ limits
424
+ });
455
425
  }
456
426
  function copyDiagnostic(value) {
457
- if (value !== null && typeof value === "object" && typeof value.code === "string" && typeof value.message === "string") {
458
- return diagnostic(
459
- value.code,
460
- value.message
461
- );
462
- }
463
- return diagnostic(
464
- "source.invalid-adapter-diagnostic",
465
- "The source adapter returned an invalid diagnostic."
466
- );
427
+ if (value !== null && typeof value === "object" && typeof value.code === "string" && typeof value.message === "string") return diagnostic(value.code, value.message);
428
+ return diagnostic("source.invalid-adapter-diagnostic", "The source adapter returned an invalid diagnostic.");
467
429
  }
468
430
  function adaptRawConfig(input, adapter, policy) {
469
- const policyValidation = validateLayerValue(null, policy);
470
- if (!policyValidation.ok && policyValidation.diagnostics.some((entry) => entry.code === "source.invalid-policy")) {
471
- return policyValidation;
472
- }
473
- const ownedPolicy = frozenPolicy(policy);
474
- const diagnostics = [];
475
- const maxDiagnostics = diagnosticLimit(ownedPolicy);
476
- let limited = false;
477
- const add = (value) => {
478
- if (limited) return;
479
- if (diagnostics.length + 1 < maxDiagnostics) {
480
- diagnostics.push(value);
481
- return;
482
- }
483
- limited = true;
484
- diagnostics.push(
485
- diagnostic("source.diagnostic-limit", "Additional source diagnostics were omitted.")
486
- );
487
- };
488
- const context = Object.freeze({
489
- policy: ownedPolicy,
490
- limits: ownedPolicy.limits,
491
- diagnose(code, message) {
492
- add(copyDiagnostic({ code, message }));
493
- }
494
- });
495
- const result = adapter.adapt(input, context);
496
- if (result === null || typeof result !== "object") {
497
- add(
498
- diagnostic("source.invalid-adapter-result", "The source adapter returned an invalid result.")
499
- );
500
- } else if (result.diagnostics !== void 0) {
501
- if (!Array.isArray(result.diagnostics)) {
502
- add(
503
- diagnostic(
504
- "source.invalid-adapter-result",
505
- "The source adapter returned an invalid result."
506
- )
507
- );
508
- } else {
509
- for (const entry of result.diagnostics) add(copyDiagnostic(entry));
510
- }
511
- }
512
- if (diagnostics.length > 0) {
513
- return { ok: false, diagnostics: Object.freeze(diagnostics) };
514
- }
515
- if (result === null || typeof result !== "object" || result.layer === void 0) {
516
- return {
517
- ok: false,
518
- diagnostics: Object.freeze([
519
- diagnostic(
520
- "source.invalid-adapter-result",
521
- "The source adapter did not return a declaration layer."
522
- )
523
- ])
524
- };
525
- }
526
- return validateLayerValue(result.layer, ownedPolicy);
431
+ const policyValidation = validateLayerValue(null, policy);
432
+ if (!policyValidation.ok && policyValidation.diagnostics.some((entry) => entry.code === "source.invalid-policy")) return policyValidation;
433
+ const ownedPolicy = frozenPolicy(policy);
434
+ const diagnostics = [];
435
+ const maxDiagnostics = diagnosticLimit(ownedPolicy);
436
+ let limited = false;
437
+ const add = (value) => {
438
+ if (limited) return;
439
+ if (diagnostics.length + 1 < maxDiagnostics) {
440
+ diagnostics.push(value);
441
+ return;
442
+ }
443
+ limited = true;
444
+ diagnostics.push(diagnostic("source.diagnostic-limit", "Additional source diagnostics were omitted."));
445
+ };
446
+ const context = Object.freeze({
447
+ policy: ownedPolicy,
448
+ limits: ownedPolicy.limits,
449
+ diagnose(code, message) {
450
+ add(copyDiagnostic({
451
+ code,
452
+ message
453
+ }));
454
+ }
455
+ });
456
+ const result = adapter.adapt(input, context);
457
+ if (result === null || typeof result !== "object") add(diagnostic("source.invalid-adapter-result", "The source adapter returned an invalid result."));
458
+ else if (result.diagnostics !== void 0) {
459
+ if (!Array.isArray(result.diagnostics)) add(diagnostic("source.invalid-adapter-result", "The source adapter returned an invalid result."));
460
+ else for (const entry of result.diagnostics) add(copyDiagnostic(entry));
461
+ }
462
+ if (diagnostics.length > 0) return {
463
+ ok: false,
464
+ diagnostics: Object.freeze(diagnostics)
465
+ };
466
+ if (result === null || typeof result !== "object" || result.layer === void 0) return {
467
+ ok: false,
468
+ diagnostics: Object.freeze([diagnostic("source.invalid-adapter-result", "The source adapter did not return a declaration layer.")])
469
+ };
470
+ return validateLayerValue(result.layer, ownedPolicy);
527
471
  }
528
- var parseResultAdapter = Object.freeze({
529
- adapt(input) {
530
- return input.ok ? { layer: input.value } : { diagnostics: input.diagnostics };
531
- }
532
- });
533
-
534
- // src/runtime-source.ts
472
+ const parseResultAdapter = Object.freeze({ adapt(input) {
473
+ return input.ok ? { layer: input.value } : { diagnostics: input.diagnostics };
474
+ } });
475
+ //#endregion
476
+ //#region src/runtime-source.ts
535
477
  function adaptationFailure(diagnostics) {
536
- return Object.freeze({
537
- status: "rejected",
538
- diagnostics: Object.freeze(
539
- diagnostics.map((entry) => Object.freeze({ code: entry.code, message: entry.message }))
540
- )
541
- });
478
+ return Object.freeze({
479
+ status: "rejected",
480
+ diagnostics: Object.freeze(diagnostics.map((entry) => Object.freeze({
481
+ code: entry.code,
482
+ message: entry.message
483
+ })))
484
+ });
542
485
  }
543
486
  function createConfigRuntimeSource(id, fetchRaw, adapter, policy) {
544
- return Object.freeze({
545
- id,
546
- async load(context) {
547
- const raw = await fetchRaw(context);
548
- const adapted = adaptRawConfig(raw, adapter, policy);
549
- if (!adapted.ok) return adaptationFailure(adapted.diagnostics);
550
- return adapted.value;
551
- }
552
- });
487
+ return Object.freeze({
488
+ id,
489
+ async load(context) {
490
+ const adapted = adaptRawConfig(await fetchRaw(context), adapter, policy);
491
+ if (!adapted.ok) return adaptationFailure(adapted.diagnostics);
492
+ return adapted.value;
493
+ }
494
+ });
553
495
  }
554
-
496
+ //#endregion
555
497
  export { adaptRawConfig, createConfigRuntimeSource, parseJsonLayer, parseResultAdapter, parseYamlLayer };
556
- //# sourceMappingURL=index.js.map
498
+
557
499
  //# sourceMappingURL=index.js.map