@hazbase/simplicity 0.4.6 → 0.4.7

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.
@@ -0,0 +1,94 @@
1
+ import type { SimplicityArtifact, SimplicityClientConfig } from "../core/types";
2
+ export declare const STRICT_POLICY_SNAPSHOT_SCHEMA: "hazbase_strict_policy_snapshot_v1";
3
+ export declare const STRICT_POLICY_SNAPSHOT_APPROVAL_SCHEMA: "hazbase_strict_policy_snapshot_approval_v1";
4
+ export declare const STRICT_POLICY_SNAPSHOT_APPROVAL_DOMAIN: "HAZBASE-RWA-POLICY-SNAPSHOT-V1";
5
+ export declare const STRICT_POLICY_AUTHORITY_SET_DOMAIN: "HAZBASE-RWA-POLICY-AUTHORITY-SET-V1";
6
+ export declare const STRICT_POLICY_VERIFIER_MAX_INPUTS: 16;
7
+ export declare const STRICT_POLICY_VERIFIER_MAX_OUTPUTS: 8;
8
+ export type StrictPolicyNetwork = "liquid-regtest" | "liquid-testnet" | "liquid-mainnet";
9
+ export interface StrictPolicyVerifierReference {
10
+ outpoint: {
11
+ txid: string;
12
+ vout: number;
13
+ };
14
+ assetId: string;
15
+ amountAtomic: string;
16
+ cmr: string;
17
+ scriptHash: string;
18
+ }
19
+ export interface StrictPolicySnapshotPayload {
20
+ schema: typeof STRICT_POLICY_SNAPSHOT_SCHEMA;
21
+ network: StrictPolicyNetwork;
22
+ liquidGenesisHash: string;
23
+ assetBindingId: string;
24
+ liquidAssetId: string;
25
+ epoch: string;
26
+ previousSnapshotHash: string | null;
27
+ policyRoot: string;
28
+ whitelistRoot: string;
29
+ verifier: StrictPolicyVerifierReference;
30
+ effectiveAt: string;
31
+ validUntil: string | null;
32
+ }
33
+ export interface StrictPolicySnapshotAuthority {
34
+ authorityType: "issuer_single";
35
+ authorityId: string;
36
+ authorityVersion: string;
37
+ authoritySetHash: string;
38
+ approvalScheme: "bip340-sha256";
39
+ approvalThreshold: 1;
40
+ signerXonly: string;
41
+ approvedAt: string;
42
+ }
43
+ export interface StrictPolicySnapshotApprovalProof {
44
+ type: "issuer_single_v1";
45
+ signerXonly: string;
46
+ signatureHex: string;
47
+ }
48
+ export interface PreparedStrictPolicySnapshot {
49
+ payload: StrictPolicySnapshotPayload;
50
+ authority: StrictPolicySnapshotAuthority;
51
+ canonicalPayload: string;
52
+ snapshotHash: string;
53
+ canonicalApprovalMessage: string;
54
+ approvalMessageHash: string;
55
+ }
56
+ export interface StrictPolicySnapshotEnvelope extends PreparedStrictPolicySnapshot {
57
+ approvalProof: StrictPolicySnapshotApprovalProof;
58
+ approvalProofHash: string;
59
+ }
60
+ export interface StrictPolicyHolderCovenantParams {
61
+ strictAssetIdJetHex: string;
62
+ verifierAssetIdJetHex: string;
63
+ verifierAmountAtomic: string;
64
+ numsInternalKey: string;
65
+ }
66
+ export interface StrictPolicyVerifierCovenantParams {
67
+ strictAssetIdJetHex: string;
68
+ verifierAssetIdJetHex: string;
69
+ verifierAmountAtomic: string;
70
+ holderProgramCmr: string;
71
+ holderNumsInternalKey: string;
72
+ whitelistRoot: string;
73
+ redemptionScriptHash: string;
74
+ authorityXonly: string;
75
+ }
76
+ export declare function normalizeStrictPolicySnapshotPayload(value: unknown): StrictPolicySnapshotPayload;
77
+ export declare function normalizeStrictPolicySnapshotAuthority(value: unknown): StrictPolicySnapshotAuthority;
78
+ export declare function normalizeStrictPolicySnapshotApprovalProof(value: unknown): StrictPolicySnapshotApprovalProof;
79
+ export declare function normalizeStrictPolicyHolderCovenantParams(value: StrictPolicyHolderCovenantParams | unknown): StrictPolicyHolderCovenantParams;
80
+ export declare function normalizeStrictPolicyVerifierCovenantParams(value: StrictPolicyVerifierCovenantParams | unknown): StrictPolicyVerifierCovenantParams;
81
+ export declare function strictPolicyHolderCovenantTemplatePath(): string;
82
+ export declare function renderStrictPolicyHolderCovenantSource(value: StrictPolicyHolderCovenantParams | unknown): Promise<string>;
83
+ export declare function compileStrictPolicyHolderCovenant(config: SimplicityClientConfig, value: StrictPolicyHolderCovenantParams | unknown): Promise<SimplicityArtifact>;
84
+ export declare function strictPolicyVerifierCovenantTemplatePath(): string;
85
+ export declare function renderStrictPolicyVerifierCovenantSource(value: StrictPolicyVerifierCovenantParams | unknown): Promise<string>;
86
+ export declare function compileStrictPolicyVerifierCovenant(config: SimplicityClientConfig, value: StrictPolicyVerifierCovenantParams | unknown): Promise<SimplicityArtifact>;
87
+ export declare function taggedHashHexUtf8(tag: string, canonicalPayload: string): string;
88
+ export declare function computeStrictPolicyAuthoritySetHash(signerXonlyValue: string): string;
89
+ export declare function prepareStrictPolicySnapshot(input: {
90
+ payload: StrictPolicySnapshotPayload | unknown;
91
+ authority: StrictPolicySnapshotAuthority | unknown;
92
+ }): PreparedStrictPolicySnapshot;
93
+ export declare function finalizeStrictPolicySnapshot(prepared: PreparedStrictPolicySnapshot, proofValue: StrictPolicySnapshotApprovalProof | unknown): StrictPolicySnapshotEnvelope;
94
+ export declare function verifyStrictPolicySnapshot(envelopeValue: StrictPolicySnapshotEnvelope): Promise<PreparedStrictPolicySnapshot>;
@@ -0,0 +1,371 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.STRICT_POLICY_VERIFIER_MAX_OUTPUTS = exports.STRICT_POLICY_VERIFIER_MAX_INPUTS = exports.STRICT_POLICY_AUTHORITY_SET_DOMAIN = exports.STRICT_POLICY_SNAPSHOT_APPROVAL_DOMAIN = exports.STRICT_POLICY_SNAPSHOT_APPROVAL_SCHEMA = exports.STRICT_POLICY_SNAPSHOT_SCHEMA = void 0;
4
+ exports.normalizeStrictPolicySnapshotPayload = normalizeStrictPolicySnapshotPayload;
5
+ exports.normalizeStrictPolicySnapshotAuthority = normalizeStrictPolicySnapshotAuthority;
6
+ exports.normalizeStrictPolicySnapshotApprovalProof = normalizeStrictPolicySnapshotApprovalProof;
7
+ exports.normalizeStrictPolicyHolderCovenantParams = normalizeStrictPolicyHolderCovenantParams;
8
+ exports.normalizeStrictPolicyVerifierCovenantParams = normalizeStrictPolicyVerifierCovenantParams;
9
+ exports.strictPolicyHolderCovenantTemplatePath = strictPolicyHolderCovenantTemplatePath;
10
+ exports.renderStrictPolicyHolderCovenantSource = renderStrictPolicyHolderCovenantSource;
11
+ exports.compileStrictPolicyHolderCovenant = compileStrictPolicyHolderCovenant;
12
+ exports.strictPolicyVerifierCovenantTemplatePath = strictPolicyVerifierCovenantTemplatePath;
13
+ exports.renderStrictPolicyVerifierCovenantSource = renderStrictPolicyVerifierCovenantSource;
14
+ exports.compileStrictPolicyVerifierCovenant = compileStrictPolicyVerifierCovenant;
15
+ exports.taggedHashHexUtf8 = taggedHashHexUtf8;
16
+ exports.computeStrictPolicyAuthoritySetHash = computeStrictPolicyAuthoritySetHash;
17
+ exports.prepareStrictPolicySnapshot = prepareStrictPolicySnapshot;
18
+ exports.finalizeStrictPolicySnapshot = finalizeStrictPolicySnapshot;
19
+ exports.verifyStrictPolicySnapshot = verifyStrictPolicySnapshot;
20
+ const node_crypto_1 = require("node:crypto");
21
+ const errors_1 = require("../core/errors");
22
+ const schnorr_1 = require("../core/schnorr");
23
+ const summary_1 = require("../core/summary");
24
+ const templating_1 = require("../core/templating");
25
+ const dampPolicy_1 = require("./dampPolicy");
26
+ // These imports support Node-only template compilation. Keep their dynamic
27
+ // importer lazy so merely importing the snapshot verifier remains compatible
28
+ // with Chrome extension CSP.
29
+ function nativeImport(specifier) {
30
+ const importModule = new Function("value", "return import(value);");
31
+ return importModule(specifier);
32
+ }
33
+ async function readTemplateFile(templatePath) {
34
+ const fileSystem = await nativeImport("node:fs/promises");
35
+ return fileSystem.readFile(templatePath, "utf8");
36
+ }
37
+ async function loadCompiler() {
38
+ return await nativeImport(`${__dirname}/../core/compiler.js`);
39
+ }
40
+ exports.STRICT_POLICY_SNAPSHOT_SCHEMA = "hazbase_strict_policy_snapshot_v1";
41
+ exports.STRICT_POLICY_SNAPSHOT_APPROVAL_SCHEMA = "hazbase_strict_policy_snapshot_approval_v1";
42
+ exports.STRICT_POLICY_SNAPSHOT_APPROVAL_DOMAIN = "HAZBASE-RWA-POLICY-SNAPSHOT-V1";
43
+ exports.STRICT_POLICY_AUTHORITY_SET_DOMAIN = "HAZBASE-RWA-POLICY-AUTHORITY-SET-V1";
44
+ exports.STRICT_POLICY_VERIFIER_MAX_INPUTS = 16;
45
+ exports.STRICT_POLICY_VERIFIER_MAX_OUTPUTS = 8;
46
+ function validationError(field, message) {
47
+ throw new errors_1.ValidationError(`${field} ${message}`, {
48
+ code: "STRICT_POLICY_SNAPSHOT_INVALID",
49
+ field,
50
+ });
51
+ }
52
+ function recordValue(value, field) {
53
+ if (!value || typeof value !== "object" || Array.isArray(value)) {
54
+ validationError(field, "must be an object");
55
+ }
56
+ return value;
57
+ }
58
+ function stringValue(value, field) {
59
+ if (typeof value !== "string" || value.trim().length === 0) {
60
+ validationError(field, "must be a non-empty string");
61
+ }
62
+ return value.trim();
63
+ }
64
+ function literalValue(value, field, allowed) {
65
+ const normalized = stringValue(value, field);
66
+ if (!allowed.includes(normalized)) {
67
+ validationError(field, `must be one of ${allowed.join(", ")}`);
68
+ }
69
+ return normalized;
70
+ }
71
+ function hexValue(value, field, byteLength) {
72
+ const normalized = stringValue(value, field).toLowerCase().replace(/^0x/u, "");
73
+ if (!/^[0-9a-f]+$/u.test(normalized) || normalized.length !== byteLength * 2) {
74
+ validationError(field, `must be ${byteLength} bytes of hex`);
75
+ }
76
+ return normalized;
77
+ }
78
+ function decimalValue(value, field, allowZero = true) {
79
+ const normalized = stringValue(value, field);
80
+ if (!/^(0|[1-9][0-9]*)$/u.test(normalized)) {
81
+ validationError(field, "must be a canonical unsigned decimal string");
82
+ }
83
+ if (!allowZero && normalized === "0") {
84
+ validationError(field, "must be greater than zero");
85
+ }
86
+ return normalized;
87
+ }
88
+ function u64DecimalValue(value, field, allowZero = true) {
89
+ const normalized = decimalValue(value, field, allowZero);
90
+ if (BigInt(normalized) > 0xffffffffffffffffn) {
91
+ validationError(field, "must fit in an unsigned 64-bit integer");
92
+ }
93
+ return normalized;
94
+ }
95
+ function timestampValue(value, field) {
96
+ const normalized = stringValue(value, field);
97
+ const date = new Date(normalized);
98
+ if (!Number.isFinite(date.getTime()) || date.toISOString() !== normalized) {
99
+ validationError(field, "must be a canonical UTC ISO-8601 timestamp");
100
+ }
101
+ return normalized;
102
+ }
103
+ function nullableHexValue(value, field, byteLength) {
104
+ return value === null ? null : hexValue(value, field, byteLength);
105
+ }
106
+ function nullableTimestampValue(value, field) {
107
+ return value === null ? null : timestampValue(value, field);
108
+ }
109
+ function voutValue(value, field) {
110
+ if (!Number.isSafeInteger(value) || value < 0 || value > 0xffff_ffff) {
111
+ validationError(field, "must be a uint32");
112
+ }
113
+ return value;
114
+ }
115
+ function normalizeStrictPolicySnapshotPayload(value) {
116
+ const record = recordValue(value, "payload");
117
+ const verifier = recordValue(record.verifier, "payload.verifier");
118
+ const outpoint = recordValue(verifier.outpoint, "payload.verifier.outpoint");
119
+ const effectiveAt = timestampValue(record.effectiveAt, "payload.effectiveAt");
120
+ const validUntil = nullableTimestampValue(record.validUntil, "payload.validUntil");
121
+ if (validUntil !== null && Date.parse(validUntil) <= Date.parse(effectiveAt)) {
122
+ validationError("payload.validUntil", "must be later than effectiveAt");
123
+ }
124
+ const epoch = decimalValue(record.epoch, "payload.epoch");
125
+ const previousSnapshotHash = nullableHexValue(record.previousSnapshotHash, "payload.previousSnapshotHash", 32);
126
+ if (epoch === "0" && previousSnapshotHash !== null) {
127
+ validationError("payload.previousSnapshotHash", "must be null for epoch 0");
128
+ }
129
+ if (epoch !== "0" && previousSnapshotHash === null) {
130
+ validationError("payload.previousSnapshotHash", "is required after epoch 0");
131
+ }
132
+ return {
133
+ schema: literalValue(record.schema, "payload.schema", [exports.STRICT_POLICY_SNAPSHOT_SCHEMA]),
134
+ network: literalValue(record.network, "payload.network", [
135
+ "liquid-regtest",
136
+ "liquid-testnet",
137
+ "liquid-mainnet",
138
+ ]),
139
+ liquidGenesisHash: hexValue(record.liquidGenesisHash, "payload.liquidGenesisHash", 32),
140
+ assetBindingId: stringValue(record.assetBindingId, "payload.assetBindingId"),
141
+ liquidAssetId: hexValue(record.liquidAssetId, "payload.liquidAssetId", 32),
142
+ epoch,
143
+ previousSnapshotHash,
144
+ policyRoot: hexValue(record.policyRoot, "payload.policyRoot", 32),
145
+ whitelistRoot: hexValue(record.whitelistRoot, "payload.whitelistRoot", 32),
146
+ verifier: {
147
+ outpoint: {
148
+ txid: hexValue(outpoint.txid, "payload.verifier.outpoint.txid", 32),
149
+ vout: voutValue(outpoint.vout, "payload.verifier.outpoint.vout"),
150
+ },
151
+ assetId: hexValue(verifier.assetId, "payload.verifier.assetId", 32),
152
+ amountAtomic: decimalValue(verifier.amountAtomic, "payload.verifier.amountAtomic", false),
153
+ cmr: hexValue(verifier.cmr, "payload.verifier.cmr", 32),
154
+ scriptHash: hexValue(verifier.scriptHash, "payload.verifier.scriptHash", 32),
155
+ },
156
+ effectiveAt,
157
+ validUntil,
158
+ };
159
+ }
160
+ function normalizeStrictPolicySnapshotAuthority(value) {
161
+ const record = recordValue(value, "authority");
162
+ const threshold = record.approvalThreshold;
163
+ if (threshold !== 1) {
164
+ validationError("authority.approvalThreshold", "must equal 1 for issuer_single");
165
+ }
166
+ const signerXonly = hexValue(record.signerXonly, "authority.signerXonly", 32);
167
+ const authoritySetHash = hexValue(record.authoritySetHash, "authority.authoritySetHash", 32);
168
+ const expectedAuthoritySetHash = computeStrictPolicyAuthoritySetHash(signerXonly);
169
+ if (authoritySetHash !== expectedAuthoritySetHash) {
170
+ validationError("authority.authoritySetHash", "does not match signerXonly and threshold");
171
+ }
172
+ return {
173
+ authorityType: literalValue(record.authorityType, "authority.authorityType", ["issuer_single"]),
174
+ authorityId: stringValue(record.authorityId, "authority.authorityId"),
175
+ authorityVersion: stringValue(record.authorityVersion, "authority.authorityVersion"),
176
+ authoritySetHash,
177
+ approvalScheme: literalValue(record.approvalScheme, "authority.approvalScheme", ["bip340-sha256"]),
178
+ approvalThreshold: threshold,
179
+ signerXonly,
180
+ approvedAt: timestampValue(record.approvedAt, "authority.approvedAt"),
181
+ };
182
+ }
183
+ function normalizeStrictPolicySnapshotApprovalProof(value) {
184
+ const record = recordValue(value, "approvalProof");
185
+ return {
186
+ type: literalValue(record.type, "approvalProof.type", ["issuer_single_v1"]),
187
+ signerXonly: hexValue(record.signerXonly, "approvalProof.signerXonly", 32),
188
+ signatureHex: hexValue(record.signatureHex, "approvalProof.signatureHex", 64),
189
+ };
190
+ }
191
+ function normalizeStrictPolicyHolderCovenantParams(value) {
192
+ const record = recordValue(value, "holderCovenant");
193
+ return {
194
+ strictAssetIdJetHex: hexValue(record.strictAssetIdJetHex, "holderCovenant.strictAssetIdJetHex", 32),
195
+ verifierAssetIdJetHex: hexValue(record.verifierAssetIdJetHex, "holderCovenant.verifierAssetIdJetHex", 32),
196
+ verifierAmountAtomic: u64DecimalValue(record.verifierAmountAtomic, "holderCovenant.verifierAmountAtomic", false),
197
+ numsInternalKey: hexValue(record.numsInternalKey, "holderCovenant.numsInternalKey", 32),
198
+ };
199
+ }
200
+ function normalizeStrictPolicyVerifierCovenantParams(value) {
201
+ const record = recordValue(value, "verifierCovenant");
202
+ const strictAssetIdJetHex = hexValue(record.strictAssetIdJetHex, "verifierCovenant.strictAssetIdJetHex", 32);
203
+ const verifierAssetIdJetHex = hexValue(record.verifierAssetIdJetHex, "verifierCovenant.verifierAssetIdJetHex", 32);
204
+ if (strictAssetIdJetHex === verifierAssetIdJetHex) {
205
+ validationError("verifierCovenant", "strict and verifier assets must be distinct");
206
+ }
207
+ return {
208
+ strictAssetIdJetHex,
209
+ verifierAssetIdJetHex,
210
+ verifierAmountAtomic: u64DecimalValue(record.verifierAmountAtomic, "verifierCovenant.verifierAmountAtomic", false),
211
+ holderProgramCmr: hexValue(record.holderProgramCmr, "verifierCovenant.holderProgramCmr", 32),
212
+ holderNumsInternalKey: hexValue(record.holderNumsInternalKey, "verifierCovenant.holderNumsInternalKey", 32),
213
+ whitelistRoot: hexValue(record.whitelistRoot, "verifierCovenant.whitelistRoot", 32),
214
+ redemptionScriptHash: hexValue(record.redemptionScriptHash, "verifierCovenant.redemptionScriptHash", 32),
215
+ authorityXonly: hexValue(record.authorityXonly, "verifierCovenant.authorityXonly", 32),
216
+ };
217
+ }
218
+ function strictPolicyHolderCovenantTemplatePath() {
219
+ return `${__dirname}/../docs/definitions/strict-holder-input-v1.simf`;
220
+ }
221
+ async function renderStrictPolicyHolderCovenantSource(value) {
222
+ const params = normalizeStrictPolicyHolderCovenantParams(value);
223
+ const source = await readTemplateFile(strictPolicyHolderCovenantTemplatePath());
224
+ return (0, templating_1.renderTemplate)(source, {
225
+ STRICT_ASSET_ID_JET_HEX: params.strictAssetIdJetHex,
226
+ VERIFIER_ASSET_ID_JET_HEX: params.verifierAssetIdJetHex,
227
+ VERIFIER_AMOUNT_ATOMIC: params.verifierAmountAtomic,
228
+ NUMS_INTERNAL_KEY: params.numsInternalKey,
229
+ });
230
+ }
231
+ async function compileStrictPolicyHolderCovenant(config, value) {
232
+ const params = normalizeStrictPolicyHolderCovenantParams(value);
233
+ const { compileFromFile } = await loadCompiler();
234
+ return compileFromFile(config, {
235
+ simfPath: strictPolicyHolderCovenantTemplatePath(),
236
+ templateVars: {
237
+ STRICT_ASSET_ID_JET_HEX: params.strictAssetIdJetHex,
238
+ VERIFIER_ASSET_ID_JET_HEX: params.verifierAssetIdJetHex,
239
+ VERIFIER_AMOUNT_ATOMIC: params.verifierAmountAtomic,
240
+ NUMS_INTERNAL_KEY: params.numsInternalKey,
241
+ },
242
+ });
243
+ }
244
+ function strictPolicyVerifierCovenantTemplatePath() {
245
+ return `${__dirname}/../docs/definitions/strict-verifier-ordinary-v1.simf`;
246
+ }
247
+ function strictPolicyVerifierTemplateVars(value) {
248
+ const params = normalizeStrictPolicyVerifierCovenantParams(value);
249
+ const tagHashes = (0, dampPolicy_1.strictPolicyWhitelistTagHashes)();
250
+ return {
251
+ STRICT_ASSET_ID_JET_HEX: params.strictAssetIdJetHex,
252
+ VERIFIER_ASSET_ID_JET_HEX: params.verifierAssetIdJetHex,
253
+ VERIFIER_AMOUNT_ATOMIC: params.verifierAmountAtomic,
254
+ HOLDER_PROGRAM_CMR: params.holderProgramCmr,
255
+ HOLDER_NUMS_INTERNAL_KEY: params.holderNumsInternalKey,
256
+ WHITELIST_ROOT: params.whitelistRoot,
257
+ REDEMPTION_SCRIPT_HASH: params.redemptionScriptHash,
258
+ AUTHORITY_XONLY: params.authorityXonly,
259
+ WHITELIST_OWNER_TAG_HASH: tagHashes.owner,
260
+ WHITELIST_NODE_TAG_HASH: tagHashes.node,
261
+ WHITELIST_DEPTH: dampPolicy_1.STRICT_POLICY_WHITELIST_DEPTH,
262
+ MAX_INPUTS: exports.STRICT_POLICY_VERIFIER_MAX_INPUTS,
263
+ MAX_OUTPUTS: exports.STRICT_POLICY_VERIFIER_MAX_OUTPUTS,
264
+ INPUT_UNIT_SLOTS: Array.from({ length: exports.STRICT_POLICY_VERIFIER_MAX_INPUTS }, () => "()").join(", "),
265
+ OUTPUT_UNIT_SLOTS: Array.from({ length: exports.STRICT_POLICY_VERIFIER_MAX_OUTPUTS }, () => "()").join(", "),
266
+ };
267
+ }
268
+ async function renderStrictPolicyVerifierCovenantSource(value) {
269
+ const source = await readTemplateFile(strictPolicyVerifierCovenantTemplatePath());
270
+ return (0, templating_1.renderTemplate)(source, strictPolicyVerifierTemplateVars(value));
271
+ }
272
+ async function compileStrictPolicyVerifierCovenant(config, value) {
273
+ const { compileFromFile } = await loadCompiler();
274
+ return compileFromFile(config, {
275
+ simfPath: strictPolicyVerifierCovenantTemplatePath(),
276
+ templateVars: strictPolicyVerifierTemplateVars(value),
277
+ });
278
+ }
279
+ function taggedHashHexUtf8(tag, canonicalPayload) {
280
+ const tagHash = (0, node_crypto_1.createHash)("sha256").update(tag, "utf8").digest();
281
+ return (0, node_crypto_1.createHash)("sha256")
282
+ .update(tagHash)
283
+ .update(tagHash)
284
+ .update(canonicalPayload, "utf8")
285
+ .digest("hex");
286
+ }
287
+ function computeStrictPolicyAuthoritySetHash(signerXonlyValue) {
288
+ const signerXonly = hexValue(signerXonlyValue, "signerXonly", 32);
289
+ return taggedHashHexUtf8(exports.STRICT_POLICY_AUTHORITY_SET_DOMAIN, (0, summary_1.stableStringify)({
290
+ authorityType: "issuer_single",
291
+ approvalThreshold: 1,
292
+ members: [signerXonly],
293
+ }));
294
+ }
295
+ function prepareStrictPolicySnapshot(input) {
296
+ const payload = normalizeStrictPolicySnapshotPayload(input.payload);
297
+ const authority = normalizeStrictPolicySnapshotAuthority(input.authority);
298
+ if (Date.parse(authority.approvedAt) > Date.parse(payload.effectiveAt)) {
299
+ validationError("authority.approvedAt", "must not be later than payload.effectiveAt");
300
+ }
301
+ const canonicalPayload = (0, summary_1.stableStringify)(payload);
302
+ const snapshotHash = (0, summary_1.sha256HexUtf8)(canonicalPayload);
303
+ const canonicalApprovalMessage = (0, summary_1.stableStringify)({
304
+ schema: exports.STRICT_POLICY_SNAPSHOT_APPROVAL_SCHEMA,
305
+ network: payload.network,
306
+ liquidGenesisHash: payload.liquidGenesisHash,
307
+ assetBindingId: payload.assetBindingId,
308
+ liquidAssetId: payload.liquidAssetId,
309
+ epoch: payload.epoch,
310
+ previousSnapshotHash: payload.previousSnapshotHash,
311
+ snapshotHash,
312
+ verifierCmr: payload.verifier.cmr,
313
+ verifierScriptHash: payload.verifier.scriptHash,
314
+ authorityType: authority.authorityType,
315
+ authorityId: authority.authorityId,
316
+ authorityVersion: authority.authorityVersion,
317
+ authoritySetHash: authority.authoritySetHash,
318
+ approvalScheme: authority.approvalScheme,
319
+ approvalThreshold: authority.approvalThreshold,
320
+ signerXonly: authority.signerXonly,
321
+ approvedAt: authority.approvedAt,
322
+ });
323
+ const approvalMessageHash = taggedHashHexUtf8(exports.STRICT_POLICY_SNAPSHOT_APPROVAL_DOMAIN, canonicalApprovalMessage);
324
+ return {
325
+ payload,
326
+ authority,
327
+ canonicalPayload,
328
+ snapshotHash,
329
+ canonicalApprovalMessage,
330
+ approvalMessageHash,
331
+ };
332
+ }
333
+ function finalizeStrictPolicySnapshot(prepared, proofValue) {
334
+ const approvalProof = normalizeStrictPolicySnapshotApprovalProof(proofValue);
335
+ if (approvalProof.signerXonly !== prepared.authority.signerXonly) {
336
+ validationError("approvalProof.signerXonly", "must match authority.signerXonly");
337
+ }
338
+ const approvalProofHash = (0, summary_1.sha256HexUtf8)((0, summary_1.stableStringify)(approvalProof));
339
+ return {
340
+ ...prepared,
341
+ approvalProof,
342
+ approvalProofHash,
343
+ };
344
+ }
345
+ async function verifyStrictPolicySnapshot(envelopeValue) {
346
+ const prepared = prepareStrictPolicySnapshot({
347
+ payload: envelopeValue.payload,
348
+ authority: envelopeValue.authority,
349
+ });
350
+ const envelope = finalizeStrictPolicySnapshot(prepared, envelopeValue.approvalProof);
351
+ if (envelopeValue.canonicalPayload !== prepared.canonicalPayload) {
352
+ validationError("canonicalPayload", "does not match the normalized snapshot payload");
353
+ }
354
+ if (envelopeValue.snapshotHash !== prepared.snapshotHash) {
355
+ validationError("snapshotHash", "does not match the canonical payload");
356
+ }
357
+ if (envelopeValue.canonicalApprovalMessage !== prepared.canonicalApprovalMessage) {
358
+ validationError("canonicalApprovalMessage", "does not match the normalized snapshot approval message");
359
+ }
360
+ if (envelopeValue.approvalMessageHash !== prepared.approvalMessageHash) {
361
+ validationError("approvalMessageHash", "does not match the canonical approval message");
362
+ }
363
+ if (envelopeValue.approvalProofHash !== envelope.approvalProofHash) {
364
+ validationError("approvalProofHash", "does not match the canonical approval proof");
365
+ }
366
+ const valid = await (0, schnorr_1.schnorrVerifyHex)(envelope.approvalProof.signatureHex, prepared.approvalMessageHash, prepared.authority.signerXonly);
367
+ if (!valid) {
368
+ validationError("approvalProof.signatureHex", "is not valid for the snapshot authority");
369
+ }
370
+ return prepared;
371
+ }
@@ -0,0 +1,61 @@
1
+ export declare const STRICT_POLICY_WHITELIST_DEPTH: 8;
2
+ export declare const STRICT_POLICY_MAX_WHITELIST_OWNERS: number;
3
+ export declare const STRICT_POLICY_WHITELIST_OWNER_DOMAIN: "HAZBASE-RWA-STRICT-WHITELIST-OWNER-V1";
4
+ export declare const STRICT_POLICY_WHITELIST_EMPTY_DOMAIN: "HAZBASE-RWA-STRICT-WHITELIST-EMPTY-V1";
5
+ export declare const STRICT_POLICY_WHITELIST_NODE_DOMAIN: "HAZBASE-RWA-STRICT-WHITELIST-NODE-V1";
6
+ export interface StrictPolicyHolderPositionParams {
7
+ holderProgramCmr: string;
8
+ numsInternalKey: string;
9
+ holderXonly: string;
10
+ }
11
+ export interface StrictPolicyHolderPosition {
12
+ holderProgramCmr: string;
13
+ holderTapleafHash: string;
14
+ holderXonly: string;
15
+ ownerTapDataHash: string;
16
+ taprootRoot: string;
17
+ numsInternalKey: string;
18
+ outputKey: string;
19
+ scriptPubKey: string;
20
+ scriptHash: string;
21
+ }
22
+ export interface StrictPolicyWhitelistProofStep {
23
+ siblingPosition: "left" | "right";
24
+ siblingHash: string;
25
+ }
26
+ export interface StrictPolicyWhitelistEntry {
27
+ ownerXonly: string;
28
+ leafHash: string;
29
+ proof: StrictPolicyWhitelistProofStep[];
30
+ }
31
+ export interface StrictPolicyWhitelist {
32
+ depth: typeof STRICT_POLICY_WHITELIST_DEPTH;
33
+ root: string;
34
+ entries: StrictPolicyWhitelistEntry[];
35
+ }
36
+ export interface StrictPolicyWhitelistProof {
37
+ ownerXonly: string;
38
+ proof: StrictPolicyWhitelistProofStep[];
39
+ }
40
+ export declare function computeStrictPolicyHolderTapleafHash(holderProgramCmrValue: string): string;
41
+ export declare function computeStrictPolicyOwnerTapDataHash(holderXonlyValue: string): string;
42
+ export declare function computeElementsTapBranch(leftValue: string, rightValue: string): string;
43
+ export declare function deriveStrictPolicyHolderPosition(value: StrictPolicyHolderPositionParams): Promise<StrictPolicyHolderPosition>;
44
+ export declare function computeStrictPolicyWhitelistOwnerLeaf(ownerXonlyValue: string): string;
45
+ export declare function computeStrictPolicyWhitelistEmptyLeaf(): string;
46
+ export declare function computeStrictPolicyWhitelistNode(leftValue: string, rightValue: string): string;
47
+ export declare function buildStrictPolicyWhitelist(ownerXonlyValues: readonly string[]): StrictPolicyWhitelist;
48
+ export declare function verifyStrictPolicyWhitelistProof(input: {
49
+ ownerXonly: string;
50
+ proof: readonly StrictPolicyWhitelistProofStep[];
51
+ expectedRoot: string;
52
+ }): boolean;
53
+ export declare function normalizeStrictPolicyWhitelistProof(input: {
54
+ ownerXonly: string;
55
+ proof: readonly StrictPolicyWhitelistProofStep[];
56
+ }): StrictPolicyWhitelistProof;
57
+ export declare function strictPolicyWhitelistTagHashes(): {
58
+ owner: string;
59
+ empty: string;
60
+ node: string;
61
+ };