@carrot-foundation/schemas 0.1.41 → 0.1.43

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 (26) hide show
  1. package/dist/index.cjs +609 -615
  2. package/dist/index.cjs.map +1 -1
  3. package/dist/index.d.cts +325 -457
  4. package/dist/index.d.ts +325 -457
  5. package/dist/index.js +601 -614
  6. package/dist/index.js.map +1 -1
  7. package/package.json +10 -3
  8. package/schemas/ipfs/collection/collection.example.json +6 -6
  9. package/schemas/ipfs/collection/collection.schema.json +7 -6
  10. package/schemas/ipfs/credit/credit.example.json +6 -6
  11. package/schemas/ipfs/credit/credit.schema.json +7 -6
  12. package/schemas/ipfs/credit-purchase-receipt/credit-purchase-receipt.example.json +40 -24
  13. package/schemas/ipfs/credit-purchase-receipt/credit-purchase-receipt.schema.json +40 -50
  14. package/schemas/ipfs/credit-retirement-receipt/credit-retirement-receipt.example.json +39 -31
  15. package/schemas/ipfs/credit-retirement-receipt/credit-retirement-receipt.schema.json +41 -51
  16. package/schemas/ipfs/gas-id/gas-id.example.json +19 -19
  17. package/schemas/ipfs/gas-id/gas-id.schema.json +85 -594
  18. package/schemas/ipfs/mass-id/mass-id.example.json +12 -7
  19. package/schemas/ipfs/mass-id/mass-id.schema.json +31 -35
  20. package/schemas/ipfs/mass-id-audit/mass-id-audit.example.json +12 -12
  21. package/schemas/ipfs/mass-id-audit/mass-id-audit.schema.json +17 -16
  22. package/schemas/ipfs/methodology/methodology.example.json +10 -10
  23. package/schemas/ipfs/methodology/methodology.schema.json +8 -7
  24. package/schemas/ipfs/recycled-id/recycled-id.example.json +20 -20
  25. package/schemas/ipfs/recycled-id/recycled-id.schema.json +85 -545
  26. package/schemas/schema-hashes.json +41 -0
package/dist/index.cjs CHANGED
@@ -3,82 +3,14 @@
3
3
  var zod = require('zod');
4
4
  require('fs');
5
5
  require('path');
6
+ var crypto = require('crypto');
7
+ var canonicalize = require('canonicalize');
8
+
9
+ function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }
10
+
11
+ var canonicalize__default = /*#__PURE__*/_interopDefault(canonicalize);
6
12
 
7
13
  // src/mass-id/mass-id.attributes.ts
