@btc-vision/transaction 1.0.100 → 1.0.102
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/.vscode/settings.json +10 -0
- package/LICENSE +21 -0
- package/browser/_version.d.ts +1 -1
- package/browser/generators/Features.d.ts +4 -1
- package/browser/generators/builders/CalldataGenerator.d.ts +1 -1
- package/browser/index.js +1 -1
- package/browser/keypair/EcKeyPair.d.ts +2 -2
- package/browser/metadata/contracts/wBTC.d.ts +2 -2
- package/browser/transaction/TransactionFactory.d.ts +4 -5
- package/browser/transaction/browser/extensions/UnisatSigner.d.ts +2 -2
- package/browser/transaction/browser/types/Unisat.d.ts +1 -2
- package/browser/transaction/builders/CustomScriptTransaction.d.ts +1 -1
- package/browser/transaction/builders/DeploymentTransaction.d.ts +1 -1
- package/browser/transaction/builders/FundingTransaction.d.ts +1 -1
- package/browser/transaction/processor/PsbtTransaction.d.ts +2 -2
- package/browser/utils/BitcoinUtils.d.ts +1 -1
- package/browser/utxo/OPNetLimitedProvider.d.ts +3 -3
- package/build/_version.d.ts +1 -1
- package/build/_version.js +1 -1
- package/build/generators/Features.d.ts +4 -1
- package/build/generators/Features.js +4 -1
- package/build/generators/builders/CalldataGenerator.d.ts +1 -1
- package/build/generators/builders/CalldataGenerator.js +5 -3
- package/build/generators/builders/MultiSignGenerator.js +2 -2
- package/build/keypair/EcKeyPair.d.ts +2 -2
- package/build/keypair/EcKeyPair.js +8 -5
- package/build/metadata/contracts/wBTC.d.ts +2 -2
- package/build/metadata/contracts/wBTC.js +2 -2
- package/build/metadata/tokens.js +2 -2
- package/build/signer/TweakedSigner.js +1 -1
- package/build/transaction/TransactionFactory.d.ts +4 -5
- package/build/transaction/TransactionFactory.js +6 -7
- package/build/transaction/browser/extensions/UnisatSigner.d.ts +2 -2
- package/build/transaction/browser/extensions/UnisatSigner.js +3 -3
- package/build/transaction/browser/types/Unisat.d.ts +1 -2
- package/build/transaction/builders/CustomScriptTransaction.d.ts +1 -1
- package/build/transaction/builders/CustomScriptTransaction.js +7 -7
- package/build/transaction/builders/DeploymentTransaction.d.ts +1 -1
- package/build/transaction/builders/DeploymentTransaction.js +2 -2
- package/build/transaction/builders/FundingTransaction.d.ts +1 -1
- package/build/transaction/builders/FundingTransaction.js +2 -2
- package/build/transaction/builders/MultiSignTransaction.js +7 -7
- package/build/transaction/builders/SharedInteractionTransaction.js +3 -3
- package/build/transaction/builders/TransactionBuilder.js +6 -6
- package/build/transaction/builders/UnwrapTransaction.js +4 -4
- package/build/transaction/builders/WrapTransaction.js +1 -1
- package/build/transaction/processor/PsbtTransaction.d.ts +2 -2
- package/build/transaction/processor/PsbtTransaction.js +2 -2
- package/build/transaction/shared/TweakedTransaction.js +4 -4
- package/build/utils/BitcoinUtils.d.ts +1 -1
- package/build/utils/BitcoinUtils.js +1 -1
- package/build/utxo/OPNetLimitedProvider.d.ts +3 -3
- package/build/utxo/OPNetLimitedProvider.js +7 -7
- package/eslint.config.js +38 -0
- package/gulpfile.js +19 -45
- package/package.json +14 -8
- package/src/_version.ts +1 -1
- package/src/generators/Features.ts +5 -1
- package/src/generators/builders/CalldataGenerator.ts +6 -4
- package/src/generators/builders/MultiSignGenerator.ts +6 -4
- package/src/keypair/EcKeyPair.ts +10 -8
- package/src/metadata/contracts/wBTC.ts +3 -3
- package/src/metadata/tokens.ts +2 -2
- package/src/signer/TweakedSigner.ts +4 -4
- package/src/transaction/TransactionFactory.ts +18 -20
- package/src/transaction/browser/extensions/UnisatSigner.ts +6 -6
- package/src/transaction/browser/types/Unisat.ts +1 -3
- package/src/transaction/builders/CustomScriptTransaction.ts +7 -7
- package/src/transaction/builders/DeploymentTransaction.ts +5 -5
- package/src/transaction/builders/FundingTransaction.ts +2 -2
- package/src/transaction/builders/MultiSignTransaction.ts +8 -7
- package/src/transaction/builders/SharedInteractionTransaction.ts +3 -3
- package/src/transaction/builders/TransactionBuilder.ts +6 -6
- package/src/transaction/builders/UnwrapTransaction.ts +4 -4
- package/src/transaction/builders/WrapTransaction.ts +1 -1
- package/src/transaction/processor/PsbtTransaction.ts +4 -4
- package/src/transaction/shared/TweakedTransaction.ts +19 -11
- package/src/utils/BitcoinUtils.ts +3 -3
- package/src/utxo/OPNetLimitedProvider.ts +19 -10
- package/webpack.config.js +1 -0
- package/LICENSE.md +0 -62
|
@@ -203,7 +203,7 @@ export class TransactionBuilder extends TweakedTransaction {
|
|
|
203
203
|
if (value < TransactionBuilder.MINIMUM_DUST) {
|
|
204
204
|
throw new Error(`Value to send is less than the minimum dust ${value} < ${TransactionBuilder.MINIMUM_DUST}`);
|
|
205
205
|
}
|
|
206
|
-
for (
|
|
206
|
+
for (const output of this.outputs) {
|
|
207
207
|
if ('address' in output && output.address === this.to) {
|
|
208
208
|
output.value += Number(value);
|
|
209
209
|
return;
|
|
@@ -219,14 +219,14 @@ export class TransactionBuilder extends TweakedTransaction {
|
|
|
219
219
|
}
|
|
220
220
|
calculateTotalUTXOAmount() {
|
|
221
221
|
let total = 0n;
|
|
222
|
-
for (
|
|
222
|
+
for (const utxo of this.utxos) {
|
|
223
223
|
total += utxo.value;
|
|
224
224
|
}
|
|
225
225
|
return total;
|
|
226
226
|
}
|
|
227
227
|
calculateTotalVOutAmount() {
|
|
228
228
|
let total = 0n;
|
|
229
|
-
for (
|
|
229
|
+
for (const utxo of this.utxos) {
|
|
230
230
|
total += utxo.value;
|
|
231
231
|
}
|
|
232
232
|
return total;
|
|
@@ -266,7 +266,7 @@ export class TransactionBuilder extends TweakedTransaction {
|
|
|
266
266
|
return this.tapData.output;
|
|
267
267
|
}
|
|
268
268
|
verifyUTXOValidity() {
|
|
269
|
-
for (
|
|
269
|
+
for (const utxo of this.utxos) {
|
|
270
270
|
if (!utxo.scriptPubKey) {
|
|
271
271
|
throw new Error('Address is required');
|
|
272
272
|
}
|
|
@@ -274,7 +274,7 @@ export class TransactionBuilder extends TweakedTransaction {
|
|
|
274
274
|
}
|
|
275
275
|
async setFeeOutput(output) {
|
|
276
276
|
const initialValue = output.value;
|
|
277
|
-
|
|
277
|
+
const fee = await this.estimateTransactionFees();
|
|
278
278
|
output.value = initialValue - Number(fee);
|
|
279
279
|
if (output.value < TransactionBuilder.MINIMUM_DUST) {
|
|
280
280
|
this.feeOutput = null;
|
|
@@ -284,7 +284,7 @@ export class TransactionBuilder extends TweakedTransaction {
|
|
|
284
284
|
}
|
|
285
285
|
else {
|
|
286
286
|
this.feeOutput = output;
|
|
287
|
-
|
|
287
|
+
const fee = await this.estimateTransactionFees();
|
|
288
288
|
if (fee > BigInt(initialValue)) {
|
|
289
289
|
throw new Error(`estimateTransactionFees: Insufficient funds to pay the fees. Fee: ${fee} > Value: ${initialValue}. Total input: ${this.totalInputAmount} sat`);
|
|
290
290
|
}
|
|
@@ -64,7 +64,7 @@ export class UnwrapTransaction extends SharedInteractionTransaction {
|
|
|
64
64
|
}
|
|
65
65
|
getRefund() {
|
|
66
66
|
let losses = -currentConsensusConfig.UNWRAP_CONSOLIDATION_PREPAID_FEES_SAT;
|
|
67
|
-
for (
|
|
67
|
+
for (const vault of this.vaultUTXOs) {
|
|
68
68
|
for (let i = 0; i < vault.utxos.length; i++) {
|
|
69
69
|
losses += currentConsensusConfig.UNWRAP_CONSOLIDATION_PREPAID_FEES_SAT;
|
|
70
70
|
}
|
|
@@ -72,13 +72,13 @@ export class UnwrapTransaction extends SharedInteractionTransaction {
|
|
|
72
72
|
return losses;
|
|
73
73
|
}
|
|
74
74
|
getFeeLossOrRefund() {
|
|
75
|
-
|
|
75
|
+
const refund = this.getRefund();
|
|
76
76
|
return refund - this.estimatedFeeLoss;
|
|
77
77
|
}
|
|
78
78
|
mergeVaults() {
|
|
79
79
|
const totalInputAmount = this.getVaultTotalOutputAmount(this.vaultUTXOs);
|
|
80
80
|
let refund = this.getRefund();
|
|
81
|
-
|
|
81
|
+
const outputLeftAmount = totalInputAmount - refund - this.amount;
|
|
82
82
|
if (outputLeftAmount === currentConsensusConfig.UNWRAP_CONSOLIDATION_PREPAID_FEES_SAT) {
|
|
83
83
|
refund += currentConsensusConfig.UNWRAP_CONSOLIDATION_PREPAID_FEES_SAT;
|
|
84
84
|
}
|
|
@@ -90,7 +90,7 @@ export class UnwrapTransaction extends SharedInteractionTransaction {
|
|
|
90
90
|
if (!bestVault) {
|
|
91
91
|
throw new Error('No vaults provided');
|
|
92
92
|
}
|
|
93
|
-
|
|
93
|
+
const hasConsolidation = outputLeftAmount > currentConsensusConfig.VAULT_MINIMUM_AMOUNT &&
|
|
94
94
|
outputLeftAmount - currentConsensusConfig.UNWRAP_CONSOLIDATION_PREPAID_FEES_SAT !== 0n;
|
|
95
95
|
if (hasConsolidation) {
|
|
96
96
|
this.success(`Consolidating output with ${outputLeftAmount} sat.`);
|
|
@@ -76,7 +76,7 @@ export class WrapTransaction extends SharedInteractionTransaction {
|
|
|
76
76
|
async buildTransaction() {
|
|
77
77
|
if (!this.to)
|
|
78
78
|
throw new Error('To address is required');
|
|
79
|
-
const selectedRedeem =
|
|
79
|
+
const selectedRedeem = this.scriptSigner
|
|
80
80
|
? this.targetScriptRedeem
|
|
81
81
|
: this.leftOverFundsScriptRedeem;
|
|
82
82
|
if (!selectedRedeem) {
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
+
import { Address } from '@btc-vision/bsi-binary';
|
|
1
2
|
import { Network, Psbt, Signer, Transaction } from 'bitcoinjs-lib';
|
|
2
|
-
import { ITweakedTransactionData, TweakedTransaction } from '../shared/TweakedTransaction.js';
|
|
3
3
|
import { PsbtInputExtended, PsbtOutputExtended } from '../interfaces/Tap.js';
|
|
4
|
-
import {
|
|
4
|
+
import { ITweakedTransactionData, TweakedTransaction } from '../shared/TweakedTransaction.js';
|
|
5
5
|
export interface PsbtTransactionData extends ITweakedTransactionData {
|
|
6
6
|
readonly psbt: Psbt;
|
|
7
7
|
readonly signer: Signer;
|
|
@@ -59,7 +59,7 @@ export class PsbtTransaction extends TweakedTransaction {
|
|
|
59
59
|
try {
|
|
60
60
|
const inputs = this.transaction.data.inputs;
|
|
61
61
|
for (let i = n; i < inputs.length; i++) {
|
|
62
|
-
|
|
62
|
+
const input = inputs[i];
|
|
63
63
|
if (input.finalScriptWitness) {
|
|
64
64
|
this.transaction.finalizeTaprootInput(i, input.finalScriptWitness);
|
|
65
65
|
}
|
|
@@ -70,7 +70,7 @@ export class PsbtTransaction extends TweakedTransaction {
|
|
|
70
70
|
return true;
|
|
71
71
|
}
|
|
72
72
|
catch (e) {
|
|
73
|
-
this.warn(e.stack);
|
|
73
|
+
this.warn(e.stack || "Couldn't finalize inputs");
|
|
74
74
|
return false;
|
|
75
75
|
}
|
|
76
76
|
}
|
|
@@ -79,7 +79,7 @@ export class TweakedTransaction extends Logger {
|
|
|
79
79
|
throw new Error('Sighash types are required');
|
|
80
80
|
}
|
|
81
81
|
let signHash = 0;
|
|
82
|
-
for (
|
|
82
|
+
for (const sighashType of sighashTypes) {
|
|
83
83
|
signHash |= sighashType;
|
|
84
84
|
}
|
|
85
85
|
return signHash || 0;
|
|
@@ -106,7 +106,7 @@ export class TweakedTransaction extends Logger {
|
|
|
106
106
|
if (this.signed)
|
|
107
107
|
throw new Error('Transaction is already signed');
|
|
108
108
|
this.sequence = TransactionSequence.FINAL;
|
|
109
|
-
for (
|
|
109
|
+
for (const input of this.inputs) {
|
|
110
110
|
input.sequence = TransactionSequence.FINAL;
|
|
111
111
|
}
|
|
112
112
|
}
|
|
@@ -168,7 +168,7 @@ export class TweakedTransaction extends Logger {
|
|
|
168
168
|
}
|
|
169
169
|
return;
|
|
170
170
|
}
|
|
171
|
-
catch
|
|
171
|
+
catch { }
|
|
172
172
|
}
|
|
173
173
|
}
|
|
174
174
|
try {
|
|
@@ -195,7 +195,7 @@ export class TweakedTransaction extends Logger {
|
|
|
195
195
|
}
|
|
196
196
|
async signInputs(transaction) {
|
|
197
197
|
for (let i = 0; i < transaction.data.inputs.length; i++) {
|
|
198
|
-
|
|
198
|
+
const input = transaction.data.inputs[i];
|
|
199
199
|
try {
|
|
200
200
|
await this.signInput(transaction, input, i);
|
|
201
201
|
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { VaultUTXOs } from '../transaction/processor/PsbtTransaction.js';
|
|
2
2
|
export declare class BitcoinUtils {
|
|
3
|
-
static btcToSatoshi(btc: number):
|
|
3
|
+
static btcToSatoshi(btc: number): bigint;
|
|
4
4
|
static rndBytes(): Buffer;
|
|
5
5
|
static getUnsafeRandomValues(length: number): Buffer;
|
|
6
6
|
static opnetHash(data: Buffer): string;
|
|
@@ -41,7 +41,7 @@ export class BitcoinUtils {
|
|
|
41
41
|
vaults = BitcoinUtils.orderVaultsByAddress(vaults);
|
|
42
42
|
let mostPublicKeys = 0;
|
|
43
43
|
let vault;
|
|
44
|
-
for (
|
|
44
|
+
for (const v of vaults) {
|
|
45
45
|
if (v.publicKeys.length > mostPublicKeys) {
|
|
46
46
|
mostPublicKeys = v.publicKeys.length;
|
|
47
47
|
vault = v;
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { FetchUTXOParams, FetchUTXOParamsMultiAddress, UTXO } from './interfaces/IUTXO.js';
|
|
2
|
-
import { WrappedGeneration } from '../wbtc/WrappedGenerationParameters.js';
|
|
3
|
-
import { BroadcastResponse } from './interfaces/BroadcastResponse.js';
|
|
4
1
|
import { Address } from '@btc-vision/bsi-binary';
|
|
5
2
|
import { UnwrapGeneration } from '../wbtc/UnwrapGeneration.js';
|
|
3
|
+
import { WrappedGeneration } from '../wbtc/WrappedGenerationParameters.js';
|
|
4
|
+
import { BroadcastResponse } from './interfaces/BroadcastResponse.js';
|
|
5
|
+
import { FetchUTXOParams, FetchUTXOParamsMultiAddress, UTXO } from './interfaces/IUTXO.js';
|
|
6
6
|
export declare class OPNetLimitedProvider {
|
|
7
7
|
private readonly opnetAPIUrl;
|
|
8
8
|
private readonly utxoPath;
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { WrappedGeneration } from '../wbtc/WrappedGenerationParameters.js';
|
|
2
|
-
import { UnwrapGeneration } from '../wbtc/UnwrapGeneration.js';
|
|
3
1
|
import { currentConsensusConfig } from '../consensus/ConsensusConfig.js';
|
|
2
|
+
import { UnwrapGeneration } from '../wbtc/UnwrapGeneration.js';
|
|
3
|
+
import { WrappedGeneration } from '../wbtc/WrappedGenerationParameters.js';
|
|
4
4
|
export class OPNetLimitedProvider {
|
|
5
5
|
constructor(opnetAPIUrl) {
|
|
6
6
|
this.opnetAPIUrl = opnetAPIUrl;
|
|
@@ -19,7 +19,7 @@ export class OPNetLimitedProvider {
|
|
|
19
19
|
if (!resp.ok) {
|
|
20
20
|
throw new Error(`Failed to fetch UTXO data: ${resp.statusText}`);
|
|
21
21
|
}
|
|
22
|
-
const fetchedData = await resp.json();
|
|
22
|
+
const fetchedData = (await resp.json());
|
|
23
23
|
if (fetchedData.length === 0) {
|
|
24
24
|
throw new Error('No UTXO found');
|
|
25
25
|
}
|
|
@@ -29,7 +29,7 @@ export class OPNetLimitedProvider {
|
|
|
29
29
|
if (meetCriteria.length === 0) {
|
|
30
30
|
throw new Error('No UTXO found (minAmount)');
|
|
31
31
|
}
|
|
32
|
-
|
|
32
|
+
const finalUTXOs = [];
|
|
33
33
|
let currentAmount = 0n;
|
|
34
34
|
const amountRequested = settings.requestedAmount;
|
|
35
35
|
for (const utxo of meetCriteria) {
|
|
@@ -52,7 +52,7 @@ export class OPNetLimitedProvider {
|
|
|
52
52
|
}
|
|
53
53
|
async fetchUTXOMultiAddr(settings) {
|
|
54
54
|
const promises = [];
|
|
55
|
-
for (
|
|
55
|
+
for (const address of settings.addresses) {
|
|
56
56
|
const params = {
|
|
57
57
|
address: address,
|
|
58
58
|
minAmount: settings.minAmount,
|
|
@@ -69,7 +69,7 @@ export class OPNetLimitedProvider {
|
|
|
69
69
|
const finalUTXOs = [];
|
|
70
70
|
let currentAmount = 0n;
|
|
71
71
|
for (let i = 0; i < all.length; i++) {
|
|
72
|
-
|
|
72
|
+
const utxo = all[i];
|
|
73
73
|
if (currentAmount >= settings.requestedAmount) {
|
|
74
74
|
break;
|
|
75
75
|
}
|
|
@@ -104,7 +104,7 @@ export class OPNetLimitedProvider {
|
|
|
104
104
|
if (!resp.ok) {
|
|
105
105
|
throw new Error(`Failed to fetch to rpc: ${resp.statusText}`);
|
|
106
106
|
}
|
|
107
|
-
const fetchedData = await resp.json();
|
|
107
|
+
const fetchedData = (await resp.json());
|
|
108
108
|
if (!fetchedData) {
|
|
109
109
|
throw new Error('No data fetched');
|
|
110
110
|
}
|
package/eslint.config.js
ADDED
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
// @ts-check
|
|
2
|
+
|
|
3
|
+
import eslint from '@eslint/js';
|
|
4
|
+
import tseslint from 'typescript-eslint';
|
|
5
|
+
|
|
6
|
+
export default tseslint.config(
|
|
7
|
+
eslint.configs.recommended,
|
|
8
|
+
...tseslint.configs.strictTypeChecked,
|
|
9
|
+
{
|
|
10
|
+
languageOptions: {
|
|
11
|
+
parserOptions: {
|
|
12
|
+
projectService: true,
|
|
13
|
+
tsconfigDirName: import.meta.dirname,
|
|
14
|
+
},
|
|
15
|
+
},
|
|
16
|
+
rules: {
|
|
17
|
+
'no-undef': 'off',
|
|
18
|
+
'@typescript-eslint/no-unused-vars': 'off',
|
|
19
|
+
'no-empty': 'off',
|
|
20
|
+
'@typescript-eslint/restrict-template-expressions': 'off',
|
|
21
|
+
'@typescript-eslint/only-throw-error': 'off',
|
|
22
|
+
'@typescript-eslint/no-unnecessary-condition': 'off',
|
|
23
|
+
'@typescript-eslint/unbound-method': 'warn',
|
|
24
|
+
'@typescript-eslint/no-confusing-void-expression': 'off',
|
|
25
|
+
'@typescript-eslint/no-extraneous-class': 'off',
|
|
26
|
+
'no-async-promise-executor': 'off',
|
|
27
|
+
'@typescript-eslint/no-misused-promises': 'off',
|
|
28
|
+
'@typescript-eslint/no-unnecessary-type-parameters': 'off',
|
|
29
|
+
'@typescript-eslint/no-duplicate-enum-values': 'off',
|
|
30
|
+
'prefer-spread': 'off',
|
|
31
|
+
'@typescript-eslint/no-empty-object-type': 'off',
|
|
32
|
+
},
|
|
33
|
+
},
|
|
34
|
+
{
|
|
35
|
+
files: ['**/*.js'],
|
|
36
|
+
...tseslint.configs.disableTypeChecked,
|
|
37
|
+
},
|
|
38
|
+
);
|
package/gulpfile.js
CHANGED
|
@@ -1,68 +1,42 @@
|
|
|
1
|
+
import gulpESLintNew from 'gulp-eslint-new';
|
|
1
2
|
import gulp from 'gulp';
|
|
2
3
|
import gulpcache from 'gulp-cached';
|
|
4
|
+
|
|
5
|
+
import gulpClean from 'gulp-clean';
|
|
3
6
|
import logger from 'gulp-logger';
|
|
4
7
|
import ts from 'gulp-typescript';
|
|
5
8
|
|
|
6
|
-
|
|
9
|
+
process.on('uncaughtException', function (err) {
|
|
10
|
+
console.log('Caught exception: ', err);
|
|
11
|
+
});
|
|
7
12
|
|
|
8
|
-
|
|
9
|
-
console.error('Error:', e);
|
|
10
|
-
}
|
|
13
|
+
const tsProject = ts.createProject('tsconfig.json');
|
|
11
14
|
|
|
12
15
|
function buildESM() {
|
|
13
|
-
return
|
|
16
|
+
return tsProject
|
|
14
17
|
.src()
|
|
15
18
|
.pipe(gulpcache('ts-esm'))
|
|
16
19
|
.pipe(
|
|
17
20
|
logger({
|
|
18
|
-
before: 'Starting
|
|
19
|
-
after: '
|
|
21
|
+
before: 'Starting...',
|
|
22
|
+
after: 'Project compiled!',
|
|
20
23
|
extname: '.js',
|
|
21
24
|
showChange: true,
|
|
22
25
|
}),
|
|
23
26
|
)
|
|
24
|
-
.pipe(
|
|
25
|
-
.
|
|
27
|
+
.pipe(gulpESLintNew())
|
|
28
|
+
.pipe(gulpESLintNew.format())
|
|
29
|
+
.pipe(tsProject())
|
|
26
30
|
.pipe(gulp.dest('build'));
|
|
27
31
|
}
|
|
28
32
|
|
|
29
|
-
function
|
|
30
|
-
return gulp
|
|
31
|
-
.src('./src/**/*.yaml')
|
|
32
|
-
.pipe(
|
|
33
|
-
logger({
|
|
34
|
-
before: 'Processing YAML files...',
|
|
35
|
-
after: 'YAML files processed!',
|
|
36
|
-
extname: '.yaml',
|
|
37
|
-
showChange: true,
|
|
38
|
-
}),
|
|
39
|
-
)
|
|
40
|
-
.pipe(gulpcache('yaml'))
|
|
41
|
-
.pipe(gulp.dest('./build/'))
|
|
42
|
-
.on('end', () => {
|
|
43
|
-
gulp.src('./src/**/*.proto')
|
|
44
|
-
.pipe(
|
|
45
|
-
logger({
|
|
46
|
-
before: 'Processing Proto files...',
|
|
47
|
-
after: 'Proto files processed!',
|
|
48
|
-
extname: '.proto',
|
|
49
|
-
showChange: true,
|
|
50
|
-
}),
|
|
51
|
-
)
|
|
52
|
-
.pipe(gulpcache('proto'))
|
|
53
|
-
.pipe(gulp.dest('./build/'));
|
|
54
|
-
});
|
|
33
|
+
export async function clean() {
|
|
34
|
+
return gulp.src('./build/src', { read: false }).pipe(gulpClean());
|
|
55
35
|
}
|
|
56
36
|
|
|
57
|
-
const build =
|
|
58
|
-
|
|
59
|
-
gulp.task('build', build);
|
|
60
|
-
gulp.task('default', build);
|
|
37
|
+
export const build = buildESM;
|
|
38
|
+
export default build;
|
|
61
39
|
|
|
62
|
-
|
|
40
|
+
export function watch() {
|
|
63
41
|
gulp.watch(['src/**/*.ts', 'src/**/*.js'], gulp.series(buildESM));
|
|
64
|
-
|
|
65
|
-
['src/**/*.yaml', 'src/**/*.proto', '*.yaml', '*.proto', '*.conf', 'src/config/*.conf'],
|
|
66
|
-
buildProtoYaml,
|
|
67
|
-
);
|
|
68
|
-
});
|
|
42
|
+
}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@btc-vision/transaction",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "1.0.
|
|
4
|
+
"version": "1.0.102",
|
|
5
5
|
"author": "BlobMaster41",
|
|
6
6
|
"description": "OPNet transaction library allows you to create and sign transactions for the OPNet network.",
|
|
7
7
|
"engines": {
|
|
@@ -9,6 +9,7 @@
|
|
|
9
9
|
},
|
|
10
10
|
"exports": {
|
|
11
11
|
".": {
|
|
12
|
+
"browser": "./browser/index.js",
|
|
12
13
|
"import": "./build/index.js",
|
|
13
14
|
"require": "./build/index.js",
|
|
14
15
|
"types": "./build/index.d.ts"
|
|
@@ -20,6 +21,8 @@
|
|
|
20
21
|
}
|
|
21
22
|
},
|
|
22
23
|
"browser": {
|
|
24
|
+
"./build/index.js": "./browser/index.js",
|
|
25
|
+
"./build/index.d.ts": "./browser/index.d.ts",
|
|
23
26
|
"Buffer": "buffer",
|
|
24
27
|
"crypto": "./src/crypto/crypto-browser.js",
|
|
25
28
|
"stream": "stream-browserify",
|
|
@@ -40,7 +43,7 @@
|
|
|
40
43
|
"smart inscriptions",
|
|
41
44
|
"ordinals"
|
|
42
45
|
],
|
|
43
|
-
"license": "
|
|
46
|
+
"license": "MIT",
|
|
44
47
|
"main": "build/index.js",
|
|
45
48
|
"types": "build/index.d.ts",
|
|
46
49
|
"typings": "build/index.d.ts",
|
|
@@ -69,7 +72,7 @@
|
|
|
69
72
|
"@babel/preset-react": "^7.24.1",
|
|
70
73
|
"@babel/preset-typescript": "^7.24.1",
|
|
71
74
|
"@types/node": "^22.5.5",
|
|
72
|
-
"eslint": "^
|
|
75
|
+
"eslint": "^9.10.0",
|
|
73
76
|
"gulp": "^5.0.0",
|
|
74
77
|
"gulp-cached": "^1.1.1",
|
|
75
78
|
"gulp-logger": "^0.0.2",
|
|
@@ -79,18 +82,19 @@
|
|
|
79
82
|
"prettier": "^3.3.1",
|
|
80
83
|
"stream-browserify": "^3.0.0",
|
|
81
84
|
"stream-http": "^3.2.0",
|
|
82
|
-
"typedoc": "^0.
|
|
83
|
-
"typedoc-material-theme": "^1.0
|
|
84
|
-
"typescript-eslint": "^
|
|
85
|
-
"webpack": "^5.
|
|
85
|
+
"typedoc": "^0.26.7",
|
|
86
|
+
"typedoc-material-theme": "^1.1.0",
|
|
87
|
+
"typescript-eslint": "^8.5.0",
|
|
88
|
+
"webpack": "^5.94.0",
|
|
86
89
|
"webpack-cli": "^5.1.4"
|
|
87
90
|
},
|
|
88
91
|
"dependencies": {
|
|
89
92
|
"@babel/plugin-proposal-object-rest-spread": "^7.20.7",
|
|
90
93
|
"@bitcoinerlab/secp256k1": "^1.1.1",
|
|
91
|
-
"@btc-vision/bsi-binary": "^1.0.
|
|
94
|
+
"@btc-vision/bsi-binary": "^1.0.39",
|
|
92
95
|
"@btc-vision/bsi-bitcoin-rpc": "^1.0.26",
|
|
93
96
|
"@btc-vision/logger": "^1.0.4",
|
|
97
|
+
"@eslint/js": "^9.10.0",
|
|
94
98
|
"assert": "^2.1.0",
|
|
95
99
|
"babel-loader": "^9.1.3",
|
|
96
100
|
"babel-plugin-transform-import-meta": "^2.2.1",
|
|
@@ -103,6 +107,8 @@
|
|
|
103
107
|
"browserify-zlib": "^0.2.0",
|
|
104
108
|
"buffer": "^6.0.3",
|
|
105
109
|
"ecpair": "^2.1.0",
|
|
110
|
+
"gulp-clean": "^0.4.0",
|
|
111
|
+
"gulp-eslint-new": "^2.3.0",
|
|
106
112
|
"gulplog": "^2.2.0",
|
|
107
113
|
"process": "^0.11.10",
|
|
108
114
|
"ts-loader": "^9.5.1",
|
package/src/_version.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export const version = '1.0.
|
|
1
|
+
export const version = '1.0.101';
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { crypto, Network, networks, opcodes, script } from 'bitcoinjs-lib';
|
|
2
2
|
import { ECPairInterface } from 'ecpair';
|
|
3
3
|
import { Compressor } from '../../bytecode/Compressor.js';
|
|
4
|
-
import { Generator } from '../Generator.js';
|
|
5
4
|
import { EcKeyPair } from '../../keypair/EcKeyPair.js';
|
|
6
|
-
import { Features } from '../Features.js';
|
|
5
|
+
import { FeatureOpCodes, Features } from '../Features.js';
|
|
6
|
+
import { Generator } from '../Generator.js';
|
|
7
7
|
|
|
8
8
|
/**
|
|
9
9
|
* Class to generate bitcoin script for interaction transactions
|
|
@@ -27,7 +27,7 @@ export class CalldataGenerator extends Generator {
|
|
|
27
27
|
public static getPubKeyAsBuffer(witnessKeys: Buffer[], network: Network): Buffer {
|
|
28
28
|
let finalBuffer: Buffer = Buffer.alloc(0);
|
|
29
29
|
|
|
30
|
-
for (
|
|
30
|
+
for (const pubKey of witnessKeys) {
|
|
31
31
|
const key: ECPairInterface = EcKeyPair.fromPublicKey(pubKey, network);
|
|
32
32
|
|
|
33
33
|
if (!key.compressed) {
|
|
@@ -130,9 +130,11 @@ export class CalldataGenerator extends Generator {
|
|
|
130
130
|
}
|
|
131
131
|
}
|
|
132
132
|
|
|
133
|
+
const featureOpcodes = features.map((feature) => FeatureOpCodes[feature]); // Get the opcodes for the features
|
|
134
|
+
|
|
133
135
|
// Write calldata
|
|
134
136
|
compiledData = compiledData.concat(
|
|
135
|
-
...
|
|
137
|
+
...featureOpcodes,
|
|
136
138
|
...[opcodes.OP_1NEGATE, ...dataChunks, opcodes.OP_ELSE, opcodes.OP_1, opcodes.OP_ENDIF],
|
|
137
139
|
);
|
|
138
140
|
|
|
@@ -21,15 +21,17 @@ export class MultiSignGenerator {
|
|
|
21
21
|
}
|
|
22
22
|
|
|
23
23
|
if (minimumSignatures > MultiSignGenerator.MAXIMUM_SUPPORTED_SIGNATURE) {
|
|
24
|
-
throw new Error(
|
|
24
|
+
throw new Error(
|
|
25
|
+
`The maximum amount of signatures is ${MultiSignGenerator.MAXIMUM_SUPPORTED_SIGNATURE}`,
|
|
26
|
+
);
|
|
25
27
|
}
|
|
26
28
|
|
|
27
29
|
const minimumRequired = Buffer.alloc(1);
|
|
28
30
|
minimumRequired.writeUInt8(minimumSignatures);
|
|
29
31
|
|
|
30
32
|
/** Remove duplicates **/
|
|
31
|
-
vaultPublicKeys = vaultPublicKeys.filter(
|
|
32
|
-
index === self.findIndex(otherBuf => buf.equals(otherBuf))
|
|
33
|
+
vaultPublicKeys = vaultPublicKeys.filter(
|
|
34
|
+
(buf, index, self) => index === self.findIndex((otherBuf) => buf.equals(otherBuf)),
|
|
33
35
|
);
|
|
34
36
|
|
|
35
37
|
/** We must order the pub keys. */
|
|
@@ -37,7 +39,7 @@ export class MultiSignGenerator {
|
|
|
37
39
|
|
|
38
40
|
let included = false;
|
|
39
41
|
const data = vaultPublicKeys.map((key) => {
|
|
40
|
-
|
|
42
|
+
const newKey = toXOnly(key);
|
|
41
43
|
if (internal && !included) included = internal.equals(newKey);
|
|
42
44
|
|
|
43
45
|
return newKey;
|
package/src/keypair/EcKeyPair.ts
CHANGED
|
@@ -1,15 +1,18 @@
|
|
|
1
|
-
import bip32, { BIP32Interface } from 'bip32';
|
|
2
|
-
import { address, initEccLib, Network, networks, payments } from 'bitcoinjs-lib';
|
|
3
|
-
import { ECPairFactory, ECPairInterface } from 'ecpair';
|
|
4
1
|
import * as ecc from '@bitcoinerlab/secp256k1';
|
|
5
2
|
import { Address } from '@btc-vision/bsi-binary';
|
|
6
|
-
import {
|
|
3
|
+
import bip32, { BIP32Factory, BIP32Interface } from 'bip32';
|
|
4
|
+
import { address, initEccLib, Network, networks, payments } from 'bitcoinjs-lib';
|
|
7
5
|
import { toXOnly } from 'bitcoinjs-lib/src/psbt/bip371.js';
|
|
6
|
+
import { ECPairFactory, ECPairInterface } from 'ecpair';
|
|
7
|
+
import { IWallet } from './interfaces/IWallet.js';
|
|
8
8
|
|
|
9
9
|
initEccLib(ecc);
|
|
10
10
|
|
|
11
|
-
|
|
12
|
-
|
|
11
|
+
const BIP32factory = typeof bip32 === 'function' ? bip32 : BIP32Factory;
|
|
12
|
+
|
|
13
|
+
if (!BIP32factory) {
|
|
14
|
+
throw new Error('Failed to load BIP32 library');
|
|
15
|
+
}
|
|
13
16
|
|
|
14
17
|
/**
|
|
15
18
|
* Class for handling EC key pairs
|
|
@@ -19,8 +22,7 @@ const BIP32Factory = typeof bip32 === 'function' ? bip32 : bip32.BIP32Factory;
|
|
|
19
22
|
* @example import { EcKeyPair } from '@btc-vision/transaction';
|
|
20
23
|
*/
|
|
21
24
|
export class EcKeyPair {
|
|
22
|
-
|
|
23
|
-
public static BIP32 = BIP32Factory(ecc);
|
|
25
|
+
public static BIP32 = BIP32factory(ecc);
|
|
24
26
|
public static ECPair = ECPairFactory(ecc);
|
|
25
27
|
|
|
26
28
|
/**
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
+
import { Address } from '@btc-vision/bsi-binary';
|
|
1
2
|
import { Network, networks } from 'bitcoinjs-lib';
|
|
3
|
+
import { ChainId } from '../../network/ChainId.js';
|
|
2
4
|
import { ContractBaseMetadata } from '../ContractBaseMetadata.js';
|
|
3
|
-
import { Address } from '@btc-vision/bsi-binary';
|
|
4
5
|
import { WBTC_ADDRESS_FRACTAL, WBTC_ADDRESS_REGTEST, WBTC_ADDRESS_TESTNET } from '../tokens.js';
|
|
5
|
-
import { ChainId } from '../../network/ChainId.js';
|
|
6
6
|
|
|
7
7
|
/**
|
|
8
8
|
* @description Wrapped Bitcoin (wBTC) contract metadata.
|
|
@@ -43,7 +43,7 @@ export class wBTC extends ContractBaseMetadata {
|
|
|
43
43
|
case networks.testnet.bech32:
|
|
44
44
|
return WBTC_ADDRESS_TESTNET;
|
|
45
45
|
default:
|
|
46
|
-
throw new Error(`Invalid network: ${network}`);
|
|
46
|
+
throw new Error(`Invalid network: ${network.bech32}`);
|
|
47
47
|
}
|
|
48
48
|
}
|
|
49
49
|
|
package/src/metadata/tokens.ts
CHANGED
|
@@ -4,8 +4,8 @@ import { ChainId } from '../network/ChainId.js';
|
|
|
4
4
|
// Addresses Regtest
|
|
5
5
|
export const FACTORY_ADDRESS_REGTEST: Address = 'bcrt1q9pf9fnpch9z2qrp5e3dgr2avzu3mypq3km2k40';
|
|
6
6
|
export const POOL_ADDRESS_REGTEST: Address = 'bcrt1qg87nx9v9ln3qyadcn0llekzjn0hx8js46ztwky';
|
|
7
|
-
export const WBTC_ADDRESS_REGTEST: Address = '
|
|
8
|
-
export const MOTO_ADDRESS_REGTEST: Address = '
|
|
7
|
+
export const WBTC_ADDRESS_REGTEST: Address = 'bcrt1qamv2ejattjgsc6k3yf3zqrp0wpuyedqgjmwx0v';
|
|
8
|
+
export const MOTO_ADDRESS_REGTEST: Address = 'bcrt1qw8w4ejas2k22y54avv7hgrslg3cd0hme58h28r';
|
|
9
9
|
export const ROUTER_ADDRESS_REGTEST: Address = 'bcrt1q9yd6mk324k0q4krmlxjky0pk65ul6hkf4u35e6';
|
|
10
10
|
|
|
11
11
|
// Addresses Testnet
|
|
@@ -1,9 +1,9 @@
|
|
|
1
|
+
import * as ecc from '@bitcoinerlab/secp256k1';
|
|
1
2
|
import { initEccLib, Network, Signer } from 'bitcoinjs-lib';
|
|
2
3
|
import { tapTweakHash } from 'bitcoinjs-lib/src/payments/bip341.js';
|
|
3
4
|
import { toXOnly } from 'bitcoinjs-lib/src/psbt/bip371.js';
|
|
4
|
-
import * as ecc from '@bitcoinerlab/secp256k1';
|
|
5
|
-
import { EcKeyPair } from '../keypair/EcKeyPair.js';
|
|
6
5
|
import { ECPairInterface } from 'ecpair';
|
|
6
|
+
import { EcKeyPair } from '../keypair/EcKeyPair.js';
|
|
7
7
|
|
|
8
8
|
initEccLib(ecc);
|
|
9
9
|
|
|
@@ -33,11 +33,11 @@ export class TweakedSigner {
|
|
|
33
33
|
* @param {TweakSettings} opts - The tweak settings
|
|
34
34
|
*/
|
|
35
35
|
public static tweakSigner(signer: ECPairInterface, opts: TweakSettings = {}): Signer {
|
|
36
|
-
let privateKey: Uint8Array | undefined = signer.privateKey
|
|
36
|
+
let privateKey: Uint8Array | undefined = signer.privateKey;
|
|
37
37
|
if (!privateKey) {
|
|
38
38
|
throw new Error('Private key is required for tweaking signer!');
|
|
39
39
|
}
|
|
40
|
-
|
|
40
|
+
|
|
41
41
|
if (signer.publicKey[0] === 3) {
|
|
42
42
|
privateKey = ecc.privateNegate(privateKey);
|
|
43
43
|
}
|