@sip-protocol/sdk 0.3.2 → 0.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/browser.d.mts +2 -2
- package/dist/browser.d.ts +2 -2
- package/dist/browser.js +2881 -295
- package/dist/browser.mjs +62 -2
- package/dist/chunk-AOZIY3GU.mjs +12995 -0
- package/dist/chunk-BCLIX5T2.mjs +12940 -0
- package/dist/chunk-DMHBKRWV.mjs +14712 -0
- package/dist/chunk-FKXPHKYD.mjs +12955 -0
- package/dist/chunk-HGU6HZRC.mjs +231 -0
- package/dist/chunk-J4Q4NJ2U.mjs +13544 -0
- package/dist/chunk-OPQ2GQIO.mjs +13013 -0
- package/dist/chunk-W2B7T6WU.mjs +14714 -0
- package/dist/index-5jAdWMA-.d.ts +8973 -0
- package/dist/index-B9Vkpaao.d.mts +8973 -0
- package/dist/index-BcWNakUD.d.ts +7990 -0
- package/dist/index-BsKY3Hr0.d.mts +7990 -0
- package/dist/index.d.mts +2 -2
- package/dist/index.d.ts +2 -2
- package/dist/index.js +2852 -266
- package/dist/index.mjs +62 -2
- package/dist/proofs/noir.mjs +1 -1
- package/package.json +2 -1
- package/src/adapters/near-intents.ts +8 -0
- package/src/bitcoin/index.ts +51 -0
- package/src/bitcoin/silent-payments.ts +865 -0
- package/src/bitcoin/taproot.ts +590 -0
- package/src/compliance/compliance-manager.ts +87 -0
- package/src/compliance/conditional-threshold.ts +379 -0
- package/src/compliance/conditional.ts +382 -0
- package/src/compliance/derivation.ts +489 -0
- package/src/compliance/index.ts +50 -8
- package/src/compliance/pdf.ts +365 -0
- package/src/compliance/reports.ts +644 -0
- package/src/compliance/threshold.ts +529 -0
- package/src/compliance/types.ts +223 -0
- package/src/cosmos/ibc-stealth.ts +825 -0
- package/src/cosmos/index.ts +83 -0
- package/src/cosmos/stealth.ts +487 -0
- package/src/errors.ts +8 -0
- package/src/index.ts +80 -1
- package/src/move/aptos.ts +369 -0
- package/src/move/index.ts +35 -0
- package/src/move/sui.ts +367 -0
- package/src/oracle/types.ts +8 -0
- package/src/settlement/backends/direct-chain.ts +8 -0
- package/src/stealth.ts +3 -3
- package/src/validation.ts +42 -1
- package/src/wallet/aptos/adapter.ts +422 -0
- package/src/wallet/aptos/index.ts +10 -0
- package/src/wallet/aptos/mock.ts +410 -0
- package/src/wallet/aptos/types.ts +278 -0
- package/src/wallet/bitcoin/adapter.ts +470 -0
- package/src/wallet/bitcoin/index.ts +38 -0
- package/src/wallet/bitcoin/mock.ts +516 -0
- package/src/wallet/bitcoin/types.ts +274 -0
- package/src/wallet/cosmos/adapter.ts +484 -0
- package/src/wallet/cosmos/index.ts +63 -0
- package/src/wallet/cosmos/mock.ts +596 -0
- package/src/wallet/cosmos/types.ts +462 -0
- package/src/wallet/index.ts +127 -0
- package/src/wallet/sui/adapter.ts +471 -0
- package/src/wallet/sui/index.ts +10 -0
- package/src/wallet/sui/mock.ts +439 -0
- package/src/wallet/sui/types.ts +245 -0
package/dist/browser.js
CHANGED
|
@@ -31,10 +31,17 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
|
|
|
31
31
|
var browser_exports = {};
|
|
32
32
|
__export(browser_exports, {
|
|
33
33
|
ATTESTATION_VERSION: () => ATTESTATION_VERSION,
|
|
34
|
+
AptosStealthService: () => AptosStealthService,
|
|
35
|
+
AuditorKeyDerivation: () => AuditorKeyDerivation,
|
|
36
|
+
AuditorType: () => AuditorType,
|
|
34
37
|
BaseWalletAdapter: () => BaseWalletAdapter,
|
|
35
38
|
BrowserNoirProvider: () => BrowserNoirProvider,
|
|
36
39
|
CHAIN_NUMERIC_IDS: () => CHAIN_NUMERIC_IDS,
|
|
40
|
+
COSMOS_CHAIN_PREFIXES: () => CHAIN_PREFIXES,
|
|
37
41
|
ComplianceManager: () => ComplianceManager,
|
|
42
|
+
ComplianceReporter: () => ComplianceReporter,
|
|
43
|
+
ConditionalDisclosure: () => ConditionalDisclosure,
|
|
44
|
+
CosmosStealthService: () => CosmosStealthService,
|
|
38
45
|
CryptoError: () => CryptoError,
|
|
39
46
|
DEFAULT_THRESHOLD: () => DEFAULT_THRESHOLD,
|
|
40
47
|
DEFAULT_TOTAL_ORACLES: () => DEFAULT_TOTAL_ORACLES,
|
|
@@ -47,7 +54,7 @@ __export(browser_exports, {
|
|
|
47
54
|
HardwareWalletError: () => HardwareWalletError,
|
|
48
55
|
IntentBuilder: () => IntentBuilder,
|
|
49
56
|
IntentError: () => IntentError,
|
|
50
|
-
IntentStatus: () =>
|
|
57
|
+
IntentStatus: () => import_types55.IntentStatus,
|
|
51
58
|
LedgerWalletAdapter: () => LedgerWalletAdapter,
|
|
52
59
|
MockEthereumAdapter: () => MockEthereumAdapter,
|
|
53
60
|
MockLedgerAdapter: () => MockLedgerAdapter,
|
|
@@ -56,28 +63,28 @@ __export(browser_exports, {
|
|
|
56
63
|
MockSolver: () => MockSolver,
|
|
57
64
|
MockTrezorAdapter: () => MockTrezorAdapter,
|
|
58
65
|
MockWalletAdapter: () => MockWalletAdapter,
|
|
59
|
-
NATIVE_TOKENS: () =>
|
|
66
|
+
NATIVE_TOKENS: () => import_types55.NATIVE_TOKENS,
|
|
60
67
|
NEARIntentsAdapter: () => NEARIntentsAdapter,
|
|
61
68
|
NEARIntentsBackend: () => NEARIntentsBackend,
|
|
62
69
|
NetworkError: () => NetworkError,
|
|
63
70
|
ORACLE_DOMAIN: () => ORACLE_DOMAIN,
|
|
64
71
|
OneClickClient: () => OneClickClient,
|
|
65
|
-
OneClickDepositMode: () =>
|
|
66
|
-
OneClickErrorCode: () =>
|
|
67
|
-
OneClickSwapStatus: () =>
|
|
68
|
-
OneClickSwapType: () =>
|
|
72
|
+
OneClickDepositMode: () => import_types59.OneClickDepositMode,
|
|
73
|
+
OneClickErrorCode: () => import_types59.OneClickErrorCode,
|
|
74
|
+
OneClickSwapStatus: () => import_types59.OneClickSwapStatus,
|
|
75
|
+
OneClickSwapType: () => import_types59.OneClickSwapType,
|
|
69
76
|
PaymentBuilder: () => PaymentBuilder,
|
|
70
|
-
PaymentStatus: () =>
|
|
71
|
-
PrivacyLevel: () =>
|
|
77
|
+
PaymentStatus: () => import_types56.PaymentStatus,
|
|
78
|
+
PrivacyLevel: () => import_types55.PrivacyLevel,
|
|
72
79
|
ProofError: () => ProofError,
|
|
73
80
|
ProofGenerationError: () => ProofGenerationError,
|
|
74
81
|
ProofNotImplementedError: () => ProofNotImplementedError,
|
|
75
82
|
ProofWorker: () => ProofWorker,
|
|
76
|
-
ProposalStatus: () =>
|
|
77
|
-
ReportStatus: () =>
|
|
83
|
+
ProposalStatus: () => import_types57.ProposalStatus,
|
|
84
|
+
ReportStatus: () => import_types58.ReportStatus,
|
|
78
85
|
SIP: () => SIP,
|
|
79
86
|
SIPError: () => SIPError,
|
|
80
|
-
SIP_VERSION: () =>
|
|
87
|
+
SIP_VERSION: () => import_types55.SIP_VERSION,
|
|
81
88
|
STABLECOIN_ADDRESSES: () => STABLECOIN_ADDRESSES,
|
|
82
89
|
STABLECOIN_DECIMALS: () => STABLECOIN_DECIMALS,
|
|
83
90
|
STABLECOIN_INFO: () => STABLECOIN_INFO,
|
|
@@ -86,12 +93,13 @@ __export(browser_exports, {
|
|
|
86
93
|
SmartRouter: () => SmartRouter,
|
|
87
94
|
SolanaWalletAdapter: () => SolanaWalletAdapter,
|
|
88
95
|
SwapStatus: () => SwapStatus,
|
|
96
|
+
ThresholdViewingKey: () => ThresholdViewingKey,
|
|
89
97
|
Treasury: () => Treasury,
|
|
90
98
|
TrezorWalletAdapter: () => TrezorWalletAdapter,
|
|
91
99
|
ValidationError: () => ValidationError,
|
|
92
100
|
WalletError: () => WalletError,
|
|
93
|
-
WalletErrorCode: () =>
|
|
94
|
-
ZcashErrorCode: () =>
|
|
101
|
+
WalletErrorCode: () => import_types54.WalletErrorCode,
|
|
102
|
+
ZcashErrorCode: () => import_types60.ZcashErrorCode,
|
|
95
103
|
ZcashNativeBackend: () => ZcashNativeBackend,
|
|
96
104
|
ZcashRPCClient: () => ZcashRPCClient,
|
|
97
105
|
ZcashRPCError: () => ZcashRPCError,
|
|
@@ -100,18 +108,22 @@ __export(browser_exports, {
|
|
|
100
108
|
addBlindings: () => addBlindings,
|
|
101
109
|
addCommitments: () => addCommitments,
|
|
102
110
|
addOracle: () => addOracle,
|
|
111
|
+
aptosAddressToAuthKey: () => aptosAddressToAuthKey,
|
|
103
112
|
attachProofs: () => attachProofs,
|
|
104
113
|
base58ToHex: () => base58ToHex,
|
|
105
|
-
browserBytesToHex: () =>
|
|
106
|
-
browserHexToBytes: () =>
|
|
114
|
+
browserBytesToHex: () => bytesToHex11,
|
|
115
|
+
browserHexToBytes: () => hexToBytes9,
|
|
116
|
+
checkAptosStealthAddress: () => checkAptosStealthAddress,
|
|
107
117
|
checkEd25519StealthAddress: () => checkEd25519StealthAddress,
|
|
108
118
|
checkMobileWASMCompatibility: () => checkMobileWASMCompatibility,
|
|
109
119
|
checkStealthAddress: () => checkStealthAddress,
|
|
110
120
|
commit: () => commit,
|
|
111
121
|
commitZero: () => commitZero,
|
|
112
122
|
computeAttestationHash: () => computeAttestationHash,
|
|
123
|
+
computeTweakedKey: () => computeTweakedKey,
|
|
113
124
|
createCommitment: () => createCommitment,
|
|
114
125
|
createEthereumAdapter: () => createEthereumAdapter,
|
|
126
|
+
createKeySpendOnlyOutput: () => createKeySpendOnlyOutput,
|
|
115
127
|
createLedgerAdapter: () => createLedgerAdapter,
|
|
116
128
|
createMockEthereumAdapter: () => createMockEthereumAdapter,
|
|
117
129
|
createMockEthereumProvider: () => createMockEthereumProvider,
|
|
@@ -130,6 +142,7 @@ __export(browser_exports, {
|
|
|
130
142
|
createShieldedPayment: () => createShieldedPayment,
|
|
131
143
|
createSmartRouter: () => createSmartRouter,
|
|
132
144
|
createSolanaAdapter: () => createSolanaAdapter,
|
|
145
|
+
createTaprootOutput: () => createTaprootOutput,
|
|
133
146
|
createTrezorAdapter: () => createTrezorAdapter,
|
|
134
147
|
createWalletFactory: () => createWalletFactory,
|
|
135
148
|
createWorkerBlobURL: () => createWorkerBlobURL,
|
|
@@ -138,8 +151,10 @@ __export(browser_exports, {
|
|
|
138
151
|
createZcashShieldedService: () => createZcashShieldedService,
|
|
139
152
|
createZcashSwapService: () => createZcashSwapService,
|
|
140
153
|
decodeStealthMetaAddress: () => decodeStealthMetaAddress,
|
|
154
|
+
decodeTaprootAddress: () => decodeTaprootAddress,
|
|
141
155
|
decryptMemo: () => decryptMemo,
|
|
142
156
|
decryptWithViewing: () => decryptWithViewing,
|
|
157
|
+
deriveAptosStealthPrivateKey: () => deriveAptosStealthPrivateKey,
|
|
143
158
|
deriveEd25519StealthPrivateKey: () => deriveEd25519StealthPrivateKey,
|
|
144
159
|
deriveOracleId: () => deriveOracleId,
|
|
145
160
|
deriveStealthPrivateKey: () => deriveStealthPrivateKey,
|
|
@@ -151,6 +166,7 @@ __export(browser_exports, {
|
|
|
151
166
|
detectMobileBrowser: () => detectMobileBrowser,
|
|
152
167
|
detectMobilePlatform: () => detectMobilePlatform,
|
|
153
168
|
detectSolanaWallets: () => detectSolanaWallets,
|
|
169
|
+
ed25519PublicKeyToAptosAddress: () => ed25519PublicKeyToAptosAddress,
|
|
154
170
|
ed25519PublicKeyToNearAddress: () => ed25519PublicKeyToNearAddress,
|
|
155
171
|
ed25519PublicKeyToSolanaAddress: () => ed25519PublicKeyToSolanaAddress,
|
|
156
172
|
encodeStealthMetaAddress: () => encodeStealthMetaAddress,
|
|
@@ -159,10 +175,14 @@ __export(browser_exports, {
|
|
|
159
175
|
formatStablecoinAmount: () => formatStablecoinAmount,
|
|
160
176
|
fromHex: () => fromHex,
|
|
161
177
|
fromStablecoinUnits: () => fromStablecoinUnits,
|
|
178
|
+
generateAptosStealthAddress: () => generateAptosStealthAddress,
|
|
162
179
|
generateBlinding: () => generateBlinding,
|
|
180
|
+
generateCosmosStealthAddress: () => generateCosmosStealthAddress,
|
|
181
|
+
generateCosmosStealthMetaAddress: () => generateCosmosStealthMetaAddress,
|
|
163
182
|
generateEd25519StealthAddress: () => generateEd25519StealthAddress,
|
|
164
183
|
generateEd25519StealthMetaAddress: () => generateEd25519StealthMetaAddress,
|
|
165
184
|
generateIntentId: () => generateIntentId,
|
|
185
|
+
generatePdfReport: () => generatePdfReport,
|
|
166
186
|
generateRandomBytes: () => generateRandomBytes,
|
|
167
187
|
generateStealthAddress: () => generateStealthAddress,
|
|
168
188
|
generateStealthMetaAddress: () => generateStealthMetaAddress,
|
|
@@ -192,6 +212,7 @@ __export(browser_exports, {
|
|
|
192
212
|
getStablecoinsForChain: () => getStablecoinsForChain,
|
|
193
213
|
getSupportedStablecoins: () => getSupportedStablecoins,
|
|
194
214
|
getTimeRemaining: () => getTimeRemaining,
|
|
215
|
+
getXOnlyPublicKey: () => getXOnlyPublicKey,
|
|
195
216
|
hasEnoughOracles: () => hasEnoughOracles,
|
|
196
217
|
hasErrorCode: () => hasErrorCode,
|
|
197
218
|
hasRequiredProofs: () => hasRequiredProofs,
|
|
@@ -202,15 +223,17 @@ __export(browser_exports, {
|
|
|
202
223
|
isExpired: () => isExpired,
|
|
203
224
|
isNonNegativeAmount: () => isNonNegativeAmount,
|
|
204
225
|
isPaymentExpired: () => isPaymentExpired,
|
|
205
|
-
isPrivate: () =>
|
|
226
|
+
isPrivate: () => import_types55.isPrivate,
|
|
206
227
|
isPrivateWalletAdapter: () => isPrivateWalletAdapter,
|
|
207
228
|
isSIPError: () => isSIPError,
|
|
208
229
|
isStablecoin: () => isStablecoin,
|
|
209
230
|
isStablecoinOnChain: () => isStablecoinOnChain,
|
|
210
231
|
isTablet: () => isTablet,
|
|
211
232
|
isValidAmount: () => isValidAmount,
|
|
233
|
+
isValidAptosAddress: () => isValidAptosAddress,
|
|
212
234
|
isValidChainId: () => isValidChainId,
|
|
213
235
|
isValidCompressedPublicKey: () => isValidCompressedPublicKey,
|
|
236
|
+
isValidCosmosAddress: () => isValidCosmosAddress,
|
|
214
237
|
isValidEd25519PublicKey: () => isValidEd25519PublicKey,
|
|
215
238
|
isValidHex: () => isValidHex,
|
|
216
239
|
isValidHexLength: () => isValidHexLength,
|
|
@@ -222,12 +245,17 @@ __export(browser_exports, {
|
|
|
222
245
|
isValidSlippage: () => isValidSlippage,
|
|
223
246
|
isValidSolanaAddress: () => isValidSolanaAddress,
|
|
224
247
|
isValidStealthMetaAddress: () => isValidStealthMetaAddress,
|
|
248
|
+
isValidTaprootAddress: () => isValidTaprootAddress,
|
|
225
249
|
nearAddressToEd25519PublicKey: () => nearAddressToEd25519PublicKey,
|
|
226
250
|
normalizeAddress: () => normalizeAddress,
|
|
227
251
|
notConnectedError: () => notConnectedError,
|
|
228
252
|
publicKeyToEthAddress: () => publicKeyToEthAddress,
|
|
229
253
|
registerWallet: () => registerWallet,
|
|
230
254
|
removeOracle: () => removeOracle,
|
|
255
|
+
schnorrSign: () => schnorrSign,
|
|
256
|
+
schnorrSignHex: () => schnorrSignHex,
|
|
257
|
+
schnorrVerify: () => schnorrVerify,
|
|
258
|
+
schnorrVerifyHex: () => schnorrVerifyHex,
|
|
231
259
|
secureWipe: () => secureWipe,
|
|
232
260
|
secureWipeAll: () => secureWipeAll,
|
|
233
261
|
serializeAttestationMessage: () => serializeAttestationMessage,
|
|
@@ -236,17 +264,19 @@ __export(browser_exports, {
|
|
|
236
264
|
signAttestationMessage: () => signAttestationMessage,
|
|
237
265
|
solanaAddressToEd25519PublicKey: () => solanaAddressToEd25519PublicKey,
|
|
238
266
|
solanaPublicKeyToHex: () => solanaPublicKeyToHex,
|
|
267
|
+
stealthKeyToCosmosAddress: () => stealthKeyToCosmosAddress,
|
|
239
268
|
subtractBlindings: () => subtractBlindings,
|
|
240
269
|
subtractCommitments: () => subtractCommitments,
|
|
241
270
|
supportsSharedArrayBuffer: () => supportsSharedArrayBuffer,
|
|
242
271
|
supportsTouch: () => supportsTouch,
|
|
243
|
-
supportsViewingKey: () =>
|
|
272
|
+
supportsViewingKey: () => import_types55.supportsViewingKey,
|
|
244
273
|
supportsWASMBulkMemory: () => supportsWASMBulkMemory,
|
|
245
274
|
supportsWASMSimd: () => supportsWASMSimd,
|
|
246
275
|
supportsWebBluetooth: () => supportsWebBluetooth,
|
|
247
276
|
supportsWebHID: () => supportsWebHID,
|
|
248
277
|
supportsWebUSB: () => supportsWebUSB,
|
|
249
278
|
supportsWebWorkers: () => supportsWebWorkers,
|
|
279
|
+
taprootAddress: () => taprootAddress,
|
|
250
280
|
toHex: () => toHex,
|
|
251
281
|
toStablecoinUnits: () => toStablecoinUnits,
|
|
252
282
|
trackIntent: () => trackIntent,
|
|
@@ -292,6 +322,14 @@ var ErrorCode = /* @__PURE__ */ ((ErrorCode2) => {
|
|
|
292
322
|
ErrorCode2["SIGNATURE_FAILED"] = "SIP_3005";
|
|
293
323
|
ErrorCode2["INVALID_CURVE_POINT"] = "SIP_3006";
|
|
294
324
|
ErrorCode2["INVALID_SCALAR"] = "SIP_3007";
|
|
325
|
+
ErrorCode2["INVALID_KEY_SIZE"] = "SIP_3008";
|
|
326
|
+
ErrorCode2["INVALID_ENCRYPTED_DATA"] = "SIP_3009";
|
|
327
|
+
ErrorCode2["INVALID_COMMITMENT"] = "SIP_3010";
|
|
328
|
+
ErrorCode2["INVALID_TIME_LOCK"] = "SIP_3011";
|
|
329
|
+
ErrorCode2["INVALID_SHARE"] = "SIP_3012";
|
|
330
|
+
ErrorCode2["INVALID_THRESHOLD"] = "SIP_3013";
|
|
331
|
+
ErrorCode2["CRYPTO_OPERATION_FAILED"] = "SIP_3014";
|
|
332
|
+
ErrorCode2["INVALID_FORMAT"] = "SIP_3015";
|
|
295
333
|
ErrorCode2["PROOF_FAILED"] = "SIP_4000";
|
|
296
334
|
ErrorCode2["PROOF_GENERATION_FAILED"] = "SIP_4001";
|
|
297
335
|
ErrorCode2["PROOF_VERIFICATION_FAILED"] = "SIP_4002";
|
|
@@ -487,7 +525,16 @@ var VALID_CHAIN_IDS = [
|
|
|
487
525
|
"polygon",
|
|
488
526
|
"arbitrum",
|
|
489
527
|
"optimism",
|
|
490
|
-
"base"
|
|
528
|
+
"base",
|
|
529
|
+
"bitcoin",
|
|
530
|
+
"aptos",
|
|
531
|
+
"sui",
|
|
532
|
+
"cosmos",
|
|
533
|
+
"osmosis",
|
|
534
|
+
"injective",
|
|
535
|
+
"celestia",
|
|
536
|
+
"sei",
|
|
537
|
+
"dydx"
|
|
491
538
|
];
|
|
492
539
|
function isValidChainId(chain) {
|
|
493
540
|
return VALID_CHAIN_IDS.includes(chain);
|
|
@@ -684,6 +731,12 @@ function isValidNearAddressFormat(address) {
|
|
|
684
731
|
if (address.includes("..")) return false;
|
|
685
732
|
return true;
|
|
686
733
|
}
|
|
734
|
+
function isValidCosmosAddressFormat(address) {
|
|
735
|
+
if (typeof address !== "string") return false;
|
|
736
|
+
if (address.length < 39 || address.length > 90) return false;
|
|
737
|
+
const bech32Pattern = /^[a-z]+1[qpzry9x8gf2tvdw0s3jn54khce6mua7l]{38,}$/;
|
|
738
|
+
return bech32Pattern.test(address);
|
|
739
|
+
}
|
|
687
740
|
function getChainAddressType(chain) {
|
|
688
741
|
switch (chain) {
|
|
689
742
|
case "ethereum":
|
|
@@ -698,6 +751,13 @@ function getChainAddressType(chain) {
|
|
|
698
751
|
return "near";
|
|
699
752
|
case "zcash":
|
|
700
753
|
return "zcash";
|
|
754
|
+
case "cosmos":
|
|
755
|
+
case "osmosis":
|
|
756
|
+
case "injective":
|
|
757
|
+
case "celestia":
|
|
758
|
+
case "sei":
|
|
759
|
+
case "dydx":
|
|
760
|
+
return "cosmos";
|
|
701
761
|
default:
|
|
702
762
|
return "unknown";
|
|
703
763
|
}
|
|
@@ -741,6 +801,15 @@ function validateAddressForChain(address, chain, field = "address") {
|
|
|
741
801
|
);
|
|
742
802
|
}
|
|
743
803
|
break;
|
|
804
|
+
case "cosmos":
|
|
805
|
+
if (!isValidCosmosAddressFormat(address)) {
|
|
806
|
+
throw new ValidationError(
|
|
807
|
+
`Invalid address format for ${chain}. Expected Cosmos bech32 address, got: ${address.slice(0, 20)}...`,
|
|
808
|
+
field,
|
|
809
|
+
{ chain, expectedFormat: "bech32" }
|
|
810
|
+
);
|
|
811
|
+
}
|
|
812
|
+
break;
|
|
744
813
|
default:
|
|
745
814
|
break;
|
|
746
815
|
}
|
|
@@ -792,7 +861,7 @@ function secureWipeAll(...buffers) {
|
|
|
792
861
|
function generateStealthMetaAddress(chain, label) {
|
|
793
862
|
if (!isValidChainId(chain)) {
|
|
794
863
|
throw new ValidationError(
|
|
795
|
-
`invalid chain '${chain}', must be one of: solana, ethereum, near, zcash, polygon, arbitrum, optimism, base`,
|
|
864
|
+
`invalid chain '${chain}', must be one of: solana, ethereum, near, zcash, polygon, arbitrum, optimism, base, bitcoin, aptos, sui, cosmos, osmosis, injective, celestia, sei, dydx`,
|
|
796
865
|
"chain"
|
|
797
866
|
);
|
|
798
867
|
}
|
|
@@ -1072,7 +1141,7 @@ function toChecksumAddress(address) {
|
|
|
1072
1141
|
return checksummed;
|
|
1073
1142
|
}
|
|
1074
1143
|
var ED25519_ORDER = 2n ** 252n + 27742317777372353535851937790883648493n;
|
|
1075
|
-
var ED25519_CHAINS = ["solana", "near"];
|
|
1144
|
+
var ED25519_CHAINS = ["solana", "near", "aptos", "sui"];
|
|
1076
1145
|
function isEd25519Chain(chain) {
|
|
1077
1146
|
return ED25519_CHAINS.includes(chain);
|
|
1078
1147
|
}
|
|
@@ -1157,7 +1226,7 @@ function bigIntToBytesLE(value, length) {
|
|
|
1157
1226
|
function generateEd25519StealthMetaAddress(chain, label) {
|
|
1158
1227
|
if (!isValidChainId(chain)) {
|
|
1159
1228
|
throw new ValidationError(
|
|
1160
|
-
`invalid chain '${chain}', must be one of: solana, ethereum, near, zcash, polygon, arbitrum, optimism, base`,
|
|
1229
|
+
`invalid chain '${chain}', must be one of: solana, ethereum, near, zcash, polygon, arbitrum, optimism, base, bitcoin, aptos, sui, cosmos, osmosis, injective, celestia, sei, dydx`,
|
|
1161
1230
|
"chain"
|
|
1162
1231
|
);
|
|
1163
1232
|
}
|
|
@@ -2527,7 +2596,15 @@ var CHAIN_BLOCKCHAIN_MAP = {
|
|
|
2527
2596
|
arbitrum: "evm",
|
|
2528
2597
|
optimism: "evm",
|
|
2529
2598
|
base: "evm",
|
|
2530
|
-
bitcoin: "bitcoin"
|
|
2599
|
+
bitcoin: "bitcoin",
|
|
2600
|
+
aptos: "aptos",
|
|
2601
|
+
sui: "sui",
|
|
2602
|
+
cosmos: "cosmos",
|
|
2603
|
+
osmosis: "cosmos",
|
|
2604
|
+
injective: "cosmos",
|
|
2605
|
+
celestia: "cosmos",
|
|
2606
|
+
sei: "cosmos",
|
|
2607
|
+
dydx: "cosmos"
|
|
2531
2608
|
};
|
|
2532
2609
|
var NEARIntentsAdapter = class {
|
|
2533
2610
|
client;
|
|
@@ -3287,6 +3364,448 @@ function createProductionSIP(config) {
|
|
|
3287
3364
|
});
|
|
3288
3365
|
}
|
|
3289
3366
|
|
|
3367
|
+
// src/move/aptos.ts
|
|
3368
|
+
var import_sha32 = require("@noble/hashes/sha3");
|
|
3369
|
+
var import_utils7 = require("@noble/hashes/utils");
|
|
3370
|
+
var APTOS_SINGLE_ED25519_SCHEME = 0;
|
|
3371
|
+
function ed25519PublicKeyToAptosAddress(publicKey) {
|
|
3372
|
+
if (!isValidHex(publicKey)) {
|
|
3373
|
+
throw new ValidationError(
|
|
3374
|
+
"publicKey must be a valid hex string with 0x prefix",
|
|
3375
|
+
"publicKey"
|
|
3376
|
+
);
|
|
3377
|
+
}
|
|
3378
|
+
if (!isValidEd25519PublicKey(publicKey)) {
|
|
3379
|
+
throw new ValidationError(
|
|
3380
|
+
"publicKey must be 32 bytes (64 hex characters)",
|
|
3381
|
+
"publicKey"
|
|
3382
|
+
);
|
|
3383
|
+
}
|
|
3384
|
+
const publicKeyBytes = (0, import_utils7.hexToBytes)(publicKey.slice(2));
|
|
3385
|
+
const authKeyInput = new Uint8Array(publicKeyBytes.length + 1);
|
|
3386
|
+
authKeyInput.set(publicKeyBytes, 0);
|
|
3387
|
+
authKeyInput[publicKeyBytes.length] = APTOS_SINGLE_ED25519_SCHEME;
|
|
3388
|
+
const addressHash = (0, import_sha32.sha3_256)(authKeyInput);
|
|
3389
|
+
return `0x${(0, import_utils7.bytesToHex)(addressHash)}`;
|
|
3390
|
+
}
|
|
3391
|
+
function isValidAptosAddress(address) {
|
|
3392
|
+
if (typeof address !== "string" || address.length === 0) {
|
|
3393
|
+
return false;
|
|
3394
|
+
}
|
|
3395
|
+
if (!address.startsWith("0x")) {
|
|
3396
|
+
return false;
|
|
3397
|
+
}
|
|
3398
|
+
const hexPart = address.slice(2);
|
|
3399
|
+
if (hexPart.length !== 64) {
|
|
3400
|
+
return false;
|
|
3401
|
+
}
|
|
3402
|
+
return /^[0-9a-fA-F]{64}$/.test(hexPart);
|
|
3403
|
+
}
|
|
3404
|
+
function aptosAddressToAuthKey(address) {
|
|
3405
|
+
if (!isValidAptosAddress(address)) {
|
|
3406
|
+
throw new ValidationError(
|
|
3407
|
+
"Invalid Aptos address format (must be 0x-prefixed 64 hex characters)",
|
|
3408
|
+
"address"
|
|
3409
|
+
);
|
|
3410
|
+
}
|
|
3411
|
+
return address.toLowerCase();
|
|
3412
|
+
}
|
|
3413
|
+
function generateAptosStealthAddress(recipientMetaAddress) {
|
|
3414
|
+
if (recipientMetaAddress.chain !== "aptos") {
|
|
3415
|
+
throw new ValidationError(
|
|
3416
|
+
`Expected chain 'aptos', got '${recipientMetaAddress.chain}'`,
|
|
3417
|
+
"recipientMetaAddress.chain"
|
|
3418
|
+
);
|
|
3419
|
+
}
|
|
3420
|
+
const { stealthAddress, sharedSecret } = generateEd25519StealthAddress(recipientMetaAddress);
|
|
3421
|
+
const aptosAddress = ed25519PublicKeyToAptosAddress(stealthAddress.address);
|
|
3422
|
+
return {
|
|
3423
|
+
stealthAddress: aptosAddress,
|
|
3424
|
+
stealthPublicKey: stealthAddress.address,
|
|
3425
|
+
ephemeralPublicKey: stealthAddress.ephemeralPublicKey,
|
|
3426
|
+
viewTag: stealthAddress.viewTag,
|
|
3427
|
+
sharedSecret
|
|
3428
|
+
};
|
|
3429
|
+
}
|
|
3430
|
+
function deriveAptosStealthPrivateKey(stealthAddress, spendingPrivateKey, viewingPrivateKey) {
|
|
3431
|
+
const recovery = deriveEd25519StealthPrivateKey(
|
|
3432
|
+
stealthAddress,
|
|
3433
|
+
spendingPrivateKey,
|
|
3434
|
+
viewingPrivateKey
|
|
3435
|
+
);
|
|
3436
|
+
const aptosAddress = ed25519PublicKeyToAptosAddress(recovery.stealthAddress);
|
|
3437
|
+
return {
|
|
3438
|
+
...recovery,
|
|
3439
|
+
aptosAddress
|
|
3440
|
+
};
|
|
3441
|
+
}
|
|
3442
|
+
function checkAptosStealthAddress(stealthAddress, spendingPrivateKey, viewingPrivateKey) {
|
|
3443
|
+
return checkEd25519StealthAddress(
|
|
3444
|
+
stealthAddress,
|
|
3445
|
+
spendingPrivateKey,
|
|
3446
|
+
viewingPrivateKey
|
|
3447
|
+
);
|
|
3448
|
+
}
|
|
3449
|
+
var AptosStealthService = class {
|
|
3450
|
+
/**
|
|
3451
|
+
* Generate a stealth address for an Aptos recipient
|
|
3452
|
+
*
|
|
3453
|
+
* @param recipientMetaAddress - Recipient's stealth meta-address
|
|
3454
|
+
* @returns Complete stealth address result
|
|
3455
|
+
*/
|
|
3456
|
+
generateStealthAddress(recipientMetaAddress) {
|
|
3457
|
+
return generateAptosStealthAddress(recipientMetaAddress);
|
|
3458
|
+
}
|
|
3459
|
+
/**
|
|
3460
|
+
* Convert an ed25519 public key to Aptos address format
|
|
3461
|
+
*
|
|
3462
|
+
* @param publicKey - 32-byte ed25519 public key
|
|
3463
|
+
* @returns Aptos address string
|
|
3464
|
+
*/
|
|
3465
|
+
stealthKeyToAptosAddress(publicKey) {
|
|
3466
|
+
return ed25519PublicKeyToAptosAddress(publicKey);
|
|
3467
|
+
}
|
|
3468
|
+
/**
|
|
3469
|
+
* Derive the private key for a stealth address
|
|
3470
|
+
*
|
|
3471
|
+
* @param stealthAddress - Stealth address data
|
|
3472
|
+
* @param spendingPrivateKey - Recipient's spending private key
|
|
3473
|
+
* @param viewingPrivateKey - Recipient's viewing private key
|
|
3474
|
+
* @returns Recovery data with derived private key
|
|
3475
|
+
*/
|
|
3476
|
+
deriveStealthPrivateKey(stealthAddress, spendingPrivateKey, viewingPrivateKey) {
|
|
3477
|
+
return deriveAptosStealthPrivateKey(stealthAddress, spendingPrivateKey, viewingPrivateKey);
|
|
3478
|
+
}
|
|
3479
|
+
/**
|
|
3480
|
+
* Check if a stealth address belongs to this recipient
|
|
3481
|
+
*
|
|
3482
|
+
* @param stealthAddress - Stealth address to check
|
|
3483
|
+
* @param spendingPrivateKey - Recipient's spending private key
|
|
3484
|
+
* @param viewingPrivateKey - Recipient's viewing private key
|
|
3485
|
+
* @returns true if the address belongs to this recipient
|
|
3486
|
+
*/
|
|
3487
|
+
checkStealthAddress(stealthAddress, spendingPrivateKey, viewingPrivateKey) {
|
|
3488
|
+
return checkAptosStealthAddress(stealthAddress, spendingPrivateKey, viewingPrivateKey);
|
|
3489
|
+
}
|
|
3490
|
+
/**
|
|
3491
|
+
* Validate an Aptos address format
|
|
3492
|
+
*
|
|
3493
|
+
* @param address - Address to validate
|
|
3494
|
+
* @returns true if valid format
|
|
3495
|
+
*/
|
|
3496
|
+
isValidAddress(address) {
|
|
3497
|
+
return isValidAptosAddress(address);
|
|
3498
|
+
}
|
|
3499
|
+
};
|
|
3500
|
+
|
|
3501
|
+
// src/move/sui.ts
|
|
3502
|
+
var import_blake2b = require("@noble/hashes/blake2b");
|
|
3503
|
+
var import_utils8 = require("@noble/hashes/utils");
|
|
3504
|
+
|
|
3505
|
+
// src/cosmos/stealth.ts
|
|
3506
|
+
var import_sha2566 = require("@noble/hashes/sha256");
|
|
3507
|
+
var import_ripemd160 = require("@noble/hashes/ripemd160");
|
|
3508
|
+
var import_utils9 = require("@noble/hashes/utils");
|
|
3509
|
+
var import_base = require("@scure/base");
|
|
3510
|
+
var CHAIN_PREFIXES = {
|
|
3511
|
+
cosmos: "cosmos",
|
|
3512
|
+
osmosis: "osmo",
|
|
3513
|
+
injective: "inj",
|
|
3514
|
+
celestia: "celestia",
|
|
3515
|
+
sei: "sei",
|
|
3516
|
+
dydx: "dydx"
|
|
3517
|
+
};
|
|
3518
|
+
var CosmosStealthService = class {
|
|
3519
|
+
/**
|
|
3520
|
+
* Generate a stealth meta-address for a Cosmos chain
|
|
3521
|
+
*
|
|
3522
|
+
* @param chain - Cosmos chain identifier
|
|
3523
|
+
* @param label - Optional human-readable label
|
|
3524
|
+
* @returns Stealth meta-address and private keys
|
|
3525
|
+
* @throws {ValidationError} If chain is invalid
|
|
3526
|
+
*
|
|
3527
|
+
* @example
|
|
3528
|
+
* ```typescript
|
|
3529
|
+
* const service = new CosmosStealthService()
|
|
3530
|
+
* const { metaAddress, spendingPrivateKey, viewingPrivateKey } =
|
|
3531
|
+
* service.generateStealthMetaAddress('cosmos', 'My Cosmos Wallet')
|
|
3532
|
+
* ```
|
|
3533
|
+
*/
|
|
3534
|
+
generateStealthMetaAddress(chain, label) {
|
|
3535
|
+
if (!this.isValidCosmosChain(chain)) {
|
|
3536
|
+
throw new ValidationError(
|
|
3537
|
+
`invalid Cosmos chain '${chain}', must be one of: ${Object.keys(CHAIN_PREFIXES).join(", ")}`,
|
|
3538
|
+
"chain"
|
|
3539
|
+
);
|
|
3540
|
+
}
|
|
3541
|
+
const result = generateStealthMetaAddress("ethereum", label);
|
|
3542
|
+
return {
|
|
3543
|
+
...result,
|
|
3544
|
+
metaAddress: {
|
|
3545
|
+
...result.metaAddress,
|
|
3546
|
+
chain
|
|
3547
|
+
// Will be updated in types package
|
|
3548
|
+
}
|
|
3549
|
+
};
|
|
3550
|
+
}
|
|
3551
|
+
/**
|
|
3552
|
+
* Generate a one-time stealth address for a Cosmos chain
|
|
3553
|
+
*
|
|
3554
|
+
* @param spendingPubKey - Recipient's spending public key (33-byte compressed)
|
|
3555
|
+
* @param viewingPubKey - Recipient's viewing public key (33-byte compressed)
|
|
3556
|
+
* @param chain - Cosmos chain identifier
|
|
3557
|
+
* @returns Cosmos stealth address with bech32 encoding
|
|
3558
|
+
* @throws {ValidationError} If keys or chain are invalid
|
|
3559
|
+
*
|
|
3560
|
+
* @example
|
|
3561
|
+
* ```typescript
|
|
3562
|
+
* const service = new CosmosStealthService()
|
|
3563
|
+
* const result = service.generateStealthAddress(
|
|
3564
|
+
* spendingKey,
|
|
3565
|
+
* viewingKey,
|
|
3566
|
+
* 'osmosis'
|
|
3567
|
+
* )
|
|
3568
|
+
* console.log(result.stealthAddress) // "osmo1..."
|
|
3569
|
+
* ```
|
|
3570
|
+
*/
|
|
3571
|
+
generateStealthAddress(spendingPubKey, viewingPubKey, chain) {
|
|
3572
|
+
if (!this.isValidCosmosChain(chain)) {
|
|
3573
|
+
throw new ValidationError(
|
|
3574
|
+
`invalid Cosmos chain '${chain}', must be one of: ${Object.keys(CHAIN_PREFIXES).join(", ")}`,
|
|
3575
|
+
"chain"
|
|
3576
|
+
);
|
|
3577
|
+
}
|
|
3578
|
+
if (spendingPubKey.length !== 33) {
|
|
3579
|
+
throw new ValidationError(
|
|
3580
|
+
"spendingPubKey must be 33 bytes (compressed secp256k1)",
|
|
3581
|
+
"spendingPubKey"
|
|
3582
|
+
);
|
|
3583
|
+
}
|
|
3584
|
+
if (viewingPubKey.length !== 33) {
|
|
3585
|
+
throw new ValidationError(
|
|
3586
|
+
"viewingPubKey must be 33 bytes (compressed secp256k1)",
|
|
3587
|
+
"viewingPubKey"
|
|
3588
|
+
);
|
|
3589
|
+
}
|
|
3590
|
+
const metaAddress = {
|
|
3591
|
+
spendingKey: `0x${(0, import_utils9.bytesToHex)(spendingPubKey)}`,
|
|
3592
|
+
viewingKey: `0x${(0, import_utils9.bytesToHex)(viewingPubKey)}`,
|
|
3593
|
+
chain: "ethereum"
|
|
3594
|
+
// Use ethereum for secp256k1 generation
|
|
3595
|
+
};
|
|
3596
|
+
const { stealthAddress, sharedSecret } = generateStealthAddress(metaAddress);
|
|
3597
|
+
const cosmosAddress = this.stealthKeyToCosmosAddress(
|
|
3598
|
+
(0, import_utils9.hexToBytes)(stealthAddress.address.slice(2)),
|
|
3599
|
+
CHAIN_PREFIXES[chain]
|
|
3600
|
+
);
|
|
3601
|
+
return {
|
|
3602
|
+
stealthAddress: cosmosAddress,
|
|
3603
|
+
stealthPublicKey: stealthAddress.address,
|
|
3604
|
+
ephemeralPublicKey: stealthAddress.ephemeralPublicKey,
|
|
3605
|
+
viewTag: stealthAddress.viewTag,
|
|
3606
|
+
viewKeyHash: sharedSecret
|
|
3607
|
+
};
|
|
3608
|
+
}
|
|
3609
|
+
/**
|
|
3610
|
+
* Generate stealth address from StealthMetaAddress
|
|
3611
|
+
*
|
|
3612
|
+
* Convenience method that accepts a StealthMetaAddress directly.
|
|
3613
|
+
*
|
|
3614
|
+
* @param recipientMetaAddress - Recipient's stealth meta-address
|
|
3615
|
+
* @param chain - Cosmos chain identifier
|
|
3616
|
+
* @returns Cosmos stealth address with bech32 encoding
|
|
3617
|
+
* @throws {ValidationError} If meta-address or chain are invalid
|
|
3618
|
+
*
|
|
3619
|
+
* @example
|
|
3620
|
+
* ```typescript
|
|
3621
|
+
* const service = new CosmosStealthService()
|
|
3622
|
+
* const result = service.generateStealthAddressFromMeta(metaAddress, 'cosmos')
|
|
3623
|
+
* ```
|
|
3624
|
+
*/
|
|
3625
|
+
generateStealthAddressFromMeta(recipientMetaAddress, chain) {
|
|
3626
|
+
const spendingPubKey = (0, import_utils9.hexToBytes)(recipientMetaAddress.spendingKey.slice(2));
|
|
3627
|
+
const viewingPubKey = (0, import_utils9.hexToBytes)(recipientMetaAddress.viewingKey.slice(2));
|
|
3628
|
+
return this.generateStealthAddress(spendingPubKey, viewingPubKey, chain);
|
|
3629
|
+
}
|
|
3630
|
+
/**
|
|
3631
|
+
* Convert stealth public key to Cosmos bech32 address
|
|
3632
|
+
*
|
|
3633
|
+
* Algorithm:
|
|
3634
|
+
* 1. SHA256 hash of compressed public key
|
|
3635
|
+
* 2. RIPEMD160 hash of SHA256 hash
|
|
3636
|
+
* 3. Bech32 encode with chain prefix
|
|
3637
|
+
*
|
|
3638
|
+
* @param publicKey - Compressed secp256k1 public key (33 bytes)
|
|
3639
|
+
* @param prefix - Bech32 address prefix (e.g., "cosmos", "osmo")
|
|
3640
|
+
* @returns Bech32-encoded address
|
|
3641
|
+
* @throws {ValidationError} If public key is invalid
|
|
3642
|
+
*
|
|
3643
|
+
* @example
|
|
3644
|
+
* ```typescript
|
|
3645
|
+
* const service = new CosmosStealthService()
|
|
3646
|
+
* const address = service.stealthKeyToCosmosAddress(pubKey, 'cosmos')
|
|
3647
|
+
* // Returns: "cosmos1abc..."
|
|
3648
|
+
* ```
|
|
3649
|
+
*/
|
|
3650
|
+
stealthKeyToCosmosAddress(publicKey, prefix) {
|
|
3651
|
+
if (publicKey.length !== 33) {
|
|
3652
|
+
throw new ValidationError(
|
|
3653
|
+
"public key must be 33 bytes (compressed secp256k1)",
|
|
3654
|
+
"publicKey"
|
|
3655
|
+
);
|
|
3656
|
+
}
|
|
3657
|
+
const sha256Hash = (0, import_sha2566.sha256)(publicKey);
|
|
3658
|
+
const hash160 = (0, import_ripemd160.ripemd160)(sha256Hash);
|
|
3659
|
+
const words = import_base.bech32.toWords(hash160);
|
|
3660
|
+
return import_base.bech32.encode(prefix, words);
|
|
3661
|
+
}
|
|
3662
|
+
/**
|
|
3663
|
+
* Derive stealth private key for recipient to claim funds
|
|
3664
|
+
*
|
|
3665
|
+
* @param stealthAddress - The stealth address to recover (as StealthAddress)
|
|
3666
|
+
* @param spendingPrivateKey - Recipient's spending private key
|
|
3667
|
+
* @param viewingPrivateKey - Recipient's viewing private key
|
|
3668
|
+
* @returns Recovery data with derived private key
|
|
3669
|
+
* @throws {ValidationError} If any input is invalid
|
|
3670
|
+
*
|
|
3671
|
+
* @example
|
|
3672
|
+
* ```typescript
|
|
3673
|
+
* const service = new CosmosStealthService()
|
|
3674
|
+
* const recovery = service.deriveStealthPrivateKey(
|
|
3675
|
+
* stealthAddress,
|
|
3676
|
+
* spendingPrivKey,
|
|
3677
|
+
* viewingPrivKey
|
|
3678
|
+
* )
|
|
3679
|
+
* // Use recovery.privateKey to spend funds
|
|
3680
|
+
* ```
|
|
3681
|
+
*/
|
|
3682
|
+
deriveStealthPrivateKey(stealthAddress, spendingPrivateKey, viewingPrivateKey) {
|
|
3683
|
+
return deriveStealthPrivateKey(
|
|
3684
|
+
stealthAddress,
|
|
3685
|
+
spendingPrivateKey,
|
|
3686
|
+
viewingPrivateKey
|
|
3687
|
+
);
|
|
3688
|
+
}
|
|
3689
|
+
/**
|
|
3690
|
+
* Check if a string is a valid Cosmos chain identifier
|
|
3691
|
+
*/
|
|
3692
|
+
isValidCosmosChain(chain) {
|
|
3693
|
+
return chain in CHAIN_PREFIXES;
|
|
3694
|
+
}
|
|
3695
|
+
/**
|
|
3696
|
+
* Decode a Cosmos bech32 address to raw hash
|
|
3697
|
+
*
|
|
3698
|
+
* @param address - Bech32-encoded address
|
|
3699
|
+
* @returns Decoded address hash (20 bytes)
|
|
3700
|
+
* @throws {ValidationError} If address is invalid
|
|
3701
|
+
*
|
|
3702
|
+
* @example
|
|
3703
|
+
* ```typescript
|
|
3704
|
+
* const service = new CosmosStealthService()
|
|
3705
|
+
* const { prefix, hash } = service.decodeBech32Address('cosmos1abc...')
|
|
3706
|
+
* ```
|
|
3707
|
+
*/
|
|
3708
|
+
decodeBech32Address(address) {
|
|
3709
|
+
try {
|
|
3710
|
+
const decoded = import_base.bech32.decode(address);
|
|
3711
|
+
const hash2 = import_base.bech32.fromWords(decoded.words);
|
|
3712
|
+
if (hash2.length !== 20) {
|
|
3713
|
+
throw new ValidationError(
|
|
3714
|
+
`invalid address hash length: ${hash2.length}, expected 20`,
|
|
3715
|
+
"address"
|
|
3716
|
+
);
|
|
3717
|
+
}
|
|
3718
|
+
return {
|
|
3719
|
+
prefix: decoded.prefix,
|
|
3720
|
+
hash: new Uint8Array(hash2)
|
|
3721
|
+
};
|
|
3722
|
+
} catch (error) {
|
|
3723
|
+
if (error instanceof ValidationError) {
|
|
3724
|
+
throw error;
|
|
3725
|
+
}
|
|
3726
|
+
throw new ValidationError(
|
|
3727
|
+
`invalid bech32 address: ${error instanceof Error ? error.message : "unknown error"}`,
|
|
3728
|
+
"address"
|
|
3729
|
+
);
|
|
3730
|
+
}
|
|
3731
|
+
}
|
|
3732
|
+
/**
|
|
3733
|
+
* Validate a Cosmos bech32 address format
|
|
3734
|
+
*
|
|
3735
|
+
* @param address - Address to validate
|
|
3736
|
+
* @param expectedChain - Optional chain to validate prefix against
|
|
3737
|
+
* @returns true if valid, false otherwise
|
|
3738
|
+
*
|
|
3739
|
+
* @example
|
|
3740
|
+
* ```typescript
|
|
3741
|
+
* const service = new CosmosStealthService()
|
|
3742
|
+
* service.isValidCosmosAddress('cosmos1abc...', 'cosmos') // true
|
|
3743
|
+
* service.isValidCosmosAddress('osmo1xyz...', 'cosmos') // false (wrong prefix)
|
|
3744
|
+
* ```
|
|
3745
|
+
*/
|
|
3746
|
+
isValidCosmosAddress(address, expectedChain) {
|
|
3747
|
+
try {
|
|
3748
|
+
const { prefix, hash: hash2 } = this.decodeBech32Address(address);
|
|
3749
|
+
if (hash2.length !== 20) {
|
|
3750
|
+
return false;
|
|
3751
|
+
}
|
|
3752
|
+
if (expectedChain) {
|
|
3753
|
+
return prefix === CHAIN_PREFIXES[expectedChain];
|
|
3754
|
+
}
|
|
3755
|
+
return Object.values(CHAIN_PREFIXES).includes(prefix);
|
|
3756
|
+
} catch {
|
|
3757
|
+
return false;
|
|
3758
|
+
}
|
|
3759
|
+
}
|
|
3760
|
+
/**
|
|
3761
|
+
* Get the chain ID from a bech32 address prefix
|
|
3762
|
+
*
|
|
3763
|
+
* @param address - Bech32-encoded address
|
|
3764
|
+
* @returns Chain ID or null if unknown prefix
|
|
3765
|
+
*
|
|
3766
|
+
* @example
|
|
3767
|
+
* ```typescript
|
|
3768
|
+
* const service = new CosmosStealthService()
|
|
3769
|
+
* service.getChainFromAddress('cosmos1abc...') // 'cosmos'
|
|
3770
|
+
* service.getChainFromAddress('osmo1xyz...') // 'osmosis'
|
|
3771
|
+
* ```
|
|
3772
|
+
*/
|
|
3773
|
+
getChainFromAddress(address) {
|
|
3774
|
+
try {
|
|
3775
|
+
const { prefix } = this.decodeBech32Address(address);
|
|
3776
|
+
for (const [chain, chainPrefix] of Object.entries(CHAIN_PREFIXES)) {
|
|
3777
|
+
if (chainPrefix === prefix) {
|
|
3778
|
+
return chain;
|
|
3779
|
+
}
|
|
3780
|
+
}
|
|
3781
|
+
return null;
|
|
3782
|
+
} catch {
|
|
3783
|
+
return null;
|
|
3784
|
+
}
|
|
3785
|
+
}
|
|
3786
|
+
};
|
|
3787
|
+
function generateCosmosStealthMetaAddress(chain, label) {
|
|
3788
|
+
const service = new CosmosStealthService();
|
|
3789
|
+
return service.generateStealthMetaAddress(chain, label);
|
|
3790
|
+
}
|
|
3791
|
+
function generateCosmosStealthAddress(spendingPubKey, viewingPubKey, chain) {
|
|
3792
|
+
const service = new CosmosStealthService();
|
|
3793
|
+
return service.generateStealthAddress(spendingPubKey, viewingPubKey, chain);
|
|
3794
|
+
}
|
|
3795
|
+
function stealthKeyToCosmosAddress(publicKey, prefix) {
|
|
3796
|
+
const service = new CosmosStealthService();
|
|
3797
|
+
return service.stealthKeyToCosmosAddress(publicKey, prefix);
|
|
3798
|
+
}
|
|
3799
|
+
function isValidCosmosAddress(address, expectedChain) {
|
|
3800
|
+
const service = new CosmosStealthService();
|
|
3801
|
+
return service.isValidCosmosAddress(address, expectedChain);
|
|
3802
|
+
}
|
|
3803
|
+
|
|
3804
|
+
// src/cosmos/ibc-stealth.ts
|
|
3805
|
+
var import_utils10 = require("@noble/hashes/utils");
|
|
3806
|
+
var import_secp256k13 = require("@noble/curves/secp256k1");
|
|
3807
|
+
var import_sha2567 = require("@noble/hashes/sha256");
|
|
3808
|
+
|
|
3290
3809
|
// src/proofs/interface.ts
|
|
3291
3810
|
var ProofGenerationError = class extends Error {
|
|
3292
3811
|
proofType;
|
|
@@ -3300,8 +3819,8 @@ var ProofGenerationError = class extends Error {
|
|
|
3300
3819
|
};
|
|
3301
3820
|
|
|
3302
3821
|
// src/proofs/mock.ts
|
|
3303
|
-
var
|
|
3304
|
-
var
|
|
3822
|
+
var import_sha2568 = require("@noble/hashes/sha256");
|
|
3823
|
+
var import_utils11 = require("@noble/hashes/utils");
|
|
3305
3824
|
var MOCK_PROOF_PREFIX = "0x4d4f434b";
|
|
3306
3825
|
var WARNING_MESSAGE = `
|
|
3307
3826
|
\u2554\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2557
|
|
@@ -3466,17 +3985,17 @@ var MockProofProvider = class {
|
|
|
3466
3985
|
{ type: proofType, params },
|
|
3467
3986
|
(_, v) => typeof v === "bigint" ? v.toString() : v
|
|
3468
3987
|
);
|
|
3469
|
-
const hash2 = (0,
|
|
3470
|
-
const random = (0,
|
|
3988
|
+
const hash2 = (0, import_sha2568.sha256)(new TextEncoder().encode(input));
|
|
3989
|
+
const random = (0, import_utils11.randomBytes)(16);
|
|
3471
3990
|
const combined = new Uint8Array(4 + hash2.length + random.length);
|
|
3472
3991
|
combined.set(new TextEncoder().encode("MOCK"), 0);
|
|
3473
3992
|
combined.set(hash2, 4);
|
|
3474
3993
|
combined.set(random, 4 + hash2.length);
|
|
3475
|
-
return `${MOCK_PROOF_PREFIX}${(0,
|
|
3994
|
+
return `${MOCK_PROOF_PREFIX}${(0, import_utils11.bytesToHex)(combined.slice(4))}`;
|
|
3476
3995
|
}
|
|
3477
3996
|
hashToHex(data) {
|
|
3478
|
-
const hash2 = (0,
|
|
3479
|
-
return `0x${(0,
|
|
3997
|
+
const hash2 = (0, import_sha2568.sha256)(new TextEncoder().encode(data));
|
|
3998
|
+
return `0x${(0, import_utils11.bytesToHex)(hash2)}`;
|
|
3480
3999
|
}
|
|
3481
4000
|
};
|
|
3482
4001
|
|
|
@@ -3755,7 +4274,7 @@ function checkMobileWASMCompatibility() {
|
|
|
3755
4274
|
recommendations
|
|
3756
4275
|
};
|
|
3757
4276
|
}
|
|
3758
|
-
function
|
|
4277
|
+
function hexToBytes9(hex) {
|
|
3759
4278
|
const h = hex.startsWith("0x") ? hex.slice(2) : hex;
|
|
3760
4279
|
if (h.length === 0) return new Uint8Array(0);
|
|
3761
4280
|
if (h.length % 2 !== 0) {
|
|
@@ -3767,7 +4286,7 @@ function hexToBytes5(hex) {
|
|
|
3767
4286
|
}
|
|
3768
4287
|
return bytes;
|
|
3769
4288
|
}
|
|
3770
|
-
function
|
|
4289
|
+
function bytesToHex11(bytes) {
|
|
3771
4290
|
return Array.from(bytes).map((b) => b.toString(16).padStart(2, "0")).join("");
|
|
3772
4291
|
}
|
|
3773
4292
|
function isBrowser() {
|
|
@@ -3809,18 +4328,34 @@ var CHAIN_NUMERIC_IDS = {
|
|
|
3809
4328
|
// Non-standard, SIP-specific
|
|
3810
4329
|
near: 502,
|
|
3811
4330
|
// Non-standard, SIP-specific
|
|
3812
|
-
zcash: 503
|
|
4331
|
+
zcash: 503,
|
|
4332
|
+
// Non-standard, SIP-specific
|
|
4333
|
+
aptos: 504,
|
|
4334
|
+
// Non-standard, SIP-specific
|
|
4335
|
+
sui: 505,
|
|
4336
|
+
// Non-standard, SIP-specific
|
|
4337
|
+
cosmos: 506,
|
|
4338
|
+
// Non-standard, SIP-specific (Cosmos Hub)
|
|
4339
|
+
osmosis: 507,
|
|
4340
|
+
// Non-standard, SIP-specific
|
|
4341
|
+
injective: 508,
|
|
4342
|
+
// Non-standard, SIP-specific
|
|
4343
|
+
celestia: 509,
|
|
4344
|
+
// Non-standard, SIP-specific
|
|
4345
|
+
sei: 510,
|
|
4346
|
+
// Non-standard, SIP-specific
|
|
4347
|
+
dydx: 511
|
|
3813
4348
|
// Non-standard, SIP-specific
|
|
3814
4349
|
};
|
|
3815
4350
|
|
|
3816
4351
|
// src/oracle/verification.ts
|
|
3817
4352
|
var import_ed255192 = require("@noble/curves/ed25519");
|
|
3818
|
-
var
|
|
3819
|
-
var
|
|
4353
|
+
var import_sha25610 = require("@noble/hashes/sha256");
|
|
4354
|
+
var import_utils13 = require("@noble/hashes/utils");
|
|
3820
4355
|
|
|
3821
4356
|
// src/oracle/serialization.ts
|
|
3822
|
-
var
|
|
3823
|
-
var
|
|
4357
|
+
var import_sha2569 = require("@noble/hashes/sha256");
|
|
4358
|
+
var import_utils12 = require("@noble/hashes/utils");
|
|
3824
4359
|
function serializeAttestationMessage(message) {
|
|
3825
4360
|
const buffer = new Uint8Array(197);
|
|
3826
4361
|
const view = new DataView(buffer.buffer);
|
|
@@ -3863,19 +4398,19 @@ function deserializeAttestationMessage(bytes) {
|
|
|
3863
4398
|
const version = bytes[offset++];
|
|
3864
4399
|
const chainId = view.getUint32(offset, false);
|
|
3865
4400
|
offset += 4;
|
|
3866
|
-
const intentHash = `0x${(0,
|
|
4401
|
+
const intentHash = `0x${(0, import_utils12.bytesToHex)(bytes.slice(offset, offset + 32))}`;
|
|
3867
4402
|
offset += 32;
|
|
3868
|
-
const recipient = `0x${(0,
|
|
4403
|
+
const recipient = `0x${(0, import_utils12.bytesToHex)(bytes.slice(offset, offset + 32))}`;
|
|
3869
4404
|
offset += 32;
|
|
3870
4405
|
const amount = bytesToBigint(bytes.slice(offset, offset + 16));
|
|
3871
4406
|
offset += 16;
|
|
3872
|
-
const assetId = `0x${(0,
|
|
4407
|
+
const assetId = `0x${(0, import_utils12.bytesToHex)(bytes.slice(offset, offset + 32))}`;
|
|
3873
4408
|
offset += 32;
|
|
3874
|
-
const txHash = `0x${(0,
|
|
4409
|
+
const txHash = `0x${(0, import_utils12.bytesToHex)(bytes.slice(offset, offset + 32))}`;
|
|
3875
4410
|
offset += 32;
|
|
3876
4411
|
const blockNumber = view.getBigUint64(offset, false);
|
|
3877
4412
|
offset += 8;
|
|
3878
|
-
const blockHash = `0x${(0,
|
|
4413
|
+
const blockHash = `0x${(0, import_utils12.bytesToHex)(bytes.slice(offset, offset + 32))}`;
|
|
3879
4414
|
offset += 32;
|
|
3880
4415
|
const timestamp = Number(view.getBigUint64(offset, false));
|
|
3881
4416
|
return {
|
|
@@ -3892,12 +4427,12 @@ function deserializeAttestationMessage(bytes) {
|
|
|
3892
4427
|
};
|
|
3893
4428
|
}
|
|
3894
4429
|
function computeAttestationHash(message) {
|
|
3895
|
-
const domain = (0,
|
|
4430
|
+
const domain = (0, import_utils12.utf8ToBytes)(ORACLE_DOMAIN);
|
|
3896
4431
|
const messageBytes = serializeAttestationMessage(message);
|
|
3897
4432
|
const toHash = new Uint8Array(domain.length + messageBytes.length);
|
|
3898
4433
|
toHash.set(domain, 0);
|
|
3899
4434
|
toHash.set(messageBytes, domain.length);
|
|
3900
|
-
return (0,
|
|
4435
|
+
return (0, import_sha2569.sha256)(toHash);
|
|
3901
4436
|
}
|
|
3902
4437
|
function getChainNumericId(chain) {
|
|
3903
4438
|
const id = CHAIN_NUMERIC_IDS[chain];
|
|
@@ -3908,7 +4443,7 @@ function getChainNumericId(chain) {
|
|
|
3908
4443
|
}
|
|
3909
4444
|
function normalizeToBytes(hex, length, field) {
|
|
3910
4445
|
const stripped = hex.startsWith("0x") ? hex.slice(2) : hex;
|
|
3911
|
-
const bytes = (0,
|
|
4446
|
+
const bytes = (0, import_utils12.hexToBytes)(stripped);
|
|
3912
4447
|
if (bytes.length === length) {
|
|
3913
4448
|
return bytes;
|
|
3914
4449
|
}
|
|
@@ -3941,9 +4476,9 @@ function bytesToBigint(bytes) {
|
|
|
3941
4476
|
|
|
3942
4477
|
// src/oracle/verification.ts
|
|
3943
4478
|
function deriveOracleId(publicKey) {
|
|
3944
|
-
const keyBytes = typeof publicKey === "string" ? (0,
|
|
3945
|
-
const hash2 = (0,
|
|
3946
|
-
return `0x${(0,
|
|
4479
|
+
const keyBytes = typeof publicKey === "string" ? (0, import_utils13.hexToBytes)(publicKey.startsWith("0x") ? publicKey.slice(2) : publicKey) : publicKey;
|
|
4480
|
+
const hash2 = (0, import_sha25610.sha256)(keyBytes);
|
|
4481
|
+
return `0x${(0, import_utils13.bytesToHex)(hash2)}`;
|
|
3947
4482
|
}
|
|
3948
4483
|
function verifyAttestation(attestation, registry) {
|
|
3949
4484
|
const { message, signatures } = attestation;
|
|
@@ -3973,10 +4508,10 @@ function verifyAttestation(attestation, registry) {
|
|
|
3973
4508
|
continue;
|
|
3974
4509
|
}
|
|
3975
4510
|
try {
|
|
3976
|
-
const publicKeyBytes = (0,
|
|
4511
|
+
const publicKeyBytes = (0, import_utils13.hexToBytes)(
|
|
3977
4512
|
oracle.publicKey.startsWith("0x") ? oracle.publicKey.slice(2) : oracle.publicKey
|
|
3978
4513
|
);
|
|
3979
|
-
const signatureBytes = (0,
|
|
4514
|
+
const signatureBytes = (0, import_utils13.hexToBytes)(
|
|
3980
4515
|
sig.signature.startsWith("0x") ? sig.signature.slice(2) : sig.signature
|
|
3981
4516
|
);
|
|
3982
4517
|
const isValid = import_ed255192.ed25519.verify(signatureBytes, messageHash, publicKeyBytes);
|
|
@@ -4001,10 +4536,10 @@ function verifyAttestation(attestation, registry) {
|
|
|
4001
4536
|
}
|
|
4002
4537
|
function verifyOracleSignature(signature, messageHash, oracle) {
|
|
4003
4538
|
try {
|
|
4004
|
-
const publicKeyBytes = (0,
|
|
4539
|
+
const publicKeyBytes = (0, import_utils13.hexToBytes)(
|
|
4005
4540
|
oracle.publicKey.startsWith("0x") ? oracle.publicKey.slice(2) : oracle.publicKey
|
|
4006
4541
|
);
|
|
4007
|
-
const signatureBytes = (0,
|
|
4542
|
+
const signatureBytes = (0, import_utils13.hexToBytes)(
|
|
4008
4543
|
signature.signature.startsWith("0x") ? signature.signature.slice(2) : signature.signature
|
|
4009
4544
|
);
|
|
4010
4545
|
return import_ed255192.ed25519.verify(signatureBytes, messageHash, publicKeyBytes);
|
|
@@ -4018,7 +4553,7 @@ function signAttestationMessage(messageHash, privateKey) {
|
|
|
4018
4553
|
const oracleId = deriveOracleId(publicKey);
|
|
4019
4554
|
return {
|
|
4020
4555
|
oracleId,
|
|
4021
|
-
signature: `0x${(0,
|
|
4556
|
+
signature: `0x${(0, import_utils13.bytesToHex)(signature)}`
|
|
4022
4557
|
};
|
|
4023
4558
|
}
|
|
4024
4559
|
function createOracleRegistry(config = {}) {
|
|
@@ -4070,14 +4605,14 @@ function hasEnoughOracles(registry) {
|
|
|
4070
4605
|
}
|
|
4071
4606
|
|
|
4072
4607
|
// src/index.ts
|
|
4073
|
-
var
|
|
4074
|
-
var
|
|
4075
|
-
var
|
|
4076
|
-
var
|
|
4608
|
+
var import_types55 = require("@sip-protocol/types");
|
|
4609
|
+
var import_types56 = require("@sip-protocol/types");
|
|
4610
|
+
var import_types57 = require("@sip-protocol/types");
|
|
4611
|
+
var import_types58 = require("@sip-protocol/types");
|
|
4077
4612
|
|
|
4078
4613
|
// src/solver/mock-solver.ts
|
|
4079
4614
|
var import_types7 = require("@sip-protocol/types");
|
|
4080
|
-
var
|
|
4615
|
+
var import_utils14 = require("@noble/hashes/utils");
|
|
4081
4616
|
var MockSolver = class {
|
|
4082
4617
|
info;
|
|
4083
4618
|
capabilities;
|
|
@@ -4159,7 +4694,7 @@ var MockSolver = class {
|
|
|
4159
4694
|
const spreadAmount = baseOutput * BigInt(Math.floor(this.spreadPercent * 1e4)) / 10000n;
|
|
4160
4695
|
const outputAmount = baseOutput + spreadAmount;
|
|
4161
4696
|
const feeAmount = outputAmount * BigInt(Math.floor(this.feePercent * 1e4)) / 10000n;
|
|
4162
|
-
const quoteId = `quote-${(0,
|
|
4697
|
+
const quoteId = `quote-${(0, import_utils14.bytesToHex)((0, import_utils14.randomBytes)(8))}`;
|
|
4163
4698
|
const now = Math.floor(Date.now() / 1e3);
|
|
4164
4699
|
const quote = {
|
|
4165
4700
|
quoteId,
|
|
@@ -4170,7 +4705,7 @@ var MockSolver = class {
|
|
|
4170
4705
|
expiry: now + 60,
|
|
4171
4706
|
// Quote valid for 1 minute
|
|
4172
4707
|
fee: feeAmount,
|
|
4173
|
-
signature: `0x${(0,
|
|
4708
|
+
signature: `0x${(0, import_utils14.bytesToHex)((0, import_utils14.randomBytes)(64))}`,
|
|
4174
4709
|
// Mock signature
|
|
4175
4710
|
validUntil: now + 60,
|
|
4176
4711
|
estimatedGas: 200000n
|
|
@@ -4207,7 +4742,7 @@ var MockSolver = class {
|
|
|
4207
4742
|
error: status.error
|
|
4208
4743
|
};
|
|
4209
4744
|
}
|
|
4210
|
-
const txHash = `0x${(0,
|
|
4745
|
+
const txHash = `0x${(0, import_utils14.bytesToHex)((0, import_utils14.randomBytes)(32))}`;
|
|
4211
4746
|
status.status = "completed";
|
|
4212
4747
|
status.txHash = txHash;
|
|
4213
4748
|
return {
|
|
@@ -4217,10 +4752,10 @@ var MockSolver = class {
|
|
|
4217
4752
|
txHash: intent.privacyLevel === "transparent" ? txHash : void 0,
|
|
4218
4753
|
fulfillmentProof: {
|
|
4219
4754
|
type: "fulfillment",
|
|
4220
|
-
proof: `0x${(0,
|
|
4755
|
+
proof: `0x${(0, import_utils14.bytesToHex)((0, import_utils14.randomBytes)(128))}`,
|
|
4221
4756
|
publicInputs: [
|
|
4222
|
-
`0x${(0,
|
|
4223
|
-
`0x${(0,
|
|
4757
|
+
`0x${(0, import_utils14.bytesToHex)(new TextEncoder().encode(intent.intentId))}`,
|
|
4758
|
+
`0x${(0, import_utils14.bytesToHex)(new TextEncoder().encode(quote.quoteId))}`
|
|
4224
4759
|
]
|
|
4225
4760
|
},
|
|
4226
4761
|
fulfilledAt: Math.floor(Date.now() / 1e3)
|
|
@@ -4258,7 +4793,7 @@ function createMockSolver(config) {
|
|
|
4258
4793
|
}
|
|
4259
4794
|
|
|
4260
4795
|
// src/index.ts
|
|
4261
|
-
var
|
|
4796
|
+
var import_types59 = require("@sip-protocol/types");
|
|
4262
4797
|
|
|
4263
4798
|
// src/settlement/interface.ts
|
|
4264
4799
|
var SwapStatus = /* @__PURE__ */ ((SwapStatus2) => {
|
|
@@ -5364,7 +5899,7 @@ function createZcashNativeBackend(config) {
|
|
|
5364
5899
|
|
|
5365
5900
|
// src/settlement/backends/direct-chain.ts
|
|
5366
5901
|
var import_types10 = require("@sip-protocol/types");
|
|
5367
|
-
var
|
|
5902
|
+
var import_utils15 = require("@noble/hashes/utils");
|
|
5368
5903
|
var DEFAULT_GAS_FEES = {
|
|
5369
5904
|
ethereum: 21000n * 50n * 1000000000n,
|
|
5370
5905
|
// 21k gas * 50 gwei = 0.00105 ETH
|
|
@@ -5382,8 +5917,24 @@ var DEFAULT_GAS_FEES = {
|
|
|
5382
5917
|
// 21k gas * 0.001 gwei ETH = 21 gwei = 21e6 wei
|
|
5383
5918
|
base: 2100000000n,
|
|
5384
5919
|
// 21k gas * 0.1 gwei ETH = 2100 gwei = 2.1e9 wei
|
|
5385
|
-
bitcoin: 10000n
|
|
5920
|
+
bitcoin: 10000n,
|
|
5386
5921
|
// 10000 sats = 0.0001 BTC (estimate for 1 input, 2 outputs)
|
|
5922
|
+
aptos: 100n,
|
|
5923
|
+
// 0.000001 APT in octas (gas units)
|
|
5924
|
+
sui: 1000n,
|
|
5925
|
+
// 0.000001 SUI in MIST
|
|
5926
|
+
cosmos: 5000n,
|
|
5927
|
+
// 0.005 ATOM in uatom
|
|
5928
|
+
osmosis: 5000n,
|
|
5929
|
+
// 0.005 OSMO in uosmo
|
|
5930
|
+
injective: 5000n,
|
|
5931
|
+
// 0.000005 INJ in inj (18 decimals)
|
|
5932
|
+
celestia: 5000n,
|
|
5933
|
+
// 0.005 TIA in utia
|
|
5934
|
+
sei: 5000n,
|
|
5935
|
+
// 0.005 SEI in usei
|
|
5936
|
+
dydx: 5000n
|
|
5937
|
+
// 0.000005 DYDX in dydx (18 decimals)
|
|
5387
5938
|
};
|
|
5388
5939
|
|
|
5389
5940
|
// src/zcash/rpc-client.ts
|
|
@@ -6668,33 +7219,321 @@ function createZcashSwapService(config) {
|
|
|
6668
7219
|
var import_types14 = require("@sip-protocol/types");
|
|
6669
7220
|
|
|
6670
7221
|
// src/index.ts
|
|
6671
|
-
var
|
|
6672
|
-
|
|
6673
|
-
// src/payment/payment.ts
|
|
6674
|
-
var import_types15 = require("@sip-protocol/types");
|
|
6675
|
-
var import_sha2569 = require("@noble/hashes/sha256");
|
|
6676
|
-
var import_utils12 = require("@noble/hashes/utils");
|
|
6677
|
-
var import_chacha2 = require("@noble/ciphers/chacha.js");
|
|
6678
|
-
var import_hkdf2 = require("@noble/hashes/hkdf");
|
|
7222
|
+
var import_types60 = require("@sip-protocol/types");
|
|
6679
7223
|
|
|
6680
|
-
// src/
|
|
6681
|
-
var
|
|
6682
|
-
|
|
6683
|
-
|
|
6684
|
-
|
|
6685
|
-
|
|
6686
|
-
|
|
6687
|
-
|
|
6688
|
-
|
|
6689
|
-
|
|
6690
|
-
|
|
6691
|
-
|
|
6692
|
-
|
|
6693
|
-
|
|
6694
|
-
|
|
6695
|
-
|
|
6696
|
-
|
|
6697
|
-
|
|
7224
|
+
// src/bitcoin/taproot.ts
|
|
7225
|
+
var import_secp256k14 = require("@noble/curves/secp256k1");
|
|
7226
|
+
var import_sha25611 = require("@noble/hashes/sha256");
|
|
7227
|
+
var import_utils16 = require("@noble/hashes/utils");
|
|
7228
|
+
var BECH32_CHARSET = "qpzry9x8gf2tvdw0s3jn54khce6mua7l";
|
|
7229
|
+
var BECH32_GENERATOR = [996825010, 642813549, 513874426, 1027748829, 705979059];
|
|
7230
|
+
function taggedHash(tag, data) {
|
|
7231
|
+
const tagHash = (0, import_sha25611.sha256)(new TextEncoder().encode(tag));
|
|
7232
|
+
const taggedData = new Uint8Array(tagHash.length * 2 + data.length);
|
|
7233
|
+
taggedData.set(tagHash, 0);
|
|
7234
|
+
taggedData.set(tagHash, tagHash.length);
|
|
7235
|
+
taggedData.set(data, tagHash.length * 2);
|
|
7236
|
+
return (0, import_sha25611.sha256)(taggedData);
|
|
7237
|
+
}
|
|
7238
|
+
function schnorrSign(message, privateKey, auxRand) {
|
|
7239
|
+
if (message.length !== 32) {
|
|
7240
|
+
throw new ValidationError("message must be 32 bytes", "message");
|
|
7241
|
+
}
|
|
7242
|
+
if (privateKey.length !== 32) {
|
|
7243
|
+
throw new ValidationError("privateKey must be 32 bytes", "privateKey");
|
|
7244
|
+
}
|
|
7245
|
+
if (auxRand && auxRand.length !== 32) {
|
|
7246
|
+
throw new ValidationError("auxRand must be 32 bytes if provided", "auxRand");
|
|
7247
|
+
}
|
|
7248
|
+
return import_secp256k14.schnorr.sign(message, privateKey, auxRand);
|
|
7249
|
+
}
|
|
7250
|
+
function schnorrVerify(signature, message, publicKey) {
|
|
7251
|
+
if (signature.length !== 64) {
|
|
7252
|
+
throw new ValidationError("signature must be 64 bytes", "signature");
|
|
7253
|
+
}
|
|
7254
|
+
if (message.length !== 32) {
|
|
7255
|
+
throw new ValidationError("message must be 32 bytes", "message");
|
|
7256
|
+
}
|
|
7257
|
+
if (publicKey.length !== 32) {
|
|
7258
|
+
throw new ValidationError("publicKey must be 32 bytes (x-only)", "publicKey");
|
|
7259
|
+
}
|
|
7260
|
+
try {
|
|
7261
|
+
return import_secp256k14.schnorr.verify(signature, message, publicKey);
|
|
7262
|
+
} catch {
|
|
7263
|
+
return false;
|
|
7264
|
+
}
|
|
7265
|
+
}
|
|
7266
|
+
function getXOnlyPublicKey(privateKey) {
|
|
7267
|
+
if (privateKey.length !== 32) {
|
|
7268
|
+
throw new ValidationError("privateKey must be 32 bytes", "privateKey");
|
|
7269
|
+
}
|
|
7270
|
+
const publicKey = import_secp256k14.secp256k1.getPublicKey(privateKey, false);
|
|
7271
|
+
return publicKey.slice(1, 33);
|
|
7272
|
+
}
|
|
7273
|
+
function computeTweakedKey(internalKey, merkleRoot) {
|
|
7274
|
+
if (internalKey.length !== 32) {
|
|
7275
|
+
throw new ValidationError("internalKey must be 32 bytes (x-only)", "internalKey");
|
|
7276
|
+
}
|
|
7277
|
+
if (merkleRoot && merkleRoot.length !== 32) {
|
|
7278
|
+
throw new ValidationError("merkleRoot must be 32 bytes if provided", "merkleRoot");
|
|
7279
|
+
}
|
|
7280
|
+
const tweakData = merkleRoot ? new Uint8Array([...internalKey, ...merkleRoot]) : internalKey;
|
|
7281
|
+
const tweak = taggedHash("TapTweak", tweakData);
|
|
7282
|
+
const tweakScalar = BigInt("0x" + (0, import_utils16.bytesToHex)(tweak)) % import_secp256k14.secp256k1.CURVE.n;
|
|
7283
|
+
const internalPoint = import_secp256k14.secp256k1.ProjectivePoint.fromHex(
|
|
7284
|
+
"02" + (0, import_utils16.bytesToHex)(internalKey)
|
|
7285
|
+
);
|
|
7286
|
+
const tweakPoint = import_secp256k14.secp256k1.ProjectivePoint.BASE.multiply(tweakScalar);
|
|
7287
|
+
const tweakedPoint = internalPoint.add(tweakPoint);
|
|
7288
|
+
const tweakedKeyBytes = tweakedPoint.toRawBytes(false);
|
|
7289
|
+
const xOnly = tweakedKeyBytes.slice(1, 33);
|
|
7290
|
+
const yCoord = tweakedKeyBytes.slice(33, 65);
|
|
7291
|
+
const yBigInt = BigInt("0x" + (0, import_utils16.bytesToHex)(yCoord));
|
|
7292
|
+
const parity = Number(yBigInt & 1n);
|
|
7293
|
+
return {
|
|
7294
|
+
tweakedKey: xOnly,
|
|
7295
|
+
parity
|
|
7296
|
+
};
|
|
7297
|
+
}
|
|
7298
|
+
function createTaprootOutput(internalKey, scripts) {
|
|
7299
|
+
if (internalKey.length !== 32) {
|
|
7300
|
+
throw new ValidationError("internalKey must be 32 bytes (x-only)", "internalKey");
|
|
7301
|
+
}
|
|
7302
|
+
let merkleRoot;
|
|
7303
|
+
if (scripts && scripts.length > 0) {
|
|
7304
|
+
if (scripts.length === 1) {
|
|
7305
|
+
const script = scripts[0];
|
|
7306
|
+
const leafData = new Uint8Array([
|
|
7307
|
+
script.leafVersion,
|
|
7308
|
+
script.script.length,
|
|
7309
|
+
...script.script
|
|
7310
|
+
]);
|
|
7311
|
+
merkleRoot = taggedHash("TapLeaf", leafData);
|
|
7312
|
+
} else {
|
|
7313
|
+
throw new ValidationError(
|
|
7314
|
+
"Multiple tapscripts not yet implemented - use single script or no scripts",
|
|
7315
|
+
"scripts"
|
|
7316
|
+
);
|
|
7317
|
+
}
|
|
7318
|
+
}
|
|
7319
|
+
const { tweakedKey, parity } = computeTweakedKey(internalKey, merkleRoot);
|
|
7320
|
+
return {
|
|
7321
|
+
tweakedKey: `0x${(0, import_utils16.bytesToHex)(tweakedKey)}`,
|
|
7322
|
+
internalKey: `0x${(0, import_utils16.bytesToHex)(internalKey)}`,
|
|
7323
|
+
merkleRoot: merkleRoot ? `0x${(0, import_utils16.bytesToHex)(merkleRoot)}` : void 0,
|
|
7324
|
+
parity
|
|
7325
|
+
};
|
|
7326
|
+
}
|
|
7327
|
+
function bech32Polymod(values) {
|
|
7328
|
+
let chk = 1;
|
|
7329
|
+
for (const value of values) {
|
|
7330
|
+
const top = chk >> 25;
|
|
7331
|
+
chk = (chk & 33554431) << 5 ^ value;
|
|
7332
|
+
for (let i = 0; i < 5; i++) {
|
|
7333
|
+
if (top >> i & 1) {
|
|
7334
|
+
chk ^= BECH32_GENERATOR[i];
|
|
7335
|
+
}
|
|
7336
|
+
}
|
|
7337
|
+
}
|
|
7338
|
+
return chk;
|
|
7339
|
+
}
|
|
7340
|
+
function bech32HrpExpand(hrp) {
|
|
7341
|
+
const result = [];
|
|
7342
|
+
for (let i = 0; i < hrp.length; i++) {
|
|
7343
|
+
result.push(hrp.charCodeAt(i) >> 5);
|
|
7344
|
+
}
|
|
7345
|
+
result.push(0);
|
|
7346
|
+
for (let i = 0; i < hrp.length; i++) {
|
|
7347
|
+
result.push(hrp.charCodeAt(i) & 31);
|
|
7348
|
+
}
|
|
7349
|
+
return result;
|
|
7350
|
+
}
|
|
7351
|
+
function bech32VerifyChecksum(hrp, data) {
|
|
7352
|
+
return bech32Polymod([...bech32HrpExpand(hrp), ...data]) === 734539939;
|
|
7353
|
+
}
|
|
7354
|
+
function bech32CreateChecksum(hrp, data) {
|
|
7355
|
+
const values = [...bech32HrpExpand(hrp), ...data, 0, 0, 0, 0, 0, 0];
|
|
7356
|
+
const polymod = bech32Polymod(values) ^ 734539939;
|
|
7357
|
+
const checksum = [];
|
|
7358
|
+
for (let i = 0; i < 6; i++) {
|
|
7359
|
+
checksum.push(polymod >> 5 * (5 - i) & 31);
|
|
7360
|
+
}
|
|
7361
|
+
return checksum;
|
|
7362
|
+
}
|
|
7363
|
+
function convertBits(data, fromBits, toBits, pad) {
|
|
7364
|
+
let acc = 0;
|
|
7365
|
+
let bits = 0;
|
|
7366
|
+
const result = [];
|
|
7367
|
+
const maxv = (1 << toBits) - 1;
|
|
7368
|
+
for (const value of data) {
|
|
7369
|
+
if (value < 0 || value >> fromBits !== 0) {
|
|
7370
|
+
return null;
|
|
7371
|
+
}
|
|
7372
|
+
acc = acc << fromBits | value;
|
|
7373
|
+
bits += fromBits;
|
|
7374
|
+
while (bits >= toBits) {
|
|
7375
|
+
bits -= toBits;
|
|
7376
|
+
result.push(acc >> bits & maxv);
|
|
7377
|
+
}
|
|
7378
|
+
}
|
|
7379
|
+
if (pad) {
|
|
7380
|
+
if (bits > 0) {
|
|
7381
|
+
result.push(acc << toBits - bits & maxv);
|
|
7382
|
+
}
|
|
7383
|
+
} else if (bits >= fromBits || acc << toBits - bits & maxv) {
|
|
7384
|
+
return null;
|
|
7385
|
+
}
|
|
7386
|
+
return result;
|
|
7387
|
+
}
|
|
7388
|
+
function taprootAddress(tweakedKey, network = "mainnet") {
|
|
7389
|
+
if (tweakedKey.length !== 32) {
|
|
7390
|
+
throw new ValidationError("tweakedKey must be 32 bytes", "tweakedKey");
|
|
7391
|
+
}
|
|
7392
|
+
const hrp = network === "mainnet" ? "bc" : network === "testnet" ? "tb" : "bcrt";
|
|
7393
|
+
const version = 1;
|
|
7394
|
+
const words = convertBits(tweakedKey, 8, 5, true);
|
|
7395
|
+
if (!words) {
|
|
7396
|
+
throw new ValidationError("Failed to convert tweaked key to bech32 format", "tweakedKey");
|
|
7397
|
+
}
|
|
7398
|
+
const data = [version, ...words];
|
|
7399
|
+
const checksum = bech32CreateChecksum(hrp, data);
|
|
7400
|
+
const combined = [...data, ...checksum];
|
|
7401
|
+
let result = hrp + "1";
|
|
7402
|
+
for (const value of combined) {
|
|
7403
|
+
result += BECH32_CHARSET[value];
|
|
7404
|
+
}
|
|
7405
|
+
return result;
|
|
7406
|
+
}
|
|
7407
|
+
function decodeTaprootAddress(address) {
|
|
7408
|
+
if (typeof address !== "string" || address.length < 14 || address.length > 90) {
|
|
7409
|
+
throw new ValidationError("Invalid Taproot address format", "address");
|
|
7410
|
+
}
|
|
7411
|
+
const addressLower = address.toLowerCase();
|
|
7412
|
+
const sepIndex = addressLower.lastIndexOf("1");
|
|
7413
|
+
if (sepIndex === -1 || sepIndex + 7 > addressLower.length) {
|
|
7414
|
+
throw new ValidationError("Invalid Taproot address: no separator", "address");
|
|
7415
|
+
}
|
|
7416
|
+
const hrp = addressLower.slice(0, sepIndex);
|
|
7417
|
+
const dataStr = addressLower.slice(sepIndex + 1);
|
|
7418
|
+
let network;
|
|
7419
|
+
if (hrp === "bc") {
|
|
7420
|
+
network = "mainnet";
|
|
7421
|
+
} else if (hrp === "tb") {
|
|
7422
|
+
network = "testnet";
|
|
7423
|
+
} else if (hrp === "bcrt") {
|
|
7424
|
+
network = "regtest";
|
|
7425
|
+
} else {
|
|
7426
|
+
throw new ValidationError(`Unknown HRP: ${hrp}`, "address");
|
|
7427
|
+
}
|
|
7428
|
+
const data = [];
|
|
7429
|
+
for (const char of dataStr) {
|
|
7430
|
+
const index = BECH32_CHARSET.indexOf(char);
|
|
7431
|
+
if (index === -1) {
|
|
7432
|
+
throw new ValidationError(`Invalid bech32 character: ${char}`, "address");
|
|
7433
|
+
}
|
|
7434
|
+
data.push(index);
|
|
7435
|
+
}
|
|
7436
|
+
if (!bech32VerifyChecksum(hrp, data)) {
|
|
7437
|
+
throw new ValidationError("Invalid Taproot address checksum", "address");
|
|
7438
|
+
}
|
|
7439
|
+
const version = data[0];
|
|
7440
|
+
if (version !== 1) {
|
|
7441
|
+
throw new ValidationError(`Expected witness version 1 (Taproot), got ${version}`, "address");
|
|
7442
|
+
}
|
|
7443
|
+
const program = convertBits(new Uint8Array(data.slice(1, -6)), 5, 8, false);
|
|
7444
|
+
if (!program || program.length !== 32) {
|
|
7445
|
+
throw new ValidationError("Invalid Taproot program length", "address");
|
|
7446
|
+
}
|
|
7447
|
+
return {
|
|
7448
|
+
tweakedKey: new Uint8Array(program),
|
|
7449
|
+
network
|
|
7450
|
+
};
|
|
7451
|
+
}
|
|
7452
|
+
function createKeySpendOnlyOutput(privateKey, network = "mainnet") {
|
|
7453
|
+
if (!isValidPrivateKey(privateKey)) {
|
|
7454
|
+
throw new ValidationError("privateKey must be a valid 32-byte hex string", "privateKey");
|
|
7455
|
+
}
|
|
7456
|
+
const privKeyBytes = (0, import_utils16.hexToBytes)(privateKey.slice(2));
|
|
7457
|
+
const internalKey = getXOnlyPublicKey(privKeyBytes);
|
|
7458
|
+
const output = createTaprootOutput(internalKey);
|
|
7459
|
+
const tweakedKeyBytes = (0, import_utils16.hexToBytes)(output.tweakedKey.slice(2));
|
|
7460
|
+
const address = taprootAddress(tweakedKeyBytes, network);
|
|
7461
|
+
return {
|
|
7462
|
+
output,
|
|
7463
|
+
address,
|
|
7464
|
+
internalPrivateKey: privateKey
|
|
7465
|
+
};
|
|
7466
|
+
}
|
|
7467
|
+
function isValidTaprootAddress(address) {
|
|
7468
|
+
try {
|
|
7469
|
+
decodeTaprootAddress(address);
|
|
7470
|
+
return true;
|
|
7471
|
+
} catch {
|
|
7472
|
+
return false;
|
|
7473
|
+
}
|
|
7474
|
+
}
|
|
7475
|
+
function schnorrSignHex(message, privateKey, auxRand) {
|
|
7476
|
+
if (!isValidHex(message)) {
|
|
7477
|
+
throw new ValidationError("message must be a hex string", "message");
|
|
7478
|
+
}
|
|
7479
|
+
if (!isValidPrivateKey(privateKey)) {
|
|
7480
|
+
throw new ValidationError("privateKey must be a valid 32-byte hex string", "privateKey");
|
|
7481
|
+
}
|
|
7482
|
+
if (auxRand && !isValidHex(auxRand)) {
|
|
7483
|
+
throw new ValidationError("auxRand must be a hex string", "auxRand");
|
|
7484
|
+
}
|
|
7485
|
+
const messageBytes = (0, import_utils16.hexToBytes)(message.slice(2));
|
|
7486
|
+
const privateKeyBytes = (0, import_utils16.hexToBytes)(privateKey.slice(2));
|
|
7487
|
+
const auxRandBytes = auxRand ? (0, import_utils16.hexToBytes)(auxRand.slice(2)) : void 0;
|
|
7488
|
+
const signature = schnorrSign(messageBytes, privateKeyBytes, auxRandBytes);
|
|
7489
|
+
return `0x${(0, import_utils16.bytesToHex)(signature)}`;
|
|
7490
|
+
}
|
|
7491
|
+
function schnorrVerifyHex(signature, message, publicKey) {
|
|
7492
|
+
if (!isValidHex(signature)) {
|
|
7493
|
+
throw new ValidationError("signature must be a hex string", "signature");
|
|
7494
|
+
}
|
|
7495
|
+
if (!isValidHex(message)) {
|
|
7496
|
+
throw new ValidationError("message must be a hex string", "message");
|
|
7497
|
+
}
|
|
7498
|
+
if (!isValidHex(publicKey)) {
|
|
7499
|
+
throw new ValidationError("publicKey must be a hex string", "publicKey");
|
|
7500
|
+
}
|
|
7501
|
+
const signatureBytes = (0, import_utils16.hexToBytes)(signature.slice(2));
|
|
7502
|
+
const messageBytes = (0, import_utils16.hexToBytes)(message.slice(2));
|
|
7503
|
+
const publicKeyBytes = (0, import_utils16.hexToBytes)(publicKey.slice(2));
|
|
7504
|
+
return schnorrVerify(signatureBytes, messageBytes, publicKeyBytes);
|
|
7505
|
+
}
|
|
7506
|
+
|
|
7507
|
+
// src/bitcoin/silent-payments.ts
|
|
7508
|
+
var import_secp256k15 = require("@noble/curves/secp256k1");
|
|
7509
|
+
var import_sha25612 = require("@noble/hashes/sha256");
|
|
7510
|
+
var import_utils17 = require("@noble/hashes/utils");
|
|
7511
|
+
|
|
7512
|
+
// src/payment/payment.ts
|
|
7513
|
+
var import_types15 = require("@sip-protocol/types");
|
|
7514
|
+
var import_sha25613 = require("@noble/hashes/sha256");
|
|
7515
|
+
var import_utils18 = require("@noble/hashes/utils");
|
|
7516
|
+
var import_chacha2 = require("@noble/ciphers/chacha.js");
|
|
7517
|
+
var import_hkdf2 = require("@noble/hashes/hkdf");
|
|
7518
|
+
|
|
7519
|
+
// src/payment/stablecoins.ts
|
|
7520
|
+
var STABLECOIN_INFO = {
|
|
7521
|
+
USDC: {
|
|
7522
|
+
symbol: "USDC",
|
|
7523
|
+
name: "USD Coin",
|
|
7524
|
+
issuer: "Circle",
|
|
7525
|
+
type: "fiat-backed",
|
|
7526
|
+
description: "Fully-reserved US dollar stablecoin by Circle"
|
|
7527
|
+
},
|
|
7528
|
+
USDT: {
|
|
7529
|
+
symbol: "USDT",
|
|
7530
|
+
name: "Tether USD",
|
|
7531
|
+
issuer: "Tether",
|
|
7532
|
+
type: "fiat-backed",
|
|
7533
|
+
description: "Largest stablecoin by market cap"
|
|
7534
|
+
},
|
|
7535
|
+
DAI: {
|
|
7536
|
+
symbol: "DAI",
|
|
6698
7537
|
name: "Dai Stablecoin",
|
|
6699
7538
|
issuer: "MakerDAO",
|
|
6700
7539
|
type: "crypto-backed",
|
|
@@ -7169,8 +8008,8 @@ async function createShieldedPayment(params, options) {
|
|
|
7169
8008
|
let viewingKeyHash;
|
|
7170
8009
|
if (viewingKey) {
|
|
7171
8010
|
const keyHex = viewingKey.startsWith("0x") ? viewingKey.slice(2) : viewingKey;
|
|
7172
|
-
const keyBytes = (0,
|
|
7173
|
-
viewingKeyHash = `0x${(0,
|
|
8011
|
+
const keyBytes = (0, import_utils18.hexToBytes)(keyHex);
|
|
8012
|
+
viewingKeyHash = `0x${(0, import_utils18.bytesToHex)((0, import_sha25613.sha256)(keyBytes))}`;
|
|
7174
8013
|
}
|
|
7175
8014
|
const privacyConfig = getPrivacyConfig(
|
|
7176
8015
|
privacy,
|
|
@@ -7210,7 +8049,7 @@ async function createShieldedPayment(params, options) {
|
|
|
7210
8049
|
if (privacy !== import_types15.PrivacyLevel.TRANSPARENT && proofProvider?.isReady) {
|
|
7211
8050
|
const hexToUint8 = (hex) => {
|
|
7212
8051
|
const cleanHex = hex.startsWith("0x") ? hex.slice(2) : hex;
|
|
7213
|
-
return (0,
|
|
8052
|
+
return (0, import_utils18.hexToBytes)(cleanHex);
|
|
7214
8053
|
};
|
|
7215
8054
|
const fundingResult = await proofProvider.generateFundingProof({
|
|
7216
8055
|
balance: amount,
|
|
@@ -7237,17 +8076,17 @@ async function createShieldedPayment(params, options) {
|
|
|
7237
8076
|
}
|
|
7238
8077
|
function encryptMemo(memo, viewingKey) {
|
|
7239
8078
|
const keyHex = viewingKey.startsWith("0x") ? viewingKey.slice(2) : viewingKey;
|
|
7240
|
-
const keyBytes = (0,
|
|
7241
|
-
const encKey = (0, import_hkdf2.hkdf)(
|
|
8079
|
+
const keyBytes = (0, import_utils18.hexToBytes)(keyHex);
|
|
8080
|
+
const encKey = (0, import_hkdf2.hkdf)(import_sha25613.sha256, keyBytes, new Uint8Array(0), new Uint8Array(0), 32);
|
|
7242
8081
|
try {
|
|
7243
|
-
const nonce = (0,
|
|
8082
|
+
const nonce = (0, import_utils18.randomBytes)(24);
|
|
7244
8083
|
const cipher = (0, import_chacha2.xchacha20poly1305)(encKey, nonce);
|
|
7245
8084
|
const plaintext = new TextEncoder().encode(memo);
|
|
7246
8085
|
const ciphertext = cipher.encrypt(plaintext);
|
|
7247
8086
|
const result = new Uint8Array(nonce.length + ciphertext.length);
|
|
7248
8087
|
result.set(nonce);
|
|
7249
8088
|
result.set(ciphertext, nonce.length);
|
|
7250
|
-
return `0x${(0,
|
|
8089
|
+
return `0x${(0, import_utils18.bytesToHex)(result)}`;
|
|
7251
8090
|
} finally {
|
|
7252
8091
|
secureWipe(keyBytes);
|
|
7253
8092
|
secureWipe(encKey);
|
|
@@ -7255,11 +8094,11 @@ function encryptMemo(memo, viewingKey) {
|
|
|
7255
8094
|
}
|
|
7256
8095
|
function decryptMemo(encryptedMemo, viewingKey) {
|
|
7257
8096
|
const keyHex = viewingKey.startsWith("0x") ? viewingKey.slice(2) : viewingKey;
|
|
7258
|
-
const keyBytes = (0,
|
|
7259
|
-
const encKey = (0, import_hkdf2.hkdf)(
|
|
8097
|
+
const keyBytes = (0, import_utils18.hexToBytes)(keyHex);
|
|
8098
|
+
const encKey = (0, import_hkdf2.hkdf)(import_sha25613.sha256, keyBytes, new Uint8Array(0), new Uint8Array(0), 32);
|
|
7260
8099
|
try {
|
|
7261
8100
|
const dataHex = encryptedMemo.startsWith("0x") ? encryptedMemo.slice(2) : encryptedMemo;
|
|
7262
|
-
const data = (0,
|
|
8101
|
+
const data = (0, import_utils18.hexToBytes)(dataHex);
|
|
7263
8102
|
const nonce = data.slice(0, 24);
|
|
7264
8103
|
const ciphertext = data.slice(24);
|
|
7265
8104
|
const cipher = (0, import_chacha2.xchacha20poly1305)(encKey, nonce);
|
|
@@ -7307,9 +8146,9 @@ function getPaymentSummary(payment) {
|
|
|
7307
8146
|
|
|
7308
8147
|
// src/treasury/treasury.ts
|
|
7309
8148
|
var import_types16 = require("@sip-protocol/types");
|
|
7310
|
-
var
|
|
7311
|
-
var
|
|
7312
|
-
var
|
|
8149
|
+
var import_secp256k16 = require("@noble/curves/secp256k1");
|
|
8150
|
+
var import_sha25614 = require("@noble/hashes/sha256");
|
|
8151
|
+
var import_utils19 = require("@noble/hashes/utils");
|
|
7313
8152
|
var DEFAULT_PROPOSAL_TTL = 7 * 24 * 60 * 60;
|
|
7314
8153
|
var Treasury = class _Treasury {
|
|
7315
8154
|
config;
|
|
@@ -7800,12 +8639,12 @@ var Treasury = class _Treasury {
|
|
|
7800
8639
|
}
|
|
7801
8640
|
};
|
|
7802
8641
|
function generateTreasuryId() {
|
|
7803
|
-
const bytes = (0,
|
|
7804
|
-
return `treasury_${(0,
|
|
8642
|
+
const bytes = (0, import_utils19.randomBytes)(16);
|
|
8643
|
+
return `treasury_${(0, import_utils19.bytesToHex)(bytes)}`;
|
|
7805
8644
|
}
|
|
7806
8645
|
function generateProposalId() {
|
|
7807
|
-
const bytes = (0,
|
|
7808
|
-
return `prop_${(0,
|
|
8646
|
+
const bytes = (0, import_utils19.randomBytes)(16);
|
|
8647
|
+
return `prop_${(0, import_utils19.bytesToHex)(bytes)}`;
|
|
7809
8648
|
}
|
|
7810
8649
|
function computeProposalHash(proposal) {
|
|
7811
8650
|
const data = JSON.stringify({
|
|
@@ -7817,13 +8656,13 @@ function computeProposalHash(proposal) {
|
|
|
7817
8656
|
createdAt: proposal.createdAt,
|
|
7818
8657
|
expiresAt: proposal.expiresAt
|
|
7819
8658
|
}, (_, value) => typeof value === "bigint" ? value.toString() : value);
|
|
7820
|
-
return (0,
|
|
8659
|
+
return (0, import_sha25614.sha256)(new TextEncoder().encode(data));
|
|
7821
8660
|
}
|
|
7822
8661
|
function signMessage(messageHash, privateKey) {
|
|
7823
8662
|
const keyHex = privateKey.startsWith("0x") ? privateKey.slice(2) : privateKey;
|
|
7824
|
-
const keyBytes = (0,
|
|
8663
|
+
const keyBytes = (0, import_utils19.hexToBytes)(keyHex);
|
|
7825
8664
|
try {
|
|
7826
|
-
const signature =
|
|
8665
|
+
const signature = import_secp256k16.secp256k1.sign(messageHash, keyBytes);
|
|
7827
8666
|
return `0x${signature.toCompactHex()}`;
|
|
7828
8667
|
} finally {
|
|
7829
8668
|
secureWipe(keyBytes);
|
|
@@ -7833,9 +8672,9 @@ function verifySignature(messageHash, signature, publicKey) {
|
|
|
7833
8672
|
const sigHex = signature.startsWith("0x") ? signature.slice(2) : signature;
|
|
7834
8673
|
const pubKeyHex = publicKey.startsWith("0x") ? publicKey.slice(2) : publicKey;
|
|
7835
8674
|
try {
|
|
7836
|
-
const sigBytes = (0,
|
|
7837
|
-
const pubKeyBytes = (0,
|
|
7838
|
-
return
|
|
8675
|
+
const sigBytes = (0, import_utils19.hexToBytes)(sigHex);
|
|
8676
|
+
const pubKeyBytes = (0, import_utils19.hexToBytes)(pubKeyHex);
|
|
8677
|
+
return import_secp256k16.secp256k1.verify(sigBytes, messageHash, pubKeyBytes);
|
|
7839
8678
|
} catch {
|
|
7840
8679
|
return false;
|
|
7841
8680
|
}
|
|
@@ -7993,7 +8832,7 @@ function validateBatchProposalParams(params, config) {
|
|
|
7993
8832
|
|
|
7994
8833
|
// src/compliance/compliance-manager.ts
|
|
7995
8834
|
var import_types17 = require("@sip-protocol/types");
|
|
7996
|
-
var
|
|
8835
|
+
var import_utils20 = require("@noble/hashes/utils");
|
|
7997
8836
|
var DEFAULTS2 = {
|
|
7998
8837
|
riskThreshold: 70,
|
|
7999
8838
|
highValueThreshold: 10000000000n,
|
|
@@ -8414,6 +9253,79 @@ var ComplianceManager = class _ComplianceManager {
|
|
|
8414
9253
|
getAllReports() {
|
|
8415
9254
|
return Array.from(this.reports.values());
|
|
8416
9255
|
}
|
|
9256
|
+
// ─── Dashboard Data API ──────────────────────────────────────────────────────
|
|
9257
|
+
/**
|
|
9258
|
+
* Get list of auditors for dashboard UI
|
|
9259
|
+
*
|
|
9260
|
+
* Returns a simplified view of auditors with essential info.
|
|
9261
|
+
* Alias for getAllAuditors() but returns AuditorRegistration directly.
|
|
9262
|
+
*
|
|
9263
|
+
* @returns Array of auditor registrations
|
|
9264
|
+
*/
|
|
9265
|
+
getAuditorList() {
|
|
9266
|
+
return this.getAllAuditors();
|
|
9267
|
+
}
|
|
9268
|
+
/**
|
|
9269
|
+
* Get pending disclosure requests for dashboard
|
|
9270
|
+
*
|
|
9271
|
+
* Returns disclosure requests waiting for approval/denial.
|
|
9272
|
+
* This is for disclosure REQUESTS, not disclosed transactions.
|
|
9273
|
+
*
|
|
9274
|
+
* @returns Array of pending disclosure requests
|
|
9275
|
+
*/
|
|
9276
|
+
getPendingDisclosures() {
|
|
9277
|
+
return this.getPendingRequests();
|
|
9278
|
+
}
|
|
9279
|
+
/**
|
|
9280
|
+
* Get disclosure history for a specific auditor
|
|
9281
|
+
*
|
|
9282
|
+
* Returns all disclosed transactions that were shared with this auditor,
|
|
9283
|
+
* sorted by disclosure date (most recent first).
|
|
9284
|
+
*
|
|
9285
|
+
* @param auditorId - Auditor ID to get history for
|
|
9286
|
+
* @returns Array of disclosed transactions for this auditor
|
|
9287
|
+
*/
|
|
9288
|
+
getDisclosureHistory(auditorId) {
|
|
9289
|
+
return this.getDisclosedTransactions(auditorId).sort((a, b) => b.disclosedAt - a.disclosedAt);
|
|
9290
|
+
}
|
|
9291
|
+
/**
|
|
9292
|
+
* Get compliance metrics for dashboard
|
|
9293
|
+
*
|
|
9294
|
+
* Calculates key compliance metrics including:
|
|
9295
|
+
* - Total auditors (active + inactive)
|
|
9296
|
+
* - Total disclosures made
|
|
9297
|
+
* - Pending disclosure requests
|
|
9298
|
+
* - Approval rate (approved / total resolved requests)
|
|
9299
|
+
* - Average processing time for disclosure requests
|
|
9300
|
+
*
|
|
9301
|
+
* @returns Compliance metrics object
|
|
9302
|
+
*/
|
|
9303
|
+
getComplianceMetrics() {
|
|
9304
|
+
const allAuditors = this.getAllAuditors();
|
|
9305
|
+
const allDisclosures = this.getDisclosedTransactions();
|
|
9306
|
+
const pendingRequests = this.getPendingRequests();
|
|
9307
|
+
const allRequests = Array.from(this.disclosureRequests.values());
|
|
9308
|
+
const resolvedRequests = allRequests.filter((r) => r.status !== "pending");
|
|
9309
|
+
const approvedRequests = resolvedRequests.filter((r) => r.status === "approved");
|
|
9310
|
+
const approvalRate = resolvedRequests.length > 0 ? approvedRequests.length / resolvedRequests.length : 0;
|
|
9311
|
+
let averageProcessingTime;
|
|
9312
|
+
if (resolvedRequests.length > 0) {
|
|
9313
|
+
const totalProcessingTime = resolvedRequests.reduce((sum, req) => {
|
|
9314
|
+
if (req.resolvedAt) {
|
|
9315
|
+
return sum + (req.resolvedAt - req.requestedAt);
|
|
9316
|
+
}
|
|
9317
|
+
return sum;
|
|
9318
|
+
}, 0);
|
|
9319
|
+
averageProcessingTime = totalProcessingTime / resolvedRequests.length;
|
|
9320
|
+
}
|
|
9321
|
+
return {
|
|
9322
|
+
totalAuditors: allAuditors.length,
|
|
9323
|
+
totalDisclosures: allDisclosures.length,
|
|
9324
|
+
pendingDisclosures: pendingRequests.length,
|
|
9325
|
+
approvalRate,
|
|
9326
|
+
averageProcessingTime
|
|
9327
|
+
};
|
|
9328
|
+
}
|
|
8417
9329
|
// ─── Audit Log ───────────────────────────────────────────────────────────────
|
|
8418
9330
|
/**
|
|
8419
9331
|
* Get audit log entries
|
|
@@ -8612,147 +9524,1767 @@ var ComplianceManager = class _ComplianceManager {
|
|
|
8612
9524
|
highRisk,
|
|
8613
9525
|
flaggedTransactions: flagged
|
|
8614
9526
|
}
|
|
8615
|
-
};
|
|
8616
|
-
if (includeTransactions) {
|
|
8617
|
-
data.transactions = transactions;
|
|
9527
|
+
};
|
|
9528
|
+
if (includeTransactions) {
|
|
9529
|
+
data.transactions = transactions;
|
|
9530
|
+
}
|
|
9531
|
+
return data;
|
|
9532
|
+
}
|
|
9533
|
+
generateCSV(transactions) {
|
|
9534
|
+
const headers = [
|
|
9535
|
+
"Transaction ID",
|
|
9536
|
+
"Disclosure ID",
|
|
9537
|
+
"Type",
|
|
9538
|
+
"Direction",
|
|
9539
|
+
"Token",
|
|
9540
|
+
"Amount",
|
|
9541
|
+
"Sender",
|
|
9542
|
+
"Recipient",
|
|
9543
|
+
"Chain",
|
|
9544
|
+
"Privacy Level",
|
|
9545
|
+
"Timestamp",
|
|
9546
|
+
"TX Hash",
|
|
9547
|
+
"Block",
|
|
9548
|
+
"Risk Score",
|
|
9549
|
+
"Purpose",
|
|
9550
|
+
"Memo"
|
|
9551
|
+
];
|
|
9552
|
+
const rows = transactions.map((tx) => [
|
|
9553
|
+
tx.transactionId,
|
|
9554
|
+
tx.disclosureId,
|
|
9555
|
+
tx.type,
|
|
9556
|
+
tx.direction,
|
|
9557
|
+
tx.token.symbol,
|
|
9558
|
+
tx.amount.toString(),
|
|
9559
|
+
tx.sender,
|
|
9560
|
+
tx.recipient,
|
|
9561
|
+
tx.chain,
|
|
9562
|
+
tx.privacyLevel,
|
|
9563
|
+
new Date(tx.timestamp * 1e3).toISOString(),
|
|
9564
|
+
tx.txHash,
|
|
9565
|
+
tx.blockNumber.toString(),
|
|
9566
|
+
tx.riskScore?.toString() ?? "",
|
|
9567
|
+
tx.purpose ?? "",
|
|
9568
|
+
tx.memo ?? ""
|
|
9569
|
+
]);
|
|
9570
|
+
const escapeForCSV = (val) => {
|
|
9571
|
+
let escaped = val;
|
|
9572
|
+
if (/^[=+\-@|\t]/.test(escaped)) {
|
|
9573
|
+
escaped = `'${escaped}`;
|
|
9574
|
+
}
|
|
9575
|
+
return `"${escaped.replace(/"/g, '""')}"`;
|
|
9576
|
+
};
|
|
9577
|
+
const csvRows = [headers, ...rows].map((row) => row.map(escapeForCSV).join(","));
|
|
9578
|
+
return csvRows.join("\n");
|
|
9579
|
+
}
|
|
9580
|
+
};
|
|
9581
|
+
function generateId(prefix) {
|
|
9582
|
+
return `${prefix}_${(0, import_utils20.bytesToHex)((0, import_utils20.randomBytes)(12))}`;
|
|
9583
|
+
}
|
|
9584
|
+
function validateRegisterAuditorParams(params) {
|
|
9585
|
+
if (!params.organization?.trim()) {
|
|
9586
|
+
throw new ValidationError(
|
|
9587
|
+
"organization is required",
|
|
9588
|
+
"organization",
|
|
9589
|
+
void 0,
|
|
9590
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9591
|
+
);
|
|
9592
|
+
}
|
|
9593
|
+
if (!params.contactName?.trim()) {
|
|
9594
|
+
throw new ValidationError(
|
|
9595
|
+
"contact name is required",
|
|
9596
|
+
"contactName",
|
|
9597
|
+
void 0,
|
|
9598
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9599
|
+
);
|
|
9600
|
+
}
|
|
9601
|
+
if (!params.contactEmail?.trim()) {
|
|
9602
|
+
throw new ValidationError(
|
|
9603
|
+
"contact email is required",
|
|
9604
|
+
"contactEmail",
|
|
9605
|
+
void 0,
|
|
9606
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9607
|
+
);
|
|
9608
|
+
}
|
|
9609
|
+
if (!params.publicKey?.trim()) {
|
|
9610
|
+
throw new ValidationError(
|
|
9611
|
+
"public key is required",
|
|
9612
|
+
"publicKey",
|
|
9613
|
+
void 0,
|
|
9614
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9615
|
+
);
|
|
9616
|
+
}
|
|
9617
|
+
if (!params.scope) {
|
|
9618
|
+
throw new ValidationError(
|
|
9619
|
+
"audit scope is required",
|
|
9620
|
+
"scope",
|
|
9621
|
+
void 0,
|
|
9622
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9623
|
+
);
|
|
9624
|
+
}
|
|
9625
|
+
}
|
|
9626
|
+
function validateReportParams(params) {
|
|
9627
|
+
if (!params.title?.trim()) {
|
|
9628
|
+
throw new ValidationError(
|
|
9629
|
+
"report title is required",
|
|
9630
|
+
"title",
|
|
9631
|
+
void 0,
|
|
9632
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9633
|
+
);
|
|
9634
|
+
}
|
|
9635
|
+
if (!params.type) {
|
|
9636
|
+
throw new ValidationError(
|
|
9637
|
+
"report type is required",
|
|
9638
|
+
"type",
|
|
9639
|
+
void 0,
|
|
9640
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9641
|
+
);
|
|
9642
|
+
}
|
|
9643
|
+
if (!params.format) {
|
|
9644
|
+
throw new ValidationError(
|
|
9645
|
+
"report format is required",
|
|
9646
|
+
"format",
|
|
9647
|
+
void 0,
|
|
9648
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9649
|
+
);
|
|
9650
|
+
}
|
|
9651
|
+
if (params.startDate === void 0 || params.startDate === null || params.endDate === void 0 || params.endDate === null) {
|
|
9652
|
+
throw new ValidationError(
|
|
9653
|
+
"date range is required",
|
|
9654
|
+
"dateRange",
|
|
9655
|
+
void 0,
|
|
9656
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9657
|
+
);
|
|
9658
|
+
}
|
|
9659
|
+
if (params.startDate >= params.endDate) {
|
|
9660
|
+
throw new ValidationError(
|
|
9661
|
+
"start date must be before end date",
|
|
9662
|
+
"dateRange",
|
|
9663
|
+
void 0,
|
|
9664
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
9665
|
+
);
|
|
9666
|
+
}
|
|
9667
|
+
}
|
|
9668
|
+
|
|
9669
|
+
// src/compliance/reports.ts
|
|
9670
|
+
var import_sha25615 = require("@noble/hashes/sha256");
|
|
9671
|
+
var import_utils21 = require("@noble/hashes/utils");
|
|
9672
|
+
|
|
9673
|
+
// src/compliance/pdf.ts
|
|
9674
|
+
function generatePdfReport(report, options = {}) {
|
|
9675
|
+
const {
|
|
9676
|
+
title = "SIP Protocol Audit Report",
|
|
9677
|
+
organization = "",
|
|
9678
|
+
includeTransactions = true,
|
|
9679
|
+
maxTransactions = 100
|
|
9680
|
+
} = options;
|
|
9681
|
+
const content = buildPdfContent(report, {
|
|
9682
|
+
title,
|
|
9683
|
+
organization,
|
|
9684
|
+
includeTransactions,
|
|
9685
|
+
maxTransactions
|
|
9686
|
+
});
|
|
9687
|
+
return generatePdfBinary(content, title);
|
|
9688
|
+
}
|
|
9689
|
+
function buildPdfContent(report, options) {
|
|
9690
|
+
const lines = [];
|
|
9691
|
+
lines.push(options.title);
|
|
9692
|
+
if (options.organization && options.organization.trim() !== "") {
|
|
9693
|
+
lines.push(`Organization: ${options.organization}`);
|
|
9694
|
+
}
|
|
9695
|
+
lines.push(`Report ID: ${report.reportId}`);
|
|
9696
|
+
lines.push(
|
|
9697
|
+
`Generated: ${report.generatedAt.toISOString().replace("T", " ").slice(0, 19)} UTC`
|
|
9698
|
+
);
|
|
9699
|
+
lines.push("");
|
|
9700
|
+
lines.push("Report Period");
|
|
9701
|
+
lines.push(` Start: ${formatDate(report.period.start)}`);
|
|
9702
|
+
lines.push(` End: ${formatDate(report.period.end)}`);
|
|
9703
|
+
lines.push("");
|
|
9704
|
+
lines.push("Summary Statistics");
|
|
9705
|
+
lines.push(` Total Transactions: ${report.summary.transactionCount}`);
|
|
9706
|
+
lines.push(
|
|
9707
|
+
` Total Volume: ${formatBigInt(report.summary.totalVolume)}`
|
|
9708
|
+
);
|
|
9709
|
+
lines.push(
|
|
9710
|
+
` Unique Counterparties: ${report.summary.uniqueCounterparties}`
|
|
9711
|
+
);
|
|
9712
|
+
lines.push("");
|
|
9713
|
+
if (options.includeTransactions && report.transactions.length > 0) {
|
|
9714
|
+
lines.push("Transaction Details");
|
|
9715
|
+
lines.push("");
|
|
9716
|
+
const txToShow = Math.min(
|
|
9717
|
+
report.transactions.length,
|
|
9718
|
+
options.maxTransactions
|
|
9719
|
+
);
|
|
9720
|
+
for (let i = 0; i < txToShow; i++) {
|
|
9721
|
+
const tx = report.transactions[i];
|
|
9722
|
+
lines.push(`Transaction ${i + 1}/${report.transactions.length}`);
|
|
9723
|
+
lines.push(` ID: ${tx.id}`);
|
|
9724
|
+
lines.push(` Sender: ${truncateAddress(tx.sender)}`);
|
|
9725
|
+
lines.push(` Recipient: ${truncateAddress(tx.recipient)}`);
|
|
9726
|
+
lines.push(` Amount: ${formatAmount(tx.amount)}`);
|
|
9727
|
+
lines.push(
|
|
9728
|
+
` Timestamp: ${formatTimestamp(tx.timestamp)}`
|
|
9729
|
+
);
|
|
9730
|
+
if (tx.txHash) {
|
|
9731
|
+
lines.push(` Tx Hash: ${truncateHash(tx.txHash)}`);
|
|
9732
|
+
}
|
|
9733
|
+
if (tx.metadata && Object.keys(tx.metadata).length > 0) {
|
|
9734
|
+
lines.push(` Metadata: ${JSON.stringify(tx.metadata)}`);
|
|
9735
|
+
}
|
|
9736
|
+
lines.push("");
|
|
9737
|
+
}
|
|
9738
|
+
if (report.transactions.length > options.maxTransactions) {
|
|
9739
|
+
lines.push(
|
|
9740
|
+
`... and ${report.transactions.length - options.maxTransactions} more transactions`
|
|
9741
|
+
);
|
|
9742
|
+
lines.push("");
|
|
9743
|
+
}
|
|
9744
|
+
}
|
|
9745
|
+
lines.push("---");
|
|
9746
|
+
lines.push(
|
|
9747
|
+
"This report was generated by SIP Protocol compliance tools."
|
|
9748
|
+
);
|
|
9749
|
+
lines.push("For verification, please contact your compliance officer.");
|
|
9750
|
+
return lines.join("\n");
|
|
9751
|
+
}
|
|
9752
|
+
function generatePdfBinary(content, title) {
|
|
9753
|
+
const objects = [];
|
|
9754
|
+
objects.push(
|
|
9755
|
+
"1 0 obj\n<< /Type /Catalog /Pages 2 0 R >>\nendobj"
|
|
9756
|
+
);
|
|
9757
|
+
objects.push(
|
|
9758
|
+
"2 0 obj\n<< /Type /Pages /Kids [3 0 R] /Count 1 >>\nendobj"
|
|
9759
|
+
);
|
|
9760
|
+
objects.push(
|
|
9761
|
+
"3 0 obj\n<< /Type /Page /Parent 2 0 R /Resources 4 0 R /MediaBox [0 0 612 792] /Contents 5 0 R >>\nendobj"
|
|
9762
|
+
);
|
|
9763
|
+
objects.push(
|
|
9764
|
+
"4 0 obj\n<< /Font << /F1 << /Type /Font /Subtype /Type1 /BaseFont /Courier >> >> >>\nendobj"
|
|
9765
|
+
);
|
|
9766
|
+
const contentStream = buildContentStream(content);
|
|
9767
|
+
objects.push(
|
|
9768
|
+
`5 0 obj
|
|
9769
|
+
<< /Length ${contentStream.length} >>
|
|
9770
|
+
stream
|
|
9771
|
+
${contentStream}
|
|
9772
|
+
endstream
|
|
9773
|
+
endobj`
|
|
9774
|
+
);
|
|
9775
|
+
const now = /* @__PURE__ */ new Date();
|
|
9776
|
+
const pdfDate = formatPdfDate(now);
|
|
9777
|
+
objects.push(
|
|
9778
|
+
`6 0 obj
|
|
9779
|
+
<< /Title (${title}) /Author (SIP Protocol) /Creator (SIP SDK) /CreationDate (${pdfDate}) >>
|
|
9780
|
+
endobj`
|
|
9781
|
+
);
|
|
9782
|
+
const pdfParts = [];
|
|
9783
|
+
pdfParts.push("%PDF-1.4\n%\xE2\xE3\xCF\xD3\n");
|
|
9784
|
+
const xrefOffsets = [0];
|
|
9785
|
+
let currentOffset = pdfParts.join("").length;
|
|
9786
|
+
for (const obj of objects) {
|
|
9787
|
+
xrefOffsets.push(currentOffset);
|
|
9788
|
+
pdfParts.push(obj + "\n");
|
|
9789
|
+
currentOffset = pdfParts.join("").length;
|
|
9790
|
+
}
|
|
9791
|
+
const xrefStart = currentOffset;
|
|
9792
|
+
pdfParts.push("xref\n");
|
|
9793
|
+
pdfParts.push(`0 ${xrefOffsets.length}
|
|
9794
|
+
`);
|
|
9795
|
+
for (let i = 0; i < xrefOffsets.length; i++) {
|
|
9796
|
+
if (i === 0) {
|
|
9797
|
+
pdfParts.push("0000000000 65535 f \n");
|
|
9798
|
+
} else {
|
|
9799
|
+
const offset = String(xrefOffsets[i]).padStart(10, "0");
|
|
9800
|
+
pdfParts.push(`${offset} 00000 n
|
|
9801
|
+
`);
|
|
9802
|
+
}
|
|
9803
|
+
}
|
|
9804
|
+
pdfParts.push("trailer\n");
|
|
9805
|
+
pdfParts.push(
|
|
9806
|
+
`<< /Size ${xrefOffsets.length} /Root 1 0 R /Info 6 0 R >>
|
|
9807
|
+
`
|
|
9808
|
+
);
|
|
9809
|
+
pdfParts.push("startxref\n");
|
|
9810
|
+
pdfParts.push(`${xrefStart}
|
|
9811
|
+
`);
|
|
9812
|
+
pdfParts.push("%%EOF");
|
|
9813
|
+
const pdfString = pdfParts.join("");
|
|
9814
|
+
const encoder = new TextEncoder();
|
|
9815
|
+
return encoder.encode(pdfString);
|
|
9816
|
+
}
|
|
9817
|
+
function buildContentStream(text) {
|
|
9818
|
+
const lines = text.split("\n");
|
|
9819
|
+
const commands = [];
|
|
9820
|
+
commands.push("BT");
|
|
9821
|
+
commands.push("/F1 10 Tf");
|
|
9822
|
+
commands.push("12 TL");
|
|
9823
|
+
let y = 742;
|
|
9824
|
+
for (const line of lines) {
|
|
9825
|
+
commands.push(`50 ${y} Td`);
|
|
9826
|
+
const escaped = escapePdfString(line);
|
|
9827
|
+
commands.push(`(${escaped}) Tj`);
|
|
9828
|
+
y -= 12;
|
|
9829
|
+
if (y < 50) {
|
|
9830
|
+
break;
|
|
9831
|
+
}
|
|
9832
|
+
}
|
|
9833
|
+
commands.push("ET");
|
|
9834
|
+
return commands.join("\n");
|
|
9835
|
+
}
|
|
9836
|
+
function escapePdfString(str) {
|
|
9837
|
+
return str.replace(/\\/g, "\\\\").replace(/\(/g, "\\(").replace(/\)/g, "\\)").replace(/\r/g, "\\r").replace(/\n/g, "\\n");
|
|
9838
|
+
}
|
|
9839
|
+
function formatPdfDate(date) {
|
|
9840
|
+
const year = date.getUTCFullYear();
|
|
9841
|
+
const month = String(date.getUTCMonth() + 1).padStart(2, "0");
|
|
9842
|
+
const day = String(date.getUTCDate()).padStart(2, "0");
|
|
9843
|
+
const hour = String(date.getUTCHours()).padStart(2, "0");
|
|
9844
|
+
const minute = String(date.getUTCMinutes()).padStart(2, "0");
|
|
9845
|
+
const second = String(date.getUTCSeconds()).padStart(2, "0");
|
|
9846
|
+
return `D:${year}${month}${day}${hour}${minute}${second}Z`;
|
|
9847
|
+
}
|
|
9848
|
+
function formatDate(date) {
|
|
9849
|
+
return date.toISOString().split("T")[0];
|
|
9850
|
+
}
|
|
9851
|
+
function formatBigInt(value) {
|
|
9852
|
+
return value.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ",");
|
|
9853
|
+
}
|
|
9854
|
+
function formatAmount(amount) {
|
|
9855
|
+
try {
|
|
9856
|
+
const num = BigInt(amount);
|
|
9857
|
+
return formatBigInt(num);
|
|
9858
|
+
} catch {
|
|
9859
|
+
return amount;
|
|
9860
|
+
}
|
|
9861
|
+
}
|
|
9862
|
+
function formatTimestamp(timestamp) {
|
|
9863
|
+
const date = new Date(timestamp * 1e3);
|
|
9864
|
+
return date.toISOString().replace("T", " ").slice(0, 19) + " UTC";
|
|
9865
|
+
}
|
|
9866
|
+
function truncateAddress(address) {
|
|
9867
|
+
if (address.length <= 12) {
|
|
9868
|
+
return address;
|
|
9869
|
+
}
|
|
9870
|
+
return `${address.slice(0, 6)}...${address.slice(-4)}`;
|
|
9871
|
+
}
|
|
9872
|
+
function truncateHash(hash2) {
|
|
9873
|
+
if (hash2.length <= 16) {
|
|
9874
|
+
return hash2;
|
|
9875
|
+
}
|
|
9876
|
+
return `${hash2.slice(0, 8)}...${hash2.slice(-8)}`;
|
|
9877
|
+
}
|
|
9878
|
+
|
|
9879
|
+
// src/compliance/reports.ts
|
|
9880
|
+
var ComplianceReporter = class {
|
|
9881
|
+
/**
|
|
9882
|
+
* Generate an audit report from encrypted transactions
|
|
9883
|
+
*
|
|
9884
|
+
* Decrypts transactions using the provided viewing key, filters by date range,
|
|
9885
|
+
* and generates a comprehensive report with summary statistics.
|
|
9886
|
+
*
|
|
9887
|
+
* @param params - Report generation parameters
|
|
9888
|
+
* @returns Audit report with decrypted transactions and statistics
|
|
9889
|
+
* @throws {ValidationError} If parameters are invalid
|
|
9890
|
+
* @throws {CryptoError} If decryption fails
|
|
9891
|
+
*/
|
|
9892
|
+
async generateAuditReport(params) {
|
|
9893
|
+
this.validateParams(params);
|
|
9894
|
+
const viewingKey = this.normalizeViewingKey(params.viewingKey);
|
|
9895
|
+
const decryptedTransactions = this.decryptTransactions(
|
|
9896
|
+
params.transactions,
|
|
9897
|
+
viewingKey,
|
|
9898
|
+
params.startDate,
|
|
9899
|
+
params.endDate
|
|
9900
|
+
);
|
|
9901
|
+
const summary = this.calculateSummary(decryptedTransactions);
|
|
9902
|
+
const period = this.determinePeriod(
|
|
9903
|
+
decryptedTransactions,
|
|
9904
|
+
params.startDate,
|
|
9905
|
+
params.endDate
|
|
9906
|
+
);
|
|
9907
|
+
const reportId = `audit_${generateRandomBytes(16).slice(2)}`;
|
|
9908
|
+
return {
|
|
9909
|
+
reportId,
|
|
9910
|
+
generatedAt: /* @__PURE__ */ new Date(),
|
|
9911
|
+
period,
|
|
9912
|
+
transactions: decryptedTransactions,
|
|
9913
|
+
summary
|
|
9914
|
+
};
|
|
9915
|
+
}
|
|
9916
|
+
/**
|
|
9917
|
+
* Validate report generation parameters
|
|
9918
|
+
*/
|
|
9919
|
+
validateParams(params) {
|
|
9920
|
+
if (!params.viewingKey) {
|
|
9921
|
+
throw new ValidationError(
|
|
9922
|
+
"viewingKey is required",
|
|
9923
|
+
"viewingKey",
|
|
9924
|
+
void 0,
|
|
9925
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9926
|
+
);
|
|
9927
|
+
}
|
|
9928
|
+
if (!params.transactions) {
|
|
9929
|
+
throw new ValidationError(
|
|
9930
|
+
"transactions array is required",
|
|
9931
|
+
"transactions",
|
|
9932
|
+
void 0,
|
|
9933
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
9934
|
+
);
|
|
9935
|
+
}
|
|
9936
|
+
if (!Array.isArray(params.transactions)) {
|
|
9937
|
+
throw new ValidationError(
|
|
9938
|
+
"transactions must be an array",
|
|
9939
|
+
"transactions",
|
|
9940
|
+
{ received: typeof params.transactions },
|
|
9941
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
9942
|
+
);
|
|
9943
|
+
}
|
|
9944
|
+
if (params.format !== "json" && params.format !== "pdf") {
|
|
9945
|
+
throw new ValidationError(
|
|
9946
|
+
"only JSON and PDF formats are supported",
|
|
9947
|
+
"format",
|
|
9948
|
+
{ received: params.format },
|
|
9949
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
9950
|
+
);
|
|
9951
|
+
}
|
|
9952
|
+
if (params.startDate && params.endDate) {
|
|
9953
|
+
if (params.startDate > params.endDate) {
|
|
9954
|
+
throw new ValidationError(
|
|
9955
|
+
"startDate must be before endDate",
|
|
9956
|
+
"startDate",
|
|
9957
|
+
{
|
|
9958
|
+
startDate: params.startDate.toISOString(),
|
|
9959
|
+
endDate: params.endDate.toISOString()
|
|
9960
|
+
},
|
|
9961
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
9962
|
+
);
|
|
9963
|
+
}
|
|
9964
|
+
}
|
|
9965
|
+
}
|
|
9966
|
+
/**
|
|
9967
|
+
* Normalize viewing key to ViewingKey object
|
|
9968
|
+
*/
|
|
9969
|
+
normalizeViewingKey(viewingKey) {
|
|
9970
|
+
if (typeof viewingKey === "string") {
|
|
9971
|
+
const keyHex = viewingKey.startsWith("0x") ? viewingKey.slice(2) : viewingKey;
|
|
9972
|
+
const keyBytes = (0, import_utils21.hexToBytes)(keyHex);
|
|
9973
|
+
const hashBytes = (0, import_sha25615.sha256)(keyBytes);
|
|
9974
|
+
return {
|
|
9975
|
+
key: `0x${keyHex}`,
|
|
9976
|
+
path: "m/0",
|
|
9977
|
+
hash: `0x${(0, import_utils21.bytesToHex)(hashBytes)}`
|
|
9978
|
+
};
|
|
9979
|
+
}
|
|
9980
|
+
return viewingKey;
|
|
9981
|
+
}
|
|
9982
|
+
/**
|
|
9983
|
+
* Decrypt transactions and filter by date range
|
|
9984
|
+
*/
|
|
9985
|
+
decryptTransactions(encrypted, viewingKey, startDate, endDate) {
|
|
9986
|
+
const decrypted = [];
|
|
9987
|
+
const errors = [];
|
|
9988
|
+
for (let i = 0; i < encrypted.length; i++) {
|
|
9989
|
+
try {
|
|
9990
|
+
const txData = decryptWithViewing(encrypted[i], viewingKey);
|
|
9991
|
+
if (startDate || endDate) {
|
|
9992
|
+
const txDate = new Date(txData.timestamp * 1e3);
|
|
9993
|
+
if (startDate && txDate < startDate) {
|
|
9994
|
+
continue;
|
|
9995
|
+
}
|
|
9996
|
+
if (endDate && txDate > endDate) {
|
|
9997
|
+
continue;
|
|
9998
|
+
}
|
|
9999
|
+
}
|
|
10000
|
+
decrypted.push({
|
|
10001
|
+
id: `tx_${i}`,
|
|
10002
|
+
sender: txData.sender,
|
|
10003
|
+
recipient: txData.recipient,
|
|
10004
|
+
amount: txData.amount,
|
|
10005
|
+
timestamp: txData.timestamp
|
|
10006
|
+
});
|
|
10007
|
+
} catch (error) {
|
|
10008
|
+
errors.push({ index: i, error });
|
|
10009
|
+
}
|
|
10010
|
+
}
|
|
10011
|
+
if (decrypted.length === 0 && encrypted.length > 0) {
|
|
10012
|
+
throw new CryptoError(
|
|
10013
|
+
`Failed to decrypt any transactions. First error: ${errors[0]?.error.message}`,
|
|
10014
|
+
"SIP_3002" /* DECRYPTION_FAILED */,
|
|
10015
|
+
{
|
|
10016
|
+
context: {
|
|
10017
|
+
totalTransactions: encrypted.length,
|
|
10018
|
+
failedCount: errors.length
|
|
10019
|
+
}
|
|
10020
|
+
}
|
|
10021
|
+
);
|
|
10022
|
+
}
|
|
10023
|
+
return decrypted;
|
|
10024
|
+
}
|
|
10025
|
+
/**
|
|
10026
|
+
* Calculate summary statistics
|
|
10027
|
+
*/
|
|
10028
|
+
calculateSummary(transactions) {
|
|
10029
|
+
let totalVolume = 0n;
|
|
10030
|
+
const counterparties = /* @__PURE__ */ new Set();
|
|
10031
|
+
for (const tx of transactions) {
|
|
10032
|
+
try {
|
|
10033
|
+
const amount = BigInt(tx.amount);
|
|
10034
|
+
totalVolume += amount;
|
|
10035
|
+
} catch (error) {
|
|
10036
|
+
console.warn(`Skipping invalid amount in transaction ${tx.id}: ${tx.amount}`);
|
|
10037
|
+
}
|
|
10038
|
+
counterparties.add(tx.sender);
|
|
10039
|
+
counterparties.add(tx.recipient);
|
|
10040
|
+
}
|
|
10041
|
+
return {
|
|
10042
|
+
totalVolume,
|
|
10043
|
+
transactionCount: transactions.length,
|
|
10044
|
+
uniqueCounterparties: counterparties.size
|
|
10045
|
+
};
|
|
10046
|
+
}
|
|
10047
|
+
/**
|
|
10048
|
+
* Determine report period from transactions and params
|
|
10049
|
+
*/
|
|
10050
|
+
determinePeriod(transactions, startDate, endDate) {
|
|
10051
|
+
if (startDate && endDate) {
|
|
10052
|
+
return { start: startDate, end: endDate };
|
|
10053
|
+
}
|
|
10054
|
+
if (transactions.length === 0) {
|
|
10055
|
+
const now = /* @__PURE__ */ new Date();
|
|
10056
|
+
return { start: now, end: now };
|
|
10057
|
+
}
|
|
10058
|
+
let minTimestamp = transactions[0].timestamp;
|
|
10059
|
+
let maxTimestamp = transactions[0].timestamp;
|
|
10060
|
+
for (const tx of transactions) {
|
|
10061
|
+
if (tx.timestamp < minTimestamp) {
|
|
10062
|
+
minTimestamp = tx.timestamp;
|
|
10063
|
+
}
|
|
10064
|
+
if (tx.timestamp > maxTimestamp) {
|
|
10065
|
+
maxTimestamp = tx.timestamp;
|
|
10066
|
+
}
|
|
10067
|
+
}
|
|
10068
|
+
return {
|
|
10069
|
+
start: startDate || new Date(minTimestamp * 1e3),
|
|
10070
|
+
end: endDate || new Date(maxTimestamp * 1e3)
|
|
10071
|
+
};
|
|
10072
|
+
}
|
|
10073
|
+
/**
|
|
10074
|
+
* Export audit report to PDF format
|
|
10075
|
+
*
|
|
10076
|
+
* Generates a professionally formatted PDF document from an audit report.
|
|
10077
|
+
* Works in both Node.js and browser environments.
|
|
10078
|
+
*
|
|
10079
|
+
* @param report - The audit report to export
|
|
10080
|
+
* @param options - PDF export options
|
|
10081
|
+
* @returns PDF document as Uint8Array
|
|
10082
|
+
*
|
|
10083
|
+
* @example
|
|
10084
|
+
* ```typescript
|
|
10085
|
+
* const reporter = new ComplianceReporter()
|
|
10086
|
+
* const report = await reporter.generateAuditReport({...})
|
|
10087
|
+
*
|
|
10088
|
+
* const pdfBytes = reporter.exportToPdf(report, {
|
|
10089
|
+
* title: 'Q1 2025 Audit Report',
|
|
10090
|
+
* organization: 'ACME Corp',
|
|
10091
|
+
* })
|
|
10092
|
+
*
|
|
10093
|
+
* // Save to file (Node.js)
|
|
10094
|
+
* fs.writeFileSync('report.pdf', pdfBytes)
|
|
10095
|
+
* ```
|
|
10096
|
+
*/
|
|
10097
|
+
exportToPdf(report, options) {
|
|
10098
|
+
return generatePdfReport(report, options);
|
|
10099
|
+
}
|
|
10100
|
+
/**
|
|
10101
|
+
* Export transactions to regulatory compliance formats
|
|
10102
|
+
*
|
|
10103
|
+
* Decrypts and exports transactions in formats required by regulators:
|
|
10104
|
+
* - FATF: Financial Action Task Force Travel Rule format
|
|
10105
|
+
* - FINCEN: FinCEN Suspicious Activity Report (SAR) format
|
|
10106
|
+
* - CSV: Generic comma-separated values format
|
|
10107
|
+
*
|
|
10108
|
+
* @param params - Export parameters
|
|
10109
|
+
* @returns Regulatory export in the specified format
|
|
10110
|
+
* @throws {ValidationError} If parameters are invalid
|
|
10111
|
+
* @throws {CryptoError} If decryption fails
|
|
10112
|
+
*
|
|
10113
|
+
* @example
|
|
10114
|
+
* ```typescript
|
|
10115
|
+
* const reporter = new ComplianceReporter()
|
|
10116
|
+
*
|
|
10117
|
+
* // FATF Travel Rule export
|
|
10118
|
+
* const fatfExport = await reporter.exportForRegulator({
|
|
10119
|
+
* viewingKey: myViewingKey,
|
|
10120
|
+
* transactions: encryptedTxs,
|
|
10121
|
+
* jurisdiction: 'EU',
|
|
10122
|
+
* format: 'FATF',
|
|
10123
|
+
* currency: 'EUR',
|
|
10124
|
+
* })
|
|
10125
|
+
*
|
|
10126
|
+
* // FINCEN SAR export (US only)
|
|
10127
|
+
* const fincenExport = await reporter.exportForRegulator({
|
|
10128
|
+
* viewingKey: myViewingKey,
|
|
10129
|
+
* transactions: suspiciousTxs,
|
|
10130
|
+
* jurisdiction: 'US',
|
|
10131
|
+
* format: 'FINCEN',
|
|
10132
|
+
* })
|
|
10133
|
+
*
|
|
10134
|
+
* // CSV export
|
|
10135
|
+
* const csvExport = await reporter.exportForRegulator({
|
|
10136
|
+
* viewingKey: myViewingKey,
|
|
10137
|
+
* transactions: encryptedTxs,
|
|
10138
|
+
* jurisdiction: 'SG',
|
|
10139
|
+
* format: 'CSV',
|
|
10140
|
+
* })
|
|
10141
|
+
* ```
|
|
10142
|
+
*/
|
|
10143
|
+
async exportForRegulator(params) {
|
|
10144
|
+
this.validateRegulatoryParams(params);
|
|
10145
|
+
const viewingKey = this.normalizeViewingKey(params.viewingKey);
|
|
10146
|
+
const decryptedTransactions = this.decryptTransactions(
|
|
10147
|
+
params.transactions,
|
|
10148
|
+
viewingKey,
|
|
10149
|
+
params.startDate,
|
|
10150
|
+
params.endDate
|
|
10151
|
+
);
|
|
10152
|
+
const reportId = `reg_${generateRandomBytes(16).slice(2)}`;
|
|
10153
|
+
switch (params.format) {
|
|
10154
|
+
case "FATF":
|
|
10155
|
+
return this.exportToFATF(
|
|
10156
|
+
reportId,
|
|
10157
|
+
decryptedTransactions,
|
|
10158
|
+
params.jurisdiction,
|
|
10159
|
+
params.currency || "USD"
|
|
10160
|
+
);
|
|
10161
|
+
case "FINCEN":
|
|
10162
|
+
return this.exportToFINCEN(
|
|
10163
|
+
reportId,
|
|
10164
|
+
decryptedTransactions,
|
|
10165
|
+
params.startDate,
|
|
10166
|
+
params.endDate,
|
|
10167
|
+
params.currency || "USD"
|
|
10168
|
+
);
|
|
10169
|
+
case "CSV":
|
|
10170
|
+
return this.exportToCSV(
|
|
10171
|
+
reportId,
|
|
10172
|
+
decryptedTransactions,
|
|
10173
|
+
params.jurisdiction,
|
|
10174
|
+
params.currency || "USD"
|
|
10175
|
+
);
|
|
10176
|
+
default:
|
|
10177
|
+
throw new ValidationError(
|
|
10178
|
+
`unsupported format: ${params.format}`,
|
|
10179
|
+
"format",
|
|
10180
|
+
{ received: params.format },
|
|
10181
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
10182
|
+
);
|
|
10183
|
+
}
|
|
10184
|
+
}
|
|
10185
|
+
/**
|
|
10186
|
+
* Validate regulatory export parameters
|
|
10187
|
+
*/
|
|
10188
|
+
validateRegulatoryParams(params) {
|
|
10189
|
+
if (!params.viewingKey) {
|
|
10190
|
+
throw new ValidationError(
|
|
10191
|
+
"viewingKey is required",
|
|
10192
|
+
"viewingKey",
|
|
10193
|
+
void 0,
|
|
10194
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
10195
|
+
);
|
|
10196
|
+
}
|
|
10197
|
+
if (!params.transactions) {
|
|
10198
|
+
throw new ValidationError(
|
|
10199
|
+
"transactions array is required",
|
|
10200
|
+
"transactions",
|
|
10201
|
+
void 0,
|
|
10202
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
10203
|
+
);
|
|
10204
|
+
}
|
|
10205
|
+
if (!Array.isArray(params.transactions)) {
|
|
10206
|
+
throw new ValidationError(
|
|
10207
|
+
"transactions must be an array",
|
|
10208
|
+
"transactions",
|
|
10209
|
+
{ received: typeof params.transactions },
|
|
10210
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
10211
|
+
);
|
|
10212
|
+
}
|
|
10213
|
+
if (!params.jurisdiction) {
|
|
10214
|
+
throw new ValidationError(
|
|
10215
|
+
"jurisdiction is required",
|
|
10216
|
+
"jurisdiction",
|
|
10217
|
+
void 0,
|
|
10218
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
10219
|
+
);
|
|
10220
|
+
}
|
|
10221
|
+
const validJurisdictions = ["US", "EU", "UK", "SG"];
|
|
10222
|
+
if (!validJurisdictions.includes(params.jurisdiction)) {
|
|
10223
|
+
throw new ValidationError(
|
|
10224
|
+
`invalid jurisdiction. Must be one of: ${validJurisdictions.join(", ")}`,
|
|
10225
|
+
"jurisdiction",
|
|
10226
|
+
{ received: params.jurisdiction },
|
|
10227
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
10228
|
+
);
|
|
10229
|
+
}
|
|
10230
|
+
if (!params.format) {
|
|
10231
|
+
throw new ValidationError(
|
|
10232
|
+
"format is required",
|
|
10233
|
+
"format",
|
|
10234
|
+
void 0,
|
|
10235
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
10236
|
+
);
|
|
10237
|
+
}
|
|
10238
|
+
const validFormats = ["FATF", "FINCEN", "CSV"];
|
|
10239
|
+
if (!validFormats.includes(params.format)) {
|
|
10240
|
+
throw new ValidationError(
|
|
10241
|
+
`invalid format. Must be one of: ${validFormats.join(", ")}`,
|
|
10242
|
+
"format",
|
|
10243
|
+
{ received: params.format },
|
|
10244
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
10245
|
+
);
|
|
10246
|
+
}
|
|
10247
|
+
if (params.format === "FINCEN" && params.jurisdiction !== "US") {
|
|
10248
|
+
throw new ValidationError(
|
|
10249
|
+
"FINCEN format is only available for US jurisdiction",
|
|
10250
|
+
"format",
|
|
10251
|
+
{ jurisdiction: params.jurisdiction, format: params.format },
|
|
10252
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
10253
|
+
);
|
|
10254
|
+
}
|
|
10255
|
+
if (params.startDate && params.endDate) {
|
|
10256
|
+
if (params.startDate > params.endDate) {
|
|
10257
|
+
throw new ValidationError(
|
|
10258
|
+
"startDate must be before endDate",
|
|
10259
|
+
"startDate",
|
|
10260
|
+
{
|
|
10261
|
+
startDate: params.startDate.toISOString(),
|
|
10262
|
+
endDate: params.endDate.toISOString()
|
|
10263
|
+
},
|
|
10264
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
10265
|
+
);
|
|
10266
|
+
}
|
|
10267
|
+
}
|
|
10268
|
+
}
|
|
10269
|
+
/**
|
|
10270
|
+
* Export to FATF Travel Rule format
|
|
10271
|
+
*/
|
|
10272
|
+
exportToFATF(reportId, transactions, jurisdiction, currency) {
|
|
10273
|
+
const fatfTransactions = transactions.map((tx) => ({
|
|
10274
|
+
originatorAccount: tx.sender,
|
|
10275
|
+
beneficiaryAccount: tx.recipient,
|
|
10276
|
+
amount: tx.amount,
|
|
10277
|
+
currency,
|
|
10278
|
+
transactionRef: tx.id,
|
|
10279
|
+
timestamp: new Date(tx.timestamp * 1e3).toISOString()
|
|
10280
|
+
}));
|
|
10281
|
+
return {
|
|
10282
|
+
reportId,
|
|
10283
|
+
generatedAt: (/* @__PURE__ */ new Date()).toISOString(),
|
|
10284
|
+
jurisdiction,
|
|
10285
|
+
transactions: fatfTransactions
|
|
10286
|
+
};
|
|
10287
|
+
}
|
|
10288
|
+
/**
|
|
10289
|
+
* Export to FINCEN SAR format
|
|
10290
|
+
*/
|
|
10291
|
+
exportToFINCEN(reportId, transactions, startDate, endDate, currency = "USD") {
|
|
10292
|
+
let totalAmount = 0n;
|
|
10293
|
+
for (const tx of transactions) {
|
|
10294
|
+
try {
|
|
10295
|
+
totalAmount += BigInt(tx.amount);
|
|
10296
|
+
} catch (error) {
|
|
10297
|
+
}
|
|
10298
|
+
}
|
|
10299
|
+
const period = this.determinePeriod(transactions, startDate, endDate);
|
|
10300
|
+
const fincenTransactions = transactions.map((tx) => ({
|
|
10301
|
+
transactionDate: new Date(tx.timestamp * 1e3).toISOString(),
|
|
10302
|
+
amount: tx.amount,
|
|
10303
|
+
currency,
|
|
10304
|
+
narrativeSummary: `Transfer from ${tx.sender} to ${tx.recipient}`,
|
|
10305
|
+
transactionRef: tx.id,
|
|
10306
|
+
parties: {
|
|
10307
|
+
sender: tx.sender,
|
|
10308
|
+
recipient: tx.recipient
|
|
10309
|
+
}
|
|
10310
|
+
}));
|
|
10311
|
+
return {
|
|
10312
|
+
reportId,
|
|
10313
|
+
filingType: "SAR",
|
|
10314
|
+
reportDate: (/* @__PURE__ */ new Date()).toISOString(),
|
|
10315
|
+
jurisdiction: "US",
|
|
10316
|
+
summary: {
|
|
10317
|
+
transactionCount: transactions.length,
|
|
10318
|
+
totalAmount: totalAmount.toString(),
|
|
10319
|
+
period: {
|
|
10320
|
+
start: period.start.toISOString(),
|
|
10321
|
+
end: period.end.toISOString()
|
|
10322
|
+
}
|
|
10323
|
+
},
|
|
10324
|
+
transactions: fincenTransactions
|
|
10325
|
+
};
|
|
10326
|
+
}
|
|
10327
|
+
/**
|
|
10328
|
+
* Export to CSV format
|
|
10329
|
+
*/
|
|
10330
|
+
exportToCSV(reportId, transactions, jurisdiction, currency) {
|
|
10331
|
+
const headers = [
|
|
10332
|
+
"Transaction ID",
|
|
10333
|
+
"Timestamp",
|
|
10334
|
+
"Sender",
|
|
10335
|
+
"Recipient",
|
|
10336
|
+
"Amount",
|
|
10337
|
+
"Currency"
|
|
10338
|
+
];
|
|
10339
|
+
const rows = transactions.map((tx) => [
|
|
10340
|
+
tx.id,
|
|
10341
|
+
new Date(tx.timestamp * 1e3).toISOString(),
|
|
10342
|
+
tx.sender,
|
|
10343
|
+
tx.recipient,
|
|
10344
|
+
tx.amount,
|
|
10345
|
+
currency
|
|
10346
|
+
]);
|
|
10347
|
+
return {
|
|
10348
|
+
reportId,
|
|
10349
|
+
generatedAt: (/* @__PURE__ */ new Date()).toISOString(),
|
|
10350
|
+
jurisdiction,
|
|
10351
|
+
headers,
|
|
10352
|
+
rows
|
|
10353
|
+
};
|
|
10354
|
+
}
|
|
10355
|
+
};
|
|
10356
|
+
|
|
10357
|
+
// src/compliance/conditional.ts
|
|
10358
|
+
var import_sha25616 = require("@noble/hashes/sha256");
|
|
10359
|
+
var import_utils22 = require("@noble/hashes/utils");
|
|
10360
|
+
var import_chacha3 = require("@noble/ciphers/chacha.js");
|
|
10361
|
+
var ConditionalDisclosure = class {
|
|
10362
|
+
/**
|
|
10363
|
+
* Create a time-locked disclosure
|
|
10364
|
+
*
|
|
10365
|
+
* Encrypts the viewing key with a deterministic key derived from
|
|
10366
|
+
* the commitment and reveal time. The key can only be reconstructed
|
|
10367
|
+
* after the specified time/block height.
|
|
10368
|
+
*
|
|
10369
|
+
* @param params - Time-lock parameters
|
|
10370
|
+
* @returns Time-lock result with encrypted key
|
|
10371
|
+
* @throws {ValidationError} If parameters are invalid
|
|
10372
|
+
* @throws {CryptoError} If encryption fails
|
|
10373
|
+
*/
|
|
10374
|
+
createTimeLocked(params) {
|
|
10375
|
+
if (!params.viewingKey || !params.viewingKey.startsWith("0x")) {
|
|
10376
|
+
throw new ValidationError(
|
|
10377
|
+
"Invalid viewing key format",
|
|
10378
|
+
"viewingKey",
|
|
10379
|
+
{ viewingKey: params.viewingKey },
|
|
10380
|
+
"SIP_2006" /* INVALID_KEY */
|
|
10381
|
+
);
|
|
10382
|
+
}
|
|
10383
|
+
if (!params.commitment || !params.commitment.startsWith("0x")) {
|
|
10384
|
+
throw new ValidationError(
|
|
10385
|
+
"Invalid commitment format",
|
|
10386
|
+
"commitment",
|
|
10387
|
+
{ commitment: params.commitment },
|
|
10388
|
+
"SIP_3010" /* INVALID_COMMITMENT */
|
|
10389
|
+
);
|
|
10390
|
+
}
|
|
10391
|
+
let revealAfterSeconds;
|
|
10392
|
+
let type;
|
|
10393
|
+
if (params.revealAfter instanceof Date) {
|
|
10394
|
+
revealAfterSeconds = Math.floor(params.revealAfter.getTime() / 1e3);
|
|
10395
|
+
type = "timestamp";
|
|
10396
|
+
} else if (typeof params.revealAfter === "number") {
|
|
10397
|
+
if (params.revealAfter > 1e10) {
|
|
10398
|
+
revealAfterSeconds = Math.floor(params.revealAfter / 1e3);
|
|
10399
|
+
type = "timestamp";
|
|
10400
|
+
} else {
|
|
10401
|
+
revealAfterSeconds = params.revealAfter;
|
|
10402
|
+
type = "blockheight";
|
|
10403
|
+
}
|
|
10404
|
+
if (revealAfterSeconds <= 0) {
|
|
10405
|
+
throw new ValidationError(
|
|
10406
|
+
"Reveal time/block height must be positive",
|
|
10407
|
+
"revealAfter",
|
|
10408
|
+
{ revealAfter: revealAfterSeconds },
|
|
10409
|
+
"SIP_3011" /* INVALID_TIME_LOCK */
|
|
10410
|
+
);
|
|
10411
|
+
}
|
|
10412
|
+
} else {
|
|
10413
|
+
throw new ValidationError(
|
|
10414
|
+
"Invalid revealAfter type (must be Date or number)",
|
|
10415
|
+
"revealAfter",
|
|
10416
|
+
{ revealAfter: params.revealAfter },
|
|
10417
|
+
"SIP_3011" /* INVALID_TIME_LOCK */
|
|
10418
|
+
);
|
|
10419
|
+
}
|
|
10420
|
+
try {
|
|
10421
|
+
const encryptionKey = this._deriveEncryptionKey(
|
|
10422
|
+
params.commitment,
|
|
10423
|
+
revealAfterSeconds
|
|
10424
|
+
);
|
|
10425
|
+
const nonce = (0, import_utils22.randomBytes)(24);
|
|
10426
|
+
const viewingKeyBytes = (0, import_utils22.hexToBytes)(params.viewingKey.slice(2));
|
|
10427
|
+
const cipher = (0, import_chacha3.xchacha20poly1305)(encryptionKey, nonce);
|
|
10428
|
+
const encryptedKey = cipher.encrypt(viewingKeyBytes);
|
|
10429
|
+
const commitmentData = new Uint8Array([
|
|
10430
|
+
...viewingKeyBytes,
|
|
10431
|
+
...this._numberToBytes(revealAfterSeconds)
|
|
10432
|
+
]);
|
|
10433
|
+
const commitmentHash = (0, import_sha25616.sha256)(commitmentData);
|
|
10434
|
+
return {
|
|
10435
|
+
encryptedKey: "0x" + (0, import_utils22.bytesToHex)(encryptedKey),
|
|
10436
|
+
nonce: "0x" + (0, import_utils22.bytesToHex)(nonce),
|
|
10437
|
+
revealAfter: revealAfterSeconds,
|
|
10438
|
+
verificationCommitment: "0x" + (0, import_utils22.bytesToHex)(commitmentHash),
|
|
10439
|
+
encryptionCommitment: params.commitment,
|
|
10440
|
+
type
|
|
10441
|
+
};
|
|
10442
|
+
} catch (error) {
|
|
10443
|
+
if (error instanceof ValidationError) {
|
|
10444
|
+
throw error;
|
|
10445
|
+
}
|
|
10446
|
+
throw new CryptoError(
|
|
10447
|
+
"Failed to create time-locked disclosure",
|
|
10448
|
+
"SIP_3001" /* ENCRYPTION_FAILED */,
|
|
10449
|
+
{
|
|
10450
|
+
cause: error instanceof Error ? error : void 0,
|
|
10451
|
+
operation: "createTimeLocked"
|
|
10452
|
+
}
|
|
10453
|
+
);
|
|
10454
|
+
}
|
|
10455
|
+
}
|
|
10456
|
+
/**
|
|
10457
|
+
* Check if a time-lock is unlocked and retrieve the viewing key
|
|
10458
|
+
*
|
|
10459
|
+
* @param timeLock - Time-lock result to check
|
|
10460
|
+
* @param currentTimeOrBlock - Current time (Date/number) or block height (number)
|
|
10461
|
+
* @returns Unlock result with viewing key if unlocked
|
|
10462
|
+
* @throws {ValidationError} If time-lock format is invalid
|
|
10463
|
+
* @throws {CryptoError} If decryption fails
|
|
10464
|
+
*/
|
|
10465
|
+
checkUnlocked(timeLock, currentTimeOrBlock) {
|
|
10466
|
+
if (!timeLock.encryptedKey || !timeLock.encryptedKey.startsWith("0x")) {
|
|
10467
|
+
throw new ValidationError(
|
|
10468
|
+
"Invalid encrypted key format",
|
|
10469
|
+
"encryptedKey",
|
|
10470
|
+
{ encryptedKey: timeLock.encryptedKey },
|
|
10471
|
+
"SIP_3009" /* INVALID_ENCRYPTED_DATA */
|
|
10472
|
+
);
|
|
10473
|
+
}
|
|
10474
|
+
if (!timeLock.nonce || !timeLock.nonce.startsWith("0x")) {
|
|
10475
|
+
throw new ValidationError(
|
|
10476
|
+
"Invalid nonce format",
|
|
10477
|
+
"nonce",
|
|
10478
|
+
{ nonce: timeLock.nonce },
|
|
10479
|
+
"SIP_3009" /* INVALID_ENCRYPTED_DATA */
|
|
10480
|
+
);
|
|
10481
|
+
}
|
|
10482
|
+
if (!timeLock.verificationCommitment || !timeLock.verificationCommitment.startsWith("0x")) {
|
|
10483
|
+
throw new ValidationError(
|
|
10484
|
+
"Invalid verification commitment format",
|
|
10485
|
+
"verificationCommitment",
|
|
10486
|
+
{ commitment: timeLock.verificationCommitment },
|
|
10487
|
+
"SIP_3010" /* INVALID_COMMITMENT */
|
|
10488
|
+
);
|
|
10489
|
+
}
|
|
10490
|
+
if (!timeLock.encryptionCommitment || !timeLock.encryptionCommitment.startsWith("0x")) {
|
|
10491
|
+
throw new ValidationError(
|
|
10492
|
+
"Invalid encryption commitment format",
|
|
10493
|
+
"encryptionCommitment",
|
|
10494
|
+
{ commitment: timeLock.encryptionCommitment },
|
|
10495
|
+
"SIP_3010" /* INVALID_COMMITMENT */
|
|
10496
|
+
);
|
|
10497
|
+
}
|
|
10498
|
+
let currentValue;
|
|
10499
|
+
if (currentTimeOrBlock instanceof Date) {
|
|
10500
|
+
currentValue = Math.floor(currentTimeOrBlock.getTime() / 1e3);
|
|
10501
|
+
} else if (typeof currentTimeOrBlock === "number") {
|
|
10502
|
+
currentValue = currentTimeOrBlock;
|
|
10503
|
+
} else {
|
|
10504
|
+
currentValue = Math.floor(Date.now() / 1e3);
|
|
10505
|
+
}
|
|
10506
|
+
const unlocked = currentValue >= timeLock.revealAfter;
|
|
10507
|
+
if (!unlocked) {
|
|
10508
|
+
return { unlocked: false };
|
|
10509
|
+
}
|
|
10510
|
+
try {
|
|
10511
|
+
const encryptionKey = this._deriveEncryptionKey(
|
|
10512
|
+
timeLock.encryptionCommitment,
|
|
10513
|
+
timeLock.revealAfter
|
|
10514
|
+
);
|
|
10515
|
+
const nonce = (0, import_utils22.hexToBytes)(timeLock.nonce.slice(2));
|
|
10516
|
+
const encryptedData = (0, import_utils22.hexToBytes)(timeLock.encryptedKey.slice(2));
|
|
10517
|
+
const cipher = (0, import_chacha3.xchacha20poly1305)(encryptionKey, nonce);
|
|
10518
|
+
const decryptedBytes = cipher.decrypt(encryptedData);
|
|
10519
|
+
const viewingKey = "0x" + (0, import_utils22.bytesToHex)(decryptedBytes);
|
|
10520
|
+
return {
|
|
10521
|
+
unlocked: true,
|
|
10522
|
+
viewingKey
|
|
10523
|
+
};
|
|
10524
|
+
} catch (error) {
|
|
10525
|
+
if (error instanceof ValidationError || error instanceof CryptoError) {
|
|
10526
|
+
throw error;
|
|
10527
|
+
}
|
|
10528
|
+
throw new CryptoError(
|
|
10529
|
+
"Failed to decrypt time-locked viewing key",
|
|
10530
|
+
"SIP_3002" /* DECRYPTION_FAILED */,
|
|
10531
|
+
{
|
|
10532
|
+
cause: error instanceof Error ? error : void 0,
|
|
10533
|
+
operation: "checkUnlocked"
|
|
10534
|
+
}
|
|
10535
|
+
);
|
|
10536
|
+
}
|
|
10537
|
+
}
|
|
10538
|
+
/**
|
|
10539
|
+
* Verify a time-lock commitment
|
|
10540
|
+
*
|
|
10541
|
+
* Verifies that the verification commitment in the time-lock matches the hash
|
|
10542
|
+
* of the provided viewing key and reveal time.
|
|
10543
|
+
*
|
|
10544
|
+
* @param timeLock - Time-lock to verify
|
|
10545
|
+
* @param viewingKey - Viewing key to verify against
|
|
10546
|
+
* @returns True if commitment is valid
|
|
10547
|
+
*/
|
|
10548
|
+
verifyCommitment(timeLock, viewingKey) {
|
|
10549
|
+
try {
|
|
10550
|
+
const viewingKeyBytes = (0, import_utils22.hexToBytes)(viewingKey.slice(2));
|
|
10551
|
+
const commitmentData = new Uint8Array([
|
|
10552
|
+
...viewingKeyBytes,
|
|
10553
|
+
...this._numberToBytes(timeLock.revealAfter)
|
|
10554
|
+
]);
|
|
10555
|
+
const expectedCommitment = (0, import_sha25616.sha256)(commitmentData);
|
|
10556
|
+
const actualCommitment = (0, import_utils22.hexToBytes)(timeLock.verificationCommitment.slice(2));
|
|
10557
|
+
if (expectedCommitment.length !== actualCommitment.length) {
|
|
10558
|
+
return false;
|
|
10559
|
+
}
|
|
10560
|
+
let diff = 0;
|
|
10561
|
+
for (let i = 0; i < expectedCommitment.length; i++) {
|
|
10562
|
+
diff |= expectedCommitment[i] ^ actualCommitment[i];
|
|
10563
|
+
}
|
|
10564
|
+
return diff === 0;
|
|
10565
|
+
} catch {
|
|
10566
|
+
return false;
|
|
10567
|
+
}
|
|
10568
|
+
}
|
|
10569
|
+
/**
|
|
10570
|
+
* Derive deterministic encryption key from commitment and reveal time
|
|
10571
|
+
*
|
|
10572
|
+
* @private
|
|
10573
|
+
*/
|
|
10574
|
+
_deriveEncryptionKey(commitment, revealAfter) {
|
|
10575
|
+
const commitmentBytes = (0, import_utils22.hexToBytes)(commitment.slice(2));
|
|
10576
|
+
const timeBytes = this._numberToBytes(revealAfter);
|
|
10577
|
+
const combined = new Uint8Array([...commitmentBytes, ...timeBytes]);
|
|
10578
|
+
const key = (0, import_sha25616.sha256)(combined);
|
|
10579
|
+
if (key.length !== 32) {
|
|
10580
|
+
throw new CryptoError(
|
|
10581
|
+
"Derived key must be 32 bytes",
|
|
10582
|
+
"SIP_3008" /* INVALID_KEY_SIZE */,
|
|
10583
|
+
{
|
|
10584
|
+
context: { actualSize: key.length, expectedSize: 32 },
|
|
10585
|
+
operation: "_deriveEncryptionKey"
|
|
10586
|
+
}
|
|
10587
|
+
);
|
|
10588
|
+
}
|
|
10589
|
+
return key;
|
|
10590
|
+
}
|
|
10591
|
+
/**
|
|
10592
|
+
* Convert number to 8-byte big-endian representation
|
|
10593
|
+
*
|
|
10594
|
+
* @private
|
|
10595
|
+
*/
|
|
10596
|
+
_numberToBytes(num) {
|
|
10597
|
+
const bytes = new Uint8Array(8);
|
|
10598
|
+
const view = new DataView(bytes.buffer);
|
|
10599
|
+
view.setBigUint64(0, BigInt(Math.floor(num)), false);
|
|
10600
|
+
return bytes;
|
|
10601
|
+
}
|
|
10602
|
+
};
|
|
10603
|
+
|
|
10604
|
+
// src/compliance/conditional-threshold.ts
|
|
10605
|
+
var import_secp256k17 = require("@noble/curves/secp256k1");
|
|
10606
|
+
var import_sha25617 = require("@noble/hashes/sha256");
|
|
10607
|
+
var import_utils23 = require("@noble/hashes/utils");
|
|
10608
|
+
var CURVE_ORDER2 = import_secp256k17.secp256k1.CURVE.n;
|
|
10609
|
+
|
|
10610
|
+
// src/compliance/threshold.ts
|
|
10611
|
+
var import_sha25618 = require("@noble/hashes/sha256");
|
|
10612
|
+
var import_utils24 = require("@noble/hashes/utils");
|
|
10613
|
+
var FIELD_PRIME = 2n ** 256n - 189n;
|
|
10614
|
+
var ThresholdViewingKey = class {
|
|
10615
|
+
/**
|
|
10616
|
+
* Create threshold shares from a viewing key
|
|
10617
|
+
*
|
|
10618
|
+
* @param params - Configuration parameters
|
|
10619
|
+
* @returns Threshold shares with commitment
|
|
10620
|
+
* @throws ValidationError if parameters are invalid
|
|
10621
|
+
*
|
|
10622
|
+
* @example
|
|
10623
|
+
* ```typescript
|
|
10624
|
+
* const threshold = ThresholdViewingKey.create({
|
|
10625
|
+
* threshold: 3,
|
|
10626
|
+
* totalShares: 5,
|
|
10627
|
+
* viewingKey: '0xabc123...',
|
|
10628
|
+
* })
|
|
10629
|
+
* ```
|
|
10630
|
+
*/
|
|
10631
|
+
static create(params) {
|
|
10632
|
+
this.validateParams(params.threshold, params.totalShares);
|
|
10633
|
+
this.validateViewingKey(params.viewingKey);
|
|
10634
|
+
const secret = this.viewingKeyToSecret(params.viewingKey);
|
|
10635
|
+
const keyLength = params.viewingKey.slice(2).length;
|
|
10636
|
+
const coefficients = this.generateCoefficients(params.threshold, secret);
|
|
10637
|
+
const commitment = this.createCommitment(secret, coefficients);
|
|
10638
|
+
const shares = [];
|
|
10639
|
+
for (let i = 1; i <= params.totalShares; i++) {
|
|
10640
|
+
const x = BigInt(i);
|
|
10641
|
+
const y = this.evaluatePolynomial(coefficients, x);
|
|
10642
|
+
shares.push(this.encodeShare(x, y, keyLength, commitment));
|
|
10643
|
+
}
|
|
10644
|
+
return {
|
|
10645
|
+
shares,
|
|
10646
|
+
commitment,
|
|
10647
|
+
threshold: params.threshold,
|
|
10648
|
+
totalShares: params.totalShares
|
|
10649
|
+
};
|
|
10650
|
+
}
|
|
10651
|
+
/**
|
|
10652
|
+
* Reconstruct viewing key from threshold shares
|
|
10653
|
+
*
|
|
10654
|
+
* @param shares - Array of encoded shares (must be >= threshold)
|
|
10655
|
+
* @returns Reconstructed viewing key
|
|
10656
|
+
* @throws ValidationError if insufficient or invalid shares
|
|
10657
|
+
*
|
|
10658
|
+
* @example
|
|
10659
|
+
* ```typescript
|
|
10660
|
+
* const viewingKey = ThresholdViewingKey.reconstruct([
|
|
10661
|
+
* 'share1',
|
|
10662
|
+
* 'share2',
|
|
10663
|
+
* 'share3',
|
|
10664
|
+
* ])
|
|
10665
|
+
* ```
|
|
10666
|
+
*/
|
|
10667
|
+
static reconstruct(shares) {
|
|
10668
|
+
if (!shares || shares.length === 0) {
|
|
10669
|
+
throw new ValidationError(
|
|
10670
|
+
"at least one share is required",
|
|
10671
|
+
"shares",
|
|
10672
|
+
{ received: shares },
|
|
10673
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
10674
|
+
);
|
|
10675
|
+
}
|
|
10676
|
+
const decodedShares = shares.map((s) => this.decodeShare(s));
|
|
10677
|
+
const commitment = decodedShares[0].commitment;
|
|
10678
|
+
const keyLength = decodedShares[0].keyLength;
|
|
10679
|
+
for (const share of decodedShares) {
|
|
10680
|
+
if (share.commitment !== commitment) {
|
|
10681
|
+
throw new ValidationError(
|
|
10682
|
+
"shares must all have the same commitment",
|
|
10683
|
+
"shares",
|
|
10684
|
+
{ commitment },
|
|
10685
|
+
"SIP_3012" /* INVALID_SHARE */
|
|
10686
|
+
);
|
|
10687
|
+
}
|
|
10688
|
+
if (share.keyLength !== keyLength) {
|
|
10689
|
+
throw new ValidationError(
|
|
10690
|
+
"shares must all have the same key length",
|
|
10691
|
+
"shares",
|
|
10692
|
+
{ keyLength },
|
|
10693
|
+
"SIP_3012" /* INVALID_SHARE */
|
|
10694
|
+
);
|
|
10695
|
+
}
|
|
10696
|
+
}
|
|
10697
|
+
const xCoords = new Set(decodedShares.map((s) => s.x.toString()));
|
|
10698
|
+
if (xCoords.size !== decodedShares.length) {
|
|
10699
|
+
throw new ValidationError(
|
|
10700
|
+
"shares must have unique x-coordinates",
|
|
10701
|
+
"shares",
|
|
10702
|
+
void 0,
|
|
10703
|
+
"SIP_3012" /* INVALID_SHARE */
|
|
10704
|
+
);
|
|
10705
|
+
}
|
|
10706
|
+
const secret = this.lagrangeInterpolate(decodedShares);
|
|
10707
|
+
return this.secretToViewingKey(secret, keyLength);
|
|
10708
|
+
}
|
|
10709
|
+
/**
|
|
10710
|
+
* Verify a share without revealing the viewing key
|
|
10711
|
+
*
|
|
10712
|
+
* @param share - Encoded share to verify
|
|
10713
|
+
* @param expectedCommitment - Expected commitment hash
|
|
10714
|
+
* @returns True if share is valid
|
|
10715
|
+
*
|
|
10716
|
+
* @example
|
|
10717
|
+
* ```typescript
|
|
10718
|
+
* const isValid = ThresholdViewingKey.verifyShare(
|
|
10719
|
+
* 'share1',
|
|
10720
|
+
* 'commitment_hash'
|
|
10721
|
+
* )
|
|
10722
|
+
* ```
|
|
10723
|
+
*/
|
|
10724
|
+
static verifyShare(share, expectedCommitment) {
|
|
10725
|
+
try {
|
|
10726
|
+
const decoded = this.decodeShare(share);
|
|
10727
|
+
return decoded.commitment === expectedCommitment;
|
|
10728
|
+
} catch {
|
|
10729
|
+
return false;
|
|
10730
|
+
}
|
|
10731
|
+
}
|
|
10732
|
+
// ─── Private Helper Methods ─────────────────────────────────────────────────
|
|
10733
|
+
/**
|
|
10734
|
+
* Validate threshold and total shares parameters
|
|
10735
|
+
*/
|
|
10736
|
+
static validateParams(threshold, totalShares) {
|
|
10737
|
+
if (!Number.isInteger(threshold) || threshold < 2) {
|
|
10738
|
+
throw new ValidationError(
|
|
10739
|
+
"threshold must be an integer >= 2",
|
|
10740
|
+
"threshold",
|
|
10741
|
+
{ received: threshold },
|
|
10742
|
+
"SIP_3013" /* INVALID_THRESHOLD */
|
|
10743
|
+
);
|
|
10744
|
+
}
|
|
10745
|
+
if (!Number.isInteger(totalShares) || totalShares < threshold) {
|
|
10746
|
+
throw new ValidationError(
|
|
10747
|
+
"totalShares must be an integer >= threshold",
|
|
10748
|
+
"totalShares",
|
|
10749
|
+
{ received: totalShares, threshold },
|
|
10750
|
+
"SIP_3013" /* INVALID_THRESHOLD */
|
|
10751
|
+
);
|
|
10752
|
+
}
|
|
10753
|
+
if (totalShares > 255) {
|
|
10754
|
+
throw new ValidationError(
|
|
10755
|
+
"totalShares must be <= 255",
|
|
10756
|
+
"totalShares",
|
|
10757
|
+
{ received: totalShares },
|
|
10758
|
+
"SIP_3013" /* INVALID_THRESHOLD */
|
|
10759
|
+
);
|
|
10760
|
+
}
|
|
10761
|
+
}
|
|
10762
|
+
/**
|
|
10763
|
+
* Validate viewing key format
|
|
10764
|
+
*/
|
|
10765
|
+
static validateViewingKey(viewingKey) {
|
|
10766
|
+
if (!viewingKey || typeof viewingKey !== "string") {
|
|
10767
|
+
throw new ValidationError(
|
|
10768
|
+
"viewingKey is required",
|
|
10769
|
+
"viewingKey",
|
|
10770
|
+
{ received: viewingKey },
|
|
10771
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
10772
|
+
);
|
|
10773
|
+
}
|
|
10774
|
+
if (!viewingKey.startsWith("0x")) {
|
|
10775
|
+
throw new ValidationError(
|
|
10776
|
+
"viewingKey must be hex-encoded (start with 0x)",
|
|
10777
|
+
"viewingKey",
|
|
10778
|
+
{ received: viewingKey },
|
|
10779
|
+
"SIP_3015" /* INVALID_FORMAT */
|
|
10780
|
+
);
|
|
10781
|
+
}
|
|
10782
|
+
if (viewingKey.length < 66) {
|
|
10783
|
+
throw new ValidationError(
|
|
10784
|
+
"viewingKey must be at least 32 bytes",
|
|
10785
|
+
"viewingKey",
|
|
10786
|
+
{ received: viewingKey.length },
|
|
10787
|
+
"SIP_3015" /* INVALID_FORMAT */
|
|
10788
|
+
);
|
|
10789
|
+
}
|
|
10790
|
+
}
|
|
10791
|
+
/**
|
|
10792
|
+
* Convert viewing key to secret (bigint)
|
|
10793
|
+
*/
|
|
10794
|
+
static viewingKeyToSecret(viewingKey) {
|
|
10795
|
+
const bytes = (0, import_utils24.hexToBytes)(viewingKey.slice(2));
|
|
10796
|
+
let secret = 0n;
|
|
10797
|
+
for (let i = 0; i < bytes.length; i++) {
|
|
10798
|
+
secret = secret << 8n | BigInt(bytes[i]);
|
|
10799
|
+
}
|
|
10800
|
+
return this.mod(secret, FIELD_PRIME);
|
|
10801
|
+
}
|
|
10802
|
+
/**
|
|
10803
|
+
* Convert secret (bigint) back to viewing key
|
|
10804
|
+
* @param secret - The secret as bigint
|
|
10805
|
+
* @param hexLength - Length of the hex string (without 0x prefix)
|
|
10806
|
+
*/
|
|
10807
|
+
static secretToViewingKey(secret, hexLength) {
|
|
10808
|
+
let hex = secret.toString(16);
|
|
10809
|
+
hex = hex.padStart(hexLength, "0");
|
|
10810
|
+
return `0x${hex}`;
|
|
10811
|
+
}
|
|
10812
|
+
/**
|
|
10813
|
+
* Generate random polynomial coefficients
|
|
10814
|
+
* Polynomial: f(x) = a₀ + a₁x + a₂x² + ... + aₙ₋₁xⁿ⁻¹
|
|
10815
|
+
* where a₀ = secret
|
|
10816
|
+
*/
|
|
10817
|
+
static generateCoefficients(threshold, secret) {
|
|
10818
|
+
const coefficients = [secret];
|
|
10819
|
+
for (let i = 1; i < threshold; i++) {
|
|
10820
|
+
const randomCoeff = this.randomFieldElement();
|
|
10821
|
+
coefficients.push(randomCoeff);
|
|
10822
|
+
}
|
|
10823
|
+
return coefficients;
|
|
10824
|
+
}
|
|
10825
|
+
/**
|
|
10826
|
+
* Generate a random field element
|
|
10827
|
+
*/
|
|
10828
|
+
static randomFieldElement() {
|
|
10829
|
+
const bytes = (0, import_utils24.randomBytes)(32);
|
|
10830
|
+
let value = 0n;
|
|
10831
|
+
for (let i = 0; i < bytes.length; i++) {
|
|
10832
|
+
value = value << 8n | BigInt(bytes[i]);
|
|
10833
|
+
}
|
|
10834
|
+
return this.mod(value, FIELD_PRIME);
|
|
10835
|
+
}
|
|
10836
|
+
/**
|
|
10837
|
+
* Evaluate polynomial at point x
|
|
10838
|
+
* f(x) = a₀ + a₁x + a₂x² + ... + aₙ₋₁xⁿ⁻¹
|
|
10839
|
+
*/
|
|
10840
|
+
static evaluatePolynomial(coefficients, x) {
|
|
10841
|
+
let result = 0n;
|
|
10842
|
+
let xPower = 1n;
|
|
10843
|
+
for (const coeff of coefficients) {
|
|
10844
|
+
result = this.mod(result + this.mod(coeff * xPower, FIELD_PRIME), FIELD_PRIME);
|
|
10845
|
+
xPower = this.mod(xPower * x, FIELD_PRIME);
|
|
10846
|
+
}
|
|
10847
|
+
return result;
|
|
10848
|
+
}
|
|
10849
|
+
/**
|
|
10850
|
+
* Create commitment hash from secret and coefficients
|
|
10851
|
+
*/
|
|
10852
|
+
static createCommitment(secret, coefficients) {
|
|
10853
|
+
const data = [secret, ...coefficients].map((c) => c.toString(16).padStart(64, "0")).join("");
|
|
10854
|
+
const hash2 = (0, import_sha25618.sha256)((0, import_utils24.hexToBytes)(data));
|
|
10855
|
+
return (0, import_utils24.bytesToHex)(hash2);
|
|
10856
|
+
}
|
|
10857
|
+
/**
|
|
10858
|
+
* Encode share as string: "x:y:len:commitment"
|
|
10859
|
+
*/
|
|
10860
|
+
static encodeShare(x, y, keyLength, commitment) {
|
|
10861
|
+
const xHex = x.toString(16).padStart(2, "0");
|
|
10862
|
+
const yHex = y.toString(16).padStart(64, "0");
|
|
10863
|
+
const lenHex = keyLength.toString(16).padStart(4, "0");
|
|
10864
|
+
return `${xHex}:${yHex}:${lenHex}:${commitment}`;
|
|
10865
|
+
}
|
|
10866
|
+
/**
|
|
10867
|
+
* Decode share from string
|
|
10868
|
+
*/
|
|
10869
|
+
static decodeShare(share) {
|
|
10870
|
+
if (!share || typeof share !== "string") {
|
|
10871
|
+
throw new ValidationError(
|
|
10872
|
+
"share must be a non-empty string",
|
|
10873
|
+
"share",
|
|
10874
|
+
{ received: share },
|
|
10875
|
+
"SIP_3012" /* INVALID_SHARE */
|
|
10876
|
+
);
|
|
10877
|
+
}
|
|
10878
|
+
const parts = share.split(":");
|
|
10879
|
+
if (parts.length !== 4) {
|
|
10880
|
+
throw new ValidationError(
|
|
10881
|
+
'share must have format "x:y:len:commitment"',
|
|
10882
|
+
"share",
|
|
10883
|
+
{ received: share },
|
|
10884
|
+
"SIP_3012" /* INVALID_SHARE */
|
|
10885
|
+
);
|
|
10886
|
+
}
|
|
10887
|
+
const [xHex, yHex, lenHex, commitment] = parts;
|
|
10888
|
+
try {
|
|
10889
|
+
const x = BigInt(`0x${xHex}`);
|
|
10890
|
+
const y = BigInt(`0x${yHex}`);
|
|
10891
|
+
const keyLength = parseInt(lenHex, 16);
|
|
10892
|
+
if (x <= 0n) {
|
|
10893
|
+
throw new ValidationError(
|
|
10894
|
+
"share x-coordinate must be positive",
|
|
10895
|
+
"share",
|
|
10896
|
+
{ x },
|
|
10897
|
+
"SIP_3012" /* INVALID_SHARE */
|
|
10898
|
+
);
|
|
10899
|
+
}
|
|
10900
|
+
if (keyLength < 64) {
|
|
10901
|
+
throw new ValidationError(
|
|
10902
|
+
"key length must be at least 64 (32 bytes)",
|
|
10903
|
+
"share",
|
|
10904
|
+
{ keyLength },
|
|
10905
|
+
"SIP_3012" /* INVALID_SHARE */
|
|
10906
|
+
);
|
|
10907
|
+
}
|
|
10908
|
+
return { x, y, keyLength, commitment };
|
|
10909
|
+
} catch (error) {
|
|
10910
|
+
throw new ValidationError(
|
|
10911
|
+
"failed to decode share",
|
|
10912
|
+
"share",
|
|
10913
|
+
{ error: error.message },
|
|
10914
|
+
"SIP_3012" /* INVALID_SHARE */
|
|
10915
|
+
);
|
|
8618
10916
|
}
|
|
8619
|
-
return data;
|
|
8620
10917
|
}
|
|
8621
|
-
|
|
8622
|
-
|
|
8623
|
-
|
|
8624
|
-
|
|
8625
|
-
|
|
8626
|
-
|
|
8627
|
-
|
|
8628
|
-
|
|
8629
|
-
|
|
8630
|
-
|
|
8631
|
-
|
|
8632
|
-
|
|
8633
|
-
|
|
8634
|
-
|
|
8635
|
-
|
|
8636
|
-
|
|
8637
|
-
"Purpose",
|
|
8638
|
-
"Memo"
|
|
8639
|
-
];
|
|
8640
|
-
const rows = transactions.map((tx) => [
|
|
8641
|
-
tx.transactionId,
|
|
8642
|
-
tx.disclosureId,
|
|
8643
|
-
tx.type,
|
|
8644
|
-
tx.direction,
|
|
8645
|
-
tx.token.symbol,
|
|
8646
|
-
tx.amount.toString(),
|
|
8647
|
-
tx.sender,
|
|
8648
|
-
tx.recipient,
|
|
8649
|
-
tx.chain,
|
|
8650
|
-
tx.privacyLevel,
|
|
8651
|
-
new Date(tx.timestamp * 1e3).toISOString(),
|
|
8652
|
-
tx.txHash,
|
|
8653
|
-
tx.blockNumber.toString(),
|
|
8654
|
-
tx.riskScore?.toString() ?? "",
|
|
8655
|
-
tx.purpose ?? "",
|
|
8656
|
-
tx.memo ?? ""
|
|
8657
|
-
]);
|
|
8658
|
-
const escapeForCSV = (val) => {
|
|
8659
|
-
let escaped = val;
|
|
8660
|
-
if (/^[=+\-@|\t]/.test(escaped)) {
|
|
8661
|
-
escaped = `'${escaped}`;
|
|
10918
|
+
/**
|
|
10919
|
+
* Lagrange interpolation to reconstruct secret
|
|
10920
|
+
* Evaluates polynomial at x=0 to get f(0) = secret
|
|
10921
|
+
*/
|
|
10922
|
+
static lagrangeInterpolate(shares) {
|
|
10923
|
+
let secret = 0n;
|
|
10924
|
+
for (let i = 0; i < shares.length; i++) {
|
|
10925
|
+
const xi = shares[i].x;
|
|
10926
|
+
const yi = shares[i].y;
|
|
10927
|
+
let numerator = 1n;
|
|
10928
|
+
let denominator = 1n;
|
|
10929
|
+
for (let j = 0; j < shares.length; j++) {
|
|
10930
|
+
if (i === j) continue;
|
|
10931
|
+
const xj = shares[j].x;
|
|
10932
|
+
numerator = this.mod(numerator * this.mod(-xj, FIELD_PRIME), FIELD_PRIME);
|
|
10933
|
+
denominator = this.mod(denominator * this.mod(xi - xj, FIELD_PRIME), FIELD_PRIME);
|
|
8662
10934
|
}
|
|
8663
|
-
|
|
8664
|
-
|
|
8665
|
-
|
|
8666
|
-
return
|
|
10935
|
+
const coeff = this.mod(numerator * this.modInverse(denominator, FIELD_PRIME), FIELD_PRIME);
|
|
10936
|
+
secret = this.mod(secret + this.mod(yi * coeff, FIELD_PRIME), FIELD_PRIME);
|
|
10937
|
+
}
|
|
10938
|
+
return secret;
|
|
8667
10939
|
}
|
|
8668
|
-
|
|
8669
|
-
|
|
8670
|
-
|
|
8671
|
-
|
|
8672
|
-
|
|
8673
|
-
if (!params.organization?.trim()) {
|
|
8674
|
-
throw new ValidationError(
|
|
8675
|
-
"organization is required",
|
|
8676
|
-
"organization",
|
|
8677
|
-
void 0,
|
|
8678
|
-
"SIP_2008" /* MISSING_REQUIRED */
|
|
8679
|
-
);
|
|
10940
|
+
/**
|
|
10941
|
+
* Modular arithmetic: a mod m
|
|
10942
|
+
*/
|
|
10943
|
+
static mod(a, m) {
|
|
10944
|
+
return (a % m + m) % m;
|
|
8680
10945
|
}
|
|
8681
|
-
|
|
8682
|
-
|
|
8683
|
-
|
|
8684
|
-
|
|
8685
|
-
|
|
8686
|
-
|
|
8687
|
-
)
|
|
10946
|
+
/**
|
|
10947
|
+
* Modular multiplicative inverse using Extended Euclidean Algorithm
|
|
10948
|
+
* Returns x such that (a * x) mod m = 1
|
|
10949
|
+
*/
|
|
10950
|
+
static modInverse(a, m) {
|
|
10951
|
+
const a0 = this.mod(a, m);
|
|
10952
|
+
if (a0 === 0n) {
|
|
10953
|
+
throw new CryptoError(
|
|
10954
|
+
"modular inverse does not exist (a = 0)",
|
|
10955
|
+
"SIP_3014" /* CRYPTO_OPERATION_FAILED */,
|
|
10956
|
+
{ operation: "modInverse" }
|
|
10957
|
+
);
|
|
10958
|
+
}
|
|
10959
|
+
let [old_r, r] = [a0, m];
|
|
10960
|
+
let [old_s, s] = [1n, 0n];
|
|
10961
|
+
while (r !== 0n) {
|
|
10962
|
+
const quotient = old_r / r;
|
|
10963
|
+
[old_r, r] = [r, old_r - quotient * r];
|
|
10964
|
+
[old_s, s] = [s, old_s - quotient * s];
|
|
10965
|
+
}
|
|
10966
|
+
if (old_r !== 1n) {
|
|
10967
|
+
throw new CryptoError(
|
|
10968
|
+
"modular inverse does not exist (gcd != 1)",
|
|
10969
|
+
"SIP_3014" /* CRYPTO_OPERATION_FAILED */,
|
|
10970
|
+
{ operation: "modInverse" }
|
|
10971
|
+
);
|
|
10972
|
+
}
|
|
10973
|
+
return this.mod(old_s, m);
|
|
8688
10974
|
}
|
|
8689
|
-
|
|
8690
|
-
|
|
8691
|
-
|
|
8692
|
-
|
|
8693
|
-
|
|
8694
|
-
|
|
8695
|
-
|
|
10975
|
+
};
|
|
10976
|
+
|
|
10977
|
+
// src/compliance/derivation.ts
|
|
10978
|
+
var import_sha25619 = require("@noble/hashes/sha256");
|
|
10979
|
+
var import_sha5123 = require("@noble/hashes/sha512");
|
|
10980
|
+
var import_hmac2 = require("@noble/hashes/hmac");
|
|
10981
|
+
var import_utils25 = require("@noble/hashes/utils");
|
|
10982
|
+
var AuditorType = /* @__PURE__ */ ((AuditorType2) => {
|
|
10983
|
+
AuditorType2[AuditorType2["PRIMARY"] = 0] = "PRIMARY";
|
|
10984
|
+
AuditorType2[AuditorType2["REGULATORY"] = 1] = "REGULATORY";
|
|
10985
|
+
AuditorType2[AuditorType2["INTERNAL"] = 2] = "INTERNAL";
|
|
10986
|
+
AuditorType2[AuditorType2["TAX"] = 3] = "TAX";
|
|
10987
|
+
return AuditorType2;
|
|
10988
|
+
})(AuditorType || {});
|
|
10989
|
+
var AuditorKeyDerivation = class {
|
|
10990
|
+
/**
|
|
10991
|
+
* SIP Protocol coin type (BIP-44 registered)
|
|
10992
|
+
*
|
|
10993
|
+
* Note: This is a placeholder. In production, register with SLIP-44:
|
|
10994
|
+
* https://github.com/satoshilabs/slips/blob/master/slip-0044.md
|
|
10995
|
+
*/
|
|
10996
|
+
static COIN_TYPE = 1234;
|
|
10997
|
+
/**
|
|
10998
|
+
* BIP-44 purpose field
|
|
10999
|
+
*/
|
|
11000
|
+
static PURPOSE = 44;
|
|
11001
|
+
/**
|
|
11002
|
+
* Hardened derivation flag (2^31)
|
|
11003
|
+
*/
|
|
11004
|
+
static HARDENED = 2147483648;
|
|
11005
|
+
/**
|
|
11006
|
+
* Generate BIP-44 derivation path
|
|
11007
|
+
*
|
|
11008
|
+
* @param auditorType - Type of auditor key
|
|
11009
|
+
* @param account - Account index (default: 0)
|
|
11010
|
+
* @returns BIP-44 style path string
|
|
11011
|
+
*
|
|
11012
|
+
* @example
|
|
11013
|
+
* ```typescript
|
|
11014
|
+
* AuditorKeyDerivation.derivePath(AuditorType.REGULATORY)
|
|
11015
|
+
* // Returns: "m/44'/1234'/0'/1"
|
|
11016
|
+
*
|
|
11017
|
+
* AuditorKeyDerivation.derivePath(AuditorType.TAX, 5)
|
|
11018
|
+
* // Returns: "m/44'/1234'/5'/3"
|
|
11019
|
+
* ```
|
|
11020
|
+
*/
|
|
11021
|
+
static derivePath(auditorType, account = 0) {
|
|
11022
|
+
this.validateAuditorType(auditorType);
|
|
11023
|
+
this.validateAccount(account);
|
|
11024
|
+
return `m/${this.PURPOSE}'/${this.COIN_TYPE}'/${account}'/${auditorType}`;
|
|
8696
11025
|
}
|
|
8697
|
-
|
|
8698
|
-
|
|
8699
|
-
|
|
8700
|
-
|
|
8701
|
-
|
|
8702
|
-
|
|
8703
|
-
|
|
11026
|
+
/**
|
|
11027
|
+
* Derive a viewing key for an auditor
|
|
11028
|
+
*
|
|
11029
|
+
* Uses BIP-32 style hierarchical deterministic key derivation:
|
|
11030
|
+
* 1. Derive master key from seed
|
|
11031
|
+
* 2. Harden purpose (44')
|
|
11032
|
+
* 3. Harden coin type (1234')
|
|
11033
|
+
* 4. Harden account index
|
|
11034
|
+
* 5. Derive auditor type (non-hardened)
|
|
11035
|
+
*
|
|
11036
|
+
* @param params - Derivation parameters
|
|
11037
|
+
* @returns Derived viewing key with metadata
|
|
11038
|
+
*
|
|
11039
|
+
* @throws {ValidationError} If parameters are invalid
|
|
11040
|
+
*
|
|
11041
|
+
* @example
|
|
11042
|
+
* ```typescript
|
|
11043
|
+
* const regulatoryKey = AuditorKeyDerivation.deriveViewingKey({
|
|
11044
|
+
* masterSeed: randomBytes(32),
|
|
11045
|
+
* auditorType: AuditorType.REGULATORY,
|
|
11046
|
+
* })
|
|
11047
|
+
*
|
|
11048
|
+
* console.log(regulatoryKey.path) // "m/44'/1234'/0'/1"
|
|
11049
|
+
* console.log(regulatoryKey.viewingKey.key) // "0x..."
|
|
11050
|
+
* ```
|
|
11051
|
+
*/
|
|
11052
|
+
static deriveViewingKey(params) {
|
|
11053
|
+
const { masterSeed, auditorType, account = 0 } = params;
|
|
11054
|
+
this.validateMasterSeed(masterSeed);
|
|
11055
|
+
this.validateAuditorType(auditorType);
|
|
11056
|
+
this.validateAccount(account);
|
|
11057
|
+
const path = this.derivePath(auditorType, account);
|
|
11058
|
+
const indices = [
|
|
11059
|
+
this.PURPOSE | this.HARDENED,
|
|
11060
|
+
// 44' (hardened)
|
|
11061
|
+
this.COIN_TYPE | this.HARDENED,
|
|
11062
|
+
// 1234' (hardened)
|
|
11063
|
+
account | this.HARDENED,
|
|
11064
|
+
// account' (hardened)
|
|
11065
|
+
auditorType
|
|
11066
|
+
// auditorType (non-hardened)
|
|
11067
|
+
];
|
|
11068
|
+
const masterData = (0, import_hmac2.hmac)(import_sha5123.sha512, (0, import_utils25.utf8ToBytes)("SIP-MASTER-SEED"), masterSeed);
|
|
11069
|
+
let currentKey = new Uint8Array(masterData.slice(0, 32));
|
|
11070
|
+
let chainCode = new Uint8Array(masterData.slice(32, 64));
|
|
11071
|
+
try {
|
|
11072
|
+
for (let i = 0; i < indices.length; i++) {
|
|
11073
|
+
const index = indices[i];
|
|
11074
|
+
const derived = this.deriveChildKey(currentKey, chainCode, index);
|
|
11075
|
+
if (i > 0) {
|
|
11076
|
+
secureWipe(currentKey);
|
|
11077
|
+
}
|
|
11078
|
+
currentKey = new Uint8Array(derived.key);
|
|
11079
|
+
chainCode = new Uint8Array(derived.chainCode);
|
|
11080
|
+
}
|
|
11081
|
+
const keyHex = `0x${(0, import_utils25.bytesToHex)(currentKey)}`;
|
|
11082
|
+
const hashBytes = (0, import_sha25619.sha256)(currentKey);
|
|
11083
|
+
const hash2 = `0x${(0, import_utils25.bytesToHex)(hashBytes)}`;
|
|
11084
|
+
const viewingKey = {
|
|
11085
|
+
key: keyHex,
|
|
11086
|
+
path,
|
|
11087
|
+
hash: hash2
|
|
11088
|
+
};
|
|
11089
|
+
return {
|
|
11090
|
+
path,
|
|
11091
|
+
viewingKey,
|
|
11092
|
+
auditorType,
|
|
11093
|
+
account
|
|
11094
|
+
};
|
|
11095
|
+
} finally {
|
|
11096
|
+
secureWipe(currentKey);
|
|
11097
|
+
secureWipe(chainCode);
|
|
11098
|
+
}
|
|
8704
11099
|
}
|
|
8705
|
-
|
|
8706
|
-
|
|
8707
|
-
|
|
8708
|
-
|
|
8709
|
-
|
|
8710
|
-
|
|
8711
|
-
|
|
11100
|
+
/**
|
|
11101
|
+
* Derive multiple viewing keys at once
|
|
11102
|
+
*
|
|
11103
|
+
* Efficiently derives keys for multiple auditor types from the same
|
|
11104
|
+
* master seed. This is more efficient than calling deriveViewingKey
|
|
11105
|
+
* multiple times as it reuses intermediate derivations.
|
|
11106
|
+
*
|
|
11107
|
+
* @param params - Derivation parameters
|
|
11108
|
+
* @returns Array of derived viewing keys
|
|
11109
|
+
*
|
|
11110
|
+
* @example
|
|
11111
|
+
* ```typescript
|
|
11112
|
+
* const keys = AuditorKeyDerivation.deriveMultiple({
|
|
11113
|
+
* masterSeed: randomBytes(32),
|
|
11114
|
+
* auditorTypes: [
|
|
11115
|
+
* AuditorType.PRIMARY,
|
|
11116
|
+
* AuditorType.REGULATORY,
|
|
11117
|
+
* AuditorType.INTERNAL,
|
|
11118
|
+
* ],
|
|
11119
|
+
* })
|
|
11120
|
+
*
|
|
11121
|
+
* // keys[0] -> PRIMARY key (m/44'/1234'/0'/0)
|
|
11122
|
+
* // keys[1] -> REGULATORY key (m/44'/1234'/0'/1)
|
|
11123
|
+
* // keys[2] -> INTERNAL key (m/44'/1234'/0'/2)
|
|
11124
|
+
* ```
|
|
11125
|
+
*/
|
|
11126
|
+
static deriveMultiple(params) {
|
|
11127
|
+
const { masterSeed, auditorTypes, account = 0 } = params;
|
|
11128
|
+
this.validateMasterSeed(masterSeed);
|
|
11129
|
+
this.validateAccount(account);
|
|
11130
|
+
if (!auditorTypes || auditorTypes.length === 0) {
|
|
11131
|
+
throw new ValidationError(
|
|
11132
|
+
"at least one auditor type is required",
|
|
11133
|
+
"auditorTypes",
|
|
11134
|
+
{ received: auditorTypes },
|
|
11135
|
+
"SIP_2008" /* MISSING_REQUIRED */
|
|
11136
|
+
);
|
|
11137
|
+
}
|
|
11138
|
+
for (const type of auditorTypes) {
|
|
11139
|
+
this.validateAuditorType(type);
|
|
11140
|
+
}
|
|
11141
|
+
const uniqueTypes = Array.from(new Set(auditorTypes));
|
|
11142
|
+
const commonIndices = [
|
|
11143
|
+
this.PURPOSE | this.HARDENED,
|
|
11144
|
+
// 44' (hardened)
|
|
11145
|
+
this.COIN_TYPE | this.HARDENED,
|
|
11146
|
+
// 1234' (hardened)
|
|
11147
|
+
account | this.HARDENED
|
|
11148
|
+
// account' (hardened)
|
|
11149
|
+
];
|
|
11150
|
+
const masterData = (0, import_hmac2.hmac)(import_sha5123.sha512, (0, import_utils25.utf8ToBytes)("SIP-MASTER-SEED"), masterSeed);
|
|
11151
|
+
let commonKey = new Uint8Array(masterData.slice(0, 32));
|
|
11152
|
+
let commonChainCode = new Uint8Array(masterData.slice(32, 64));
|
|
11153
|
+
try {
|
|
11154
|
+
for (let i = 0; i < commonIndices.length; i++) {
|
|
11155
|
+
const index = commonIndices[i];
|
|
11156
|
+
const derived = this.deriveChildKey(commonKey, commonChainCode, index);
|
|
11157
|
+
if (i > 0) {
|
|
11158
|
+
secureWipe(commonKey);
|
|
11159
|
+
}
|
|
11160
|
+
commonKey = new Uint8Array(derived.key);
|
|
11161
|
+
commonChainCode = new Uint8Array(derived.chainCode);
|
|
11162
|
+
}
|
|
11163
|
+
const results = [];
|
|
11164
|
+
for (const auditorType of uniqueTypes) {
|
|
11165
|
+
const derived = this.deriveChildKey(commonKey, commonChainCode, auditorType);
|
|
11166
|
+
try {
|
|
11167
|
+
const keyHex = `0x${(0, import_utils25.bytesToHex)(derived.key)}`;
|
|
11168
|
+
const hashBytes = (0, import_sha25619.sha256)(derived.key);
|
|
11169
|
+
const hash2 = `0x${(0, import_utils25.bytesToHex)(hashBytes)}`;
|
|
11170
|
+
const path = this.derivePath(auditorType, account);
|
|
11171
|
+
const viewingKey = {
|
|
11172
|
+
key: keyHex,
|
|
11173
|
+
path,
|
|
11174
|
+
hash: hash2
|
|
11175
|
+
};
|
|
11176
|
+
results.push({
|
|
11177
|
+
path,
|
|
11178
|
+
viewingKey,
|
|
11179
|
+
auditorType,
|
|
11180
|
+
account
|
|
11181
|
+
});
|
|
11182
|
+
} finally {
|
|
11183
|
+
secureWipe(derived.key);
|
|
11184
|
+
secureWipe(derived.chainCode);
|
|
11185
|
+
}
|
|
11186
|
+
}
|
|
11187
|
+
return results;
|
|
11188
|
+
} finally {
|
|
11189
|
+
secureWipe(commonKey);
|
|
11190
|
+
secureWipe(commonChainCode);
|
|
11191
|
+
}
|
|
8712
11192
|
}
|
|
8713
|
-
|
|
8714
|
-
|
|
8715
|
-
|
|
8716
|
-
|
|
8717
|
-
|
|
8718
|
-
|
|
8719
|
-
|
|
8720
|
-
|
|
8721
|
-
|
|
11193
|
+
/**
|
|
11194
|
+
* Get human-readable name for auditor type
|
|
11195
|
+
*
|
|
11196
|
+
* @param auditorType - Auditor type enum value
|
|
11197
|
+
* @returns Friendly name string
|
|
11198
|
+
*/
|
|
11199
|
+
static getAuditorTypeName(auditorType) {
|
|
11200
|
+
switch (auditorType) {
|
|
11201
|
+
case 0 /* PRIMARY */:
|
|
11202
|
+
return "Primary";
|
|
11203
|
+
case 1 /* REGULATORY */:
|
|
11204
|
+
return "Regulatory";
|
|
11205
|
+
case 2 /* INTERNAL */:
|
|
11206
|
+
return "Internal";
|
|
11207
|
+
case 3 /* TAX */:
|
|
11208
|
+
return "Tax Authority";
|
|
11209
|
+
default:
|
|
11210
|
+
return `Unknown (${auditorType})`;
|
|
11211
|
+
}
|
|
8722
11212
|
}
|
|
8723
|
-
|
|
8724
|
-
|
|
8725
|
-
|
|
8726
|
-
|
|
8727
|
-
|
|
8728
|
-
|
|
8729
|
-
|
|
11213
|
+
// ─── Private Helpers ─────────────────────────────────────────────────────────
|
|
11214
|
+
/**
|
|
11215
|
+
* Derive a child key using BIP-32 HMAC-SHA512 derivation
|
|
11216
|
+
*
|
|
11217
|
+
* @param parentKey - Parent key bytes (32 bytes)
|
|
11218
|
+
* @param chainCode - Parent chain code (32 bytes)
|
|
11219
|
+
* @param index - Child index (use | HARDENED for hardened derivation)
|
|
11220
|
+
* @returns Derived key and chain code
|
|
11221
|
+
*/
|
|
11222
|
+
static deriveChildKey(parentKey, chainCode, index) {
|
|
11223
|
+
const isHardened = (index & this.HARDENED) !== 0;
|
|
11224
|
+
const data = new Uint8Array(37);
|
|
11225
|
+
if (isHardened) {
|
|
11226
|
+
data[0] = 0;
|
|
11227
|
+
data.set(parentKey, 1);
|
|
11228
|
+
} else {
|
|
11229
|
+
data[0] = 1;
|
|
11230
|
+
data.set(parentKey, 1);
|
|
11231
|
+
}
|
|
11232
|
+
const indexView = new DataView(data.buffer, 33, 4);
|
|
11233
|
+
indexView.setUint32(0, index, false);
|
|
11234
|
+
const hmacResult = (0, import_hmac2.hmac)(import_sha5123.sha512, chainCode, data);
|
|
11235
|
+
const childKey = new Uint8Array(hmacResult.slice(0, 32));
|
|
11236
|
+
const childChainCode = new Uint8Array(hmacResult.slice(32, 64));
|
|
11237
|
+
return {
|
|
11238
|
+
key: childKey,
|
|
11239
|
+
chainCode: childChainCode
|
|
11240
|
+
};
|
|
8730
11241
|
}
|
|
8731
|
-
|
|
8732
|
-
|
|
8733
|
-
|
|
8734
|
-
|
|
8735
|
-
|
|
8736
|
-
|
|
8737
|
-
|
|
11242
|
+
/**
|
|
11243
|
+
* Validate master seed
|
|
11244
|
+
*/
|
|
11245
|
+
static validateMasterSeed(seed) {
|
|
11246
|
+
if (!seed || seed.length < 32) {
|
|
11247
|
+
throw new ValidationError(
|
|
11248
|
+
"master seed must be at least 32 bytes",
|
|
11249
|
+
"masterSeed",
|
|
11250
|
+
{ received: seed?.length ?? 0 },
|
|
11251
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
11252
|
+
);
|
|
11253
|
+
}
|
|
8738
11254
|
}
|
|
8739
|
-
|
|
8740
|
-
|
|
8741
|
-
|
|
8742
|
-
|
|
8743
|
-
|
|
8744
|
-
|
|
8745
|
-
|
|
11255
|
+
/**
|
|
11256
|
+
* Validate auditor type
|
|
11257
|
+
*/
|
|
11258
|
+
static validateAuditorType(type) {
|
|
11259
|
+
const validTypes = [
|
|
11260
|
+
0 /* PRIMARY */,
|
|
11261
|
+
1 /* REGULATORY */,
|
|
11262
|
+
2 /* INTERNAL */,
|
|
11263
|
+
3 /* TAX */
|
|
11264
|
+
];
|
|
11265
|
+
if (!validTypes.includes(type)) {
|
|
11266
|
+
throw new ValidationError(
|
|
11267
|
+
`invalid auditor type: ${type}`,
|
|
11268
|
+
"auditorType",
|
|
11269
|
+
{ received: type, valid: validTypes },
|
|
11270
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
11271
|
+
);
|
|
11272
|
+
}
|
|
8746
11273
|
}
|
|
8747
|
-
|
|
8748
|
-
|
|
8749
|
-
|
|
8750
|
-
|
|
8751
|
-
|
|
8752
|
-
|
|
8753
|
-
|
|
11274
|
+
/**
|
|
11275
|
+
* Validate account index
|
|
11276
|
+
*/
|
|
11277
|
+
static validateAccount(account) {
|
|
11278
|
+
if (!Number.isInteger(account) || account < 0 || account >= this.HARDENED) {
|
|
11279
|
+
throw new ValidationError(
|
|
11280
|
+
`account must be a non-negative integer less than ${this.HARDENED}`,
|
|
11281
|
+
"account",
|
|
11282
|
+
{ received: account },
|
|
11283
|
+
"SIP_2001" /* INVALID_INPUT */
|
|
11284
|
+
);
|
|
11285
|
+
}
|
|
8754
11286
|
}
|
|
8755
|
-
}
|
|
11287
|
+
};
|
|
8756
11288
|
|
|
8757
11289
|
// src/wallet/errors.ts
|
|
8758
11290
|
var import_types18 = require("@sip-protocol/types");
|
|
@@ -10911,6 +13443,30 @@ function createMockEthereumProvider(config = {}) {
|
|
|
10911
13443
|
return provider;
|
|
10912
13444
|
}
|
|
10913
13445
|
|
|
13446
|
+
// src/wallet/cosmos/adapter.ts
|
|
13447
|
+
var import_types29 = require("@sip-protocol/types");
|
|
13448
|
+
|
|
13449
|
+
// src/wallet/cosmos/mock.ts
|
|
13450
|
+
var import_types31 = require("@sip-protocol/types");
|
|
13451
|
+
|
|
13452
|
+
// src/wallet/bitcoin/adapter.ts
|
|
13453
|
+
var import_types34 = require("@sip-protocol/types");
|
|
13454
|
+
|
|
13455
|
+
// src/wallet/bitcoin/mock.ts
|
|
13456
|
+
var import_types36 = require("@sip-protocol/types");
|
|
13457
|
+
|
|
13458
|
+
// src/wallet/aptos/adapter.ts
|
|
13459
|
+
var import_types39 = require("@sip-protocol/types");
|
|
13460
|
+
|
|
13461
|
+
// src/wallet/aptos/mock.ts
|
|
13462
|
+
var import_types41 = require("@sip-protocol/types");
|
|
13463
|
+
|
|
13464
|
+
// src/wallet/sui/adapter.ts
|
|
13465
|
+
var import_types43 = require("@sip-protocol/types");
|
|
13466
|
+
|
|
13467
|
+
// src/wallet/sui/mock.ts
|
|
13468
|
+
var import_types45 = require("@sip-protocol/types");
|
|
13469
|
+
|
|
10914
13470
|
// src/wallet/hardware/types.ts
|
|
10915
13471
|
var DerivationPath = {
|
|
10916
13472
|
/** Ethereum: m/44'/60'/0'/0/index */
|
|
@@ -10986,7 +13542,7 @@ function getAvailableTransports() {
|
|
|
10986
13542
|
}
|
|
10987
13543
|
|
|
10988
13544
|
// src/wallet/hardware/ledger.ts
|
|
10989
|
-
var
|
|
13545
|
+
var import_types47 = require("@sip-protocol/types");
|
|
10990
13546
|
var LedgerWalletAdapter = class extends BaseWalletAdapter {
|
|
10991
13547
|
chain;
|
|
10992
13548
|
name = "ledger";
|
|
@@ -11139,7 +13695,7 @@ var LedgerWalletAdapter = class extends BaseWalletAdapter {
|
|
|
11139
13695
|
async getBalance() {
|
|
11140
13696
|
throw new WalletError(
|
|
11141
13697
|
"Hardware wallets do not track balances. Use an RPC provider.",
|
|
11142
|
-
|
|
13698
|
+
import_types47.WalletErrorCode.UNSUPPORTED_OPERATION
|
|
11143
13699
|
);
|
|
11144
13700
|
}
|
|
11145
13701
|
/**
|
|
@@ -11150,7 +13706,7 @@ var LedgerWalletAdapter = class extends BaseWalletAdapter {
|
|
|
11150
13706
|
async getTokenBalance(_asset) {
|
|
11151
13707
|
throw new WalletError(
|
|
11152
13708
|
"Hardware wallets do not track balances. Use an RPC provider.",
|
|
11153
|
-
|
|
13709
|
+
import_types47.WalletErrorCode.UNSUPPORTED_OPERATION
|
|
11154
13710
|
);
|
|
11155
13711
|
}
|
|
11156
13712
|
// ─── Account Management ─────────────────────────────────────────────────────
|
|
@@ -11438,7 +13994,7 @@ function createLedgerAdapter(config) {
|
|
|
11438
13994
|
}
|
|
11439
13995
|
|
|
11440
13996
|
// src/wallet/hardware/trezor.ts
|
|
11441
|
-
var
|
|
13997
|
+
var import_types49 = require("@sip-protocol/types");
|
|
11442
13998
|
var TrezorWalletAdapter = class extends BaseWalletAdapter {
|
|
11443
13999
|
chain;
|
|
11444
14000
|
name = "trezor";
|
|
@@ -11584,7 +14140,7 @@ var TrezorWalletAdapter = class extends BaseWalletAdapter {
|
|
|
11584
14140
|
async getBalance() {
|
|
11585
14141
|
throw new WalletError(
|
|
11586
14142
|
"Hardware wallets do not track balances. Use an RPC provider.",
|
|
11587
|
-
|
|
14143
|
+
import_types49.WalletErrorCode.UNSUPPORTED_OPERATION
|
|
11588
14144
|
);
|
|
11589
14145
|
}
|
|
11590
14146
|
/**
|
|
@@ -11595,7 +14151,7 @@ var TrezorWalletAdapter = class extends BaseWalletAdapter {
|
|
|
11595
14151
|
async getTokenBalance(_asset) {
|
|
11596
14152
|
throw new WalletError(
|
|
11597
14153
|
"Hardware wallets do not track balances. Use an RPC provider.",
|
|
11598
|
-
|
|
14154
|
+
import_types49.WalletErrorCode.UNSUPPORTED_OPERATION
|
|
11599
14155
|
);
|
|
11600
14156
|
}
|
|
11601
14157
|
// ─── Account Management ─────────────────────────────────────────────────────
|
|
@@ -11876,8 +14432,8 @@ function createTrezorAdapter(config) {
|
|
|
11876
14432
|
}
|
|
11877
14433
|
|
|
11878
14434
|
// src/wallet/hardware/mock.ts
|
|
11879
|
-
var
|
|
11880
|
-
var
|
|
14435
|
+
var import_types51 = require("@sip-protocol/types");
|
|
14436
|
+
var import_utils26 = require("@noble/hashes/utils");
|
|
11881
14437
|
var MockLedgerAdapter = class extends BaseWalletAdapter {
|
|
11882
14438
|
chain;
|
|
11883
14439
|
name = "mock-ledger";
|
|
@@ -12024,7 +14580,7 @@ var MockLedgerAdapter = class extends BaseWalletAdapter {
|
|
|
12024
14580
|
async getBalance() {
|
|
12025
14581
|
throw new WalletError(
|
|
12026
14582
|
"Hardware wallets do not track balances",
|
|
12027
|
-
|
|
14583
|
+
import_types51.WalletErrorCode.UNSUPPORTED_OPERATION
|
|
12028
14584
|
);
|
|
12029
14585
|
}
|
|
12030
14586
|
/**
|
|
@@ -12033,7 +14589,7 @@ var MockLedgerAdapter = class extends BaseWalletAdapter {
|
|
|
12033
14589
|
async getTokenBalance(_asset) {
|
|
12034
14590
|
throw new WalletError(
|
|
12035
14591
|
"Hardware wallets do not track balances",
|
|
12036
|
-
|
|
14592
|
+
import_types51.WalletErrorCode.UNSUPPORTED_OPERATION
|
|
12037
14593
|
);
|
|
12038
14594
|
}
|
|
12039
14595
|
/**
|
|
@@ -12122,15 +14678,15 @@ var MockLedgerAdapter = class extends BaseWalletAdapter {
|
|
|
12122
14678
|
}
|
|
12123
14679
|
}
|
|
12124
14680
|
generateMockAddress(index) {
|
|
12125
|
-
const bytes = (0,
|
|
14681
|
+
const bytes = (0, import_utils26.randomBytes)(20);
|
|
12126
14682
|
bytes[0] = index;
|
|
12127
|
-
return `0x${(0,
|
|
14683
|
+
return `0x${(0, import_utils26.bytesToHex)(bytes)}`;
|
|
12128
14684
|
}
|
|
12129
14685
|
generateMockPublicKey(index) {
|
|
12130
|
-
const bytes = (0,
|
|
14686
|
+
const bytes = (0, import_utils26.randomBytes)(33);
|
|
12131
14687
|
bytes[0] = 2;
|
|
12132
14688
|
bytes[1] = index;
|
|
12133
|
-
return `0x${(0,
|
|
14689
|
+
return `0x${(0, import_utils26.bytesToHex)(bytes)}`;
|
|
12134
14690
|
}
|
|
12135
14691
|
generateMockSignature(data) {
|
|
12136
14692
|
const sig = new Uint8Array(65);
|
|
@@ -12139,7 +14695,7 @@ var MockLedgerAdapter = class extends BaseWalletAdapter {
|
|
|
12139
14695
|
sig[32 + i] = (data[i % data.length] ?? 0) ^ i * 11;
|
|
12140
14696
|
}
|
|
12141
14697
|
sig[64] = 27;
|
|
12142
|
-
return `0x${(0,
|
|
14698
|
+
return `0x${(0, import_utils26.bytesToHex)(sig)}`;
|
|
12143
14699
|
}
|
|
12144
14700
|
delay(ms) {
|
|
12145
14701
|
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
@@ -12263,13 +14819,13 @@ var MockTrezorAdapter = class extends BaseWalletAdapter {
|
|
|
12263
14819
|
async getBalance() {
|
|
12264
14820
|
throw new WalletError(
|
|
12265
14821
|
"Hardware wallets do not track balances",
|
|
12266
|
-
|
|
14822
|
+
import_types51.WalletErrorCode.UNSUPPORTED_OPERATION
|
|
12267
14823
|
);
|
|
12268
14824
|
}
|
|
12269
14825
|
async getTokenBalance(_asset) {
|
|
12270
14826
|
throw new WalletError(
|
|
12271
14827
|
"Hardware wallets do not track balances",
|
|
12272
|
-
|
|
14828
|
+
import_types51.WalletErrorCode.UNSUPPORTED_OPERATION
|
|
12273
14829
|
);
|
|
12274
14830
|
}
|
|
12275
14831
|
async getAccounts(startIndex = 0, count = 5) {
|
|
@@ -12328,15 +14884,15 @@ var MockTrezorAdapter = class extends BaseWalletAdapter {
|
|
|
12328
14884
|
}
|
|
12329
14885
|
}
|
|
12330
14886
|
generateMockAddress(index) {
|
|
12331
|
-
const bytes = (0,
|
|
14887
|
+
const bytes = (0, import_utils26.randomBytes)(20);
|
|
12332
14888
|
bytes[0] = index + 100;
|
|
12333
|
-
return `0x${(0,
|
|
14889
|
+
return `0x${(0, import_utils26.bytesToHex)(bytes)}`;
|
|
12334
14890
|
}
|
|
12335
14891
|
generateMockPublicKey(index) {
|
|
12336
|
-
const bytes = (0,
|
|
14892
|
+
const bytes = (0, import_utils26.randomBytes)(33);
|
|
12337
14893
|
bytes[0] = 3;
|
|
12338
14894
|
bytes[1] = index + 100;
|
|
12339
|
-
return `0x${(0,
|
|
14895
|
+
return `0x${(0, import_utils26.bytesToHex)(bytes)}`;
|
|
12340
14896
|
}
|
|
12341
14897
|
generateMockSignature(data) {
|
|
12342
14898
|
const sig = new Uint8Array(65);
|
|
@@ -12345,7 +14901,7 @@ var MockTrezorAdapter = class extends BaseWalletAdapter {
|
|
|
12345
14901
|
sig[32 + i] = (data[i % data.length] ?? 0) ^ i * 17;
|
|
12346
14902
|
}
|
|
12347
14903
|
sig[64] = 28;
|
|
12348
|
-
return `0x${(0,
|
|
14904
|
+
return `0x${(0, import_utils26.bytesToHex)(sig)}`;
|
|
12349
14905
|
}
|
|
12350
14906
|
delay(ms) {
|
|
12351
14907
|
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
@@ -12359,12 +14915,12 @@ function createMockTrezorAdapter(config) {
|
|
|
12359
14915
|
}
|
|
12360
14916
|
|
|
12361
14917
|
// src/wallet/index.ts
|
|
12362
|
-
var
|
|
14918
|
+
var import_types54 = require("@sip-protocol/types");
|
|
12363
14919
|
|
|
12364
14920
|
// src/proofs/browser.ts
|
|
12365
14921
|
var import_noir_js = require("@noir-lang/noir_js");
|
|
12366
14922
|
var import_bb = require("@aztec/bb.js");
|
|
12367
|
-
var
|
|
14923
|
+
var import_secp256k18 = require("@noble/curves/secp256k1");
|
|
12368
14924
|
|
|
12369
14925
|
// src/proofs/circuits/funding_proof.json
|
|
12370
14926
|
var funding_proof_default = { noir_version: "1.0.0-beta.15+83245db91dcf63420ef4bcbbd85b98f397fee663", hash: "3859649086066977477", abi: { parameters: [{ name: "minimum_required", type: { kind: "integer", sign: "unsigned", width: 64 }, visibility: "public" }, { name: "asset_id", type: { kind: "field" }, visibility: "public" }, { name: "balance", type: { kind: "integer", sign: "unsigned", width: 64 }, visibility: "private" }, { name: "blinding", type: { kind: "field" }, visibility: "private" }], return_type: { abi_type: { kind: "array", length: 32, type: { kind: "integer", sign: "unsigned", width: 8 } }, visibility: "public" }, error_types: { "2900908756532713827": { error_kind: "string", string: "Insufficient balance" }, "15764276373176857197": { error_kind: "string", string: "Stack too deep" }, "15835548349546956319": { error_kind: "string", string: "Field failed to decompose into specified 32 limbs" } } }, bytecode: "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", debug_symbols: "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", file_map: { "17": { source: `use crate::field::field_less_than;
|
|
@@ -13377,7 +15933,7 @@ var BrowserNoirProvider = class _BrowserNoirProvider {
|
|
|
13377
15933
|
* Derive secp256k1 public key coordinates from a private key
|
|
13378
15934
|
*/
|
|
13379
15935
|
static derivePublicKey(privateKey) {
|
|
13380
|
-
const uncompressedPubKey =
|
|
15936
|
+
const uncompressedPubKey = import_secp256k18.secp256k1.getPublicKey(privateKey, false);
|
|
13381
15937
|
const x = Array.from(uncompressedPubKey.slice(1, 33));
|
|
13382
15938
|
const y = Array.from(uncompressedPubKey.slice(33, 65));
|
|
13383
15939
|
return { x, y };
|
|
@@ -13590,7 +16146,7 @@ var BrowserNoirProvider = class _BrowserNoirProvider {
|
|
|
13590
16146
|
message: "Proof generated successfully"
|
|
13591
16147
|
});
|
|
13592
16148
|
const commitmentHashBytes = returnValue;
|
|
13593
|
-
const commitmentHashHex =
|
|
16149
|
+
const commitmentHashHex = bytesToHex11(new Uint8Array(commitmentHashBytes));
|
|
13594
16150
|
const publicInputs = [
|
|
13595
16151
|
`0x${params.minimumRequired.toString(16).padStart(16, "0")}`,
|
|
13596
16152
|
`0x${this.assetIdToField(params.assetId)}`,
|
|
@@ -13598,7 +16154,7 @@ var BrowserNoirProvider = class _BrowserNoirProvider {
|
|
|
13598
16154
|
];
|
|
13599
16155
|
const proof = {
|
|
13600
16156
|
type: "funding",
|
|
13601
|
-
proof: `0x${
|
|
16157
|
+
proof: `0x${bytesToHex11(proofData.proof)}`,
|
|
13602
16158
|
publicInputs
|
|
13603
16159
|
};
|
|
13604
16160
|
return { proof, publicInputs };
|
|
@@ -13692,7 +16248,7 @@ var BrowserNoirProvider = class _BrowserNoirProvider {
|
|
|
13692
16248
|
];
|
|
13693
16249
|
const proof = {
|
|
13694
16250
|
type: "validity",
|
|
13695
|
-
proof: `0x${
|
|
16251
|
+
proof: `0x${bytesToHex11(proofData.proof)}`,
|
|
13696
16252
|
publicInputs
|
|
13697
16253
|
};
|
|
13698
16254
|
return { proof, publicInputs };
|
|
@@ -13792,7 +16348,7 @@ var BrowserNoirProvider = class _BrowserNoirProvider {
|
|
|
13792
16348
|
];
|
|
13793
16349
|
const proof = {
|
|
13794
16350
|
type: "fulfillment",
|
|
13795
|
-
proof: `0x${
|
|
16351
|
+
proof: `0x${bytesToHex11(proofData.proof)}`,
|
|
13796
16352
|
publicInputs
|
|
13797
16353
|
};
|
|
13798
16354
|
return { proof, publicInputs };
|
|
@@ -13832,7 +16388,7 @@ var BrowserNoirProvider = class _BrowserNoirProvider {
|
|
|
13832
16388
|
}
|
|
13833
16389
|
try {
|
|
13834
16390
|
const proofHex = proof.proof.startsWith("0x") ? proof.proof.slice(2) : proof.proof;
|
|
13835
|
-
const proofBytes =
|
|
16391
|
+
const proofBytes = hexToBytes9(proofHex);
|
|
13836
16392
|
const isValid = await backend.verifyProof({
|
|
13837
16393
|
proof: proofBytes,
|
|
13838
16394
|
publicInputs: proof.publicInputs.map(
|
|
@@ -13883,14 +16439,14 @@ var BrowserNoirProvider = class _BrowserNoirProvider {
|
|
|
13883
16439
|
}
|
|
13884
16440
|
async computeCommitmentHash(balance, blindingFactor, assetId) {
|
|
13885
16441
|
const blindingField = this.bytesToField(blindingFactor);
|
|
13886
|
-
const { sha256:
|
|
16442
|
+
const { sha256: sha25620 } = await import("@noble/hashes/sha256");
|
|
13887
16443
|
const { bytesToHex: nobleToHex } = await import("@noble/hashes/utils");
|
|
13888
16444
|
const preimage = new Uint8Array([
|
|
13889
16445
|
...this.bigintToBytes(balance, 8),
|
|
13890
16446
|
...blindingFactor.slice(0, 32),
|
|
13891
|
-
...
|
|
16447
|
+
...hexToBytes9(this.assetIdToField(assetId))
|
|
13892
16448
|
]);
|
|
13893
|
-
const hash2 =
|
|
16449
|
+
const hash2 = sha25620(preimage);
|
|
13894
16450
|
const commitmentHash = nobleToHex(hash2);
|
|
13895
16451
|
return { commitmentHash, blindingField };
|
|
13896
16452
|
}
|
|
@@ -13936,49 +16492,49 @@ var BrowserNoirProvider = class _BrowserNoirProvider {
|
|
|
13936
16492
|
return bytes;
|
|
13937
16493
|
}
|
|
13938
16494
|
async computeSenderCommitment(senderAddressField, senderBlindingField) {
|
|
13939
|
-
const { sha256:
|
|
16495
|
+
const { sha256: sha25620 } = await import("@noble/hashes/sha256");
|
|
13940
16496
|
const { bytesToHex: nobleToHex } = await import("@noble/hashes/utils");
|
|
13941
|
-
const addressBytes =
|
|
13942
|
-
const blindingBytes =
|
|
16497
|
+
const addressBytes = hexToBytes9(senderAddressField);
|
|
16498
|
+
const blindingBytes = hexToBytes9(senderBlindingField.padStart(64, "0"));
|
|
13943
16499
|
const preimage = new Uint8Array([...addressBytes, ...blindingBytes]);
|
|
13944
|
-
const hash2 =
|
|
16500
|
+
const hash2 = sha25620(preimage);
|
|
13945
16501
|
const commitmentX = nobleToHex(hash2.slice(0, 16)).padStart(64, "0");
|
|
13946
16502
|
const commitmentY = nobleToHex(hash2.slice(16, 32)).padStart(64, "0");
|
|
13947
16503
|
return { commitmentX, commitmentY };
|
|
13948
16504
|
}
|
|
13949
16505
|
async computeNullifier(senderSecretField, intentHashField, nonceField) {
|
|
13950
|
-
const { sha256:
|
|
16506
|
+
const { sha256: sha25620 } = await import("@noble/hashes/sha256");
|
|
13951
16507
|
const { bytesToHex: nobleToHex } = await import("@noble/hashes/utils");
|
|
13952
|
-
const secretBytes =
|
|
13953
|
-
const intentBytes =
|
|
13954
|
-
const nonceBytes =
|
|
16508
|
+
const secretBytes = hexToBytes9(senderSecretField.padStart(64, "0"));
|
|
16509
|
+
const intentBytes = hexToBytes9(intentHashField);
|
|
16510
|
+
const nonceBytes = hexToBytes9(nonceField.padStart(64, "0"));
|
|
13955
16511
|
const preimage = new Uint8Array([...secretBytes, ...intentBytes, ...nonceBytes]);
|
|
13956
|
-
const hash2 =
|
|
16512
|
+
const hash2 = sha25620(preimage);
|
|
13957
16513
|
return nobleToHex(hash2);
|
|
13958
16514
|
}
|
|
13959
16515
|
async computeOutputCommitment(outputAmount, outputBlinding) {
|
|
13960
|
-
const { sha256:
|
|
16516
|
+
const { sha256: sha25620 } = await import("@noble/hashes/sha256");
|
|
13961
16517
|
const { bytesToHex: nobleToHex } = await import("@noble/hashes/utils");
|
|
13962
16518
|
const amountBytes = this.bigintToBytes(outputAmount, 8);
|
|
13963
16519
|
const blindingBytes = outputBlinding.slice(0, 32);
|
|
13964
16520
|
const preimage = new Uint8Array([...amountBytes, ...blindingBytes]);
|
|
13965
|
-
const hash2 =
|
|
16521
|
+
const hash2 = sha25620(preimage);
|
|
13966
16522
|
const commitmentX = nobleToHex(hash2.slice(0, 16)).padStart(64, "0");
|
|
13967
16523
|
const commitmentY = nobleToHex(hash2.slice(16, 32)).padStart(64, "0");
|
|
13968
16524
|
return { commitmentX, commitmentY };
|
|
13969
16525
|
}
|
|
13970
16526
|
async computeSolverId(solverSecretField) {
|
|
13971
|
-
const { sha256:
|
|
16527
|
+
const { sha256: sha25620 } = await import("@noble/hashes/sha256");
|
|
13972
16528
|
const { bytesToHex: nobleToHex } = await import("@noble/hashes/utils");
|
|
13973
|
-
const secretBytes =
|
|
13974
|
-
const hash2 =
|
|
16529
|
+
const secretBytes = hexToBytes9(solverSecretField.padStart(64, "0"));
|
|
16530
|
+
const hash2 = sha25620(secretBytes);
|
|
13975
16531
|
return nobleToHex(hash2);
|
|
13976
16532
|
}
|
|
13977
16533
|
async computeOracleMessageHash(recipient, amount, txHash, blockNumber) {
|
|
13978
|
-
const { sha256:
|
|
13979
|
-
const recipientBytes =
|
|
16534
|
+
const { sha256: sha25620 } = await import("@noble/hashes/sha256");
|
|
16535
|
+
const recipientBytes = hexToBytes9(this.hexToField(recipient));
|
|
13980
16536
|
const amountBytes = this.bigintToBytes(amount, 8);
|
|
13981
|
-
const txHashBytes =
|
|
16537
|
+
const txHashBytes = hexToBytes9(this.hexToField(txHash));
|
|
13982
16538
|
const blockBytes = this.bigintToBytes(blockNumber, 8);
|
|
13983
16539
|
const preimage = new Uint8Array([
|
|
13984
16540
|
...recipientBytes,
|
|
@@ -13986,11 +16542,11 @@ var BrowserNoirProvider = class _BrowserNoirProvider {
|
|
|
13986
16542
|
...txHashBytes,
|
|
13987
16543
|
...blockBytes
|
|
13988
16544
|
]);
|
|
13989
|
-
const hash2 =
|
|
16545
|
+
const hash2 = sha25620(preimage);
|
|
13990
16546
|
return Array.from(hash2);
|
|
13991
16547
|
}
|
|
13992
16548
|
getPublicKeyCoordinates(privateKey) {
|
|
13993
|
-
const uncompressedPubKey =
|
|
16549
|
+
const uncompressedPubKey = import_secp256k18.secp256k1.getPublicKey(privateKey, false);
|
|
13994
16550
|
const x = Array.from(uncompressedPubKey.slice(1, 33));
|
|
13995
16551
|
const y = Array.from(uncompressedPubKey.slice(33, 65));
|
|
13996
16552
|
return { x, y };
|
|
@@ -14543,10 +17099,17 @@ var ProofWorker = class _ProofWorker {
|
|
|
14543
17099
|
// Annotate the CommonJS export names for ESM import in node:
|
|
14544
17100
|
0 && (module.exports = {
|
|
14545
17101
|
ATTESTATION_VERSION,
|
|
17102
|
+
AptosStealthService,
|
|
17103
|
+
AuditorKeyDerivation,
|
|
17104
|
+
AuditorType,
|
|
14546
17105
|
BaseWalletAdapter,
|
|
14547
17106
|
BrowserNoirProvider,
|
|
14548
17107
|
CHAIN_NUMERIC_IDS,
|
|
17108
|
+
COSMOS_CHAIN_PREFIXES,
|
|
14549
17109
|
ComplianceManager,
|
|
17110
|
+
ComplianceReporter,
|
|
17111
|
+
ConditionalDisclosure,
|
|
17112
|
+
CosmosStealthService,
|
|
14550
17113
|
CryptoError,
|
|
14551
17114
|
DEFAULT_THRESHOLD,
|
|
14552
17115
|
DEFAULT_TOTAL_ORACLES,
|
|
@@ -14598,6 +17161,7 @@ var ProofWorker = class _ProofWorker {
|
|
|
14598
17161
|
SmartRouter,
|
|
14599
17162
|
SolanaWalletAdapter,
|
|
14600
17163
|
SwapStatus,
|
|
17164
|
+
ThresholdViewingKey,
|
|
14601
17165
|
Treasury,
|
|
14602
17166
|
TrezorWalletAdapter,
|
|
14603
17167
|
ValidationError,
|
|
@@ -14612,18 +17176,22 @@ var ProofWorker = class _ProofWorker {
|
|
|
14612
17176
|
addBlindings,
|
|
14613
17177
|
addCommitments,
|
|
14614
17178
|
addOracle,
|
|
17179
|
+
aptosAddressToAuthKey,
|
|
14615
17180
|
attachProofs,
|
|
14616
17181
|
base58ToHex,
|
|
14617
17182
|
browserBytesToHex,
|
|
14618
17183
|
browserHexToBytes,
|
|
17184
|
+
checkAptosStealthAddress,
|
|
14619
17185
|
checkEd25519StealthAddress,
|
|
14620
17186
|
checkMobileWASMCompatibility,
|
|
14621
17187
|
checkStealthAddress,
|
|
14622
17188
|
commit,
|
|
14623
17189
|
commitZero,
|
|
14624
17190
|
computeAttestationHash,
|
|
17191
|
+
computeTweakedKey,
|
|
14625
17192
|
createCommitment,
|
|
14626
17193
|
createEthereumAdapter,
|
|
17194
|
+
createKeySpendOnlyOutput,
|
|
14627
17195
|
createLedgerAdapter,
|
|
14628
17196
|
createMockEthereumAdapter,
|
|
14629
17197
|
createMockEthereumProvider,
|
|
@@ -14642,6 +17210,7 @@ var ProofWorker = class _ProofWorker {
|
|
|
14642
17210
|
createShieldedPayment,
|
|
14643
17211
|
createSmartRouter,
|
|
14644
17212
|
createSolanaAdapter,
|
|
17213
|
+
createTaprootOutput,
|
|
14645
17214
|
createTrezorAdapter,
|
|
14646
17215
|
createWalletFactory,
|
|
14647
17216
|
createWorkerBlobURL,
|
|
@@ -14650,8 +17219,10 @@ var ProofWorker = class _ProofWorker {
|
|
|
14650
17219
|
createZcashShieldedService,
|
|
14651
17220
|
createZcashSwapService,
|
|
14652
17221
|
decodeStealthMetaAddress,
|
|
17222
|
+
decodeTaprootAddress,
|
|
14653
17223
|
decryptMemo,
|
|
14654
17224
|
decryptWithViewing,
|
|
17225
|
+
deriveAptosStealthPrivateKey,
|
|
14655
17226
|
deriveEd25519StealthPrivateKey,
|
|
14656
17227
|
deriveOracleId,
|
|
14657
17228
|
deriveStealthPrivateKey,
|
|
@@ -14663,6 +17234,7 @@ var ProofWorker = class _ProofWorker {
|
|
|
14663
17234
|
detectMobileBrowser,
|
|
14664
17235
|
detectMobilePlatform,
|
|
14665
17236
|
detectSolanaWallets,
|
|
17237
|
+
ed25519PublicKeyToAptosAddress,
|
|
14666
17238
|
ed25519PublicKeyToNearAddress,
|
|
14667
17239
|
ed25519PublicKeyToSolanaAddress,
|
|
14668
17240
|
encodeStealthMetaAddress,
|
|
@@ -14671,10 +17243,14 @@ var ProofWorker = class _ProofWorker {
|
|
|
14671
17243
|
formatStablecoinAmount,
|
|
14672
17244
|
fromHex,
|
|
14673
17245
|
fromStablecoinUnits,
|
|
17246
|
+
generateAptosStealthAddress,
|
|
14674
17247
|
generateBlinding,
|
|
17248
|
+
generateCosmosStealthAddress,
|
|
17249
|
+
generateCosmosStealthMetaAddress,
|
|
14675
17250
|
generateEd25519StealthAddress,
|
|
14676
17251
|
generateEd25519StealthMetaAddress,
|
|
14677
17252
|
generateIntentId,
|
|
17253
|
+
generatePdfReport,
|
|
14678
17254
|
generateRandomBytes,
|
|
14679
17255
|
generateStealthAddress,
|
|
14680
17256
|
generateStealthMetaAddress,
|
|
@@ -14704,6 +17280,7 @@ var ProofWorker = class _ProofWorker {
|
|
|
14704
17280
|
getStablecoinsForChain,
|
|
14705
17281
|
getSupportedStablecoins,
|
|
14706
17282
|
getTimeRemaining,
|
|
17283
|
+
getXOnlyPublicKey,
|
|
14707
17284
|
hasEnoughOracles,
|
|
14708
17285
|
hasErrorCode,
|
|
14709
17286
|
hasRequiredProofs,
|
|
@@ -14721,8 +17298,10 @@ var ProofWorker = class _ProofWorker {
|
|
|
14721
17298
|
isStablecoinOnChain,
|
|
14722
17299
|
isTablet,
|
|
14723
17300
|
isValidAmount,
|
|
17301
|
+
isValidAptosAddress,
|
|
14724
17302
|
isValidChainId,
|
|
14725
17303
|
isValidCompressedPublicKey,
|
|
17304
|
+
isValidCosmosAddress,
|
|
14726
17305
|
isValidEd25519PublicKey,
|
|
14727
17306
|
isValidHex,
|
|
14728
17307
|
isValidHexLength,
|
|
@@ -14734,12 +17313,17 @@ var ProofWorker = class _ProofWorker {
|
|
|
14734
17313
|
isValidSlippage,
|
|
14735
17314
|
isValidSolanaAddress,
|
|
14736
17315
|
isValidStealthMetaAddress,
|
|
17316
|
+
isValidTaprootAddress,
|
|
14737
17317
|
nearAddressToEd25519PublicKey,
|
|
14738
17318
|
normalizeAddress,
|
|
14739
17319
|
notConnectedError,
|
|
14740
17320
|
publicKeyToEthAddress,
|
|
14741
17321
|
registerWallet,
|
|
14742
17322
|
removeOracle,
|
|
17323
|
+
schnorrSign,
|
|
17324
|
+
schnorrSignHex,
|
|
17325
|
+
schnorrVerify,
|
|
17326
|
+
schnorrVerifyHex,
|
|
14743
17327
|
secureWipe,
|
|
14744
17328
|
secureWipeAll,
|
|
14745
17329
|
serializeAttestationMessage,
|
|
@@ -14748,6 +17332,7 @@ var ProofWorker = class _ProofWorker {
|
|
|
14748
17332
|
signAttestationMessage,
|
|
14749
17333
|
solanaAddressToEd25519PublicKey,
|
|
14750
17334
|
solanaPublicKeyToHex,
|
|
17335
|
+
stealthKeyToCosmosAddress,
|
|
14751
17336
|
subtractBlindings,
|
|
14752
17337
|
subtractCommitments,
|
|
14753
17338
|
supportsSharedArrayBuffer,
|
|
@@ -14759,6 +17344,7 @@ var ProofWorker = class _ProofWorker {
|
|
|
14759
17344
|
supportsWebHID,
|
|
14760
17345
|
supportsWebUSB,
|
|
14761
17346
|
supportsWebWorkers,
|
|
17347
|
+
taprootAddress,
|
|
14762
17348
|
toHex,
|
|
14763
17349
|
toStablecoinUnits,
|
|
14764
17350
|
trackIntent,
|