8
- var nativeDateParse = Date.parse.bind(Date);
9
- var ISO_TIMESTAMP_REGEX = /^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}(?:\.\d{1,3})?(?:Z|[+-]\d{2}:\d{2})$/;
10
- var UuidSchema = zod.z.uuidv4().meta({
11
- title: "UUID V4",
12
- description: "A universally unique identifier version 4",
13
- examples: ["ad44dd3f-f176-4b98-bf78-5ee6e77d0530"]
14
- });
15
- var EthereumAddressSchema = zod.z.string().regex(
16
- /^0x[a-f0-9]{40}$/,
17
- "Must be a valid Ethereum address in lowercase hexadecimal format"
18
- ).meta({
19
- title: "Ethereum Address",
20
- description: "A valid Ethereum address in hexadecimal format",
21
- examples: ["0x1234567890abcdef1234567890abcdef12345678"]
22
- });
23
- var IsoTimestampSchema = zod.z.string().regex(
24
- ISO_TIMESTAMP_REGEX,
25
- "Must be a valid ISO 8601 timestamp with timezone information"
26
- ).superRefine((value, ctx) => {
27
- const parsed = nativeDateParse(value);
28
- if (Number.isNaN(parsed)) {
29
- ctx.addIssue({
30
- code: "custom",
31
- message: "Must be a valid ISO 8601 timestamp with timezone information"
32
- });
33
- }
34
- }).meta({
35
- title: "ISO Timestamp",
36
- description: "ISO 8601 formatted timestamp with timezone information",
37
- examples: ["2024-12-05T11:02:47.000Z"]
38
- });
39
- var IsoDateSchema = zod.z.iso.date("Must be a valid ISO 8601 date (YYYY-MM-DD)").meta({
40
- title: "ISO Date",
41
- description: "ISO 8601 formatted date in YYYY-MM-DD format",
42
- examples: ["2024-12-05"]
43
- });
44
- var UnixTimestampSchema = zod.z.number().int().positive().meta({
45
- title: "Unix Timestamp",
46
- description: "Unix timestamp in milliseconds since epoch (January 1, 1970 00:00:00 UTC)",
47
- examples: [17040672e5]
48
- });
49
- var IsoCountryCodeSchema = zod.z.string().regex(/^[A-Z]{2}$/, "Must be a valid ISO 3166-1 alpha-2 country code").meta({
50
- title: "ISO Country Code",
51
- description: "Two-letter country code following ISO 3166-1 alpha-2 standard",
52
- examples: ["BR", "US", "DE"]
53
- });
54
- var IsoAdministrativeDivisionCodeSchema = zod.z.string().regex(
55
- /^[A-Z]{2}-[A-Z0-9]{1,3}$/,
56
- "Must be a valid ISO 3166-2 administrative division code"
57
- ).meta({
58
- title: "ISO Administrative Division Code",
59
- description: "Administrative division code following ISO 3166-2 standard",
60
- examples: ["BR-AP", "BR-ES", "US-CA"]
61
- });
62
- var LatitudeSchema = zod.z.number().min(-90).max(90).multipleOf(1e-3).meta({
63
- title: "Latitude",
64
- description: "Geographic latitude coordinate in decimal degrees with maximum 3 decimal places precision (~100m-1km accuracy for city-level)",
65
- examples: [-0.02, -20.38, 40.713]
66
- });
67
- var LongitudeSchema = zod.z.number().min(-180).max(180).multipleOf(1e-3).meta({
68
- title: "Longitude",
69
- description: "Geographic longitude coordinate in decimal degrees with maximum 3 decimal places precision (~100m-1km accuracy for city-level)",
70
- examples: [-51.06, -40.34, -74.006]
71
- });
72
- var NonNegativeFloatSchema = zod.z.number().min(0).meta({
73
- title: "Non-Negative Float",
74
- description: "Floating-point number that is zero or positive",
75
- examples: [0, 45.2, 72.5]
76
- });
77
- var WeightKgSchema = NonNegativeFloatSchema.meta({
78
- title: "Weight (kg)",
79
- description: "Weight measurement in kilograms",
80
- examples: [3e3, 1500, 500]
81
- });
82
14
  var NonEmptyStringSchema = zod.z.string().min(1, "Cannot be empty").meta({
83
15
  title: "Non-Empty String",
84
16
  description: "A string that contains at least one character",
@@ -109,14 +41,6 @@ var MethodologyNameSchema = NonEmptyStringSchema.max(100).meta({
109
41
  description: "Name of the methodology used for certification",
110
42
  examples: ["BOLD Recycling", "BOLD Carbon (CH\u2084)"]
111
43
  });
112
- var StringifiedTokenIdSchema = NonEmptyStringSchema.regex(
113
- /^#\d+$/,
114
- "Must match pattern #<token_id>"
115
- ).meta({
116
- title: "Token ID",
117
- description: "Token ID represented as #<token_id>",
118
- example: "#123"
119
- });
120
44
  var SlugSchema = NonEmptyStringSchema.regex(
121
45
  /^[a-z0-9-]+$/,
122
46
  "Must contain only lowercase letters, numbers, and hyphens"
@@ -130,16 +54,6 @@ var CollectionSlugSchema = SlugSchema.meta({
130
54
  description: "URL-friendly identifier for a collection",
131
55
  examples: ["bold-cold-start-carazinho", "bold-brazil"]
132
56
  });
133
- var WasteTypeSchema = NonEmptyStringSchema.max(100).meta({
134
- title: "Waste Type",
135
- description: "Category or type of waste material",
136
- examples: ["Organic", "Plastic", "Metal"]
137
- });
138
- var WasteSubtypeSchema = NonEmptyStringSchema.max(100).meta({
139
- title: "Waste Subtype",
140
- description: "Specific subcategory of waste within a waste type",
141
- examples: ["Food, Food Waste and Beverages", "Domestic Sludge"]
142
- });
143
57
  var ParticipantRoleSchema = NonEmptyStringSchema.max(100).meta({
144
58
  title: "Participant Role",
145
59
  description: "Role that a participant plays in the waste management supply chain",
@@ -150,27 +64,38 @@ var ParticipantNameSchema = NonEmptyStringSchema.max(100).meta({
150
64
  description: "Name of a participant in the waste management system",
151
65
  examples: ["Enlatados Produ\xE7\xE3o", "Eco Reciclagem", "Green Tech Corp"]
152
66
  });
153
- var BlockchainChainIdSchema = zod.z.union([zod.z.literal(137), zod.z.literal(80002)]).meta({
154
- title: "Chain ID",
155
- description: "Supported Polygon chain identifiers",
156
- examples: [137, 80002]
67
+ var WasteTypeSchema = NonEmptyStringSchema.max(100).meta({
68
+ title: "Waste Type",
69
+ description: "Category or type of waste material",
70
+ examples: ["Organic", "Plastic", "Metal"]
157
71
  });
158
- var BlockchainNetworkNameSchema = zod.z.enum(["Polygon", "Amoy"]).meta({
159
- title: "Blockchain Network Name",
160
- description: "Supported Polygon network names",
161
- examples: ["Polygon", "Amoy"]
72
+ var WasteSubtypeSchema = NonEmptyStringSchema.max(100).meta({
73
+ title: "Waste Subtype",
74
+ description: "Specific subcategory of waste within a waste type",
75
+ examples: ["Food, Food Waste and Beverages", "Domestic Sludge"]
162
76
  });
163
- var SmartContractAddressSchema = EthereumAddressSchema.meta({
164
- title: "Smart Contract Address",
165
- description: "Address of the smart contract"
77
+ var CreditTypeSchema = NonEmptyStringSchema.max(100).meta({
78
+ title: "Credit Type",
79
+ description: "Type of credit issued",
80
+ examples: ["Organic", "Carbon (CH\u2084)"]
166
81
  });
167
- var SmartContractSchema = zod.z.strictObject({
168
- address: SmartContractAddressSchema,
169
- chain_id: BlockchainChainIdSchema,
170
- network_name: BlockchainNetworkNameSchema
171
- }).meta({
172
- title: "Smart Contract",
173
- description: "Smart contract details for on-chain references"
82
+ var HexColorSchema = NonEmptyStringSchema.regex(
83
+ /^#[0-9A-F]{6}$/,
84
+ "Must be a hex color code with # prefix and uppercase"
85
+ ).meta({
86
+ title: "Hex Color",
87
+ description: "Hexadecimal color code with hash prefix",
88
+ examples: ["#2D5A27", "#FF5733"]
89
+ });
90
+ var NonNegativeFloatSchema = zod.z.number().min(0).meta({
91
+ title: "Non-Negative Float",
92
+ description: "Floating-point number that is zero or positive",
93
+ examples: [0, 45.2, 72.5]
94
+ });
95
+ var WeightKgSchema = NonNegativeFloatSchema.meta({
96
+ title: "Weight (kg)",
97
+ description: "Weight measurement in kilograms",
98
+ examples: [3e3, 1500, 500]
174
99
  });
175
100
  var PercentageSchema = NonNegativeFloatSchema.max(100).meta({
176
101
  title: "Percentage",
@@ -187,43 +112,107 @@ var PositiveIntegerSchema = zod.z.number().int().min(1).meta({
187
112
  description: "Integer value that is greater than zero",
188
113
  examples: [1, 123, 456]
189
114
  });
190
- var CreditTypeSchema = NonEmptyStringSchema.max(100).meta({
191
- title: "Credit Type",
192
- description: "Type of credit issued",
193
- examples: ["Organic", "Carbon (CH\u2084)"]
194
- });
195
115
  var CreditAmountSchema = NonNegativeFloatSchema.meta({
196
116
  title: "Credit Amount",
197
117
  description: "Amount of credits issued"
198
118
  });
199
- var HoursSchema = zod.z.number().min(0).multipleOf(0.1).meta({
200
- title: "Hours",
201
- description: "Time duration in hours with 0.1 hour precision",
202
- examples: [72.5, 24, 168.5]
119
+ var IsoTimestampSchema = zod.z.string().datetime({
120
+ message: "Must be a valid ISO 8601 timestamp with timezone information",
121
+ offset: true
122
+ }).meta({
123
+ title: "ISO Timestamp",
124
+ description: "ISO 8601 formatted timestamp with timezone information",
125
+ examples: ["2024-12-05T11:02:47.000Z"]
203
126
  });
204
- var MinutesSchema = NonNegativeIntegerSchema.meta({
205
- title: "Minutes",
206
- description: "Time duration in minutes",
207
- examples: [4350, 1440, 10110]
127
+ var IsoDateSchema = zod.z.iso.date("Must be a valid ISO 8601 date (YYYY-MM-DD)").meta({
128
+ title: "ISO Date",
129
+ description: "ISO 8601 formatted date in YYYY-MM-DD format",
130
+ examples: ["2024-12-05"]
208
131
  });
209
- var IpfsUriSchema = NonEmptyStringSchema.regex(
210
- /^ipfs:\/\/[a-zA-Z0-9]+(\/.*)?$/,
211
- "Must be a valid IPFS URI with CID"
132
+ var UnixTimestampSchema = zod.z.number().int().positive().meta({
133
+ title: "Unix Timestamp",
134
+ description: "Unix timestamp in milliseconds since epoch (January 1, 1970 00:00:00 UTC)",
135
+ examples: [17040672e5]
136
+ });
137
+ var IsoCountryCodeSchema = zod.z.string().regex(/^[A-Z]{2}$/, "Must be a valid ISO 3166-1 alpha-2 country code").meta({
138
+ title: "ISO Country Code",
139
+ description: "Two-letter country code following ISO 3166-1 alpha-2 standard",
140
+ examples: ["BR", "US", "DE"]
141
+ });
142
+ var IsoAdministrativeDivisionCodeSchema = zod.z.string().regex(
143
+ /^[A-Z]{2}-[A-Z0-9]{1,3}$/,
144
+ "Must be a valid ISO 3166-2 administrative division code"
212
145
  ).meta({
213
- title: "IPFS URI",
214
- description: "InterPlanetary File System URI pointing to distributed content",
215
- examples: [
216
- "ipfs://QmTy8w65yBXgyfG2ZBg5TrfB2hPjrDQH3RCQFJGkARStJb/mass-id-organic.png",
217
- "ipfs://QmYjtig7VJQ6XsnUjqqJvj7QaMcCAwtrgNdahSiFofrE7o"
218
- ]
146
+ title: "ISO Administrative Division Code",
147
+ description: "Administrative division code following ISO 3166-2 standard",
148
+ examples: ["BR-AP", "BR-ES", "US-CA"]
219
149
  });
220
- var SemanticVersionSchema = NonEmptyStringSchema.regex(
221
- /^v?\d+\.\d+\.\d+(-[a-zA-Z0-9.-]+)?(\+[a-zA-Z0-9.-]+)?$/,
222
- "Must be a valid semantic version string"
150
+ var LatitudeSchema = zod.z.number().min(-90).max(90).multipleOf(1e-3).meta({
151
+ title: "Latitude",
152
+ description: "Geographic latitude coordinate in decimal degrees with maximum 3 decimal places precision (~100m-1km accuracy for city-level)",
153
+ examples: [-0.02, -20.38, 40.713]
154
+ });
155
+ var LongitudeSchema = zod.z.number().min(-180).max(180).multipleOf(1e-3).meta({
156
+ title: "Longitude",
157
+ description: "Geographic longitude coordinate in decimal degrees with maximum 3 decimal places precision (~100m-1km accuracy for city-level)",
158
+ examples: [-51.06, -40.34, -74.006]
159
+ });
160
+ var BLOCKCHAIN_NETWORK_CONFIG = {
161
+ mainnet: { chain_id: 137, network_name: "Polygon" },
162
+ testnet: { chain_id: 80002, network_name: "Amoy" }
163
+ };
164
+ var ALLOWED_BLOCKCHAIN_NETWORKS = Object.values(
165
+ BLOCKCHAIN_NETWORK_CONFIG
166
+ );
167
+ var BLOCKCHAIN_CHAIN_IDS = [
168
+ BLOCKCHAIN_NETWORK_CONFIG.mainnet.chain_id,
169
+ BLOCKCHAIN_NETWORK_CONFIG.testnet.chain_id
170
+ ];
171
+ var BLOCKCHAIN_NETWORK_NAMES = [
172
+ BLOCKCHAIN_NETWORK_CONFIG.mainnet.network_name,
173
+ BLOCKCHAIN_NETWORK_CONFIG.testnet.network_name
174
+ ];
175
+ var EthereumAddressSchema = zod.z.string().regex(
176
+ /^0x[a-f0-9]{40}$/,
177
+ "Must be a valid Ethereum address in lowercase hexadecimal format"
223
178
  ).meta({
224
- title: "Semantic Version",
225
- description: "Version string following semantic versioning specification",
226
- examples: ["0.1.0", "1.0.0", "2.1.3"]
179
+ title: "Ethereum Address",
180
+ description: "A valid Ethereum address in hexadecimal format",
181
+ examples: ["0x1234567890abcdef1234567890abcdef12345678"]
182
+ });
183
+ var BlockchainChainIdSchema = zod.z.union([
184
+ zod.z.literal(BLOCKCHAIN_NETWORK_CONFIG.mainnet.chain_id),
185
+ zod.z.literal(BLOCKCHAIN_NETWORK_CONFIG.testnet.chain_id)
186
+ ]).meta({
187
+ title: "Chain ID",
188
+ description: "Supported Polygon chain identifiers",
189
+ examples: BLOCKCHAIN_CHAIN_IDS
190
+ });
191
+ var BlockchainNetworkNameSchema = zod.z.enum(BLOCKCHAIN_NETWORK_NAMES).meta({
192
+ title: "Blockchain Network Name",
193
+ description: "Supported Polygon network names",
194
+ examples: BLOCKCHAIN_NETWORK_NAMES
195
+ });
196
+ var SmartContractAddressSchema = EthereumAddressSchema.meta({
197
+ title: "Smart Contract Address",
198
+ description: "Address of the smart contract"
199
+ });
200
+ var SmartContractSchema = zod.z.strictObject({
201
+ address: SmartContractAddressSchema,
202
+ chain_id: BlockchainChainIdSchema,
203
+ network_name: BlockchainNetworkNameSchema
204
+ }).meta({
205
+ title: "Smart Contract",
206
+ description: "Smart contract details for on-chain references"
207
+ });
208
+ var UuidSchema = zod.z.uuidv4().meta({
209
+ title: "UUID V4",
210
+ description: "A universally unique identifier version 4",
211
+ examples: ["ad44dd3f-f176-4b98-bf78-5ee6e77d0530"]
212
+ });
213
+ var ExternalIdSchema = UuidSchema.meta({
214
+ title: "External ID",
215
+ description: "UUID identifier for external system references"
227
216
  });
228
217
  var TokenIdSchema = NonEmptyStringSchema.regex(
229
218
  /^\d+$/,
@@ -233,16 +222,16 @@ var TokenIdSchema = NonEmptyStringSchema.regex(
233
222
  description: "Numeric identifier for blockchain tokens as string",
234
223
  examples: ["456789", "1000000"]
235
224
  });
236
- var HexColorSchema = NonEmptyStringSchema.regex(
237
- /^#[0-9A-F]{6}$/,
238
- "Must be a hex color code with # prefix and uppercase"
225
+ var StringifiedTokenIdSchema = NonEmptyStringSchema.regex(
226
+ /^#\d+$/,
227
+ "Must match pattern #<token_id>"
239
228
  ).meta({
240
- title: "Hex Color",
241
- description: "Hexadecimal color code with hash prefix",
242
- examples: ["#2D5A27", "#FF5733"]
229
+ title: "Token ID",
230
+ description: "Token ID represented as #<token_id>",
231
+ example: "#123"
243
232
  });
244
233
  var Sha256HashSchema = zod.z.hash("sha256", {
245
- error: "Must be a SHA-256 hash as 32-byte hex string"
234
+ error: "Must be a SHA256 hash as 32-byte hex string"
246
235
  }).meta({
247
236
  format: void 0,
248
237
  title: "SHA-256 Hash",
@@ -251,18 +240,33 @@ var Sha256HashSchema = zod.z.hash("sha256", {
251
240
  "87f633634cc4b02f628685651f0a29b7bfa22a0bd841f725c6772dd00a58d489"
252
241
  ]
253
242
  });
254
- var ExternalIdSchema = UuidSchema.meta({
255
- title: "External ID",
256
- description: "UUID identifier for external system references"
257
- });
258
243
  var ExternalUrlSchema = zod.z.url().meta({
259
244
  title: "External URL",
260
245
  description: "URL pointing to external resources",
246
+ examples: ["https://explore.carrot.eco/", "https://whitepaper.carrot.eco/"]
247
+ });
248
+ var ipfsUriPattern = /^ipfs:\/\/(?:Qm[1-9A-HJ-NP-Za-km-z]{44}|[bB][a-z2-7]{58,}|[zZ][1-9A-HJ-NP-Za-km-z]{48,})(?:\/[^\s]*)?$/;
249
+ var IpfsUriSchema = NonEmptyStringSchema.regex(
250
+ ipfsUriPattern,
251
+ "Must be a valid IPFS URI with CID"
252
+ ).meta({
253
+ title: "IPFS URI",
254
+ description: "InterPlanetary File System URI pointing to distributed content",
261
255
  examples: [
262
- "https://explore.carrot.eco/",
263
- "https://https://whitepaper.carrot.eco/"
256
+ "ipfs://bafybeigdyrztvzl5cceubvaxob7iqh6f3f7s36c74ojav2xsz2uib2g3vm/mass-id-organic.png",
257
+ "ipfs://bafybeihdwdcefgh4dqkjv67uzcmw7ojee6xedzdetojuzjevtenxquvyku"
264
258
  ]
265
259
  });
260
+
261
+ // src/shared/schemas/primitives/version.schema.ts
262
+ var SemanticVersionSchema = NonEmptyStringSchema.regex(
263
+ /^v?\d+\.\d+\.\d+(-[a-zA-Z0-9.-]+)?(\+[a-zA-Z0-9.-]+)?$/,
264
+ "Must be a valid semantic version string"
265
+ ).meta({
266
+ title: "Semantic Version",
267
+ description: "Version string following semantic versioning specification",
268
+ examples: ["0.1.0", "1.0.0", "2.1.3"]
269
+ });
266
270
  var RecordSchemaTypeSchema = zod.z.enum([
267
271
  "MassID",
268
272
  "MassID Audit",
@@ -278,308 +282,26 @@ var RecordSchemaTypeSchema = zod.z.enum([
278
282
  description: "Type of schema in the Carrot ecosystem",
279
283
  examples: ["MassID", "RecycledID", "GasID"]
280
284
  });
281
- var TokenSymbolSchema = NonEmptyStringSchema.max(10).regex(
282
- /^[A-Z0-9-]+$/,
283
- "Must contain only uppercase letters, numbers, and hyphens"
284
- ).meta({
285
- title: "Token Symbol",
286
- description: "Symbol representing a token or cryptocurrency",
287
- examples: ["MASS", "REC", "GAS"]
288
- });
289
- var CreditTokenSymbolSchema = TokenSymbolSchema.meta({
290
- title: "Credit Token Symbol",
291
- description: "Symbol of the credit token (e.g., C-CARB, C-BIOW)",
292
- examples: ["C-CARB", "C-BIOW"]
293
- });
294
- function uniqueArrayItems(schema, errorMessage = "Array items must be unique") {
295
- return zod.z.array(schema).refine((items) => new Set(items).size === items.length, {
296
- message: errorMessage
297
- });
298
- }
299
- function uniqueBy(schema, selector, errorMessage = "Items must be unique") {
300
- return zod.z.array(schema).refine(
301
- (items) => {
302
- const values = items.map(selector);
303
- return new Set(values).size === values.length;
304
- },
305
- {
306
- message: errorMessage
307
- }
308
- );
309
- }
310
-
311
- // src/shared/entities/participant.schema.ts
312
- var ParticipantSchema = zod.z.strictObject({
313
- id_hash: Sha256HashSchema.meta({
314
- title: "Participant ID Hash",
315
- description: "Anonymized identifier for the participant"
316
- }),
317
- name: ParticipantNameSchema.meta({
318
- title: "Participant Name",
319
- description: "Name of the participant"
320
- }),
321
- roles: uniqueArrayItems(
322
- ParticipantRoleSchema,
323
- "Participant roles must be unique"
324
- ).min(1).meta({
325
- title: "Participant Roles",
326
- description: "Roles of the participant in the waste management supply chain"
327
- })
328
- }).meta({
329
- title: "Participant",
330
- description: "A participant in the waste management supply chain"
331
- });
332
- var PrecisionLevelSchema = zod.z.enum(["city", "region", "country"]).meta({
333
- title: "Coordinate Precision Level",
334
- description: "Level of coordinate precision",
335
- examples: ["city"]
336
- });
337
- var CoordinatesSchema = zod.z.strictObject({
338
- latitude: LatitudeSchema,
339
- longitude: LongitudeSchema,
340
- precision_level: PrecisionLevelSchema
341
- }).meta({
342
- title: "Coordinates",
343
- description: "GPS coordinates of the location"
344
- });
345
- var LocationSchema = zod.z.strictObject({
346
- id_hash: Sha256HashSchema.meta({
347
- title: "Location ID Hash",
348
- description: "Anonymized identifier for the location"
349
- }),
350
- municipality: MunicipalitySchema,
351
- administrative_division: AdministrativeDivisionSchema,
352
- administrative_division_code: IsoAdministrativeDivisionCodeSchema.optional(),
353
- country: CountryNameSchema,
354
- country_code: IsoCountryCodeSchema,
355
- responsible_participant_id_hash: Sha256HashSchema.meta({
356
- title: "Responsible Participant ID Hash",
357
- description: "Anonymized ID of the participant responsible for this location"
358
- }),
359
- coordinates: CoordinatesSchema
360
- }).meta({
361
- title: "Location",
362
- description: "Geographic location with address and coordinate information"
363
- });
364
- var MethodologyComplianceSchema = zod.z.enum(["PASSED", "FAILED"]).meta({
365
- title: "Methodology Compliance",
366
- description: "Result of methodology compliance check",
367
- examples: ["PASSED", "FAILED"]
368
- });
369
- var AuditReferenceSchema = zod.z.strictObject({
370
- date: IsoDateSchema.meta({
371
- title: "Audit Date",
372
- description: "Date when the audit was completed"
373
- }),
374
- external_id: ExternalIdSchema.meta({
375
- title: "Audit External ID",
376
- description: "Unique identifier for the audit"
377
- }),
378
- external_url: ExternalUrlSchema.meta({
379
- title: "Audit External URL",
380
- description: "URL to view the audit on Carrot Explorer"
381
- }),
382
- methodology_compliance: MethodologyComplianceSchema.meta({
383
- title: "Methodology Compliance",
384
- description: "Result of methodology compliance check"
385
- }),
386
- rules_executed: NonNegativeIntegerSchema.meta({
387
- title: "Rules Executed",
388
- description: "Number of rules executed during the audit"
389
- }),
390
- report: IpfsUriSchema.meta({
391
- title: "Audit Report",
392
- description: "IPFS URI of the audit report"
393
- })
394
- }).meta({
395
- title: "Audit Reference",
396
- description: "Reference to an audit record"
397
- });
398
- var GasIDReferenceSchema = zod.z.strictObject({
399
- external_id: ExternalIdSchema.meta({
400
- title: "GasID External ID",
401
- description: "Unique identifier for the GasID"
402
- }),
403
- token_id: TokenIdSchema.meta({
404
- title: "GasID Token ID",
405
- description: "NFT token ID of the GasID"
406
- }),
407
- external_url: ExternalUrlSchema.meta({
408
- title: "GasID External URL",
409
- description: "URL to view the GasID on Carrot Explorer"
410
- }),
411
- uri: IpfsUriSchema.meta({
412
- title: "GasID IPFS URI",
413
- description: "IPFS URI of the GasID record"
414
- })
415
- }).meta({
416
- title: "GasID Reference",
417
- description: "Reference to a GasID record"
418
- });
419
- var MassIDReferenceSchema = zod.z.strictObject({
420
- external_id: ExternalIdSchema.meta({
421
- title: "MassID External ID",
422
- description: "Unique identifier for the MassID"
423
- }),
424
- token_id: TokenIdSchema.meta({
425
- title: "MassID Token ID",
426
- description: "NFT token ID of the MassID"
427
- }),
428
- external_url: ExternalUrlSchema.meta({
429
- title: "MassID External URL",
430
- description: "URL to view the MassID on Carrot Explorer"
431
- }),
432
- uri: IpfsUriSchema.meta({
433
- title: "MassID IPFS URI",
434
- description: "IPFS URI of the MassID record"
435
- })
436
- }).meta({
437
- title: "MassID Reference",
438
- description: "Reference to a MassID record"
439
- });
440
- var MethodologyReferenceSchema = zod.z.strictObject({
441
- external_id: ExternalIdSchema.meta({
442
- title: "Methodology External ID",
443
- description: "Unique identifier for the methodology"
444
- }),
445
- name: NonEmptyStringSchema.min(5).max(150).meta({
446
- title: "Methodology Name",
447
- description: "Human-readable name of the methodology",
448
- examples: ["BOLD Carbon (CH\u2084)", "BOLD Recycling"]
449
- }),
450
- version: SemanticVersionSchema.meta({
451
- title: "Methodology Version",
452
- description: "Version of the methodology"
453
- }),
454
- external_url: ExternalUrlSchema.meta({
455
- title: "Methodology External URL",
456
- description: "URL to view the methodology on Carrot Explorer"
457
- }),
458
- uri: IpfsUriSchema.optional().meta({
459
- title: "Methodology IPFS URI",
460
- description: "IPFS URI to the methodology record"
461
- })
462
- }).meta({
463
- title: "Methodology Reference",
464
- description: "Reference to a methodology record"
465
- });
466
- var WasteClassificationSchema = zod.z.strictObject({
467
- primary_type: WasteTypeSchema.meta({
468
- title: "Source Waste Primary Type",
469
- description: "Primary type of the source waste"
470
- }),
471
- subtype: WasteSubtypeSchema.meta({
472
- title: "Source Waste Subtype",
473
- description: "Subtype of the source waste"
474
- }),
475
- net_weight_kg: WeightKgSchema.meta({
476
- title: "Source Waste Net Weight",
477
- description: "Net weight of the source waste"
478
- })
479
- }).meta({
480
- title: "Waste Classification",
481
- description: "Classification of the source waste (MassID)"
482
- });
483
- var AccreditedParticipantSchema = zod.z.strictObject({
484
- participant_id: UuidSchema.meta({
485
- title: "Participant ID",
486
- description: "Unique identifier for the participant"
487
- }),
488
- name: ParticipantNameSchema.meta({
489
- title: "Participant Name",
490
- description: "Name of the participant"
491
- }),
492
- role: ParticipantRoleSchema.meta({
493
- title: "Participant Role",
494
- description: "Role of the participant in the supply chain"
495
- }),
496
- accreditation_id: UuidSchema.meta({
497
- title: "Accreditation ID",
498
- description: "Unique identifier for the participant accreditation"
499
- }),
500
- external_url: ExternalUrlSchema.meta({
501
- title: "Participant Accreditation External URL",
502
- description: "URL to view the participant accreditation on Carrot Explorer"
503
- })
504
- }).meta({
505
- title: "Accredited Participant",
506
- description: "Participant with valid accreditation in the supply chain"
507
- });
508
- var AccreditedParticipantsSchema = zod.z.array(AccreditedParticipantSchema).min(1).meta({
509
- title: "Accredited Participants",
510
- description: "List of participants with valid accreditations"
511
- });
512
- var RewardAllocationSchema = zod.z.strictObject({
513
- participant_id: UuidSchema.meta({
514
- title: "Participant ID",
515
- description: "Unique identifier for the participant receiving the reward"
516
- }),
517
- participant_name: ParticipantNameSchema.meta({
518
- title: "Participant Name",
519
- description: "Name of the participant receiving the reward"
520
- }),
521
- role: ParticipantRoleSchema.meta({
522
- title: "Participant Role",
523
- description: "Role of the participant in the supply chain"
524
- }),
525
- reward_percentage: PercentageSchema.meta({
526
- title: "Reward Percentage",
527
- description: "Reward percentage allocated to the participant"
528
- }),
529
- large_business_discount_applied: zod.z.boolean().optional().meta({
530
- title: "Large Business Discount Applied",
531
- description: "Whether the large business discount was applied"
532
- }),
533
- effective_percentage: PercentageSchema.meta({
534
- title: "Effective Percentage",
535
- description: "Effective percentage of the reward after discounts"
536
- })
537
- }).meta({
538
- title: "Reward Allocation",
539
- description: "Reward allocation for a specific participant"
540
- });
541
- var DistributionNotesSchema = zod.z.strictObject({
542
- large_business_discount_applied: NonEmptyStringSchema.optional().meta({
543
- title: "Large Business Discount Applied",
544
- description: "Description of the large business discount applied",
545
- examples: [
546
- "50% reduction applied to participants with >$4M annual revenue"
547
- ]
548
- }),
549
- redirected_rewards: NonEmptyStringSchema.optional().meta({
550
- title: "Redirected Rewards",
551
- description: "Description of the redirected rewards",
552
- examples: [
553
- "Discounted rewards from large businesses redirected to accredited NGOs"
554
- ]
555
- })
556
- }).meta({
557
- title: "Distribution Notes",
558
- description: "Additional notes about the reward distribution"
559
- });
560
- var ParticipantRewardsSchema = zod.z.strictObject({
561
- distribution_basis: NonEmptyStringSchema.max(200).meta({
562
- title: "Distribution Basis",
563
- description: "Basis for the rewards distribution"
564
- }),
565
- reward_allocations: zod.z.array(RewardAllocationSchema).min(1).meta({
566
- title: "Reward Allocations",
567
- description: "Rewards percentage allocated to each participant"
568
- }),
569
- distribution_notes: DistributionNotesSchema.optional().meta({
570
- title: "Distribution Notes",
571
- description: "Additional notes about the reward distribution"
572
- })
573
- }).meta({
574
- title: "Participant Rewards",
575
- description: "Rewards distribution to participants"
285
+ var TokenSymbolSchema = NonEmptyStringSchema.max(10).regex(
286
+ /^[A-Z0-9-]+$/,
287
+ "Must contain only uppercase letters, numbers, and hyphens"
288
+ ).meta({
289
+ title: "Token Symbol",
290
+ description: "Symbol representing a token or cryptocurrency",
291
+ examples: ["MASS", "REC", "GAS"]
576
292
  });
577
- var SchemaHashSchema = Sha256HashSchema.meta({
578
- title: "Schema Hash",
579
- description: "SHA-256 hash of the JSON Schema this record was validated against"
293
+ var CreditTokenSymbolSchema = TokenSymbolSchema.meta({
294
+ title: "Credit Token Symbol",
295
+ description: "Symbol of the credit token (e.g., C-CARB, C-BIOW)",
296
+ examples: ["C-CARB", "C-BIOW"]
580
297
  });
298
+
299
+ // src/shared/schemas/core/base.schema.ts
581
300
  var SchemaInfoSchema = zod.z.strictObject({
582
- hash: SchemaHashSchema,
301
+ hash: Sha256HashSchema.meta({
302
+ title: "Schema Hash",
303
+ description: "SHA-256 hash of the JSON Schema this record was validated against"
304
+ }),
583
305
  type: RecordSchemaTypeSchema,
584
306
  version: SemanticVersionSchema.meta({
585
307
  title: "Schema Version",
@@ -636,11 +358,24 @@ var BaseIpfsSchema = zod.z.strictObject({
636
358
  title: "Base IPFS Record",
637
359
  description: "Base fields for all Carrot IPFS records, providing common structure for any JSON content stored in IPFS"
638
360
  });
639
- var BLOCKCHAIN_NETWORK_CONFIG = {
640
- mainnet: { chain_id: 137, network_name: "Polygon" },
641
- testnet: { chain_id: 80002, network_name: "Amoy" }
642
- };
643
- var ALLOWED_BLOCKCHAIN_NETWORKS = Object.values(BLOCKCHAIN_NETWORK_CONFIG);
361
+ function uniqueArrayItems(schema, errorMessage = "Array items must be unique") {
362
+ return zod.z.array(schema).refine((items) => new Set(items).size === items.length, {
363
+ message: errorMessage
364
+ });
365
+ }
366
+ function uniqueBy(schema, selector, errorMessage = "Items must be unique") {
367
+ return zod.z.array(schema).refine(
368
+ (items) => {
369
+ const values = items.map(selector);
370
+ return new Set(values).size === values.length;
371
+ },
372
+ {
373
+ message: errorMessage
374
+ }
375
+ );
376
+ }
377
+
378
+ // src/shared/schemas/core/nft.schema.ts
644
379
  var NftSchemaTypeSchema = RecordSchemaTypeSchema.extract([
645
380
  "MassID",
646
381
  "RecycledID",
@@ -652,16 +387,10 @@ var NftSchemaTypeSchema = RecordSchemaTypeSchema.extract([
652
387
  description: "Type of schema for NFT records"
653
388
  });
654
389
  var BlockchainReferenceSchema = zod.z.strictObject({
655
- smart_contract_address: EthereumAddressSchema.meta({
656
- title: "Smart Contract Address"
657
- }),
658
- chain_id: BlockchainChainIdSchema.meta({
659
- title: "Chain ID",
660
- description: "Blockchain chain ID"
661
- }),
390
+ smart_contract_address: SmartContractAddressSchema,
391
+ chain_id: BlockchainChainIdSchema,
662
392
  network_name: BlockchainNetworkNameSchema,
663
393
  token_id: TokenIdSchema.meta({
664
- title: "Token ID",
665
394
  description: "NFT token ID"
666
395
  })
667
396
  }).superRefine((value, ctx) => {
@@ -685,11 +414,11 @@ var BlockchainReferenceSchema = zod.z.strictObject({
685
414
  description: "Blockchain-specific information for the NFT"
686
415
  });
687
416
  var ExternalLinkSchema = zod.z.strictObject({
688
- label: zod.z.string().min(1).max(50).meta({
417
+ label: NonEmptyStringSchema.max(50).meta({
689
418
  title: "Link Label",
690
419
  description: "Display name for the external link"
691
420
  }),
692
- url: zod.z.url("Must be a valid URI").meta({
421
+ url: ExternalUrlSchema.meta({
693
422
  title: "Link URL",
694
423
  description: "Direct URI to the linked resource"
695
424
  }),
@@ -702,7 +431,7 @@ var ExternalLinkSchema = zod.z.strictObject({
702
431
  description: "External link with label and description"
703
432
  });
704
433
  var NftAttributeSchema = zod.z.strictObject({
705
- trait_type: zod.z.string().max(50).meta({
434
+ trait_type: NonEmptyStringSchema.max(50).meta({
706
435
  title: "Trait Type",
707
436
  description: "Name of the trait or attribute"
708
437
  }),
@@ -730,7 +459,7 @@ var NftIpfsSchema = BaseIpfsSchema.safeExtend({
730
459
  })
731
460
  }),
732
461
  blockchain: BlockchainReferenceSchema,
733
- name: zod.z.string().min(1).max(100).meta({
462
+ name: NonEmptyStringSchema.max(100).meta({
734
463
  title: "NFT Name",
735
464
  description: "Full display name for this NFT, including extra context",
736
465
  examples: [
@@ -739,12 +468,12 @@ var NftIpfsSchema = BaseIpfsSchema.safeExtend({
739
468
  "GasID #789 \u2022 Methane \u2022 1000 m\xB3"
740
469
  ]
741
470
  }),
742
- short_name: zod.z.string().min(1).max(50).meta({
471
+ short_name: NonEmptyStringSchema.max(50).meta({
743
472
  title: "Short Name",
744
473
  description: "Compact name for UI summaries, tables, or tooltips",
745
474
  examples: ["MassID #123", "RecycledID #456", "GasID #789"]
746
475
  }),
747
- description: zod.z.string().min(10).max(500).meta({
476
+ description: NonEmptyStringSchema.max(500).meta({
748
477
  title: "Description",
749
478
  description: "Human-readable summary of the NFT's role and context. Ideally, maximum 300 characters.",
750
479
  examples: [
@@ -764,31 +493,17 @@ var NftIpfsSchema = BaseIpfsSchema.safeExtend({
764
493
  title: "Animation URL",
765
494
  description: "IPFS URI pointing to an animated or interactive media file",
766
495
  examples: [
767
- "ipfs://QmAnimation123/mass-id-animation.mp4",
768
- "ipfs://QmInteractive456/recycled-visualization.webm"
496
+ "ipfs://bafybeigdyrztvzl5cceubvaxob7iqh6f3f7s36c74ojav2xsz2uib2g3vm/mass-id-animation.mp4",
497
+ "ipfs://bafybeihdwdcefgh4dqkjv67uzcmw7ojee6xedzdetojuzjevtenxquvyku/recycled-visualization.webm"
769
498
  ]
770
499
  }),
771
500
  external_links: uniqueBy(
772
501
  ExternalLinkSchema,
773
502
  (link) => link.url,
774
503
  "External link URLs must be unique"
775
- ).max(10).optional().meta({
504
+ ).optional().meta({
776
505
  title: "External Links",
777
- description: "Optional list of public resource links with labels",
778
- examples: [
779
- [
780
- {
781
- label: "Carrot Explorer",
782
- url: "https://explore.carrot.eco/document/ad44dd3f-f176-4b98-bf78-5ee6e77d0530",
783
- description: "Complete chain of custody and audit trail"
784
- },
785
- {
786
- label: "Carrot White Paper",
787
- url: "https://carrot.eco/whitepaper.pdf",
788
- description: "Carrot Foundation technical and impact white paper"
789
- }
790
- ]
791
- ]
506
+ description: "Optional list of public resource links with labels"
792
507
  }),
793
508
  attributes: uniqueBy(
794
509
  NftAttributeSchema,
@@ -796,33 +511,7 @@ var NftIpfsSchema = BaseIpfsSchema.safeExtend({
796
511
  "Attribute trait_type values must be unique"
797
512
  ).meta({
798
513
  title: "NFT Attributes",
799
- description: "List of visual traits and filterable attributes compatible with NFT marketplaces",
800
- examples: [
801
- [
802
- {
803
- trait_type: "Waste Type",
804
- value: "Organic"
805
- },
806
- {
807
- trait_type: "Waste Subtype",
808
- value: "Food, Food Waste and Beverages"
809
- },
810
- {
811
- trait_type: "Weight (kg)",
812
- value: 3e3,
813
- display_type: "number"
814
- },
815
- {
816
- trait_type: "Origin Country",
817
- value: "Brazil"
818
- },
819
- {
820
- trait_type: "Pick-up Date",
821
- value: "2024-12-05",
822
- display_type: "date"
823
- }
824
- ]
825
- ]
514
+ description: "List of visual traits and filterable attributes compatible with NFT marketplaces"
826
515
  })
827
516
  }).superRefine((value, ctx) => {
828
517
  const environmentNetwork = value.environment?.blockchain_network;
@@ -848,16 +537,6 @@ var NftIpfsSchema = BaseIpfsSchema.safeExtend({
848
537
  title: "NFT IPFS Record",
849
538
  description: "NFT-specific fields for Carrot IPFS records"
850
539
  });
851
- function getSchemaBaseUrl() {
852
- return `https://raw.githubusercontent.com/carrot-foundation/schemas/refs/tags/${getSchemaVersionOrDefault()}/schemas/ipfs`;
853
- }
854
- function buildSchemaUrl(schemaPath) {
855
- const cleanPath = schemaPath.startsWith("/") ? schemaPath.slice(1) : schemaPath;
856
- return `${getSchemaBaseUrl()}/${cleanPath}`;
857
- }
858
- function getSchemaVersionOrDefault() {
859
- return "0.1.41";
860
- }
861
540
  var MethodologyAttributeSchema = NftAttributeSchema.safeExtend({
862
541
  trait_type: zod.z.literal("Methodology"),
863
542
  value: MethodologyNameSchema
@@ -920,117 +599,377 @@ var RecyclerAttributeSchema = NftAttributeSchema.safeExtend({
920
599
  example: "Eco Reciclagem"
921
600
  })
922
601
  }).meta({
923
- title: "Recycler Attribute",
924
- description: "Recycler attribute"
602
+ title: "Recycler Attribute",
603
+ description: "Recycler attribute"
604
+ });
605
+ var MassIDTokenIdAttributeSchema = NftAttributeSchema.safeExtend({
606
+ trait_type: zod.z.literal("MassID"),
607
+ value: StringifiedTokenIdSchema.meta({
608
+ title: "MassID Token ID",
609
+ description: "Token ID of the source MassID NFT as #<token_id>"
610
+ })
611
+ }).meta({
612
+ title: "MassID Token ID Attribute",
613
+ description: "MassID token ID attribute"
614
+ });
615
+ var MassIDRecyclingDateAttributeSchema = NftAttributeSchema.omit({
616
+ max_value: true
617
+ }).safeExtend({
618
+ trait_type: zod.z.literal("MassID Recycling Date"),
619
+ value: UnixTimestampSchema.meta({
620
+ title: "MassID Recycling Date",
621
+ description: "Unix timestamp in milliseconds when the source waste was recycled"
622
+ }),
623
+ display_type: zod.z.literal("date")
624
+ }).meta({
625
+ title: "MassID Recycling Date Attribute",
626
+ description: "MassID recycling date attribute using Unix timestamp in milliseconds"
627
+ });
628
+ var MethodologyComplianceSchema = zod.z.enum(["PASSED", "FAILED"]).meta({
629
+ title: "Methodology Compliance",
630
+ description: "Result of methodology compliance check",
631
+ examples: ["PASSED", "FAILED"]
632
+ });
633
+ var AuditReferenceSchema = zod.z.strictObject({
634
+ date: IsoDateSchema.meta({
635
+ title: "Audit Date",
636
+ description: "Date when the audit was completed"
637
+ }),
638
+ external_id: ExternalIdSchema.meta({
639
+ title: "Audit External ID",
640
+ description: "Unique identifier for the audit"
641
+ }),
642
+ external_url: ExternalUrlSchema.meta({
643
+ title: "Audit External URL",
644
+ description: "URL to view the audit on Carrot Explorer"
645
+ }),
646
+ methodology_compliance: MethodologyComplianceSchema.meta({
647
+ title: "Methodology Compliance",
648
+ description: "Result of methodology compliance check"
649
+ }),
650
+ rules_executed: NonNegativeIntegerSchema.meta({
651
+ title: "Rules Executed",
652
+ description: "Number of rules executed during the audit"
653
+ }),
654
+ report: IpfsUriSchema.meta({
655
+ title: "Audit Report",
656
+ description: "IPFS URI of the audit report"
657
+ })
658
+ }).meta({
659
+ title: "Audit Reference",
660
+ description: "Reference to an audit record"
661
+ });
662
+
663
+ // src/shared/schemas/audit.schema.ts
664
+ var AuditRuleDefinitionSchema = zod.z.strictObject({
665
+ rule_id: UuidSchema.meta({
666
+ title: "Rule ID",
667
+ description: "Unique identifier for the audit rule"
668
+ }),
669
+ rule_slug: SlugSchema.meta({
670
+ title: "Rule Slug",
671
+ description: "URL-friendly identifier for the rule"
672
+ }),
673
+ rule_name: NonEmptyStringSchema.max(100).meta({
674
+ title: "Rule Name",
675
+ description: "Human-readable name of the rule",
676
+ examples: ["Waste Mass is Unique", "No Conflicting GasID or Credit"]
677
+ }),
678
+ description: zod.z.string().min(10).max(500).meta({
679
+ title: "Rule Description",
680
+ description: "Detailed description of what the rule validates and why it is necessary",
681
+ examples: [
682
+ "Validates that each MassID is unique within the system to prevent duplicate entries"
683
+ ]
684
+ }),
685
+ source_code_url: zod.z.url().regex(/^https:\/\/github\.com\/.*$/, "Must be a GitHub URL").meta({
686
+ title: "Rule Source Code URL",
687
+ description: "GitHub URL pointing to the implementation source code for this rule",
688
+ examples: [
689
+ "https://github.com/carrot-foundation/methodologies/blob/main/bold-carbon/rules/waste-mass-unique.js"
690
+ ]
691
+ }),
692
+ execution_order: PositiveIntegerSchema.meta({
693
+ title: "Rule Execution Order",
694
+ description: "Sequential order in which this rule must be executed"
695
+ })
696
+ }).meta({
697
+ title: "Audit Rule Definition",
698
+ description: "Definition of an audit rule that must be executed for methodology compliance"
699
+ });
700
+ var AuditRuleDefinitionsSchema = zod.z.array(AuditRuleDefinitionSchema).min(1).meta({
701
+ title: "Audit Rule Definitions",
702
+ description: "List of audit rules that must be executed to check methodology compliance"
703
+ });
704
+ var AuditRuleExecutionResultSchema = zod.z.strictObject({
705
+ rule_name: NonEmptyStringSchema.meta({
706
+ title: "Rule Name",
707
+ description: "Human-readable name of the audit rule"
708
+ }),
709
+ rule_id: UuidSchema.meta({
710
+ title: "Rule ID",
711
+ description: "Unique identifier for the rule"
712
+ }),
713
+ rule_slug: SlugSchema.meta({
714
+ title: "Rule Slug",
715
+ description: "URL-friendly identifier for the rule"
716
+ }),
717
+ execution_order: PositiveIntegerSchema.meta({
718
+ title: "Rule Execution Order",
719
+ description: "Sequential order in which this rule was executed"
720
+ }),
721
+ result: MethodologyComplianceSchema.meta({
722
+ title: "Rule Execution Result",
723
+ description: "Result of the rule execution"
724
+ }),
725
+ description: zod.z.string().min(1).max(2e3).meta({
726
+ title: "Rule Description",
727
+ description: "Detailed description of what this rule validates"
728
+ }),
729
+ rule_processor_checksum: NonEmptyStringSchema.max(200).meta({
730
+ title: "Rule Processor Checksum",
731
+ description: "Checksum for rule processor integrity verification"
732
+ }),
733
+ rule_source_code_version: NonEmptyStringSchema.max(200).meta({
734
+ title: "Rule Source Code Version",
735
+ description: "Version identifier for the rule source code"
736
+ })
737
+ }).meta({
738
+ title: "Audit Rule Execution Result",
739
+ description: "Detailed result of an audit rule execution"
740
+ });
741
+ var AuditRuleExecutionResultsSchema = zod.z.array(AuditRuleExecutionResultSchema).meta({
742
+ title: "Audit Rule Execution Results",
743
+ description: "Detailed results of each audit rule execution"
744
+ });
745
+ var ParticipantSchema = zod.z.strictObject({
746
+ id_hash: Sha256HashSchema.meta({
747
+ title: "Participant ID Hash",
748
+ description: "Anonymized identifier for the participant"
749
+ }),
750
+ name: ParticipantNameSchema,
751
+ roles: uniqueArrayItems(
752
+ ParticipantRoleSchema,
753
+ "Participant roles must be unique"
754
+ ).min(1).meta({
755
+ title: "Participant Roles",
756
+ description: "Roles of the participant in the waste management supply chain"
757
+ })
758
+ }).meta({
759
+ title: "Participant",
760
+ description: "A participant in the waste management supply chain"
761
+ });
762
+ var PrecisionLevelSchema = zod.z.enum(["city", "region", "country"]).meta({
763
+ title: "Coordinate Precision Level",
764
+ description: "Level of coordinate precision",
765
+ examples: ["city"]
766
+ });
767
+ var CoordinatesSchema = zod.z.strictObject({
768
+ latitude: LatitudeSchema,
769
+ longitude: LongitudeSchema,
770
+ precision_level: PrecisionLevelSchema
771
+ }).meta({
772
+ title: "Coordinates",
773
+ description: "GPS coordinates of the location"
774
+ });
775
+ var LocationSchema = zod.z.strictObject({
776
+ id_hash: Sha256HashSchema.meta({
777
+ title: "Location ID Hash",
778
+ description: "Anonymized identifier for the location"
779
+ }),
780
+ municipality: MunicipalitySchema,
781
+ administrative_division: AdministrativeDivisionSchema,
782
+ administrative_division_code: IsoAdministrativeDivisionCodeSchema.optional(),
783
+ country: CountryNameSchema,
784
+ country_code: IsoCountryCodeSchema,
785
+ responsible_participant_id_hash: Sha256HashSchema.meta({
786
+ title: "Responsible Participant ID Hash",
787
+ description: "Anonymized ID of the participant responsible for this location"
788
+ }),
789
+ coordinates: CoordinatesSchema
790
+ }).meta({
791
+ title: "Location",
792
+ description: "Geographic location with address and coordinate information"
793
+ });
794
+ var GasIDReferenceSchema = zod.z.strictObject({
795
+ external_id: ExternalIdSchema.meta({
796
+ title: "GasID External ID",
797
+ description: "Unique identifier for the GasID"
798
+ }),
799
+ token_id: TokenIdSchema.meta({
800
+ title: "GasID Token ID",
801
+ description: "NFT token ID of the GasID"
802
+ }),
803
+ external_url: ExternalUrlSchema.meta({
804
+ title: "GasID External URL",
805
+ description: "URL to view the GasID on Carrot Explorer"
806
+ }),
807
+ uri: IpfsUriSchema.meta({
808
+ title: "GasID IPFS URI",
809
+ description: "IPFS URI of the GasID record"
810
+ })
811
+ }).meta({
812
+ title: "GasID Reference",
813
+ description: "Reference to a GasID record"
925
814
  });
926
- var MassIDTokenIdAttributeSchema = NftAttributeSchema.safeExtend({
927
- trait_type: zod.z.literal("MassID"),
928
- value: StringifiedTokenIdSchema.meta({
815
+ var MassIDReferenceSchema = zod.z.strictObject({
816
+ external_id: ExternalIdSchema.meta({
817
+ title: "MassID External ID",
818
+ description: "Unique identifier for the MassID"
819
+ }),
820
+ token_id: TokenIdSchema.meta({
929
821
  title: "MassID Token ID",
930
- description: "Token ID of the source MassID NFT as #<token_id>"
822
+ description: "NFT token ID of the MassID"
823
+ }),
824
+ external_url: ExternalUrlSchema.meta({
825
+ title: "MassID External URL",
826
+ description: "URL to view the MassID on Carrot Explorer"
827
+ }),
828
+ uri: IpfsUriSchema.meta({
829
+ title: "MassID IPFS URI",
830
+ description: "IPFS URI of the MassID record"
931
831
  })
932
832
  }).meta({
933
- title: "MassID Token ID Attribute",
934
- description: "MassID token ID attribute"
833
+ title: "MassID Reference",
834
+ description: "Reference to a MassID record"
935
835
  });
936
- var MassIDRecyclingDateAttributeSchema = NftAttributeSchema.omit({
937
- max_value: true
938
- }).safeExtend({
939
- trait_type: zod.z.literal("MassID Recycling Date"),
940
- value: UnixTimestampSchema.meta({
941
- title: "MassID Recycling Date",
942
- description: "Unix timestamp in milliseconds when the source waste was recycled"
836
+ var MethodologyReferenceSchema = zod.z.strictObject({
837
+ external_id: ExternalIdSchema.meta({
838
+ title: "Methodology External ID",
839
+ description: "Unique identifier for the methodology"
943
840
  }),
944
- display_type: zod.z.literal("date")
841
+ name: NonEmptyStringSchema.min(5).max(150).meta({
842
+ title: "Methodology Name",
843
+ description: "Human-readable name of the methodology",
844
+ examples: ["BOLD Carbon (CH\u2084)", "BOLD Recycling"]
845
+ }),
846
+ version: SemanticVersionSchema.meta({
847
+ title: "Methodology Version",
848
+ description: "Version of the methodology"
849
+ }),
850
+ external_url: ExternalUrlSchema.meta({
851
+ title: "Methodology External URL",
852
+ description: "URL to view the methodology on Carrot Explorer"
853
+ }),
854
+ uri: IpfsUriSchema.optional().meta({
855
+ title: "Methodology IPFS URI",
856
+ description: "IPFS URI to the methodology record"
857
+ })
945
858
  }).meta({
946
- title: "MassID Recycling Date Attribute",
947
- description: "MassID recycling date attribute using Unix timestamp in milliseconds"
859
+ title: "Methodology Reference",
860
+ description: "Reference to a methodology record"
948
861
  });
949
- var AuditRuleDefinitionSchema = zod.z.strictObject({
950
- rule_id: UuidSchema.meta({
951
- title: "Rule ID",
952
- description: "Unique identifier for the audit rule"
862
+ var WasteClassificationSchema = zod.z.strictObject({
863
+ primary_type: WasteTypeSchema.meta({
864
+ title: "Source Waste Primary Type",
865
+ description: "Primary type of the source waste"
953
866
  }),
954
- rule_slug: SlugSchema.meta({
955
- title: "Rule Slug",
956
- description: "URL-friendly identifier for the rule"
867
+ subtype: WasteSubtypeSchema.meta({
868
+ title: "Source Waste Subtype",
869
+ description: "Subtype of the source waste"
957
870
  }),
958
- rule_name: NonEmptyStringSchema.max(100).meta({
959
- title: "Rule Name",
960
- description: "Human-readable name of the rule",
961
- examples: ["Waste Mass is Unique", "No Conflicting GasID or Credit"]
871
+ net_weight_kg: WeightKgSchema.meta({
872
+ title: "Source Waste Net Weight",
873
+ description: "Net weight of the source waste"
874
+ })
875
+ }).meta({
876
+ title: "Waste Classification",
877
+ description: "Classification of the source waste (MassID)"
878
+ });
879
+ var AccreditedParticipantSchema = zod.z.strictObject({
880
+ participant_id: UuidSchema.meta({
881
+ title: "Participant ID",
882
+ description: "Unique identifier for the participant"
962
883
  }),
963
- description: zod.z.string().min(10).max(500).meta({
964
- title: "Rule Description",
965
- description: "Detailed description of what the rule validates and why it is necessary",
966
- examples: [
967
- "Validates that each MassID is unique within the system to prevent duplicate entries"
968
- ]
884
+ name: ParticipantNameSchema.meta({
885
+ title: "Participant Name",
886
+ description: "Name of the participant"
969
887
  }),
970
- source_code_url: zod.z.url().regex(/^https:\/\/github\.com\/.*$/, "Must be a GitHub URL").meta({
971
- title: "Rule Source Code URL",
972
- description: "GitHub URL pointing to the implementation source code for this rule",
973
- examples: [
974
- "https://github.com/carrot-foundation/methodologies/blob/main/bold-carbon/rules/waste-mass-unique.js"
975
- ]
888
+ role: ParticipantRoleSchema.meta({
889
+ title: "Participant Role",
890
+ description: "Role of the participant in the supply chain"
976
891
  }),
977
- execution_order: PositiveIntegerSchema.meta({
978
- title: "Rule Execution Order",
979
- description: "Sequential order in which this rule must be executed"
892
+ accreditation_id: UuidSchema.meta({
893
+ title: "Accreditation ID",
894
+ description: "Unique identifier for the participant accreditation"
895
+ }),
896
+ external_url: ExternalUrlSchema.meta({
897
+ title: "Participant Accreditation External URL",
898
+ description: "URL to view the participant accreditation on Carrot Explorer"
980
899
  })
981
900
  }).meta({
982
- title: "Audit Rule Definition",
983
- description: "Definition of an audit rule that must be executed for methodology compliance"
901
+ title: "Accredited Participant",
902
+ description: "Participant with valid accreditation in the supply chain"
984
903
  });
985
- var AuditRuleDefinitionsSchema = zod.z.array(AuditRuleDefinitionSchema).min(1).meta({
986
- title: "Audit Rule Definitions",
987
- description: "List of audit rules that must be executed to check methodology compliance"
904
+ var AccreditedParticipantsSchema = zod.z.array(AccreditedParticipantSchema).min(1).meta({
905
+ title: "Accredited Participants",
906
+ description: "List of participants with valid accreditations"
988
907
  });
989
- var AuditRuleExecutionResultSchema = zod.z.strictObject({
990
- rule_name: NonEmptyStringSchema.meta({
991
- title: "Rule Name",
992
- description: "Human-readable name of the audit rule"
993
- }),
994
- rule_id: UuidSchema.meta({
995
- title: "Rule ID",
996
- description: "Unique identifier for the rule"
908
+ var RewardAllocationSchema = zod.z.strictObject({
909
+ participant_id: UuidSchema.meta({
910
+ title: "Participant ID",
911
+ description: "Unique identifier for the participant receiving the reward"
997
912
  }),
998
- rule_slug: SlugSchema.meta({
999
- title: "Rule Slug",
1000
- description: "URL-friendly identifier for the rule"
913
+ participant_name: ParticipantNameSchema.meta({
914
+ title: "Participant Name",
915
+ description: "Name of the participant receiving the reward"
1001
916
  }),
1002
- execution_order: PositiveIntegerSchema.meta({
1003
- title: "Rule Execution Order",
1004
- description: "Sequential order in which this rule was executed"
917
+ role: ParticipantRoleSchema.meta({
918
+ title: "Participant Role",
919
+ description: "Role of the participant in the supply chain"
1005
920
  }),
1006
- result: MethodologyComplianceSchema.meta({
1007
- title: "Rule Execution Result",
1008
- description: "Result of the rule execution"
921
+ reward_percentage: PercentageSchema.meta({
922
+ title: "Reward Percentage",
923
+ description: "Reward percentage allocated to the participant"
1009
924
  }),
1010
- description: zod.z.string().min(1).max(2e3).meta({
1011
- title: "Rule Description",
1012
- description: "Detailed description of what this rule validates"
925
+ large_business_discount_applied: zod.z.boolean().optional().meta({
926
+ title: "Large Business Discount Applied",
927
+ description: "Whether the large business discount was applied"
1013
928
  }),
1014
- rule_processor_checksum: NonEmptyStringSchema.max(200).meta({
1015
- title: "Rule Processor Checksum",
1016
- description: "Checksum for rule processor integrity verification"
929
+ effective_percentage: PercentageSchema.meta({
930
+ title: "Effective Percentage",
931
+ description: "Effective percentage of the reward after discounts"
932
+ })
933
+ }).meta({
934
+ title: "Reward Allocation",
935
+ description: "Reward allocation for a specific participant"
936
+ });
937
+ var DistributionNotesSchema = zod.z.strictObject({
938
+ large_business_discount_applied: NonEmptyStringSchema.optional().meta({
939
+ title: "Large Business Discount Applied",
940
+ description: "Description of the large business discount applied",
941
+ examples: [
942
+ "50% reduction applied to participants with >$4M annual revenue"
943
+ ]
1017
944
  }),
1018
- rule_source_code_version: NonEmptyStringSchema.max(200).meta({
1019
- title: "Rule Source Code Version",
1020
- description: "Version identifier for the rule source code"
945
+ redirected_rewards: NonEmptyStringSchema.optional().meta({
946
+ title: "Redirected Rewards",
947
+ description: "Description of the redirected rewards",
948
+ examples: [
949
+ "Discounted rewards from large businesses redirected to accredited NGOs"
950
+ ]
1021
951
  })
1022
952
  }).meta({
1023
- title: "Audit Rule Execution Result",
1024
- description: "Detailed result of an audit rule execution"
953
+ title: "Distribution Notes",
954
+ description: "Additional notes about the reward distribution"
1025
955
  });
1026
- var AuditRuleExecutionResultsSchema = zod.z.array(AuditRuleExecutionResultSchema).meta({
1027
- title: "Audit Rule Execution Results",
1028
- description: "Detailed results of each audit rule execution"
956
+ var ParticipantRewardsSchema = zod.z.strictObject({
957
+ distribution_basis: NonEmptyStringSchema.max(200).meta({
958
+ title: "Distribution Basis",
959
+ description: "Basis for the rewards distribution"
960
+ }),
961
+ reward_allocations: zod.z.array(RewardAllocationSchema).min(1).meta({
962
+ title: "Reward Allocations",
963
+ description: "Rewards percentage allocated to each participant"
964
+ }),
965
+ distribution_notes: DistributionNotesSchema.optional().meta({
966
+ title: "Distribution Notes",
967
+ description: "Additional notes about the reward distribution"
968
+ })
969
+ }).meta({
970
+ title: "Participant Rewards",
971
+ description: "Rewards distribution to participants"
1029
972
  });
1030
- var EPSILON = 1e-9;
1031
- function nearlyEqual(a, b, epsilon = EPSILON) {
1032
- return Math.abs(a - b) <= epsilon;
1033
- }
1034
973
  var SummaryBaseSchema = zod.z.strictObject({
1035
974
  total_certificates: PositiveIntegerSchema.meta({
1036
975
  title: "Total Certificates",
@@ -1202,8 +1141,22 @@ function createReceiptCertificateSchema(params) {
1202
1141
  ...params.additionalShape
1203
1142
  }).meta(params.meta);
1204
1143
  }
1144
+ function getSchemaBaseUrl() {
1145
+ return `https://raw.githubusercontent.com/carrot-foundation/schemas/refs/tags/${getSchemaVersionOrDefault()}/schemas/ipfs`;
1146
+ }
1147
+ function buildSchemaUrl(schemaPath) {
1148
+ const cleanPath = schemaPath.startsWith("/") ? schemaPath.slice(1) : schemaPath;
1149
+ return `${getSchemaBaseUrl()}/${cleanPath}`;
1150
+ }
1151
+ function getSchemaVersionOrDefault() {
1152
+ return "0.1.43";
1153
+ }
1205
1154
 
1206
- // src/shared/receipt/receipt.validation.ts
1155
+ // src/shared/schema-validation.ts
1156
+ var EPSILON = 1e-9;
1157
+ function nearlyEqual(a, b, epsilon = EPSILON) {
1158
+ return Math.abs(a - b) <= epsilon;
1159
+ }
1207
1160
  function buildMessage(message, value) {
1208
1161
  return typeof message === "function" ? message(value) : message;
1209
1162
  }
@@ -1352,6 +1305,20 @@ function validateAttributesForItems(params) {
1352
1305
  }
1353
1306
  });
1354
1307
  }
1308
+ function canonicalizeForHash(value) {
1309
+ const canonical = canonicalize__default.default(value);
1310
+ if (canonical === void 0) {
1311
+ throw new TypeError("Value is not serializable to canonical JSON");
1312
+ }
1313
+ return canonical;
1314
+ }
1315
+ function hashCanonicalJson(canonicalJson) {
1316
+ return crypto.createHash("sha256").update(canonicalJson, "utf8").digest("hex");
1317
+ }
1318
+ function hashObject(value) {
1319
+ const canonical = canonicalizeForHash(value);
1320
+ return hashCanonicalJson(canonical);
1321
+ }
1355
1322
  var IbamaWasteClassificationSchema = zod.z.string().regex(/^\d{2} \d{2} \d{2}\*?$/, "Invalid Ibama code format").meta({
1356
1323
  title: "Ibama Classification Code",
1357
1324
  description: "Ibama waste classification code in the format NN NN NN with required spaces and optional trailing *",
@@ -2122,8 +2089,17 @@ var GasIDIpfsSchema = NftIpfsSchema.safeExtend({
2122
2089
  description: "GasID NFT schema type"
2123
2090
  })
2124
2091
  }),
2125
- attributes: GasIDAttributesSchema,
2126
2092
  data: GasIDDataSchema
2093
+ }).superRefine((value, ctx) => {
2094
+ const attributesResult = GasIDAttributesSchema.safeParse(value.attributes);
2095
+ if (!attributesResult.success) {
2096
+ attributesResult.error.issues.forEach((issue) => {
2097
+ ctx.addIssue({
2098
+ ...issue,
2099
+ path: ["attributes", ...issue.path]
2100
+ });
2101
+ });
2102
+ }
2127
2103
  }).meta(GasIDIpfsSchemaMeta);
2128
2104
  var RecycledIDAttributeMethodologySchema = MethodologyAttributeSchema;
2129
2105
  var RecycledIDAttributeRecycledMassWeightSchema = NftAttributeSchema.safeExtend({
@@ -2202,8 +2178,19 @@ var RecycledIDIpfsSchema = NftIpfsSchema.safeExtend({
2202
2178
  description: "RecycledID NFT schema type"
2203
2179
  })
2204
2180
  }),
2205
- attributes: RecycledIDAttributesSchema,
2206
2181
  data: RecycledIDDataSchema
2182
+ }).superRefine((value, ctx) => {
2183
+ const attributesResult = RecycledIDAttributesSchema.safeParse(
2184
+ value.attributes
2185
+ );
2186
+ if (!attributesResult.success) {
2187
+ attributesResult.error.issues.forEach((issue) => {
2188
+ ctx.addIssue({
2189
+ ...issue,
2190
+ path: ["attributes", ...issue.path]
2191
+ });
2192
+ });
2193
+ }
2207
2194
  }).meta(RecycledIDIpfsSchemaMeta);
2208
2195
  var CreditPurchaseReceiptCreditAttributeSchema = NftAttributeSchema.safeExtend({
2209
2196
  trait_type: TokenSymbolSchema.meta({
@@ -3294,7 +3281,9 @@ var CollectionSchema = BaseIpfsSchema.safeExtend({
3294
3281
  image: IpfsUriSchema.meta({
3295
3282
  title: "Collection Image",
3296
3283
  description: "IPFS URI pointing to the collection's visual representation",
3297
- examples: ["ipfs://QmCollectionImageHash/collection-icon.png"]
3284
+ examples: [
3285
+ "ipfs://bafybeihdwdcefgh4dqkjv67uzcmw7ojee6xedzdetojuzjevtenxquvyku/collection-icon.png"
3286
+ ]
3298
3287
  }),
3299
3288
  description: zod.z.string().min(50).max(1e3).meta({
3300
3289
  title: "Collection Description",
@@ -3336,7 +3325,9 @@ var CreditSchema = BaseIpfsSchema.safeExtend({
3336
3325
  image: IpfsUriSchema.meta({
3337
3326
  title: "Token Image",
3338
3327
  description: "IPFS URI pointing to the token's visual representation image",
3339
- examples: ["ipfs://QmTokenImageHash/credit-icon.png"]
3328
+ examples: [
3329
+ "ipfs://bafybeigdyrztvzl5cceubvaxob7iqh6f3f7s36c74ojav2xsz2uib2g3vm/credit-icon.png"
3330
+ ]
3340
3331
  }),
3341
3332
  description: zod.z.string().min(50).max(1e3).meta({
3342
3333
  title: "Token Description",
@@ -3459,6 +3450,7 @@ var MassIDAuditSchema = BaseIpfsSchema.safeExtend({
3459
3450
  data: MassIDAuditDataSchema
3460
3451
  }).meta(MassIDAuditSchemaMeta);
3461
3452
 
3453
+ exports.ALLOWED_BLOCKCHAIN_NETWORKS = ALLOWED_BLOCKCHAIN_NETWORKS;
3462
3454
  exports.AccreditedParticipantSchema = AccreditedParticipantSchema;
3463
3455
  exports.AccreditedParticipantsSchema = AccreditedParticipantsSchema;
3464
3456
  exports.AdministrativeDivisionSchema = AdministrativeDivisionSchema;
@@ -3467,6 +3459,7 @@ exports.AuditRuleDefinitionSchema = AuditRuleDefinitionSchema;
3467
3459
  exports.AuditRuleDefinitionsSchema = AuditRuleDefinitionsSchema;
3468
3460
  exports.AuditRuleExecutionResultSchema = AuditRuleExecutionResultSchema;
3469
3461
  exports.AuditRuleExecutionResultsSchema = AuditRuleExecutionResultsSchema;
3462
+ exports.BLOCKCHAIN_NETWORK_CONFIG = BLOCKCHAIN_NETWORK_CONFIG;
3470
3463
  exports.BaseIpfsSchema = BaseIpfsSchema;
3471
3464
  exports.BlockchainChainIdSchema = BlockchainChainIdSchema;
3472
3465
  exports.BlockchainNetworkNameSchema = BlockchainNetworkNameSchema;
@@ -3504,7 +3497,6 @@ exports.GasIDIpfsSchema = GasIDIpfsSchema;
3504
3497
  exports.GasIDIpfsSchemaMeta = GasIDIpfsSchemaMeta;
3505
3498
  exports.GasIDReferenceSchema = GasIDReferenceSchema;
3506
3499
  exports.HexColorSchema = HexColorSchema;
3507
- exports.HoursSchema = HoursSchema;
3508
3500
  exports.IbamaWasteClassificationSchema = IbamaWasteClassificationSchema;
3509
3501
  exports.IpfsUriSchema = IpfsUriSchema;
3510
3502
  exports.IsoAdministrativeDivisionCodeSchema = IsoAdministrativeDivisionCodeSchema;
@@ -3532,7 +3524,6 @@ exports.MethodologyNameSchema = MethodologyNameSchema;
3532
3524
  exports.MethodologyReferenceSchema = MethodologyReferenceSchema;
3533
3525
  exports.MethodologySchema = MethodologySchema;
3534
3526
  exports.MethodologySchemaMeta = MethodologySchemaMeta;
3535
- exports.MinutesSchema = MinutesSchema;
3536
3527
  exports.MunicipalitySchema = MunicipalitySchema;
3537
3528
  exports.NftAttributeSchema = NftAttributeSchema;
3538
3529
  exports.NftIpfsSchema = NftIpfsSchema;
@@ -3573,12 +3564,15 @@ exports.WasteSubtypeSchema = WasteSubtypeSchema;
3573
3564
  exports.WasteTypeSchema = WasteTypeSchema;
3574
3565
  exports.WeightKgSchema = WeightKgSchema;
3575
3566
  exports.buildSchemaUrl = buildSchemaUrl;
3567
+ exports.canonicalizeForHash = canonicalizeForHash;
3576
3568
  exports.createAttributeMap = createAttributeMap;
3577
3569
  exports.createReceiptCertificateSchema = createReceiptCertificateSchema;
3578
3570
  exports.createReceiptCollectionSchema = createReceiptCollectionSchema;
3579
3571
  exports.createReceiptCreditSchema = createReceiptCreditSchema;
3580
3572
  exports.getSchemaBaseUrl = getSchemaBaseUrl;
3581
3573
  exports.getSchemaVersionOrDefault = getSchemaVersionOrDefault;
3574
+ exports.hashCanonicalJson = hashCanonicalJson;
3575
+ exports.hashObject = hashObject;
3582
3576
  exports.nearlyEqual = nearlyEqual;
3583
3577
  exports.uniqueArrayItems = uniqueArrayItems;
3584
3578
  exports.uniqueBy = uniqueBy;