@did-btcr2/bitcoin 0.6.0 → 0.8.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/README.md +102 -2
- package/dist/.tsbuildinfo +1 -1
- package/dist/cjs/client/rest/protocol.js +2 -2
- package/dist/cjs/client/rpc/protocol.js +1 -1
- package/dist/cjs/connection.js +9 -31
- package/dist/cjs/constants.js +1 -46
- package/dist/cjs/fee-estimator.js +33 -0
- package/dist/cjs/index.js +4 -2
- package/dist/esm/client/rest/protocol.js +2 -2
- package/dist/esm/client/rpc/protocol.js +1 -1
- package/dist/esm/connection.js +9 -31
- package/dist/esm/connection.js.map +1 -1
- package/dist/esm/constants.js +0 -45
- package/dist/esm/constants.js.map +1 -1
- package/dist/esm/fee-estimator.js +30 -0
- package/dist/esm/fee-estimator.js.map +1 -0
- package/dist/esm/index.js +3 -1
- package/dist/esm/index.js.map +1 -1
- package/dist/types/client/http.d.ts +1 -1
- package/dist/types/client/rest/protocol.d.ts +2 -2
- package/dist/types/client/rpc/protocol.d.ts +1 -1
- package/dist/types/connection.d.ts +9 -17
- package/dist/types/connection.d.ts.map +1 -1
- package/dist/types/constants.d.ts +0 -57
- package/dist/types/constants.d.ts.map +1 -1
- package/dist/types/fee-estimator.d.ts +40 -0
- package/dist/types/fee-estimator.d.ts.map +1 -0
- package/dist/types/index.d.ts +3 -1
- package/dist/types/index.d.ts.map +1 -1
- package/package.json +3 -3
- package/src/client/http.ts +1 -1
- package/src/client/rest/protocol.ts +2 -2
- package/src/client/rpc/protocol.ts +1 -1
- package/src/connection.ts +9 -43
- package/src/constants.ts +0 -46
- package/src/fee-estimator.ts +52 -0
- package/src/index.ts +4 -1
|
@@ -4,7 +4,7 @@ import { toBase64 } from '../utils.js';
|
|
|
4
4
|
* Sans-I/O JSON-RPC protocol for Bitcoin Core.
|
|
5
5
|
*
|
|
6
6
|
* Builds {@link HttpRequest} descriptors for JSON-RPC method calls and
|
|
7
|
-
* provides response parsing
|
|
7
|
+
* provides response parsing, without performing any I/O.
|
|
8
8
|
*
|
|
9
9
|
* **Security note:** Built requests include an `Authorization` header when
|
|
10
10
|
* credentials are configured. Do not log or persist {@link HttpRequest}
|
package/dist/esm/connection.js
CHANGED
|
@@ -1,8 +1,6 @@
|
|
|
1
|
-
import { MethodError } from '@did-btcr2/common';
|
|
2
1
|
import { BitcoinRestClient } from './client/rest/index.js';
|
|
3
2
|
import { BitcoinCoreRpcClient } from './client/rpc/index.js';
|
|
4
3
|
import { getNetwork } from './network.js';
|
|
5
|
-
import { DEFAULT_BITCOIN_NETWORK_CONFIG } from './constants.js';
|
|
6
4
|
/**
|
|
7
5
|
* Represents a connection to a single Bitcoin network.
|
|
8
6
|
* Holds the REST and optional RPC clients for that network.
|
|
@@ -12,13 +10,19 @@ import { DEFAULT_BITCOIN_NETWORK_CONFIG } from './constants.js';
|
|
|
12
10
|
* executed via the global `fetch` function. Supply a custom
|
|
13
11
|
* {@link HttpExecutor} to use any HTTP client.
|
|
14
12
|
*
|
|
13
|
+
* Endpoints are explicit: this transport layer holds no service URLs. Callers
|
|
14
|
+
* supply the REST host (and optional RPC) themselves, or use the SDK facade
|
|
15
|
+
* ({@link https://github.com/dcdpr/did-btcr2-js/tree/main/packages/api | @did-btcr2/api}),
|
|
16
|
+
* which carries per-network convenience defaults.
|
|
17
|
+
*
|
|
15
18
|
* @example
|
|
16
19
|
* ```ts
|
|
17
|
-
* //
|
|
18
|
-
* const btc = BitcoinConnection
|
|
20
|
+
* // Explicit endpoint (uses the global fetch executor by default)
|
|
21
|
+
* const btc = new BitcoinConnection({ network: 'regtest', rest: { host: 'http://localhost:3000' } });
|
|
19
22
|
*
|
|
20
23
|
* // With a custom HTTP executor
|
|
21
|
-
* const btc = BitcoinConnection
|
|
24
|
+
* const btc = new BitcoinConnection({
|
|
25
|
+
* network: 'testnet4',
|
|
22
26
|
* rest: { host: 'https://my-mempool/api' },
|
|
23
27
|
* executor: myCustomExecutor,
|
|
24
28
|
* });
|
|
@@ -47,32 +51,6 @@ export class BitcoinConnection {
|
|
|
47
51
|
this.rpc = options.rpc ? new BitcoinCoreRpcClient(options.rpc, options.executor) : undefined;
|
|
48
52
|
this.data = getNetwork(options.network);
|
|
49
53
|
}
|
|
50
|
-
/**
|
|
51
|
-
* Create a connection for a single network with optional REST/RPC endpoint overrides.
|
|
52
|
-
* Merges overrides on top of defaults from DEFAULT_BITCOIN_NETWORK_CONFIG.
|
|
53
|
-
* Does not read environment variables.
|
|
54
|
-
*
|
|
55
|
-
* @param network The network name (e.g., 'regtest', 'testnet4', 'bitcoin').
|
|
56
|
-
* @param overrides Optional endpoint and executor overrides.
|
|
57
|
-
* @returns A BitcoinConnection for the requested network.
|
|
58
|
-
*/
|
|
59
|
-
static forNetwork(network, overrides) {
|
|
60
|
-
const defaults = DEFAULT_BITCOIN_NETWORK_CONFIG[network];
|
|
61
|
-
if (!defaults) {
|
|
62
|
-
throw new MethodError(`Unknown network '${network}'. Available: bitcoin, testnet3, testnet4, signet, mutinynet, regtest`, 'UNKNOWN_NETWORK', { network });
|
|
63
|
-
}
|
|
64
|
-
const restCfg = { ...defaults.rest, ...overrides?.rest };
|
|
65
|
-
const hasRpc = defaults.rpc !== undefined || overrides?.rpc !== undefined;
|
|
66
|
-
const rpcCfg = hasRpc
|
|
67
|
-
? { ...defaults.rpc, ...overrides?.rpc }
|
|
68
|
-
: undefined;
|
|
69
|
-
return new BitcoinConnection({
|
|
70
|
-
network,
|
|
71
|
-
rest: restCfg,
|
|
72
|
-
rpc: rpcCfg,
|
|
73
|
-
executor: overrides?.executor,
|
|
74
|
-
});
|
|
75
|
-
}
|
|
76
54
|
/**
|
|
77
55
|
* Converts Bitcoin (BTC) to satoshis.
|
|
78
56
|
* Uses string-based arithmetic to avoid floating-point precision errors.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"connection.js","sourceRoot":"","sources":["../../src/connection.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"connection.js","sourceRoot":"","sources":["../../src/connection.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;AAC3D,OAAO,EAAE,oBAAoB,EAAE,MAAM,uBAAuB,CAAC;AAE7D,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAc1C;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAkCG;AACH,MAAM,OAAO,iBAAiB;IAC5B,2CAA2C;IAClC,IAAI,CAAc;IAE3B,iCAAiC;IACxB,IAAI,CAAoB;IAEjC,qEAAqE;IAC5D,GAAG,CAAwB;IAEpC,2EAA2E;IAClE,IAAI,CAAa;IAE1B,YAAY,OAAiC;QAC3C,IAAI,CAAC,IAAI,GAAG,OAAO,CAAC,OAAO,CAAC;QAC5B,IAAI,CAAC,IAAI,GAAG,IAAI,iBAAiB,CAAC,OAAO,CAAC,IAAI,EAAE,OAAO,CAAC,QAAQ,CAAC,CAAC;QAClE,IAAI,CAAC,GAAG,GAAI,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,IAAI,oBAAoB,CAAC,OAAO,CAAC,GAAG,EAAE,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QAC9F,IAAI,CAAC,IAAI,GAAG,UAAU,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;IAC1C,CAAC;IAED;;;;OAIG;IACH,MAAM,CAAC,SAAS,CAAC,GAAW;QAC1B,MAAM,GAAG,GAAG,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC;QAC3B,MAAM,CAAC,KAAK,EAAE,IAAI,CAAC,GAAG,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;QACrC,iDAAiD;QACjD,IAAI,IAAI,CAAC,GAAG,CAAC,GAAG,GAAG,MAAM,CAAC,GAAG,CAAC,CAAC,GAAG,MAAM,CAAC,OAAO,EAAE,CAAC;YACjD,MAAM,IAAI,UAAU,CAAC,aAAa,GAAG,wCAAwC,CAAC,CAAC;QACjF,CAAC;QACD,OAAO,MAAM,CAAC,KAAK,CAAC,GAAG,GAAG,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC;IAC5C,CAAC;IAED;;;;OAIG;IACH,MAAM,CAAC,SAAS,CAAC,IAAY;QAC3B,MAAM,QAAQ,GAAG,IAAI,GAAG,CAAC,CAAC;QAC1B,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;QAC3B,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,GAAG,GAAG,CAAC,CAAC;QACpC,MAAM,IAAI,GAAG,GAAG,GAAG,GAAG,CAAC;QACvB,MAAM,MAAM,GAAG,MAAM,CAAC,GAAG,KAAK,IAAI,IAAI,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC,EAAE,CAAC,CAAC;QACtE,OAAO,QAAQ,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC;IACrC,CAAC;CACF"}
|
package/dist/esm/constants.js
CHANGED
|
@@ -4,49 +4,4 @@ export const COINBASE_MATURITY_DELAY = 100;
|
|
|
4
4
|
export const DEFAULT_BLOCK_CONFIRMATIONS = 7;
|
|
5
5
|
export const TXIN_WITNESS_COINBASE = '0000000000000000000000000000000000000000000000000000000000000000';
|
|
6
6
|
export const GENESIS_TX_ID = '4a5e1e4baab89f3a32518a88c31bc87f618f76673e2cc77ab2127b7afdeda33b';
|
|
7
|
-
/**
|
|
8
|
-
* Default endpoint configuration per Bitcoin network.
|
|
9
|
-
*
|
|
10
|
-
* **Regtest RPC:** Credentials are intentionally omitted — callers must
|
|
11
|
-
* provide `username` and `password` via overrides or explicit config.
|
|
12
|
-
* This prevents accidentally using hardcoded credentials in non-local
|
|
13
|
-
* environments.
|
|
14
|
-
*
|
|
15
|
-
* @example
|
|
16
|
-
* ```ts
|
|
17
|
-
* // Provide credentials explicitly
|
|
18
|
-
* BitcoinConnection.forNetwork('regtest', {
|
|
19
|
-
* rpc: { username: 'polaruser', password: 'polarpass' },
|
|
20
|
-
* });
|
|
21
|
-
* ```
|
|
22
|
-
*/
|
|
23
|
-
export const DEFAULT_BITCOIN_NETWORK_CONFIG = {
|
|
24
|
-
bitcoin: {
|
|
25
|
-
rpc: undefined,
|
|
26
|
-
rest: { host: 'https://mempool.space/api' }
|
|
27
|
-
},
|
|
28
|
-
testnet3: {
|
|
29
|
-
rpc: undefined,
|
|
30
|
-
rest: { host: 'https://mempool.space/testnet/api' }
|
|
31
|
-
},
|
|
32
|
-
testnet4: {
|
|
33
|
-
rpc: undefined,
|
|
34
|
-
rest: { host: 'https://mempool.space/testnet4/api' }
|
|
35
|
-
},
|
|
36
|
-
signet: {
|
|
37
|
-
rpc: undefined,
|
|
38
|
-
rest: { host: 'https://mempool.space/signet/api' }
|
|
39
|
-
},
|
|
40
|
-
mutinynet: {
|
|
41
|
-
rpc: undefined,
|
|
42
|
-
rest: { host: 'https://mutinynet.com/api' }
|
|
43
|
-
},
|
|
44
|
-
regtest: {
|
|
45
|
-
rpc: {
|
|
46
|
-
host: 'http://localhost:18443',
|
|
47
|
-
allowDefaultWallet: true,
|
|
48
|
-
},
|
|
49
|
-
rest: { host: 'http://localhost:3000' }
|
|
50
|
-
},
|
|
51
|
-
};
|
|
52
7
|
//# sourceMappingURL=constants.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"constants.js","sourceRoot":"","sources":["../../src/constants.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,oBAAoB,GAAG,EAAE,CAAC;AACvC,MAAM,CAAC,MAAM,gBAAgB,GAAG,GAAG,CAAC;AACpC,MAAM,CAAC,MAAM,uBAAuB,GAAG,GAAG,CAAC;AAC3C,MAAM,CAAC,MAAM,2BAA2B,GAAG,CAAC,CAAC;AAC7C,MAAM,CAAC,MAAM,qBAAqB,GAAG,kEAAkE,CAAC;AACxG,MAAM,CAAC,MAAM,aAAa,GAAG,kEAAkE,CAAC
|
|
1
|
+
{"version":3,"file":"constants.js","sourceRoot":"","sources":["../../src/constants.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,oBAAoB,GAAG,EAAE,CAAC;AACvC,MAAM,CAAC,MAAM,gBAAgB,GAAG,GAAG,CAAC;AACpC,MAAM,CAAC,MAAM,uBAAuB,GAAG,GAAG,CAAC;AAC3C,MAAM,CAAC,MAAM,2BAA2B,GAAG,CAAC,CAAC;AAC7C,MAAM,CAAC,MAAM,qBAAqB,GAAG,kEAAkE,CAAC;AACxG,MAAM,CAAC,MAAM,aAAa,GAAG,kEAAkE,CAAC"}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Fee estimator that returns a fixed fee rate regardless of network conditions.
|
|
3
|
+
*
|
|
4
|
+
* Suitable for:
|
|
5
|
+
* - Tests (deterministic outputs)
|
|
6
|
+
* - Regtest (no real fee market)
|
|
7
|
+
* - Environments where a fee rate is supplied out-of-band
|
|
8
|
+
*
|
|
9
|
+
* For mainnet production use, prefer a dynamic estimator that queries current
|
|
10
|
+
* network conditions (mempool APIs, Bitcoin Core RPC).
|
|
11
|
+
*/
|
|
12
|
+
export class StaticFeeEstimator {
|
|
13
|
+
satsPerVbyte;
|
|
14
|
+
/**
|
|
15
|
+
* @param satsPerVbyte Fee rate in satoshis per virtual byte. Default: 5 sat/vB.
|
|
16
|
+
*/
|
|
17
|
+
constructor(satsPerVbyte = 5) {
|
|
18
|
+
if (satsPerVbyte < 0 || !Number.isFinite(satsPerVbyte)) {
|
|
19
|
+
throw new Error(`Invalid satsPerVbyte: ${satsPerVbyte}`);
|
|
20
|
+
}
|
|
21
|
+
this.satsPerVbyte = satsPerVbyte;
|
|
22
|
+
}
|
|
23
|
+
async estimateFee(vsize) {
|
|
24
|
+
if (vsize < 0 || !Number.isFinite(vsize)) {
|
|
25
|
+
throw new Error(`Invalid vsize: ${vsize}`);
|
|
26
|
+
}
|
|
27
|
+
return BigInt(Math.ceil(vsize * this.satsPerVbyte));
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
//# sourceMappingURL=fee-estimator.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"fee-estimator.js","sourceRoot":"","sources":["../../src/fee-estimator.ts"],"names":[],"mappings":"AAqBA;;;;;;;;;;GAUG;AACH,MAAM,OAAO,kBAAkB;IACpB,YAAY,CAAS;IAE9B;;OAEG;IACH,YAAY,eAAuB,CAAC;QAClC,IAAG,YAAY,GAAG,CAAC,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,YAAY,CAAC,EAAE,CAAC;YACtD,MAAM,IAAI,KAAK,CAAC,yBAAyB,YAAY,EAAE,CAAC,CAAC;QAC3D,CAAC;QACD,IAAI,CAAC,YAAY,GAAG,YAAY,CAAC;IACnC,CAAC;IAED,KAAK,CAAC,WAAW,CAAC,KAAa;QAC7B,IAAG,KAAK,GAAG,CAAC,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,EAAE,CAAC;YACxC,MAAM,IAAI,KAAK,CAAC,kBAAkB,KAAK,EAAE,CAAC,CAAC;QAC7C,CAAC;QACD,OAAO,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,YAAY,CAAC,CAAC,CAAC;IACtD,CAAC;CACF"}
|
package/dist/esm/index.js
CHANGED
|
@@ -13,10 +13,12 @@ export { BitcoinTransaction } from './client/rest/transaction.js';
|
|
|
13
13
|
export { JsonRpcTransport } from './client/rpc/json-rpc.js';
|
|
14
14
|
// Errors
|
|
15
15
|
export { BitcoinRpcError, BitcoinRestError } from './errors.js';
|
|
16
|
+
// Fee estimation
|
|
17
|
+
export { StaticFeeEstimator } from './fee-estimator.js';
|
|
16
18
|
// Helpers
|
|
17
19
|
export { getNetwork } from './network.js';
|
|
18
20
|
export { toBase64, safeText } from './client/utils.js';
|
|
19
21
|
// Constants
|
|
20
|
-
export {
|
|
22
|
+
export { INITIAL_BLOCK_REWARD, HALVING_INTERVAL, COINBASE_MATURITY_DELAY, DEFAULT_BLOCK_CONFIRMATIONS, TXIN_WITNESS_COINBASE, GENESIS_TX_ID, } from './constants.js';
|
|
21
23
|
export { VerbosityLevel } from './types.js';
|
|
22
24
|
//# sourceMappingURL=index.js.map
|
package/dist/esm/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,OAAO;AACP,OAAO,EAAE,iBAAiB,EAAiC,MAAM,iBAAiB,CAAC;AAInF,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AACvD,OAAO,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAC;AAC5D,OAAO,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAE3D,2DAA2D;AAC3D,OAAO,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;AAC3D,OAAO,EAAE,oBAAoB,EAAE,MAAM,uBAAuB,CAAC;AAI7D,iEAAiE;AACjE,OAAO,EAAE,cAAc,EAAE,MAAM,0BAA0B,CAAC;AAC1D,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AACtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,8BAA8B,CAAC;AAClE,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAE5D,SAAS;AACT,OAAO,EAAE,eAAe,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAGhE,UAAU;AACV,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE1C,OAAO,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAEvD,YAAY;AACZ,OAAO,EACL,
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,OAAO;AACP,OAAO,EAAE,iBAAiB,EAAiC,MAAM,iBAAiB,CAAC;AAInF,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AACvD,OAAO,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAC;AAC5D,OAAO,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAE3D,2DAA2D;AAC3D,OAAO,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;AAC3D,OAAO,EAAE,oBAAoB,EAAE,MAAM,uBAAuB,CAAC;AAI7D,iEAAiE;AACjE,OAAO,EAAE,cAAc,EAAE,MAAM,0BAA0B,CAAC;AAC1D,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AACtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,8BAA8B,CAAC;AAClE,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAE5D,SAAS;AACT,OAAO,EAAE,eAAe,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAGhE,iBAAiB;AACjB,OAAO,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAGxD,UAAU;AACV,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE1C,OAAO,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAEvD,YAAY;AACZ,OAAO,EACL,oBAAoB,EACpB,gBAAgB,EAChB,uBAAuB,EACvB,2BAA2B,EAC3B,qBAAqB,EACrB,aAAa,GACd,MAAM,gBAAgB,CAAC;AA0CxB,OAAO,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* HTTP request descriptor. Represents a request that can be executed
|
|
3
|
-
* by any HTTP client
|
|
3
|
+
* by any HTTP client - the library never performs I/O itself at the
|
|
4
4
|
* protocol layer.
|
|
5
5
|
*/
|
|
6
6
|
export interface HttpRequest {
|
|
@@ -3,8 +3,8 @@ import type { HttpRequest } from '../http.js';
|
|
|
3
3
|
/**
|
|
4
4
|
* Sans-I/O Esplora REST API protocol.
|
|
5
5
|
*
|
|
6
|
-
* Every method returns an {@link HttpRequest} descriptor
|
|
7
|
-
* describing *what* to request
|
|
6
|
+
* Every method returns an {@link HttpRequest} descriptor (a plain object
|
|
7
|
+
* describing *what* to request) without performing any I/O. The caller
|
|
8
8
|
* is responsible for executing the request with an HTTP client of their
|
|
9
9
|
* choice and deserializing the response.
|
|
10
10
|
*
|
|
@@ -4,7 +4,7 @@ import type { HttpRequest } from '../http.js';
|
|
|
4
4
|
* Sans-I/O JSON-RPC protocol for Bitcoin Core.
|
|
5
5
|
*
|
|
6
6
|
* Builds {@link HttpRequest} descriptors for JSON-RPC method calls and
|
|
7
|
-
* provides response parsing
|
|
7
|
+
* provides response parsing, without performing any I/O.
|
|
8
8
|
*
|
|
9
9
|
* **Security note:** Built requests include an `Authorization` header when
|
|
10
10
|
* credentials are configured. Do not log or persist {@link HttpRequest}
|
|
@@ -22,13 +22,19 @@ export type BitcoinConnectionOptions = {
|
|
|
22
22
|
* executed via the global `fetch` function. Supply a custom
|
|
23
23
|
* {@link HttpExecutor} to use any HTTP client.
|
|
24
24
|
*
|
|
25
|
+
* Endpoints are explicit: this transport layer holds no service URLs. Callers
|
|
26
|
+
* supply the REST host (and optional RPC) themselves, or use the SDK facade
|
|
27
|
+
* ({@link https://github.com/dcdpr/did-btcr2-js/tree/main/packages/api | @did-btcr2/api}),
|
|
28
|
+
* which carries per-network convenience defaults.
|
|
29
|
+
*
|
|
25
30
|
* @example
|
|
26
31
|
* ```ts
|
|
27
|
-
* //
|
|
28
|
-
* const btc = BitcoinConnection
|
|
32
|
+
* // Explicit endpoint (uses the global fetch executor by default)
|
|
33
|
+
* const btc = new BitcoinConnection({ network: 'regtest', rest: { host: 'http://localhost:3000' } });
|
|
29
34
|
*
|
|
30
35
|
* // With a custom HTTP executor
|
|
31
|
-
* const btc = BitcoinConnection
|
|
36
|
+
* const btc = new BitcoinConnection({
|
|
37
|
+
* network: 'testnet4',
|
|
32
38
|
* rest: { host: 'https://my-mempool/api' },
|
|
33
39
|
* executor: myCustomExecutor,
|
|
34
40
|
* });
|
|
@@ -52,20 +58,6 @@ export declare class BitcoinConnection {
|
|
|
52
58
|
/** Bitcoin network params (for address derivation, PSBT signing, etc.). */
|
|
53
59
|
readonly data: BTCNetwork;
|
|
54
60
|
constructor(options: BitcoinConnectionOptions);
|
|
55
|
-
/**
|
|
56
|
-
* Create a connection for a single network with optional REST/RPC endpoint overrides.
|
|
57
|
-
* Merges overrides on top of defaults from DEFAULT_BITCOIN_NETWORK_CONFIG.
|
|
58
|
-
* Does not read environment variables.
|
|
59
|
-
*
|
|
60
|
-
* @param network The network name (e.g., 'regtest', 'testnet4', 'bitcoin').
|
|
61
|
-
* @param overrides Optional endpoint and executor overrides.
|
|
62
|
-
* @returns A BitcoinConnection for the requested network.
|
|
63
|
-
*/
|
|
64
|
-
static forNetwork(network: NetworkName, overrides?: {
|
|
65
|
-
rest?: Partial<RestConfig>;
|
|
66
|
-
rpc?: RpcConfig;
|
|
67
|
-
executor?: HttpExecutor;
|
|
68
|
-
}): BitcoinConnection;
|
|
69
61
|
/**
|
|
70
62
|
* Converts Bitcoin (BTC) to satoshis.
|
|
71
63
|
* Uses string-based arithmetic to avoid floating-point precision errors.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"connection.d.ts","sourceRoot":"","sources":["../../src/connection.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"connection.d.ts","sourceRoot":"","sources":["../../src/connection.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AACrD,OAAO,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;AAC3D,OAAO,EAAE,oBAAoB,EAAE,MAAM,uBAAuB,CAAC;AAC7D,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE/C,OAAO,KAAK,EAAE,WAAW,EAAE,UAAU,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAErE;;GAEG;AACH,MAAM,MAAM,wBAAwB,GAAG;IACrC,OAAO,EAAE,WAAW,CAAC;IACrB,IAAI,EAAE,UAAU,CAAC;IACjB,GAAG,CAAC,EAAE,SAAS,CAAC;IAChB,6EAA6E;IAC7E,QAAQ,CAAC,EAAE,YAAY,CAAC;CACzB,CAAC;AAEF;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAkCG;AACH,qBAAa,iBAAiB;IAC5B,2CAA2C;IAC3C,QAAQ,CAAC,IAAI,EAAE,WAAW,CAAC;IAE3B,iCAAiC;IACjC,QAAQ,CAAC,IAAI,EAAE,iBAAiB,CAAC;IAEjC,qEAAqE;IACrE,QAAQ,CAAC,GAAG,CAAC,EAAE,oBAAoB,CAAC;IAEpC,2EAA2E;IAC3E,QAAQ,CAAC,IAAI,EAAE,UAAU,CAAC;gBAEd,OAAO,EAAE,wBAAwB;IAO7C;;;;OAIG;IACH,MAAM,CAAC,SAAS,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM;IAUrC;;;;OAIG;IACH,MAAM,CAAC,SAAS,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM;CAQvC"}
|
|
@@ -4,61 +4,4 @@ export declare const COINBASE_MATURITY_DELAY = 100;
|
|
|
4
4
|
export declare const DEFAULT_BLOCK_CONFIRMATIONS = 7;
|
|
5
5
|
export declare const TXIN_WITNESS_COINBASE = "0000000000000000000000000000000000000000000000000000000000000000";
|
|
6
6
|
export declare const GENESIS_TX_ID = "4a5e1e4baab89f3a32518a88c31bc87f618f76673e2cc77ab2127b7afdeda33b";
|
|
7
|
-
/**
|
|
8
|
-
* Default endpoint configuration per Bitcoin network.
|
|
9
|
-
*
|
|
10
|
-
* **Regtest RPC:** Credentials are intentionally omitted — callers must
|
|
11
|
-
* provide `username` and `password` via overrides or explicit config.
|
|
12
|
-
* This prevents accidentally using hardcoded credentials in non-local
|
|
13
|
-
* environments.
|
|
14
|
-
*
|
|
15
|
-
* @example
|
|
16
|
-
* ```ts
|
|
17
|
-
* // Provide credentials explicitly
|
|
18
|
-
* BitcoinConnection.forNetwork('regtest', {
|
|
19
|
-
* rpc: { username: 'polaruser', password: 'polarpass' },
|
|
20
|
-
* });
|
|
21
|
-
* ```
|
|
22
|
-
*/
|
|
23
|
-
export declare const DEFAULT_BITCOIN_NETWORK_CONFIG: {
|
|
24
|
-
readonly bitcoin: {
|
|
25
|
-
readonly rpc: undefined;
|
|
26
|
-
readonly rest: {
|
|
27
|
-
readonly host: "https://mempool.space/api";
|
|
28
|
-
};
|
|
29
|
-
};
|
|
30
|
-
readonly testnet3: {
|
|
31
|
-
readonly rpc: undefined;
|
|
32
|
-
readonly rest: {
|
|
33
|
-
readonly host: "https://mempool.space/testnet/api";
|
|
34
|
-
};
|
|
35
|
-
};
|
|
36
|
-
readonly testnet4: {
|
|
37
|
-
readonly rpc: undefined;
|
|
38
|
-
readonly rest: {
|
|
39
|
-
readonly host: "https://mempool.space/testnet4/api";
|
|
40
|
-
};
|
|
41
|
-
};
|
|
42
|
-
readonly signet: {
|
|
43
|
-
readonly rpc: undefined;
|
|
44
|
-
readonly rest: {
|
|
45
|
-
readonly host: "https://mempool.space/signet/api";
|
|
46
|
-
};
|
|
47
|
-
};
|
|
48
|
-
readonly mutinynet: {
|
|
49
|
-
readonly rpc: undefined;
|
|
50
|
-
readonly rest: {
|
|
51
|
-
readonly host: "https://mutinynet.com/api";
|
|
52
|
-
};
|
|
53
|
-
};
|
|
54
|
-
readonly regtest: {
|
|
55
|
-
readonly rpc: {
|
|
56
|
-
readonly host: "http://localhost:18443";
|
|
57
|
-
readonly allowDefaultWallet: true;
|
|
58
|
-
};
|
|
59
|
-
readonly rest: {
|
|
60
|
-
readonly host: "http://localhost:3000";
|
|
61
|
-
};
|
|
62
|
-
};
|
|
63
|
-
};
|
|
64
7
|
//# sourceMappingURL=constants.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../../src/constants.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,oBAAoB,KAAK,CAAC;AACvC,eAAO,MAAM,gBAAgB,MAAM,CAAC;AACpC,eAAO,MAAM,uBAAuB,MAAM,CAAC;AAC3C,eAAO,MAAM,2BAA2B,IAAI,CAAC;AAC7C,eAAO,MAAM,qBAAqB,qEAAqE,CAAC;AACxG,eAAO,MAAM,aAAa,qEAAqE,CAAC
|
|
1
|
+
{"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../../src/constants.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,oBAAoB,KAAK,CAAC;AACvC,eAAO,MAAM,gBAAgB,MAAM,CAAC;AACpC,eAAO,MAAM,uBAAuB,MAAM,CAAC;AAC3C,eAAO,MAAM,2BAA2B,IAAI,CAAC;AAC7C,eAAO,MAAM,qBAAqB,qEAAqE,CAAC;AACxG,eAAO,MAAM,aAAa,qEAAqE,CAAC"}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Estimates the fee (in satoshis) for a transaction of a given virtual size.
|
|
3
|
+
*
|
|
4
|
+
* Callers that build Bitcoin transactions (the did:btcr2 beacon broadcast paths,
|
|
5
|
+
* single-party and aggregated) delegate fee calculation to a `FeeEstimator` so they
|
|
6
|
+
* can plug in different strategies: static fee rates for tests/regtest, mempool APIs
|
|
7
|
+
* for mainnet, Bitcoin Core `estimatesmartfee` RPC for full-node setups, etc.
|
|
8
|
+
*
|
|
9
|
+
* Implementations return the **total fee in satoshis** for a transaction of the given
|
|
10
|
+
* virtual size (`vsize`). Callers pass the vsize; the estimator decides the fee rate
|
|
11
|
+
* and computes the total.
|
|
12
|
+
*/
|
|
13
|
+
export interface FeeEstimator {
|
|
14
|
+
/**
|
|
15
|
+
* Estimate the total fee in satoshis for a transaction of the given vsize.
|
|
16
|
+
* @param vsize Transaction virtual size in vbytes.
|
|
17
|
+
* @returns Total fee in satoshis.
|
|
18
|
+
*/
|
|
19
|
+
estimateFee(vsize: number): Promise<bigint>;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Fee estimator that returns a fixed fee rate regardless of network conditions.
|
|
23
|
+
*
|
|
24
|
+
* Suitable for:
|
|
25
|
+
* - Tests (deterministic outputs)
|
|
26
|
+
* - Regtest (no real fee market)
|
|
27
|
+
* - Environments where a fee rate is supplied out-of-band
|
|
28
|
+
*
|
|
29
|
+
* For mainnet production use, prefer a dynamic estimator that queries current
|
|
30
|
+
* network conditions (mempool APIs, Bitcoin Core RPC).
|
|
31
|
+
*/
|
|
32
|
+
export declare class StaticFeeEstimator implements FeeEstimator {
|
|
33
|
+
readonly satsPerVbyte: number;
|
|
34
|
+
/**
|
|
35
|
+
* @param satsPerVbyte Fee rate in satoshis per virtual byte. Default: 5 sat/vB.
|
|
36
|
+
*/
|
|
37
|
+
constructor(satsPerVbyte?: number);
|
|
38
|
+
estimateFee(vsize: number): Promise<bigint>;
|
|
39
|
+
}
|
|
40
|
+
//# sourceMappingURL=fee-estimator.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"fee-estimator.d.ts","sourceRoot":"","sources":["../../src/fee-estimator.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AACH,MAAM,WAAW,YAAY;IAC3B;;;;OAIG;IACH,WAAW,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;CAC7C;AAED;;;;;;;;;;GAUG;AACH,qBAAa,kBAAmB,YAAW,YAAY;IACrD,QAAQ,CAAC,YAAY,EAAE,MAAM,CAAC;IAE9B;;OAEG;gBACS,YAAY,GAAE,MAAU;IAO9B,WAAW,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;CAMlD"}
|
package/dist/types/index.d.ts
CHANGED
|
@@ -13,10 +13,12 @@ export { BitcoinTransaction } from './client/rest/transaction.js';
|
|
|
13
13
|
export { JsonRpcTransport } from './client/rpc/json-rpc.js';
|
|
14
14
|
export { BitcoinRpcError, BitcoinRestError } from './errors.js';
|
|
15
15
|
export type { RpcErrorType } from './errors.js';
|
|
16
|
+
export { StaticFeeEstimator } from './fee-estimator.js';
|
|
17
|
+
export type { FeeEstimator } from './fee-estimator.js';
|
|
16
18
|
export { getNetwork } from './network.js';
|
|
17
19
|
export type { BTCNetwork } from './network.js';
|
|
18
20
|
export { toBase64, safeText } from './client/utils.js';
|
|
19
|
-
export {
|
|
21
|
+
export { INITIAL_BLOCK_REWARD, HALVING_INTERVAL, COINBASE_MATURITY_DELAY, DEFAULT_BLOCK_CONFIRMATIONS, TXIN_WITNESS_COINBASE, GENESIS_TX_ID, } from './constants.js';
|
|
20
22
|
export type { NetworkName, RestConfig, EsploraBlock, TransactionStatus, Vin, Vout, ChainStats, MempoolStats, AddressInfo, RawTransactionRest, AddressUtxo, RpcConfig, ChainInfo, GetBlockParams, BlockResponse, BlockV0, BlockV1, BlockV2, BlockV3, RawTransactionResponse, RawTransactionV0, RawTransactionV1, RawTransactionV2, CreateRawTxInputs, CreateRawTxOutputs, SignedRawTx, UnspentTxInfo, WalletTransaction, DerivedAddresses, ListTransactionsParams, ListTransactionsResult, MethodNameInLowerCase, FeeEstimateMode, } from './types.js';
|
|
21
23
|
export { VerbosityLevel } from './types.js';
|
|
22
24
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,iBAAiB,EAAE,KAAK,wBAAwB,EAAE,MAAM,iBAAiB,CAAC;AAGnF,YAAY,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAClE,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AACvD,OAAO,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAC;AAC5D,OAAO,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAG3D,OAAO,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;AAC3D,OAAO,EAAE,oBAAoB,EAAE,MAAM,uBAAuB,CAAC;AAC7D,YAAY,EAAE,YAAY,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AAC1E,YAAY,EAAE,gBAAgB,EAAE,MAAM,2BAA2B,CAAC;AAGlE,OAAO,EAAE,cAAc,EAAE,MAAM,0BAA0B,CAAC;AAC1D,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AACtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,8BAA8B,CAAC;AAClE,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAG5D,OAAO,EAAE,eAAe,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAChE,YAAY,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAGhD,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAC1C,YAAY,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAC/C,OAAO,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAGvD,OAAO,EACL,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,iBAAiB,EAAE,KAAK,wBAAwB,EAAE,MAAM,iBAAiB,CAAC;AAGnF,YAAY,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAClE,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AACvD,OAAO,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAC;AAC5D,OAAO,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAG3D,OAAO,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;AAC3D,OAAO,EAAE,oBAAoB,EAAE,MAAM,uBAAuB,CAAC;AAC7D,YAAY,EAAE,YAAY,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AAC1E,YAAY,EAAE,gBAAgB,EAAE,MAAM,2BAA2B,CAAC;AAGlE,OAAO,EAAE,cAAc,EAAE,MAAM,0BAA0B,CAAC;AAC1D,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AACtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,8BAA8B,CAAC;AAClE,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAG5D,OAAO,EAAE,eAAe,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAChE,YAAY,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAGhD,OAAO,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AACxD,YAAY,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAGvD,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAC1C,YAAY,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAC/C,OAAO,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAGvD,OAAO,EACL,oBAAoB,EACpB,gBAAgB,EAChB,uBAAuB,EACvB,2BAA2B,EAC3B,qBAAqB,EACrB,aAAa,GACd,MAAM,gBAAgB,CAAC;AAGxB,YAAY,EAEV,WAAW,EAEX,UAAU,EACV,YAAY,EACZ,iBAAiB,EACjB,GAAG,EACH,IAAI,EACJ,UAAU,EACV,YAAY,EACZ,WAAW,EACX,kBAAkB,EAClB,WAAW,EAEX,SAAS,EACT,SAAS,EACT,cAAc,EACd,aAAa,EACb,OAAO,EACP,OAAO,EACP,OAAO,EACP,OAAO,EACP,sBAAsB,EACtB,gBAAgB,EAChB,gBAAgB,EAChB,gBAAgB,EAChB,iBAAiB,EACjB,kBAAkB,EAClB,WAAW,EACX,aAAa,EACb,iBAAiB,EACjB,gBAAgB,EAChB,sBAAsB,EACtB,sBAAsB,EACtB,qBAAqB,EACrB,eAAe,GAChB,MAAM,YAAY,CAAC;AAEpB,OAAO,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@did-btcr2/bitcoin",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.8.0",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Bitcoin Core RPC and Rest Client Implementations in JS/TS. Used by @did-btcr2/method.",
|
|
6
6
|
"main": "./dist/cjs/index.js",
|
|
@@ -60,8 +60,8 @@
|
|
|
60
60
|
"@noble/hashes": "^2.0.1",
|
|
61
61
|
"@noble/secp256k1": "^2.3.0",
|
|
62
62
|
"@scure/btc-signer": "^1.8.1",
|
|
63
|
-
"@did-btcr2/common": "^9.
|
|
64
|
-
"@did-btcr2/keypair": "^0.
|
|
63
|
+
"@did-btcr2/common": "^9.1.0",
|
|
64
|
+
"@did-btcr2/keypair": "^0.13.1"
|
|
65
65
|
},
|
|
66
66
|
"devDependencies": {
|
|
67
67
|
"@eslint/js": "^9.22.0",
|
package/src/client/http.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* HTTP request descriptor. Represents a request that can be executed
|
|
3
|
-
* by any HTTP client
|
|
3
|
+
* by any HTTP client - the library never performs I/O itself at the
|
|
4
4
|
* protocol layer.
|
|
5
5
|
*/
|
|
6
6
|
export interface HttpRequest {
|
|
@@ -7,8 +7,8 @@ const HEX64_RE = /^[0-9a-f]{64}$/i;
|
|
|
7
7
|
/**
|
|
8
8
|
* Sans-I/O Esplora REST API protocol.
|
|
9
9
|
*
|
|
10
|
-
* Every method returns an {@link HttpRequest} descriptor
|
|
11
|
-
* describing *what* to request
|
|
10
|
+
* Every method returns an {@link HttpRequest} descriptor (a plain object
|
|
11
|
+
* describing *what* to request) without performing any I/O. The caller
|
|
12
12
|
* is responsible for executing the request with an HTTP client of their
|
|
13
13
|
* choice and deserializing the response.
|
|
14
14
|
*
|
|
@@ -7,7 +7,7 @@ import { toBase64 } from '../utils.js';
|
|
|
7
7
|
* Sans-I/O JSON-RPC protocol for Bitcoin Core.
|
|
8
8
|
*
|
|
9
9
|
* Builds {@link HttpRequest} descriptors for JSON-RPC method calls and
|
|
10
|
-
* provides response parsing
|
|
10
|
+
* provides response parsing, without performing any I/O.
|
|
11
11
|
*
|
|
12
12
|
* **Security note:** Built requests include an `Authorization` header when
|
|
13
13
|
* credentials are configured. Do not log or persist {@link HttpRequest}
|
package/src/connection.ts
CHANGED
|
@@ -1,11 +1,9 @@
|
|
|
1
|
-
import { MethodError } from '@did-btcr2/common';
|
|
2
1
|
import type { HttpExecutor } from './client/http.js';
|
|
3
2
|
import { BitcoinRestClient } from './client/rest/index.js';
|
|
4
3
|
import { BitcoinCoreRpcClient } from './client/rpc/index.js';
|
|
5
4
|
import type { BTCNetwork } from './network.js';
|
|
6
5
|
import { getNetwork } from './network.js';
|
|
7
6
|
import type { NetworkName, RestConfig, RpcConfig } from './types.js';
|
|
8
|
-
import { DEFAULT_BITCOIN_NETWORK_CONFIG } from './constants.js';
|
|
9
7
|
|
|
10
8
|
/**
|
|
11
9
|
* Options for creating a BitcoinConnection.
|
|
@@ -27,13 +25,19 @@ export type BitcoinConnectionOptions = {
|
|
|
27
25
|
* executed via the global `fetch` function. Supply a custom
|
|
28
26
|
* {@link HttpExecutor} to use any HTTP client.
|
|
29
27
|
*
|
|
28
|
+
* Endpoints are explicit: this transport layer holds no service URLs. Callers
|
|
29
|
+
* supply the REST host (and optional RPC) themselves, or use the SDK facade
|
|
30
|
+
* ({@link https://github.com/dcdpr/did-btcr2-js/tree/main/packages/api | @did-btcr2/api}),
|
|
31
|
+
* which carries per-network convenience defaults.
|
|
32
|
+
*
|
|
30
33
|
* @example
|
|
31
34
|
* ```ts
|
|
32
|
-
* //
|
|
33
|
-
* const btc = BitcoinConnection
|
|
35
|
+
* // Explicit endpoint (uses the global fetch executor by default)
|
|
36
|
+
* const btc = new BitcoinConnection({ network: 'regtest', rest: { host: 'http://localhost:3000' } });
|
|
34
37
|
*
|
|
35
38
|
* // With a custom HTTP executor
|
|
36
|
-
* const btc = BitcoinConnection
|
|
39
|
+
* const btc = new BitcoinConnection({
|
|
40
|
+
* network: 'testnet4',
|
|
37
41
|
* rest: { host: 'https://my-mempool/api' },
|
|
38
42
|
* executor: myCustomExecutor,
|
|
39
43
|
* });
|
|
@@ -67,44 +71,6 @@ export class BitcoinConnection {
|
|
|
67
71
|
this.data = getNetwork(options.network);
|
|
68
72
|
}
|
|
69
73
|
|
|
70
|
-
/**
|
|
71
|
-
* Create a connection for a single network with optional REST/RPC endpoint overrides.
|
|
72
|
-
* Merges overrides on top of defaults from DEFAULT_BITCOIN_NETWORK_CONFIG.
|
|
73
|
-
* Does not read environment variables.
|
|
74
|
-
*
|
|
75
|
-
* @param network The network name (e.g., 'regtest', 'testnet4', 'bitcoin').
|
|
76
|
-
* @param overrides Optional endpoint and executor overrides.
|
|
77
|
-
* @returns A BitcoinConnection for the requested network.
|
|
78
|
-
*/
|
|
79
|
-
static forNetwork(
|
|
80
|
-
network: NetworkName,
|
|
81
|
-
overrides?: { rest?: Partial<RestConfig>; rpc?: RpcConfig; executor?: HttpExecutor }
|
|
82
|
-
): BitcoinConnection {
|
|
83
|
-
const defaults = DEFAULT_BITCOIN_NETWORK_CONFIG[network];
|
|
84
|
-
|
|
85
|
-
if (!defaults) {
|
|
86
|
-
throw new MethodError(
|
|
87
|
-
`Unknown network '${network}'. Available: bitcoin, testnet3, testnet4, signet, mutinynet, regtest`,
|
|
88
|
-
'UNKNOWN_NETWORK',
|
|
89
|
-
{ network }
|
|
90
|
-
);
|
|
91
|
-
}
|
|
92
|
-
|
|
93
|
-
const restCfg: RestConfig = { ...defaults.rest, ...overrides?.rest };
|
|
94
|
-
|
|
95
|
-
const hasRpc = defaults.rpc !== undefined || overrides?.rpc !== undefined;
|
|
96
|
-
const rpcCfg = hasRpc
|
|
97
|
-
? { ...defaults.rpc, ...overrides?.rpc } as RpcConfig
|
|
98
|
-
: undefined;
|
|
99
|
-
|
|
100
|
-
return new BitcoinConnection({
|
|
101
|
-
network,
|
|
102
|
-
rest : restCfg,
|
|
103
|
-
rpc : rpcCfg,
|
|
104
|
-
executor : overrides?.executor,
|
|
105
|
-
});
|
|
106
|
-
}
|
|
107
|
-
|
|
108
74
|
/**
|
|
109
75
|
* Converts Bitcoin (BTC) to satoshis.
|
|
110
76
|
* Uses string-based arithmetic to avoid floating-point precision errors.
|
package/src/constants.ts
CHANGED
|
@@ -4,49 +4,3 @@ export const COINBASE_MATURITY_DELAY = 100;
|
|
|
4
4
|
export const DEFAULT_BLOCK_CONFIRMATIONS = 7;
|
|
5
5
|
export const TXIN_WITNESS_COINBASE = '0000000000000000000000000000000000000000000000000000000000000000';
|
|
6
6
|
export const GENESIS_TX_ID = '4a5e1e4baab89f3a32518a88c31bc87f618f76673e2cc77ab2127b7afdeda33b';
|
|
7
|
-
|
|
8
|
-
/**
|
|
9
|
-
* Default endpoint configuration per Bitcoin network.
|
|
10
|
-
*
|
|
11
|
-
* **Regtest RPC:** Credentials are intentionally omitted — callers must
|
|
12
|
-
* provide `username` and `password` via overrides or explicit config.
|
|
13
|
-
* This prevents accidentally using hardcoded credentials in non-local
|
|
14
|
-
* environments.
|
|
15
|
-
*
|
|
16
|
-
* @example
|
|
17
|
-
* ```ts
|
|
18
|
-
* // Provide credentials explicitly
|
|
19
|
-
* BitcoinConnection.forNetwork('regtest', {
|
|
20
|
-
* rpc: { username: 'polaruser', password: 'polarpass' },
|
|
21
|
-
* });
|
|
22
|
-
* ```
|
|
23
|
-
*/
|
|
24
|
-
export const DEFAULT_BITCOIN_NETWORK_CONFIG = {
|
|
25
|
-
bitcoin : {
|
|
26
|
-
rpc : undefined,
|
|
27
|
-
rest : { host: 'https://mempool.space/api' }
|
|
28
|
-
},
|
|
29
|
-
testnet3 : {
|
|
30
|
-
rpc : undefined,
|
|
31
|
-
rest : { host: 'https://mempool.space/testnet/api' }
|
|
32
|
-
},
|
|
33
|
-
testnet4 : {
|
|
34
|
-
rpc : undefined,
|
|
35
|
-
rest : { host: 'https://mempool.space/testnet4/api' }
|
|
36
|
-
},
|
|
37
|
-
signet : {
|
|
38
|
-
rpc : undefined,
|
|
39
|
-
rest : { host: 'https://mempool.space/signet/api' }
|
|
40
|
-
},
|
|
41
|
-
mutinynet : {
|
|
42
|
-
rpc : undefined,
|
|
43
|
-
rest : { host: 'https://mutinynet.com/api' }
|
|
44
|
-
},
|
|
45
|
-
regtest : {
|
|
46
|
-
rpc : {
|
|
47
|
-
host : 'http://localhost:18443',
|
|
48
|
-
allowDefaultWallet : true,
|
|
49
|
-
},
|
|
50
|
-
rest : { host: 'http://localhost:3000' }
|
|
51
|
-
},
|
|
52
|
-
} as const;
|