@gvnrdao/dh-lit-actions 0.0.81 → 0.0.82
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/package.json +1 -1
- package/pkg-dist/pkg-src/constants/chunks/lit-actions-registry.d.ts +1 -9
- package/pkg-dist/pkg-src/constants/chunks/lit-actions-registry.d.ts.map +1 -1
- package/pkg-dist/pkg-src/constants/chunks/lit-actions-registry.js +114 -173
- package/pkg-dist/pkg-src/constants/chunks/lit-actions-registry.js.map +1 -1
- package/pkg-dist/pkg-src/constants/chunks/package-registry.d.ts.map +1 -1
- package/pkg-dist/pkg-src/constants/chunks/package-registry.js +0 -2
- package/pkg-dist/pkg-src/constants/chunks/package-registry.js.map +1 -1
- package/pkg-dist/pkg-src/interfaces/chunks/diamond-hands-lit-actions.i.d.ts +6 -0
- package/pkg-dist/pkg-src/interfaces/chunks/diamond-hands-lit-actions.i.d.ts.map +1 -1
- package/pkg-dist/pkg-src/interfaces/chunks/lit-action-registry.i.d.ts +0 -2
- package/pkg-dist/pkg-src/interfaces/chunks/lit-action-registry.i.d.ts.map +1 -1
- package/pkg-dist/pkg-src/utils/chunks/lit-action-helpers.d.ts.map +1 -1
- package/pkg-dist/pkg-src/utils/chunks/lit-action-helpers.js +18 -4
- package/pkg-dist/pkg-src/utils/chunks/lit-action-helpers.js.map +1 -1
- package/pkg-dist/pkg-src/utils/chunks/pkp-setup.d.ts.map +1 -1
- package/pkg-dist/pkg-src/utils/chunks/pkp-setup.js +6 -2
- package/pkg-dist/pkg-src/utils/chunks/pkp-setup.js.map +1 -1
- package/pkg-dist/src/constants/chunks/bitcoin-network-config.js +4 -4
- package/pkg-dist/src/constants/chunks/bitcoin-network-config.js.map +1 -1
- package/pkg-dist/src/interfaces/chunks/owner-authorization.d.ts +18 -0
- package/pkg-dist/src/interfaces/chunks/owner-authorization.d.ts.map +1 -1
- package/pkg-dist/src/interfaces/chunks/vault-balance.i.d.ts +1 -0
- package/pkg-dist/src/interfaces/chunks/vault-balance.i.d.ts.map +1 -1
- package/pkg-dist/src/modules/authorization.module.d.ts +86 -0
- package/pkg-dist/src/modules/authorization.module.d.ts.map +1 -1
- package/pkg-dist/src/modules/authorization.module.js +175 -0
- package/pkg-dist/src/modules/authorization.module.js.map +1 -1
- package/pkg-dist/src/modules/bitcoin/address.d.ts +40 -0
- package/pkg-dist/src/modules/bitcoin/address.d.ts.map +1 -0
- package/pkg-dist/src/modules/bitcoin/address.js +323 -0
- package/pkg-dist/src/modules/bitcoin/address.js.map +1 -0
- package/pkg-dist/src/modules/bitcoin/provider.d.ts +55 -0
- package/pkg-dist/src/modules/bitcoin/provider.d.ts.map +1 -0
- package/pkg-dist/src/modules/bitcoin/provider.js +67 -0
- package/pkg-dist/src/modules/bitcoin/provider.js.map +1 -0
- package/pkg-dist/src/modules/bitcoin/signature.d.ts +24 -0
- package/pkg-dist/src/modules/bitcoin/signature.d.ts.map +1 -0
- package/pkg-dist/src/modules/bitcoin/signature.js +64 -0
- package/pkg-dist/src/modules/bitcoin/signature.js.map +1 -0
- package/pkg-dist/src/modules/bitcoin/transaction.d.ts +63 -0
- package/pkg-dist/src/modules/bitcoin/transaction.d.ts.map +1 -0
- package/pkg-dist/src/modules/bitcoin/transaction.js +187 -0
- package/pkg-dist/src/modules/bitcoin/transaction.js.map +1 -0
- package/pkg-dist/src/modules/bitcoin-data-provider.module.d.ts +5 -0
- package/pkg-dist/src/modules/bitcoin-data-provider.module.d.ts.map +1 -1
- package/pkg-dist/src/modules/bitcoin-data-provider.module.js +77 -9
- package/pkg-dist/src/modules/bitcoin-data-provider.module.js.map +1 -1
- package/pkg-dist/src/modules/price-oracle.module.d.ts +9 -1
- package/pkg-dist/src/modules/price-oracle.module.d.ts.map +1 -1
- package/pkg-dist/src/modules/price-oracle.module.js +142 -87
- package/pkg-dist/src/modules/price-oracle.module.js.map +1 -1
- package/pkg-dist/src/modules/vault-snapshot.d.ts.map +1 -1
- package/pkg-dist/src/modules/vault-snapshot.js +37 -30
- package/pkg-dist/src/modules/vault-snapshot.js.map +1 -1
|
@@ -0,0 +1,187 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Bitcoin Transaction Module
|
|
4
|
+
*
|
|
5
|
+
* Provides Bitcoin transaction building and signature hash computation.
|
|
6
|
+
* Implements Bitcoin protocol transaction structure and SIGHASH_ALL signing.
|
|
7
|
+
*/
|
|
8
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
9
|
+
exports.buildBitcoinTransaction = buildBitcoinTransaction;
|
|
10
|
+
const address_1 = require("./address");
|
|
11
|
+
/**
|
|
12
|
+
* Build Bitcoin transaction and compute signature hash
|
|
13
|
+
*
|
|
14
|
+
* Creates a SegWit (P2WPKH) Bitcoin transaction following BIP 143:
|
|
15
|
+
* - Version: 4 bytes (little endian) - version 2
|
|
16
|
+
* - Input count: varint
|
|
17
|
+
* - Inputs: txid (reversed) + vout + scriptSig (empty for witness) + sequence
|
|
18
|
+
* - Output count: varint
|
|
19
|
+
* - Outputs: value + scriptPubKey
|
|
20
|
+
* - Locktime: 4 bytes
|
|
21
|
+
*
|
|
22
|
+
* For BIP 143 SIGHASH_ALL signature hash (P2WPKH):
|
|
23
|
+
* The sighash preimage includes:
|
|
24
|
+
* 1. nVersion (4 bytes)
|
|
25
|
+
* 2. hashPrevouts (32 bytes) - double SHA256 of all input outpoints
|
|
26
|
+
* 3. hashSequence (32 bytes) - double SHA256 of all input sequences
|
|
27
|
+
* 4. outpoint (36 bytes) - txid + vout of input being signed
|
|
28
|
+
* 5. scriptCode (variable) - for P2WPKH: OP_DUP OP_HASH160 <20-byte-hash> OP_EQUALVERIFY OP_CHECKSIG
|
|
29
|
+
* 6. value (8 bytes) - value of output being spent
|
|
30
|
+
* 7. nSequence (4 bytes) - sequence of input being signed
|
|
31
|
+
* 8. hashOutputs (32 bytes) - double SHA256 of all outputs
|
|
32
|
+
* 9. nLocktime (4 bytes)
|
|
33
|
+
* 10. nHashType (4 bytes) - SIGHASH_ALL = 0x01000000
|
|
34
|
+
*
|
|
35
|
+
* @param params - Transaction parameters
|
|
36
|
+
* @returns Transaction hex and signature hash
|
|
37
|
+
*/
|
|
38
|
+
function buildBitcoinTransaction(params) {
|
|
39
|
+
const { utxo, destination, amount, changeAddress, changeAmount, pkpPublicKey, } = params;
|
|
40
|
+
// Transaction structure components
|
|
41
|
+
const txVersion = "02000000"; // Version 2 (little endian)
|
|
42
|
+
const inputCount = "01"; // 1 input
|
|
43
|
+
// Input: txid (reversed) + vout + empty scriptSig + sequence
|
|
44
|
+
const txidReversed = reverseHex(utxo.txid);
|
|
45
|
+
const voutHex = numToLittleEndianHex(utxo.vout, 4);
|
|
46
|
+
const sequence = "ffffffff"; // No locktime
|
|
47
|
+
// Build outputs
|
|
48
|
+
const outputs = [];
|
|
49
|
+
// Output 1: To destination
|
|
50
|
+
const destinationScript = (0, address_1.addressToScriptPubKey)(destination);
|
|
51
|
+
const destinationValue = numToLittleEndianHex(amount, 8);
|
|
52
|
+
const destinationScriptLen = numToVarInt(destinationScript.length / 2);
|
|
53
|
+
outputs.push(destinationValue + destinationScriptLen + destinationScript);
|
|
54
|
+
// Output 2: Change (if any)
|
|
55
|
+
if (changeAmount > 0) {
|
|
56
|
+
const changeScript = (0, address_1.addressToScriptPubKey)(changeAddress);
|
|
57
|
+
const changeValue = numToLittleEndianHex(changeAmount, 8);
|
|
58
|
+
const changeScriptLen = numToVarInt(changeScript.length / 2);
|
|
59
|
+
outputs.push(changeValue + changeScriptLen + changeScript);
|
|
60
|
+
}
|
|
61
|
+
const outputCount = numToVarInt(outputs.length);
|
|
62
|
+
const outputsHex = outputs.join("");
|
|
63
|
+
const locktime = "00000000"; // No locktime
|
|
64
|
+
// ========================================================================
|
|
65
|
+
// BIP 143 Signature Hash Computation (for P2WPKH)
|
|
66
|
+
// ========================================================================
|
|
67
|
+
// 1. nVersion (4 bytes)
|
|
68
|
+
const nVersion = txVersion;
|
|
69
|
+
// 2. hashPrevouts - double SHA256 of all input outpoints (txid + vout)
|
|
70
|
+
const outpoint = reverseHex(utxo.txid) + voutHex;
|
|
71
|
+
// @ts-ignore - ethers available in LIT runtime
|
|
72
|
+
const hashPrevouts = ethers.utils.sha256(
|
|
73
|
+
// @ts-ignore
|
|
74
|
+
ethers.utils.sha256("0x" + outpoint));
|
|
75
|
+
// 3. hashSequence - double SHA256 of all input sequences
|
|
76
|
+
// @ts-ignore - ethers available in LIT runtime
|
|
77
|
+
const hashSequence = ethers.utils.sha256(
|
|
78
|
+
// @ts-ignore
|
|
79
|
+
ethers.utils.sha256("0x" + sequence));
|
|
80
|
+
// 4. outpoint being signed (txid + vout)
|
|
81
|
+
const outpointSigning = outpoint;
|
|
82
|
+
// 5. scriptCode for P2WPKH
|
|
83
|
+
// For P2WPKH, scriptCode is: OP_DUP OP_HASH160 <20-byte-pubkey-hash> OP_EQUALVERIFY OP_CHECKSIG
|
|
84
|
+
// Extract the 20-byte hash from the P2WPKH scriptPubKey
|
|
85
|
+
const scriptPubKeyHex = utxo.scriptPubKey.startsWith("0x")
|
|
86
|
+
? utxo.scriptPubKey.slice(2)
|
|
87
|
+
: utxo.scriptPubKey;
|
|
88
|
+
// P2WPKH scriptPubKey format: OP_0 (0x00) + PUSH20 (0x14) + 20-byte-hash
|
|
89
|
+
// Extract the 20-byte hash (skip first 2 bytes: 0x00 0x14)
|
|
90
|
+
const pubkeyHash = scriptPubKeyHex.slice(4); // Skip "0014"
|
|
91
|
+
// Build scriptCode: OP_DUP OP_HASH160 <20-byte-hash> OP_EQUALVERIFY OP_CHECKSIG
|
|
92
|
+
// 0x76 = OP_DUP, 0xa9 = OP_HASH160, 0x14 = PUSH 20 bytes, 0x88 = OP_EQUALVERIFY, 0xac = OP_CHECKSIG
|
|
93
|
+
const scriptCode = "1976a914" + pubkeyHash + "88ac";
|
|
94
|
+
// 6. value of output being spent (8 bytes, little endian)
|
|
95
|
+
const valueHex = numToLittleEndianHex(utxo.value, 8);
|
|
96
|
+
// 7. nSequence of input being signed
|
|
97
|
+
const nSequence = sequence;
|
|
98
|
+
// 8. hashOutputs - double SHA256 of all outputs
|
|
99
|
+
// @ts-ignore - ethers available in LIT runtime
|
|
100
|
+
const hashOutputs = ethers.utils.sha256(
|
|
101
|
+
// @ts-ignore
|
|
102
|
+
ethers.utils.sha256("0x" + outputsHex));
|
|
103
|
+
// 9. nLocktime
|
|
104
|
+
const nLocktime = locktime;
|
|
105
|
+
// 10. nHashType (SIGHASH_ALL = 0x01000000)
|
|
106
|
+
const nHashType = "01000000";
|
|
107
|
+
// Build BIP 143 preimage
|
|
108
|
+
const bip143Preimage = nVersion +
|
|
109
|
+
hashPrevouts.slice(2) + // Remove 0x prefix
|
|
110
|
+
hashSequence.slice(2) +
|
|
111
|
+
outpointSigning +
|
|
112
|
+
scriptCode +
|
|
113
|
+
valueHex +
|
|
114
|
+
nSequence +
|
|
115
|
+
hashOutputs.slice(2) +
|
|
116
|
+
nLocktime +
|
|
117
|
+
nHashType;
|
|
118
|
+
// Double SHA256 for BIP 143 signature hash
|
|
119
|
+
// @ts-ignore - ethers available in LIT runtime
|
|
120
|
+
const hash1 = ethers.utils.sha256("0x" + bip143Preimage);
|
|
121
|
+
// @ts-ignore - ethers available in LIT runtime
|
|
122
|
+
const sigHash = ethers.utils.sha256(hash1);
|
|
123
|
+
// Unsigned transaction WITHOUT SegWit marker/flag
|
|
124
|
+
// SDK will convert this to proper SegWit format using PSBT
|
|
125
|
+
// For P2WPKH, the scriptSig MUST be empty (witness data separate)
|
|
126
|
+
const unsignedTx = txVersion +
|
|
127
|
+
inputCount +
|
|
128
|
+
txidReversed +
|
|
129
|
+
voutHex +
|
|
130
|
+
"00" + // Empty scriptSig - P2WPKH requires this
|
|
131
|
+
sequence +
|
|
132
|
+
outputCount +
|
|
133
|
+
outputsHex +
|
|
134
|
+
locktime;
|
|
135
|
+
return {
|
|
136
|
+
txHex: unsignedTx,
|
|
137
|
+
sigHash: sigHash,
|
|
138
|
+
};
|
|
139
|
+
}
|
|
140
|
+
/**
|
|
141
|
+
* Reverse hex string (for txid byte order)
|
|
142
|
+
* Bitcoin stores txid in reverse byte order
|
|
143
|
+
*/
|
|
144
|
+
function reverseHex(hex) {
|
|
145
|
+
const clean = hex.startsWith("0x") ? hex.slice(2) : hex;
|
|
146
|
+
const bytes = clean.match(/../g);
|
|
147
|
+
if (!bytes) {
|
|
148
|
+
throw new Error(`Invalid hex string: ${hex}`);
|
|
149
|
+
}
|
|
150
|
+
return bytes.reverse().join("");
|
|
151
|
+
}
|
|
152
|
+
/**
|
|
153
|
+
* Convert number to little-endian hex
|
|
154
|
+
* Bitcoin uses little-endian byte order
|
|
155
|
+
*/
|
|
156
|
+
function numToLittleEndianHex(num, bytes) {
|
|
157
|
+
let hex = num.toString(16).padStart(bytes * 2, "0");
|
|
158
|
+
const pairs = hex.match(/../g);
|
|
159
|
+
if (!pairs) {
|
|
160
|
+
throw new Error(`Invalid hex conversion: ${num}`);
|
|
161
|
+
}
|
|
162
|
+
return pairs.reverse().join("");
|
|
163
|
+
}
|
|
164
|
+
/**
|
|
165
|
+
* VarInt encoding (Bitcoin compact size)
|
|
166
|
+
*
|
|
167
|
+
* Format:
|
|
168
|
+
* - < 0xfd: 1 byte
|
|
169
|
+
* - <= 0xffff: 0xfd + 2 bytes (little endian)
|
|
170
|
+
* - <= 0xffffffff: 0xfe + 4 bytes (little endian)
|
|
171
|
+
* - > 0xffffffff: 0xff + 8 bytes (little endian)
|
|
172
|
+
*/
|
|
173
|
+
function numToVarInt(num) {
|
|
174
|
+
if (num < 0xfd) {
|
|
175
|
+
return num.toString(16).padStart(2, "0");
|
|
176
|
+
}
|
|
177
|
+
else if (num <= 0xffff) {
|
|
178
|
+
return "fd" + numToLittleEndianHex(num, 2);
|
|
179
|
+
}
|
|
180
|
+
else if (num <= 0xffffffff) {
|
|
181
|
+
return "fe" + numToLittleEndianHex(num, 4);
|
|
182
|
+
}
|
|
183
|
+
else {
|
|
184
|
+
return "ff" + numToLittleEndianHex(num, 8);
|
|
185
|
+
}
|
|
186
|
+
}
|
|
187
|
+
//# sourceMappingURL=transaction.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"transaction.js","sourceRoot":"","sources":["../../../../src/modules/bitcoin/transaction.ts"],"names":[],"mappings":"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"}
|
|
@@ -20,6 +20,10 @@ export declare class BitcoinDataProvider implements IBitcoinDataProvider {
|
|
|
20
20
|
private config;
|
|
21
21
|
private timeout;
|
|
22
22
|
constructor(config: BitcoinDataProviderConfig);
|
|
23
|
+
/**
|
|
24
|
+
* Get current Bitcoin block height from provider
|
|
25
|
+
*/
|
|
26
|
+
private getCurrentBlockHeight;
|
|
23
27
|
/**
|
|
24
28
|
* Fetch all UTXOs for a Bitcoin address
|
|
25
29
|
*
|
|
@@ -49,6 +53,7 @@ export declare class BitcoinDataProvider implements IBitcoinDataProvider {
|
|
|
49
53
|
* - Blockstream format: {txid, vout, value, confirmations}
|
|
50
54
|
*
|
|
51
55
|
* @param data Raw response from provider API
|
|
56
|
+
* @param currentBlockHeight Current block height (for calculating confirmations from block_height)
|
|
52
57
|
* @returns Array of normalized UTXOs
|
|
53
58
|
*/
|
|
54
59
|
private parseBlockstreamUTXOs;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"bitcoin-data-provider.module.d.ts","sourceRoot":"","sources":["../../../src/modules/bitcoin-data-provider.module.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,OAAO,EACL,yBAAyB,EACzB,IAAI,EACJ,OAAO,EACR,MAAM,sCAAsC,CAAC;AAC9C,OAAO,EAAE,oBAAoB,EAAE,MAAM,8CAA8C,CAAC;AAEpF;;;;;GAKG;AACH,qBAAa,mBAAoB,YAAW,oBAAoB;IAC9D,OAAO,CAAC,MAAM,CAA4B;IAC1C,OAAO,CAAC,OAAO,CAAS;gBAEZ,MAAM,EAAE,yBAAyB;IAK7C;;;;;OAKG;IACG,QAAQ,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,EAAE,CAAC;IAqDhD;;;;;;;;OAQG;IACH,OAAO,CAAC,kBAAkB;IAK1B;;OAEG;YACW,iBAAiB;IAqB/B
|
|
1
|
+
{"version":3,"file":"bitcoin-data-provider.module.d.ts","sourceRoot":"","sources":["../../../src/modules/bitcoin-data-provider.module.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,OAAO,EACL,yBAAyB,EACzB,IAAI,EACJ,OAAO,EACR,MAAM,sCAAsC,CAAC;AAC9C,OAAO,EAAE,oBAAoB,EAAE,MAAM,8CAA8C,CAAC;AAEpF;;;;;GAKG;AACH,qBAAa,mBAAoB,YAAW,oBAAoB;IAC9D,OAAO,CAAC,MAAM,CAA4B;IAC1C,OAAO,CAAC,OAAO,CAAS;gBAEZ,MAAM,EAAE,yBAAyB;IAK7C;;OAEG;YACW,qBAAqB;IA8CnC;;;;;OAKG;IACG,QAAQ,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,EAAE,CAAC;IAqDhD;;;;;;;;OAQG;IACH,OAAO,CAAC,kBAAkB;IAK1B;;OAEG;YACW,iBAAiB;IAqB/B;;;;;;;;;;OAUG;IACH,OAAO,CAAC,qBAAqB;IAwC7B;;;;;;OAMG;YACW,sBAAsB;IAsDpC;;;;;;;;;OASG;IACG,UAAU,CACd,OAAO,EAAE,MAAM,EACf,gBAAgB,EAAE,MAAM,GACvB,OAAO,CAAC,OAAO,CAAC;IA6CnB;;;;;;;;OAQG;IACG,cAAc,CAClB,IAAI,EAAE,MAAM,GACX,OAAO,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,aAAa,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;CA+E3D;AAED;;;GAGG;AACH,wBAAgB,yBAAyB,CACvC,MAAM,EAAE,yBAAyB,GAChC,mBAAmB,CAErB"}
|
|
@@ -23,6 +23,46 @@ class BitcoinDataProvider {
|
|
|
23
23
|
this.config = config;
|
|
24
24
|
this.timeout = config.timeout || 10000; // Default 10 seconds
|
|
25
25
|
}
|
|
26
|
+
/**
|
|
27
|
+
* Get current Bitcoin block height from provider
|
|
28
|
+
*/
|
|
29
|
+
async getCurrentBlockHeight() {
|
|
30
|
+
// If RPC helper is provided, use it
|
|
31
|
+
if (this.config.rpcHelper) {
|
|
32
|
+
const blockCount = await this.config.rpcHelper.getBlockCount();
|
|
33
|
+
return blockCount;
|
|
34
|
+
}
|
|
35
|
+
// Fetch from Esplora API
|
|
36
|
+
const controller = new AbortController();
|
|
37
|
+
const timeoutId = setTimeout(() => controller.abort(), this.timeout);
|
|
38
|
+
try {
|
|
39
|
+
const response = await fetch(`${this.config.providerUrl}/blocks/tip/height`, {
|
|
40
|
+
signal: controller.signal,
|
|
41
|
+
headers: {
|
|
42
|
+
Accept: "text/plain",
|
|
43
|
+
"User-Agent": "Mozilla/5.0 (compatible; DiamondHandsValidator/1.0)",
|
|
44
|
+
"ngrok-skip-browser-warning": "true",
|
|
45
|
+
},
|
|
46
|
+
});
|
|
47
|
+
clearTimeout(timeoutId);
|
|
48
|
+
if (!response.ok) {
|
|
49
|
+
throw new Error(`Failed to fetch block height: ${response.status} ${response.statusText}`);
|
|
50
|
+
}
|
|
51
|
+
const heightText = await response.text();
|
|
52
|
+
const height = parseInt(heightText.trim(), 10);
|
|
53
|
+
if (isNaN(height)) {
|
|
54
|
+
throw new Error(`Invalid block height response: ${heightText}`);
|
|
55
|
+
}
|
|
56
|
+
return height;
|
|
57
|
+
}
|
|
58
|
+
catch (error) {
|
|
59
|
+
clearTimeout(timeoutId);
|
|
60
|
+
if (error.name === "AbortError") {
|
|
61
|
+
throw new Error(`Request timeout after ${this.timeout}ms`);
|
|
62
|
+
}
|
|
63
|
+
throw error;
|
|
64
|
+
}
|
|
65
|
+
}
|
|
26
66
|
/**
|
|
27
67
|
* Fetch all UTXOs for a Bitcoin address
|
|
28
68
|
*
|
|
@@ -100,9 +140,10 @@ class BitcoinDataProvider {
|
|
|
100
140
|
* - Blockstream format: {txid, vout, value, confirmations}
|
|
101
141
|
*
|
|
102
142
|
* @param data Raw response from provider API
|
|
143
|
+
* @param currentBlockHeight Current block height (for calculating confirmations from block_height)
|
|
103
144
|
* @returns Array of normalized UTXOs
|
|
104
145
|
*/
|
|
105
|
-
parseBlockstreamUTXOs(data) {
|
|
146
|
+
parseBlockstreamUTXOs(data, currentBlockHeight) {
|
|
106
147
|
if (!Array.isArray(data)) {
|
|
107
148
|
throw new Error("Invalid Blockstream response format: expected an array");
|
|
108
149
|
}
|
|
@@ -113,14 +154,13 @@ class BitcoinDataProvider {
|
|
|
113
154
|
// Check for Esplora format (status.confirmed and status.block_height)
|
|
114
155
|
if (utxo.status && typeof utxo.status === 'object') {
|
|
115
156
|
if (utxo.status.confirmed) {
|
|
116
|
-
// For Esplora format:
|
|
117
|
-
//
|
|
118
|
-
// treat as at least 1 confirmation (regtest blocks are mined instantly)
|
|
157
|
+
// For Esplora format: calculate confirmations from block heights
|
|
158
|
+
// confirmations = current_height - tx_block_height + 1
|
|
119
159
|
if (utxo.status.block_height !== undefined && utxo.status.block_height > 0) {
|
|
120
|
-
confirmations = utxo.status.block_height;
|
|
160
|
+
confirmations = currentBlockHeight - utxo.status.block_height + 1;
|
|
121
161
|
}
|
|
122
162
|
else {
|
|
123
|
-
// Confirmed but no block_height (or block_height is 0)
|
|
163
|
+
// Confirmed but no block_height (or block_height is 0)
|
|
124
164
|
// This handles regtest where blocks are mined instantly
|
|
125
165
|
confirmations = 1;
|
|
126
166
|
}
|
|
@@ -152,6 +192,9 @@ class BitcoinDataProvider {
|
|
|
152
192
|
// providerUrl must include full base path (e.g., "http://localhost:3002/api/esplora")
|
|
153
193
|
const endpoint = `${providerUrl}/address/${address}/utxos`;
|
|
154
194
|
console.log(`Fetching UTXOs from ${endpoint}`);
|
|
195
|
+
// Get current block height for confirmation calculation
|
|
196
|
+
const currentBlockHeight = await this.getCurrentBlockHeight();
|
|
197
|
+
console.log(`[Bitcoin Data] Current block height: ${currentBlockHeight}`);
|
|
155
198
|
const controller = new AbortController();
|
|
156
199
|
const timeoutId = setTimeout(() => controller.abort(), this.timeout);
|
|
157
200
|
try {
|
|
@@ -171,8 +214,8 @@ class BitcoinDataProvider {
|
|
|
171
214
|
const data = await response.json();
|
|
172
215
|
// Log the parsed data
|
|
173
216
|
console.log(`[Bitcoin Data] Raw API Response:`, JSON.stringify(data, null, 2));
|
|
174
|
-
// Parse standard Esplora/Blockstream format
|
|
175
|
-
return this.parseBlockstreamUTXOs(data);
|
|
217
|
+
// Parse standard Esplora/Blockstream format with current block height
|
|
218
|
+
return this.parseBlockstreamUTXOs(data, currentBlockHeight);
|
|
176
219
|
}
|
|
177
220
|
catch (error) {
|
|
178
221
|
clearTimeout(timeoutId);
|
|
@@ -193,7 +236,32 @@ class BitcoinDataProvider {
|
|
|
193
236
|
* @returns Complete UTXO set with balance breakdown
|
|
194
237
|
*/
|
|
195
238
|
async getUTXOSet(address, minConfirmations) {
|
|
196
|
-
|
|
239
|
+
// Retry logic to handle transient failures from Bitcoin provider
|
|
240
|
+
let utxos = [];
|
|
241
|
+
let lastError = null;
|
|
242
|
+
const maxRetries = 3;
|
|
243
|
+
const retryDelay = 500; // 500ms between retries
|
|
244
|
+
for (let attempt = 1; attempt <= maxRetries; attempt++) {
|
|
245
|
+
try {
|
|
246
|
+
console.log(`[Bitcoin Data] UTXO query attempt ${attempt}/${maxRetries}...`);
|
|
247
|
+
utxos = await this.getUTXOs(address);
|
|
248
|
+
console.log(`[Bitcoin Data] UTXO query succeeded on attempt ${attempt}`);
|
|
249
|
+
lastError = null;
|
|
250
|
+
break; // Success - exit retry loop
|
|
251
|
+
}
|
|
252
|
+
catch (error) {
|
|
253
|
+
lastError = error;
|
|
254
|
+
console.error(`[Bitcoin Data] UTXO query failed on attempt ${attempt}:`, error.message);
|
|
255
|
+
if (attempt < maxRetries) {
|
|
256
|
+
console.log(`[Bitcoin Data] Waiting ${retryDelay}ms before retry...`);
|
|
257
|
+
await new Promise(resolve => setTimeout(resolve, retryDelay));
|
|
258
|
+
}
|
|
259
|
+
}
|
|
260
|
+
}
|
|
261
|
+
// If all retries failed, throw the last error
|
|
262
|
+
if (lastError) {
|
|
263
|
+
throw new Error(`Failed to query UTXOs after ${maxRetries} attempts: ${lastError.message}`);
|
|
264
|
+
}
|
|
197
265
|
const totalBalance = utxos.reduce((sum, utxo) => sum + utxo.satoshis, 0n);
|
|
198
266
|
const confirmedBalance = utxos
|
|
199
267
|
.filter((utxo) => utxo.confirmations >= minConfirmations)
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"bitcoin-data-provider.module.js","sourceRoot":"","sources":["../../../src/modules/bitcoin-data-provider.module.ts"],"names":[],"mappings":";AAAA;;;;;;;;;GASG;;;
|
|
1
|
+
{"version":3,"file":"bitcoin-data-provider.module.js","sourceRoot":"","sources":["../../../src/modules/bitcoin-data-provider.module.ts"],"names":[],"mappings":"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"}
|
|
@@ -16,7 +16,15 @@ export declare class PriceOracleModule implements IPriceOracle {
|
|
|
16
16
|
private getDefaultSources;
|
|
17
17
|
/**
|
|
18
18
|
* Get BTC price in USD with 8 decimals
|
|
19
|
-
*
|
|
19
|
+
*
|
|
20
|
+
* CRITICAL OPTIMIZATION: Queries all sources in parallel with Promise.race()
|
|
21
|
+
* This prevents timeout when multiple sources fail sequentially.
|
|
22
|
+
*
|
|
23
|
+
* Master's Wisdom: "The fastest path to truth is asking all at once"
|
|
24
|
+
* - All sources queried simultaneously
|
|
25
|
+
* - First successful response wins
|
|
26
|
+
* - No waiting for slow/failed providers
|
|
27
|
+
* - Total time = fastest provider, not sum of all attempts
|
|
20
28
|
*/
|
|
21
29
|
getBTCPrice(): Promise<bigint>;
|
|
22
30
|
/**
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"price-oracle.module.d.ts","sourceRoot":"","sources":["../../../src/modules/price-oracle.module.ts"],"names":[],"mappings":"AACA,OAAO,EACL,YAAY,EACZ,iBAAiB,EAClB,MAAM,qCAAqC,CAAC;AAM7C,qBAAa,iBAAkB,YAAW,YAAY;IACpD,OAAO,CAAC,OAAO,CAAsB;gBAGnC,sBAAsB,CAAC,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,MAAM,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC,GAAG,GAAG,EACvE,aAAa,CAAC,EAAE,iBAAiB,EAAE;
|
|
1
|
+
{"version":3,"file":"price-oracle.module.d.ts","sourceRoot":"","sources":["../../../src/modules/price-oracle.module.ts"],"names":[],"mappings":"AACA,OAAO,EACL,YAAY,EACZ,iBAAiB,EAClB,MAAM,qCAAqC,CAAC;AAM7C,qBAAa,iBAAkB,YAAW,YAAY;IACpD,OAAO,CAAC,OAAO,CAAsB;gBAGnC,sBAAsB,CAAC,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,MAAM,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC,GAAG,GAAG,EACvE,aAAa,CAAC,EAAE,iBAAiB,EAAE;IAkBrC;;OAEG;IACH,OAAO,CAAC,YAAY;IA4CpB;;OAEG;IACH,OAAO,CAAC,yBAAyB;IAuDjC,OAAO,CAAC,iBAAiB;IA2HzB;;;;;;;;;;;OAWG;IACG,WAAW,IAAI,OAAO,CAAC,MAAM,CAAC;IA+FpC;;;;;;;;;;;;;;;OAeG;IACG,oBAAoB,IAAI,OAAO,CAAC,MAAM,CAAC;CA+G9C"}
|