@spottoai/types-package 1.0.2-beta.360 → 1.0.2-beta.361
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/README.md +28 -0
- package/dist/azure/billingArtifactCanonicalization.d.ts +3 -1
- package/dist/azure/billingArtifactCanonicalization.d.ts.map +1 -1
- package/dist/azure/billingArtifactCanonicalization.js +123 -43
- package/dist/azure/billingArtifactCanonicalization.js.map +1 -1
- package/dist/azure/billingArtifactGeneration.d.ts +53 -1
- package/dist/azure/billingArtifactGeneration.d.ts.map +1 -1
- package/dist/azure/billingArtifactGeneration.js +190 -25
- package/dist/azure/billingArtifactGeneration.js.map +1 -1
- package/dist/azure/billingArtifactLimits.d.ts +19 -0
- package/dist/azure/billingArtifactLimits.d.ts.map +1 -0
- package/dist/azure/billingArtifactLimits.js +22 -0
- package/dist/azure/billingArtifactLimits.js.map +1 -0
- package/dist/azure/billingPlots.d.ts +26 -3
- package/dist/azure/billingPlots.d.ts.map +1 -1
- package/dist/azure/billingPlots.js +257 -10
- package/dist/azure/billingPlots.js.map +1 -1
- package/dist/azure/views.d.ts.map +1 -1
- package/dist/azure/views.js +15 -3
- package/dist/azure/views.js.map +1 -1
- package/dist/common/artifactControlData.d.ts +16 -2
- package/dist/common/artifactControlData.d.ts.map +1 -1
- package/dist/common/artifactControlData.js +129 -23
- package/dist/common/artifactControlData.js.map +1 -1
- package/dist/esm/azure/billingArtifactCanonicalization.js +121 -42
- package/dist/esm/azure/billingArtifactGeneration.js +186 -25
- package/dist/esm/azure/billingArtifactLimits.js +18 -0
- package/dist/esm/azure/billingPlots.js +253 -10
- package/dist/esm/azure/views.js +16 -4
- package/dist/esm/common/artifactControlData.js +127 -22
- package/dist/esm/index.js +1 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/package.json +4 -2
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"artifactControlData.d.ts","sourceRoot":"","sources":["../../src/common/artifactControlData.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"artifactControlData.d.ts","sourceRoot":"","sources":["../../src/common/artifactControlData.ts"],"names":[],"mappings":"AAgDA,eAAO,MAAM,uCAAuC,SAAU,CAAC;AAE/D,MAAM,WAAW,6BAA6B;IAC5C,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAChC,GAAG,EAAE,MAAM,CAAC;IACZ,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,2BAA2B,CAAC,EAAE,OAAO,CAAC;IACtC,eAAe,CAAC,EAAE,OAAO,CAAC;IAC1B,iBAAiB,CAAC,EAAE,OAAO,CAAC;IAC5B,wBAAwB,CAAC,EAAE,OAAO,CAAC;CACpC;AAED,UAAU,+BAA+B;IACvC,sBAAsB,CAAC,EAAE,OAAO,CAAC;IACjC,2BAA2B,CAAC,EAAE,OAAO,CAAC;IACtC,sBAAsB,CAAC,EAAE,WAAW,CAAC,MAAM,CAAC,CAAC;IAC7C,mCAAmC,CAAC,EAAE,OAAO,CAAC;CAC/C;AAkCD,2FAA2F;AAC3F,eAAO,MAAM,6BAA6B,GAAI,QAAQ,OAAO,EAAE,KAAK,MAAM,KAAG,6BAA6B,EAC/D,CAAC;AAE5C,iGAAiG;AACjG,eAAO,MAAM,4BAA4B,GAAI,QAAQ,OAAO,EAAE,KAAK,MAAM,KAAG,6BAA6B,EACxC,CAAC;AAElE,4FAA4F;AAC5F,eAAO,MAAM,6BAA6B,GAAI,QAAQ,OAAO,EAAE,KAAK,MAAM,KAAG,6BAA6B,EAC/B,CAAC;AAoI5E,sGAAsG;AACtG,eAAO,MAAM,oCAAoC,GAC/C,OAAO,OAAO,EACd,yBAAwB,6BAA6B,EAAO,EAC5D,UAAS,+BAAoC,KAC5C,OAA4H,CAAC"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.containsForbiddenArtifactControlData = exports.allowedArtifactIdentityField = exports.allowedArtifactReferenceField = void 0;
|
|
3
|
+
exports.containsForbiddenArtifactControlData = exports.allowedArtifactTraversalField = exports.allowedArtifactIdentityField = exports.allowedArtifactReferenceField = exports.ARTIFACT_CONTROL_DATA_MAX_VISITED_NODES = void 0;
|
|
4
4
|
const FORBIDDEN_SENSITIVE_FIELDS = new Set([
|
|
5
5
|
'accountkey',
|
|
6
6
|
'accesskey',
|
|
@@ -18,6 +18,7 @@ const FORBIDDEN_SENSITIVE_FIELDS = new Set([
|
|
|
18
18
|
'sharedaccesssignature',
|
|
19
19
|
'token',
|
|
20
20
|
]);
|
|
21
|
+
const FORBIDDEN_PROTOTYPE_FIELDS = new Set(['proto', 'prototype', 'constructor']);
|
|
21
22
|
const PHYSICAL_REFERENCE_FIELDS = new Set([
|
|
22
23
|
'artifactpath',
|
|
23
24
|
'blobpath',
|
|
@@ -46,13 +47,16 @@ const PHYSICAL_REFERENCE_FIELDS = new Set([
|
|
|
46
47
|
]);
|
|
47
48
|
const PERCENT_ENCODED_BYTE_PATTERN = /%[0-9A-Fa-f]{2}/;
|
|
48
49
|
const URI_SCHEME_PATTERN = /^[A-Za-z][A-Za-z0-9+.-]*:/;
|
|
50
|
+
const SHA256_PATTERN = /^[0-9A-Fa-f]{64}$/;
|
|
51
|
+
exports.ARTIFACT_CONTROL_DATA_MAX_VISITED_NODES = 100000;
|
|
49
52
|
const isRecord = (value) => typeof value === 'object' && value !== null && !Array.isArray(value);
|
|
50
53
|
const hasControlCharacters = (value) => Array.from(value).some(character => character.charCodeAt(0) < 32 || character.charCodeAt(0) === 127);
|
|
51
54
|
const normalizeFieldName = (key) => key.replace(/[-_\s]/g, '').toLowerCase();
|
|
52
55
|
const hasDotTraversal = (value) => value.split(/[\\/]/).some(segment => segment === '.' || segment === '..');
|
|
53
|
-
const isForbiddenReferenceValue = (value, allowUriScheme = false) => hasControlCharacters(value) ||
|
|
56
|
+
const isForbiddenReferenceValue = (value, allowUriScheme = false, allowDigestLike = false, rejectDigestLikeValues = false) => hasControlCharacters(value) ||
|
|
54
57
|
PERCENT_ENCODED_BYTE_PATTERN.test(value) ||
|
|
55
58
|
(!allowUriScheme && URI_SCHEME_PATTERN.test(value)) ||
|
|
59
|
+
(rejectDigestLikeValues && !allowDigestLike && SHA256_PATTERN.test(value)) ||
|
|
56
60
|
value.startsWith('/') ||
|
|
57
61
|
value.startsWith('\\\\') ||
|
|
58
62
|
/^[A-Za-z]:[\\/]/.test(value) ||
|
|
@@ -74,29 +78,131 @@ exports.allowedArtifactReferenceField = allowedArtifactReferenceField;
|
|
|
74
78
|
/** Marks a structurally validated identity field whose value is allowed by its owning schema. */
|
|
75
79
|
const allowedArtifactIdentityField = (object, key) => isRecord(object) ? [{ object, key, allowUriScheme: true }] : [];
|
|
76
80
|
exports.allowedArtifactIdentityField = allowedArtifactIdentityField;
|
|
77
|
-
/**
|
|
78
|
-
const
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
const
|
|
89
|
-
|
|
81
|
+
/** Marks an exact schema edge whose descendants may use object-indexed field allowances. */
|
|
82
|
+
const allowedArtifactTraversalField = (object, key) => isRecord(object) ? [{ object, key, allowChildArtifactFields: true }] : [];
|
|
83
|
+
exports.allowedArtifactTraversalField = allowedArtifactTraversalField;
|
|
84
|
+
const indexAllowedArtifactFields = (allowedReferenceFields) => {
|
|
85
|
+
const index = new WeakMap();
|
|
86
|
+
for (const field of allowedReferenceFields) {
|
|
87
|
+
let objectFields = index.get(field.object);
|
|
88
|
+
if (!objectFields) {
|
|
89
|
+
objectFields = new Map();
|
|
90
|
+
index.set(field.object, objectFields);
|
|
91
|
+
}
|
|
92
|
+
const existing = objectFields.get(field.key);
|
|
93
|
+
objectFields.set(field.key, {
|
|
94
|
+
object: field.object,
|
|
95
|
+
key: field.key,
|
|
96
|
+
allowUriScheme: existing?.allowUriScheme || field.allowUriScheme,
|
|
97
|
+
allowUriSchemeInStringArray: existing?.allowUriSchemeInStringArray || field.allowUriSchemeInStringArray,
|
|
98
|
+
allowDigestLike: existing?.allowDigestLike || field.allowDigestLike,
|
|
99
|
+
allowControlField: existing?.allowControlField || field.allowControlField,
|
|
100
|
+
allowChildArtifactFields: existing?.allowChildArtifactFields || field.allowChildArtifactFields,
|
|
101
|
+
});
|
|
102
|
+
}
|
|
103
|
+
return index;
|
|
104
|
+
};
|
|
105
|
+
const containsForbiddenArtifactControlDataWithIndex = (value, allowedReferenceFields, options) => {
|
|
106
|
+
const pending = [{ kind: 'visit', value, allowIndexedFields: true }];
|
|
107
|
+
const activeContainers = new WeakSet();
|
|
108
|
+
const completedScanPolicies = new WeakMap();
|
|
109
|
+
let visitedNodeCount = 0;
|
|
110
|
+
const hasCompletedStricterScan = (container, scanPolicy) => completedScanPolicies.get(container)?.some(completedPolicy => (completedPolicy & scanPolicy) === completedPolicy) ?? false;
|
|
111
|
+
const completeScan = (container, scanPolicy) => {
|
|
112
|
+
const completedPolicies = completedScanPolicies.get(container) ?? [];
|
|
113
|
+
if (completedPolicies.some(completedPolicy => (completedPolicy & scanPolicy) === completedPolicy))
|
|
114
|
+
return;
|
|
115
|
+
completedScanPolicies.set(container, [...completedPolicies.filter(completedPolicy => (scanPolicy & completedPolicy) !== scanPolicy), scanPolicy]);
|
|
116
|
+
};
|
|
117
|
+
while (pending.length > 0) {
|
|
118
|
+
const candidate = pending.pop();
|
|
119
|
+
if (candidate.kind === 'leave') {
|
|
120
|
+
activeContainers.delete(candidate.container);
|
|
121
|
+
completeScan(candidate.container, candidate.scanPolicy);
|
|
122
|
+
continue;
|
|
123
|
+
}
|
|
124
|
+
if (typeof candidate.value === 'string') {
|
|
125
|
+
if (isForbiddenReferenceValue(candidate.value, false, false, options.rejectDigestLikeValues))
|
|
126
|
+
return true;
|
|
127
|
+
continue;
|
|
128
|
+
}
|
|
129
|
+
if (Array.isArray(candidate.value)) {
|
|
130
|
+
visitedNodeCount += 1;
|
|
131
|
+
if (visitedNodeCount > exports.ARTIFACT_CONTROL_DATA_MAX_VISITED_NODES)
|
|
132
|
+
return true;
|
|
133
|
+
if (activeContainers.has(candidate.value))
|
|
134
|
+
return true;
|
|
135
|
+
const scanPolicy = (candidate.allowIndexedFields ? 1 : 0) |
|
|
136
|
+
(candidate.allowedStringArrayField ? 2 : 0) |
|
|
137
|
+
(candidate.allowedStringArrayField?.allowDigestLike ? 4 : 0);
|
|
138
|
+
if (hasCompletedStricterScan(candidate.value, scanPolicy))
|
|
139
|
+
continue;
|
|
140
|
+
activeContainers.add(candidate.value);
|
|
141
|
+
pending.push({ kind: 'leave', container: candidate.value, scanPolicy });
|
|
142
|
+
for (let index = candidate.value.length - 1; index >= 0; index -= 1) {
|
|
143
|
+
const child = candidate.value[index];
|
|
144
|
+
if (candidate.allowedStringArrayField && typeof child === 'string') {
|
|
145
|
+
if (isForbiddenReferenceValue(child, true, candidate.allowedStringArrayField.allowDigestLike, options.rejectDigestLikeValues)) {
|
|
146
|
+
return true;
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
else {
|
|
150
|
+
pending.push({ kind: 'visit', value: child, allowIndexedFields: candidate.allowIndexedFields });
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
continue;
|
|
154
|
+
}
|
|
155
|
+
if (!isRecord(candidate.value))
|
|
156
|
+
continue;
|
|
157
|
+
visitedNodeCount += 1;
|
|
158
|
+
if (visitedNodeCount > exports.ARTIFACT_CONTROL_DATA_MAX_VISITED_NODES)
|
|
90
159
|
return true;
|
|
91
|
-
|
|
92
|
-
if (allowedField?.allowUriScheme && typeof child === 'string')
|
|
93
|
-
return isForbiddenReferenceValue(child, true);
|
|
94
|
-
if (PHYSICAL_REFERENCE_FIELDS.has(normalizedKey) && !allowedField)
|
|
160
|
+
if (activeContainers.has(candidate.value))
|
|
95
161
|
return true;
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
162
|
+
const scanPolicy = candidate.allowIndexedFields ? 1 : 0;
|
|
163
|
+
if (hasCompletedStricterScan(candidate.value, scanPolicy))
|
|
164
|
+
continue;
|
|
165
|
+
activeContainers.add(candidate.value);
|
|
166
|
+
pending.push({ kind: 'leave', container: candidate.value, scanPolicy });
|
|
167
|
+
for (const [key, child] of Object.entries(candidate.value)) {
|
|
168
|
+
if (hasControlCharacters(key))
|
|
169
|
+
return true;
|
|
170
|
+
const normalizedKey = normalizeFieldName(key);
|
|
171
|
+
if (FORBIDDEN_PROTOTYPE_FIELDS.has(normalizedKey))
|
|
172
|
+
return true;
|
|
173
|
+
if (FORBIDDEN_SENSITIVE_FIELDS.has(normalizedKey))
|
|
174
|
+
return true;
|
|
175
|
+
const allowedField = candidate.allowIndexedFields ? allowedReferenceFields.get(candidate.value)?.get(key) : undefined;
|
|
176
|
+
if (options.forbiddenControlFields?.has(normalizedKey) && !allowedField?.allowControlField)
|
|
177
|
+
return true;
|
|
178
|
+
if (options.requireSafeAzureResourceIds && normalizedKey === 'resourceid') {
|
|
179
|
+
if (!isSafeAzureResourceId(key, child))
|
|
180
|
+
return true;
|
|
181
|
+
continue;
|
|
182
|
+
}
|
|
183
|
+
if (allowedField && typeof child === 'string' && (allowedField.allowUriScheme || allowedField.allowDigestLike)) {
|
|
184
|
+
if (isForbiddenReferenceValue(child, allowedField.allowUriScheme, allowedField.allowDigestLike, options.rejectDigestLikeValues))
|
|
185
|
+
return true;
|
|
186
|
+
continue;
|
|
187
|
+
}
|
|
188
|
+
if (allowedField?.allowUriSchemeInStringArray && Array.isArray(child)) {
|
|
189
|
+
pending.push({ kind: 'visit', value: child, allowedStringArrayField: allowedField });
|
|
190
|
+
continue;
|
|
191
|
+
}
|
|
192
|
+
if (PHYSICAL_REFERENCE_FIELDS.has(normalizedKey) && !allowedField)
|
|
193
|
+
return true;
|
|
194
|
+
if (isSafeAzureResourceId(key, child))
|
|
195
|
+
continue;
|
|
196
|
+
pending.push({
|
|
197
|
+
kind: 'visit',
|
|
198
|
+
value: child,
|
|
199
|
+
allowIndexedFields: !options.requireAllowedFieldTraversalContext || Boolean(candidate.allowIndexedFields && allowedField?.allowChildArtifactFields),
|
|
200
|
+
});
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
return false;
|
|
100
204
|
};
|
|
205
|
+
/** Rejects normalized sensitive fields and physical-reference control data with bounded traversal. */
|
|
206
|
+
const containsForbiddenArtifactControlData = (value, allowedReferenceFields = [], options = {}) => containsForbiddenArtifactControlDataWithIndex(value, indexAllowedArtifactFields(allowedReferenceFields), options);
|
|
101
207
|
exports.containsForbiddenArtifactControlData = containsForbiddenArtifactControlData;
|
|
102
208
|
//# sourceMappingURL=artifactControlData.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"artifactControlData.js","sourceRoot":"","sources":["../../src/common/artifactControlData.ts"],"names":[],"mappings":";;;AAAA,MAAM,0BAA0B,GAAG,IAAI,GAAG,CAAC;IACzC,YAAY;IACZ,WAAW;IACX,aAAa;IACb,QAAQ;IACR,eAAe;IACf,cAAc;IACd,kBAAkB;IAClB,YAAY;IACZ,aAAa;IACb,UAAU;IACV,cAAc;IACd,UAAU;IACV,QAAQ;IACR,uBAAuB;IACvB,OAAO;CACR,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"artifactControlData.js","sourceRoot":"","sources":["../../src/common/artifactControlData.ts"],"names":[],"mappings":";;;AAAA,MAAM,0BAA0B,GAAG,IAAI,GAAG,CAAC;IACzC,YAAY;IACZ,WAAW;IACX,aAAa;IACb,QAAQ;IACR,eAAe;IACf,cAAc;IACd,kBAAkB;IAClB,YAAY;IACZ,aAAa;IACb,UAAU;IACV,cAAc;IACd,UAAU;IACV,QAAQ;IACR,uBAAuB;IACvB,OAAO;CACR,CAAC,CAAC;AACH,MAAM,0BAA0B,GAAG,IAAI,GAAG,CAAC,CAAC,OAAO,EAAE,WAAW,EAAE,aAAa,CAAC,CAAC,CAAC;AAElF,MAAM,yBAAyB,GAAG,IAAI,GAAG,CAAC;IACxC,cAAc;IACd,UAAU;IACV,SAAS;IACT,SAAS;IACT,eAAe;IACf,cAAc;IACd,cAAc;IACd,UAAU;IACV,gBAAgB;IAChB,mBAAmB;IACnB,cAAc;IACd,oBAAoB;IACpB,MAAM;IACN,cAAc;IACd,aAAa;IACb,aAAa;IACb,YAAY;IACZ,WAAW;IACX,WAAW;IACX,aAAa;IACb,YAAY;IACZ,YAAY;IACZ,KAAK;IACL,KAAK;CACN,CAAC,CAAC;AACH,MAAM,4BAA4B,GAAG,iBAAiB,CAAC;AACvD,MAAM,kBAAkB,GAAG,2BAA2B,CAAC;AACvD,MAAM,cAAc,GAAG,mBAAmB,CAAC;AAC9B,QAAA,uCAAuC,GAAG,MAAO,CAAC;AAmB/D,MAAM,QAAQ,GAAG,CAAC,KAAc,EAAoC,EAAE,CAAC,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;AAE5I,MAAM,oBAAoB,GAAG,CAAC,KAAa,EAAW,EAAE,CACtD,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,SAAS,CAAC,EAAE,CAAC,SAAS,CAAC,UAAU,CAAC,CAAC,CAAC,GAAG,EAAE,IAAI,SAAS,CAAC,UAAU,CAAC,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC;AAEvG,MAAM,kBAAkB,GAAG,CAAC,GAAW,EAAU,EAAE,CAAC,GAAG,CAAC,OAAO,CAAC,SAAS,EAAE,EAAE,CAAC,CAAC,WAAW,EAAE,CAAC;AAE7F,MAAM,eAAe,GAAG,CAAC,KAAa,EAAW,EAAE,CAAC,KAAK,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,EAAE,CAAC,OAAO,KAAK,GAAG,IAAI,OAAO,KAAK,IAAI,CAAC,CAAC;AAE9H,MAAM,yBAAyB,GAAG,CAAC,KAAa,EAAE,cAAc,GAAG,KAAK,EAAE,eAAe,GAAG,KAAK,EAAE,sBAAsB,GAAG,KAAK,EAAW,EAAE,CAC5I,oBAAoB,CAAC,KAAK,CAAC;IAC3B,4BAA4B,CAAC,IAAI,CAAC,KAAK,CAAC;IACxC,CAAC,CAAC,cAAc,IAAI,kBAAkB,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IACnD,CAAC,sBAAsB,IAAI,CAAC,eAAe,IAAI,cAAc,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAC1E,KAAK,CAAC,UAAU,CAAC,GAAG,CAAC;IACrB,KAAK,CAAC,UAAU,CAAC,MAAM,CAAC;IACxB,iBAAiB,CAAC,IAAI,CAAC,KAAK,CAAC;IAC7B,eAAe,CAAC,KAAK,CAAC,CAAC;AAEzB,MAAM,qBAAqB,GAAG,CAAC,GAAW,EAAE,KAAc,EAAmB,EAAE;IAC7E,IAAI,GAAG,KAAK,YAAY,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,oBAAoB,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC;QAAE,OAAO,KAAK,CAAC;IAC3H,MAAM,QAAQ,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;IAClC,OAAO,CACL,QAAQ,CAAC,MAAM,IAAI,CAAC;QACpB,QAAQ,CAAC,CAAC,CAAC,KAAK,EAAE;QAClB,QAAQ,CAAC,CAAC,CAAC,CAAC,WAAW,EAAE,KAAK,eAAe;QAC7C,QAAQ;aACL,KAAK,CAAC,CAAC,CAAC;aACR,KAAK,CAAC,OAAO,CAAC,EAAE,CAAC,OAAO,CAAC,IAAI,EAAE,KAAK,OAAO,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,IAAI,OAAO,KAAK,GAAG,IAAI,OAAO,KAAK,IAAI,CAAC,CACvI,CAAC;AACJ,CAAC,CAAC;AAEF,2FAA2F;AACpF,MAAM,6BAA6B,GAAG,CAAC,MAAe,EAAE,GAAW,EAAmC,EAAE,CAC7G,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,GAAG,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;AAD/B,QAAA,6BAA6B,iCACE;AAE5C,iGAAiG;AAC1F,MAAM,4BAA4B,GAAG,CAAC,MAAe,EAAE,GAAW,EAAmC,EAAE,CAC5G,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,GAAG,EAAE,cAAc,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;AADrD,QAAA,4BAA4B,gCACyB;AAElE,4FAA4F;AACrF,MAAM,6BAA6B,GAAG,CAAC,MAAe,EAAE,GAAW,EAAmC,EAAE,CAC7G,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,GAAG,EAAE,wBAAwB,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;AAD/D,QAAA,6BAA6B,iCACkC;AAI5E,MAAM,0BAA0B,GAAG,CAAC,sBAAuD,EAA6B,EAAE;IACxH,MAAM,KAAK,GAA8B,IAAI,OAAO,EAAE,CAAC;IACvD,KAAK,MAAM,KAAK,IAAI,sBAAsB,EAAE,CAAC;QAC3C,IAAI,YAAY,GAAG,KAAK,CAAC,GAAG,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;QAC3C,IAAI,CAAC,YAAY,EAAE,CAAC;YAClB,YAAY,GAAG,IAAI,GAAG,EAAE,CAAC;YACzB,KAAK,CAAC,GAAG,CAAC,KAAK,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;QACxC,CAAC;QACD,MAAM,QAAQ,GAAG,YAAY,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;QAC7C,YAAY,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,EAAE;YAC1B,MAAM,EAAE,KAAK,CAAC,MAAM;YACpB,GAAG,EAAE,KAAK,CAAC,GAAG;YACd,cAAc,EAAE,QAAQ,EAAE,cAAc,IAAI,KAAK,CAAC,cAAc;YAChE,2BAA2B,EAAE,QAAQ,EAAE,2BAA2B,IAAI,KAAK,CAAC,2BAA2B;YACvG,eAAe,EAAE,QAAQ,EAAE,eAAe,IAAI,KAAK,CAAC,eAAe;YACnE,iBAAiB,EAAE,QAAQ,EAAE,iBAAiB,IAAI,KAAK,CAAC,iBAAiB;YACzE,wBAAwB,EAAE,QAAQ,EAAE,wBAAwB,IAAI,KAAK,CAAC,wBAAwB;SAC/F,CAAC,CAAC;IACL,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC,CAAC;AAEF,MAAM,6CAA6C,GAAG,CACpD,KAAc,EACd,sBAAiD,EACjD,OAAwC,EAC/B,EAAE;IAaX,MAAM,OAAO,GAAmB,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,kBAAkB,EAAE,IAAI,EAAE,CAAC,CAAC;IACrF,MAAM,gBAAgB,GAAG,IAAI,OAAO,EAAU,CAAC;IAC/C,MAAM,qBAAqB,GAAG,IAAI,OAAO,EAAoB,CAAC;IAC9D,IAAI,gBAAgB,GAAG,CAAC,CAAC;IAEzB,MAAM,wBAAwB,GAAG,CAAC,SAAiB,EAAE,UAAkB,EAAW,EAAE,CAClF,qBAAqB,CAAC,GAAG,CAAC,SAAS,CAAC,EAAE,IAAI,CAAC,eAAe,CAAC,EAAE,CAAC,CAAC,eAAe,GAAG,UAAU,CAAC,KAAK,eAAe,CAAC,IAAI,KAAK,CAAC;IAE7H,MAAM,YAAY,GAAG,CAAC,SAAiB,EAAE,UAAkB,EAAQ,EAAE;QACnE,MAAM,iBAAiB,GAAG,qBAAqB,CAAC,GAAG,CAAC,SAAS,CAAC,IAAI,EAAE,CAAC;QACrE,IAAI,iBAAiB,CAAC,IAAI,CAAC,eAAe,CAAC,EAAE,CAAC,CAAC,eAAe,GAAG,UAAU,CAAC,KAAK,eAAe,CAAC;YAAE,OAAO;QAC1G,qBAAqB,CAAC,GAAG,CAAC,SAAS,EAAE,CAAC,GAAG,iBAAiB,CAAC,MAAM,CAAC,eAAe,CAAC,EAAE,CAAC,CAAC,UAAU,GAAG,eAAe,CAAC,KAAK,UAAU,CAAC,EAAE,UAAU,CAAC,CAAC,CAAC;IACpJ,CAAC,CAAC;IAEF,OAAO,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QAC1B,MAAM,SAAS,GAAG,OAAO,CAAC,GAAG,EAAkB,CAAC;QAChD,IAAI,SAAS,CAAC,IAAI,KAAK,OAAO,EAAE,CAAC;YAC/B,gBAAgB,CAAC,MAAM,CAAC,SAAS,CAAC,SAAS,CAAC,CAAC;YAC7C,YAAY,CAAC,SAAS,CAAC,SAAS,EAAE,SAAS,CAAC,UAAU,CAAC,CAAC;YACxD,SAAS;QACX,CAAC;QACD,IAAI,OAAO,SAAS,CAAC,KAAK,KAAK,QAAQ,EAAE,CAAC;YACxC,IAAI,yBAAyB,CAAC,SAAS,CAAC,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,OAAO,CAAC,sBAAsB,CAAC;gBAAE,OAAO,IAAI,CAAC;YAC1G,SAAS;QACX,CAAC;QACD,IAAI,KAAK,CAAC,OAAO,CAAC,SAAS,CAAC,KAAK,CAAC,EAAE,CAAC;YACnC,gBAAgB,IAAI,CAAC,CAAC;YACtB,IAAI,gBAAgB,GAAG,+CAAuC;gBAAE,OAAO,IAAI,CAAC;YAC5E,IAAI,gBAAgB,CAAC,GAAG,CAAC,SAAS,CAAC,KAAK,CAAC;gBAAE,OAAO,IAAI,CAAC;YACvD,MAAM,UAAU,GACd,CAAC,SAAS,CAAC,kBAAkB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;gBACtC,CAAC,SAAS,CAAC,uBAAuB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;gBAC3C,CAAC,SAAS,CAAC,uBAAuB,EAAE,eAAe,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;YAC/D,IAAI,wBAAwB,CAAC,SAAS,CAAC,KAAK,EAAE,UAAU,CAAC;gBAAE,SAAS;YACpE,gBAAgB,CAAC,GAAG,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC;YACtC,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,SAAS,EAAE,SAAS,CAAC,KAAK,EAAE,UAAU,EAAE,CAAC,CAAC;YACxE,KAAK,IAAI,KAAK,GAAG,SAAS,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,EAAE,KAAK,IAAI,CAAC,EAAE,KAAK,IAAI,CAAC,EAAE,CAAC;gBACpE,MAAM,KAAK,GAAG,SAAS,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;gBACrC,IAAI,SAAS,CAAC,uBAAuB,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;oBACnE,IAAI,yBAAyB,CAAC,KAAK,EAAE,IAAI,EAAE,SAAS,CAAC,uBAAuB,CAAC,eAAe,EAAE,OAAO,CAAC,sBAAsB,CAAC,EAAE,CAAC;wBAC9H,OAAO,IAAI,CAAC;oBACd,CAAC;gBACH,CAAC;qBAAM,CAAC;oBACN,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,kBAAkB,EAAE,SAAS,CAAC,kBAAkB,EAAE,CAAC,CAAC;gBAClG,CAAC;YACH,CAAC;YACD,SAAS;QACX,CAAC;QACD,IAAI,CAAC,QAAQ,CAAC,SAAS,CAAC,KAAK,CAAC;YAAE,SAAS;QACzC,gBAAgB,IAAI,CAAC,CAAC;QACtB,IAAI,gBAAgB,GAAG,+CAAuC;YAAE,OAAO,IAAI,CAAC;QAC5E,IAAI,gBAAgB,CAAC,GAAG,CAAC,SAAS,CAAC,KAAK,CAAC;YAAE,OAAO,IAAI,CAAC;QACvD,MAAM,UAAU,GAAG,SAAS,CAAC,kBAAkB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QACxD,IAAI,wBAAwB,CAAC,SAAS,CAAC,KAAK,EAAE,UAAU,CAAC;YAAE,SAAS;QACpE,gBAAgB,CAAC,GAAG,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC;QACtC,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,SAAS,EAAE,SAAS,CAAC,KAAK,EAAE,UAAU,EAAE,CAAC,CAAC;QAExE,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,SAAS,CAAC,KAAK,CAAC,EAAE,CAAC;YAC3D,IAAI,oBAAoB,CAAC,GAAG,CAAC;gBAAE,OAAO,IAAI,CAAC;YAC3C,MAAM,aAAa,GAAG,kBAAkB,CAAC,GAAG,CAAC,CAAC;YAC9C,IAAI,0BAA0B,CAAC,GAAG,CAAC,aAAa,CAAC;gBAAE,OAAO,IAAI,CAAC;YAC/D,IAAI,0BAA0B,CAAC,GAAG,CAAC,aAAa,CAAC;gBAAE,OAAO,IAAI,CAAC;YAC/D,MAAM,YAAY,GAAG,SAAS,CAAC,kBAAkB,CAAC,CAAC,CAAC,sBAAsB,CAAC,GAAG,CAAC,SAAS,CAAC,KAAK,CAAC,EAAE,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;YACtH,IAAI,OAAO,CAAC,sBAAsB,EAAE,GAAG,CAAC,aAAa,CAAC,IAAI,CAAC,YAAY,EAAE,iBAAiB;gBAAE,OAAO,IAAI,CAAC;YACxG,IAAI,OAAO,CAAC,2BAA2B,IAAI,aAAa,KAAK,YAAY,EAAE,CAAC;gBAC1E,IAAI,CAAC,qBAAqB,CAAC,GAAG,EAAE,KAAK,CAAC;oBAAE,OAAO,IAAI,CAAC;gBACpD,SAAS;YACX,CAAC;YACD,IAAI,YAAY,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,CAAC,YAAY,CAAC,cAAc,IAAI,YAAY,CAAC,eAAe,CAAC,EAAE,CAAC;gBAC/G,IAAI,yBAAyB,CAAC,KAAK,EAAE,YAAY,CAAC,cAAc,EAAE,YAAY,CAAC,eAAe,EAAE,OAAO,CAAC,sBAAsB,CAAC;oBAAE,OAAO,IAAI,CAAC;gBAC7I,SAAS;YACX,CAAC;YACD,IAAI,YAAY,EAAE,2BAA2B,IAAI,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;gBACtE,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,uBAAuB,EAAE,YAAY,EAAE,CAAC,CAAC;gBACrF,SAAS;YACX,CAAC;YACD,IAAI,yBAAyB,CAAC,GAAG,CAAC,aAAa,CAAC,IAAI,CAAC,YAAY;gBAAE,OAAO,IAAI,CAAC;YAC/E,IAAI,qBAAqB,CAAC,GAAG,EAAE,KAAK,CAAC;gBAAE,SAAS;YAChD,OAAO,CAAC,IAAI,CAAC;gBACX,IAAI,EAAE,OAAO;gBACb,KAAK,EAAE,KAAK;gBACZ,kBAAkB,EAChB,CAAC,OAAO,CAAC,mCAAmC,IAAI,OAAO,CAAC,SAAS,CAAC,kBAAkB,IAAI,YAAY,EAAE,wBAAwB,CAAC;aAClI,CAAC,CAAC;QACL,CAAC;IACH,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC,CAAC;AAEF,sGAAsG;AAC/F,MAAM,oCAAoC,GAAG,CAClD,KAAc,EACd,yBAA0D,EAAE,EAC5D,UAA2C,EAAE,EACpC,EAAE,CAAC,6CAA6C,CAAC,KAAK,EAAE,0BAA0B,CAAC,sBAAsB,CAAC,EAAE,OAAO,CAAC,CAAC;AAJnH,QAAA,oCAAoC,wCAI+E"}
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { ARTIFACT_CONTROL_DATA_MAX_VISITED_NODES, allowedArtifactReferenceField, containsForbiddenArtifactControlData, } from '../common/artifactControlData.js';
|
|
1
2
|
const hasOwn = (value, key) => Object.prototype.hasOwnProperty.call(value, key);
|
|
2
3
|
const isRecord = (value) => typeof value === 'object' && value !== null && !Array.isArray(value);
|
|
3
4
|
const requirePlainRecord = (value, name) => {
|
|
@@ -158,6 +159,47 @@ const projectPublicationDecision = (value) => {
|
|
|
158
159
|
issues: issues.map(projectIssue),
|
|
159
160
|
};
|
|
160
161
|
};
|
|
162
|
+
const projectPromotionEvaluation = (value) => {
|
|
163
|
+
const source = requirePlainRecord(value, 'Billing promotion observation evaluation');
|
|
164
|
+
const projected = {
|
|
165
|
+
comparison: readDataProperty(source, 'comparison'),
|
|
166
|
+
projectedOutcome: readDataProperty(source, 'projectedOutcome'),
|
|
167
|
+
};
|
|
168
|
+
selectOptional(source, projected, 'outputDigestRelation');
|
|
169
|
+
return projected;
|
|
170
|
+
};
|
|
171
|
+
const projectPromotionObservation = (value) => {
|
|
172
|
+
const source = requirePlainRecord(value, 'Billing promotion observation');
|
|
173
|
+
const observationDigest = readDataProperty(source, 'observationDigest');
|
|
174
|
+
if (typeof observationDigest !== 'string')
|
|
175
|
+
throw new TypeError('Billing promotion observation requires an observationDigest string.');
|
|
176
|
+
const projected = {
|
|
177
|
+
schemaVersion: readDataProperty(source, 'schemaVersion'),
|
|
178
|
+
documentType: readDataProperty(source, 'documentType'),
|
|
179
|
+
authority: readDataProperty(source, 'authority'),
|
|
180
|
+
publicationMode: readDataProperty(source, 'publicationMode'),
|
|
181
|
+
processingState: readDataProperty(source, 'processingState'),
|
|
182
|
+
subscriptionId: readDataProperty(source, 'subscriptionId'),
|
|
183
|
+
generationId: readDataProperty(source, 'generationId'),
|
|
184
|
+
ownership: projectOwnership(readDataProperty(source, 'ownership')),
|
|
185
|
+
revision: projectRevision(readDataProperty(source, 'revision')),
|
|
186
|
+
messageId: readDataProperty(source, 'messageId'),
|
|
187
|
+
correlationId: readDataProperty(source, 'correlationId'),
|
|
188
|
+
inputManifestPath: readDataProperty(source, 'inputManifestPath'),
|
|
189
|
+
inputManifestDigest: readDataProperty(source, 'inputManifestDigest'),
|
|
190
|
+
outputManifestPath: readDataProperty(source, 'outputManifestPath'),
|
|
191
|
+
outputManifestDigest: readDataProperty(source, 'outputManifestDigest'),
|
|
192
|
+
evaluation: projectPromotionEvaluation(readDataProperty(source, 'evaluation')),
|
|
193
|
+
observedAt: readDataProperty(source, 'observedAt'),
|
|
194
|
+
};
|
|
195
|
+
if (containsForbiddenArtifactControlData(projected, [
|
|
196
|
+
...allowedArtifactReferenceField(projected, 'inputManifestPath'),
|
|
197
|
+
...allowedArtifactReferenceField(projected, 'outputManifestPath'),
|
|
198
|
+
])) {
|
|
199
|
+
throw new TypeError('Billing promotion observation contains forbidden control data.');
|
|
200
|
+
}
|
|
201
|
+
return projected;
|
|
202
|
+
};
|
|
161
203
|
const projectBinding = (subscriptionId, generationId, ownership, revision, inputManifestDigest, publicationDecision) => ({
|
|
162
204
|
kind: 'billing-analysis-output',
|
|
163
205
|
schemaVersion: 1,
|
|
@@ -180,68 +222,103 @@ export const projectBillingOutputBindingV1FromMetadata = (metadata) => {
|
|
|
180
222
|
};
|
|
181
223
|
const canonicalizeJson = (value) => {
|
|
182
224
|
const active = new Set();
|
|
183
|
-
const
|
|
184
|
-
|
|
185
|
-
|
|
225
|
+
const fragments = [];
|
|
226
|
+
const pending = [{ kind: 'value', value }];
|
|
227
|
+
let visitedContainerCount = 0;
|
|
228
|
+
while (pending.length > 0) {
|
|
229
|
+
const frame = pending.pop();
|
|
230
|
+
if (frame === undefined)
|
|
231
|
+
break;
|
|
232
|
+
if (frame.kind === 'fragment') {
|
|
233
|
+
fragments.push(frame.value);
|
|
234
|
+
continue;
|
|
235
|
+
}
|
|
236
|
+
if (frame.kind === 'leave') {
|
|
237
|
+
active.delete(frame.value);
|
|
238
|
+
continue;
|
|
239
|
+
}
|
|
240
|
+
const candidate = frame.value;
|
|
241
|
+
if (candidate === null || typeof candidate === 'boolean') {
|
|
242
|
+
fragments.push(JSON.stringify(candidate));
|
|
243
|
+
continue;
|
|
244
|
+
}
|
|
186
245
|
if (typeof candidate === 'string') {
|
|
187
246
|
if (hasUnpairedSurrogate(candidate))
|
|
188
247
|
throw new TypeError('Canonical JSON rejects invalid Unicode surrogate data.');
|
|
189
|
-
|
|
248
|
+
fragments.push(JSON.stringify(candidate));
|
|
249
|
+
continue;
|
|
190
250
|
}
|
|
191
251
|
if (typeof candidate === 'number') {
|
|
192
252
|
if (!Number.isFinite(candidate) || Object.is(candidate, -0) || (Number.isInteger(candidate) && !Number.isSafeInteger(candidate))) {
|
|
193
253
|
throw new TypeError('Canonical JSON requires finite, safe, non-negative-zero numbers.');
|
|
194
254
|
}
|
|
195
|
-
|
|
255
|
+
fragments.push(JSON.stringify(candidate));
|
|
256
|
+
continue;
|
|
196
257
|
}
|
|
197
258
|
if (typeof candidate !== 'object' || candidate === undefined)
|
|
198
259
|
throw new TypeError('Canonical JSON rejects non-JSON values.');
|
|
260
|
+
visitedContainerCount += 1;
|
|
261
|
+
if (visitedContainerCount > ARTIFACT_CONTROL_DATA_MAX_VISITED_NODES) {
|
|
262
|
+
throw new TypeError('Canonical JSON exceeds its 100000-container limit.');
|
|
263
|
+
}
|
|
199
264
|
if (active.has(candidate))
|
|
200
265
|
throw new TypeError('Canonical JSON rejects cyclic values.');
|
|
201
266
|
active.add(candidate);
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
}
|
|
211
|
-
const values = [];
|
|
212
|
-
for (let index = 0; index < candidate.length; index += 1) {
|
|
213
|
-
if (!hasOwn(candidate, index))
|
|
214
|
-
throw new TypeError('Canonical JSON rejects sparse arrays.');
|
|
215
|
-
const descriptor = Object.getOwnPropertyDescriptor(candidate, String(index));
|
|
216
|
-
if (descriptor === undefined || !('value' in descriptor) || !descriptor.enumerable || descriptor.value === undefined) {
|
|
217
|
-
throw new TypeError('Canonical JSON array entries must be enumerable JSON values.');
|
|
218
|
-
}
|
|
219
|
-
values.push(serialize(descriptor.value));
|
|
220
|
-
}
|
|
221
|
-
return `[${values.join(',')}]`;
|
|
267
|
+
pending.push({ kind: 'leave', value: candidate });
|
|
268
|
+
if (Array.isArray(candidate)) {
|
|
269
|
+
if (Object.getPrototypeOf(candidate) !== Array.prototype)
|
|
270
|
+
throw new TypeError('Canonical JSON requires plain arrays.');
|
|
271
|
+
const ownKeys = Reflect.ownKeys(candidate);
|
|
272
|
+
if (ownKeys.some(key => typeof key === 'symbol') ||
|
|
273
|
+
ownKeys.some(key => typeof key === 'string' && key !== 'length' && !/^(0|[1-9]\d*)$/.test(key))) {
|
|
274
|
+
throw new TypeError('Canonical JSON arrays cannot contain custom properties.');
|
|
222
275
|
}
|
|
223
|
-
const
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
const entries = [];
|
|
229
|
-
for (const key of Object.getOwnPropertyNames(candidate).sort()) {
|
|
230
|
-
if (hasUnpairedSurrogate(key))
|
|
231
|
-
throw new TypeError('Canonical JSON rejects invalid Unicode property names.');
|
|
232
|
-
const descriptor = Object.getOwnPropertyDescriptor(candidate, key);
|
|
276
|
+
const values = [];
|
|
277
|
+
for (let index = 0; index < candidate.length; index += 1) {
|
|
278
|
+
if (!hasOwn(candidate, index))
|
|
279
|
+
throw new TypeError('Canonical JSON rejects sparse arrays.');
|
|
280
|
+
const descriptor = Object.getOwnPropertyDescriptor(candidate, String(index));
|
|
233
281
|
if (descriptor === undefined || !('value' in descriptor) || !descriptor.enumerable || descriptor.value === undefined) {
|
|
234
|
-
throw new TypeError('Canonical JSON
|
|
282
|
+
throw new TypeError('Canonical JSON array entries must be enumerable JSON values.');
|
|
235
283
|
}
|
|
236
|
-
|
|
284
|
+
values.push(descriptor.value);
|
|
237
285
|
}
|
|
238
|
-
|
|
286
|
+
fragments.push('[');
|
|
287
|
+
pending.push({ kind: 'fragment', value: ']' });
|
|
288
|
+
for (let index = values.length - 1; index >= 0; index -= 1) {
|
|
289
|
+
pending.push({ kind: 'value', value: values[index] });
|
|
290
|
+
if (index > 0)
|
|
291
|
+
pending.push({ kind: 'fragment', value: ',' });
|
|
292
|
+
}
|
|
293
|
+
continue;
|
|
294
|
+
}
|
|
295
|
+
const prototype = Object.getPrototypeOf(candidate);
|
|
296
|
+
if (prototype !== Object.prototype && prototype !== null)
|
|
297
|
+
throw new TypeError('Canonical JSON requires plain objects.');
|
|
298
|
+
if (Object.getOwnPropertySymbols(candidate).length > 0)
|
|
299
|
+
throw new TypeError('Canonical JSON rejects symbol properties.');
|
|
300
|
+
const entries = [];
|
|
301
|
+
for (const key of Object.getOwnPropertyNames(candidate).sort()) {
|
|
302
|
+
if (hasUnpairedSurrogate(key))
|
|
303
|
+
throw new TypeError('Canonical JSON rejects invalid Unicode property names.');
|
|
304
|
+
const descriptor = Object.getOwnPropertyDescriptor(candidate, key);
|
|
305
|
+
if (descriptor === undefined || !('value' in descriptor) || !descriptor.enumerable || descriptor.value === undefined) {
|
|
306
|
+
throw new TypeError('Canonical JSON object fields must be enumerable JSON values.');
|
|
307
|
+
}
|
|
308
|
+
entries.push({ key, value: descriptor.value });
|
|
239
309
|
}
|
|
240
|
-
|
|
241
|
-
|
|
310
|
+
fragments.push('{');
|
|
311
|
+
pending.push({ kind: 'fragment', value: '}' });
|
|
312
|
+
for (let index = entries.length - 1; index >= 0; index -= 1) {
|
|
313
|
+
const entry = entries[index];
|
|
314
|
+
pending.push({ kind: 'value', value: entry.value });
|
|
315
|
+
pending.push({
|
|
316
|
+
kind: 'fragment',
|
|
317
|
+
value: `${index > 0 ? ',' : ''}${JSON.stringify(entry.key)}:`,
|
|
318
|
+
});
|
|
242
319
|
}
|
|
243
|
-
}
|
|
244
|
-
return
|
|
320
|
+
}
|
|
321
|
+
return fragments.join('');
|
|
245
322
|
};
|
|
246
323
|
const withoutManifestDigest = (manifest) => {
|
|
247
324
|
const prototype = Object.getPrototypeOf(manifest);
|
|
@@ -277,5 +354,7 @@ export const canonicalizeBillingOutputBindingV1 = (binding) => {
|
|
|
277
354
|
export const canonicalizeBillingAnalyzerInputManifestV2ForDigest = (manifest) => canonicalizeJson(withoutManifestDigest(manifest));
|
|
278
355
|
/** Returns the canonical output-manifest digest preimage, excluding only top-level manifestDigest. */
|
|
279
356
|
export const canonicalizeBillingAnalyzerOutputManifestV2ForDigest = (manifest) => canonicalizeJson(withoutManifestDigest(manifest));
|
|
357
|
+
/** Returns the exact promotion-observation digest preimage, excluding observationDigest and additive fields. */
|
|
358
|
+
export const canonicalizeBillingAnalysisPromotionObservationV1ForDigest = (observation) => canonicalizeJson(projectPromotionObservation(observation));
|
|
280
359
|
/** Returns the RFC 8785/JCS-compatible canonical JSON string for a validated JSON value. */
|
|
281
360
|
export const canonicalizeBillingArtifactJson = (value) => canonicalizeJson(value);
|