@btc-vision/transaction 1.2.1 → 1.2.3

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.
Files changed (84) hide show
  1. package/browser/_version.d.ts +1 -1
  2. package/browser/crypto/crypto-browser.d.ts +1 -1
  3. package/browser/generators/builders/CalldataGenerator.d.ts +1 -1
  4. package/browser/generators/builders/DeploymentGenerator.d.ts +1 -1
  5. package/browser/generators/builders/MineableReward.d.ts +7 -0
  6. package/browser/index.js +1 -1
  7. package/browser/opnet.d.ts +4 -0
  8. package/browser/transaction/ContractAddress.d.ts +1 -0
  9. package/browser/transaction/TransactionFactory.d.ts +19 -4
  10. package/browser/transaction/browser/WalletConnection.d.ts +18 -0
  11. package/browser/transaction/browser/types/Xverse.d.ts +24 -10
  12. package/browser/transaction/builders/ChallengeSolutionTransaction.d.ts +18 -0
  13. package/browser/transaction/builders/DeploymentTransaction.d.ts +4 -0
  14. package/browser/transaction/builders/SharedInteractionTransaction.d.ts +5 -0
  15. package/browser/transaction/builders/TransactionBuilder.d.ts +2 -0
  16. package/browser/transaction/enums/TransactionType.d.ts +3 -4
  17. package/browser/transaction/interfaces/ITransactionParameters.d.ts +6 -0
  18. package/browser/transaction/mineable/ChallengeGenerator.d.ts +9 -0
  19. package/browser/utxo/interfaces/IUTXO.d.ts +1 -1
  20. package/browser/verification/TapscriptVerificator.d.ts +1 -1
  21. package/build/_version.d.ts +1 -1
  22. package/build/_version.js +1 -1
  23. package/build/generators/Generator.js +1 -1
  24. package/build/generators/builders/CalldataGenerator.d.ts +1 -1
  25. package/build/generators/builders/CalldataGenerator.js +7 -26
  26. package/build/generators/builders/DeploymentGenerator.d.ts +1 -1
  27. package/build/generators/builders/DeploymentGenerator.js +9 -6
  28. package/build/generators/builders/LegacyCalldataGenerator.js +5 -1
  29. package/build/generators/builders/MineableReward.d.ts +7 -0
  30. package/build/generators/builders/MineableReward.js +47 -0
  31. package/build/opnet.d.ts +4 -0
  32. package/build/opnet.js +4 -0
  33. package/build/transaction/ContractAddress.d.ts +1 -0
  34. package/build/transaction/ContractAddress.js +4 -1
  35. package/build/transaction/TransactionFactory.d.ts +19 -4
  36. package/build/transaction/TransactionFactory.js +32 -0
  37. package/build/transaction/browser/WalletConnection.d.ts +18 -0
  38. package/build/transaction/browser/WalletConnection.js +95 -0
  39. package/build/transaction/browser/extensions/UnisatSigner.js +5 -2
  40. package/build/transaction/browser/extensions/XverseSigner.js +15 -9
  41. package/build/transaction/browser/types/Xverse.d.ts +24 -10
  42. package/build/transaction/builders/ChallengeSolutionTransaction.d.ts +18 -0
  43. package/build/transaction/builders/ChallengeSolutionTransaction.js +51 -0
  44. package/build/transaction/builders/DeploymentTransaction.d.ts +4 -0
  45. package/build/transaction/builders/DeploymentTransaction.js +23 -4
  46. package/build/transaction/builders/InteractionTransaction.js +1 -1
  47. package/build/transaction/builders/SharedInteractionTransaction.d.ts +5 -0
  48. package/build/transaction/builders/SharedInteractionTransaction.js +35 -13
  49. package/build/transaction/builders/TransactionBuilder.d.ts +2 -0
  50. package/build/transaction/builders/TransactionBuilder.js +2 -0
  51. package/build/transaction/enums/TransactionType.d.ts +3 -4
  52. package/build/transaction/enums/TransactionType.js +3 -4
  53. package/build/transaction/interfaces/ITransactionParameters.d.ts +6 -0
  54. package/build/transaction/mineable/ChallengeGenerator.d.ts +9 -0
  55. package/build/transaction/mineable/ChallengeGenerator.js +28 -0
  56. package/build/transaction/shared/TweakedTransaction.js +1 -1
  57. package/build/utxo/interfaces/IUTXO.d.ts +1 -1
  58. package/build/verification/TapscriptVerificator.d.ts +1 -1
  59. package/build/verification/TapscriptVerificator.js +2 -8
  60. package/package.json +3 -3
  61. package/src/_version.ts +1 -1
  62. package/src/generators/Generator.ts +1 -1
  63. package/src/generators/builders/CalldataGenerator.ts +10 -41
  64. package/src/generators/builders/DeploymentGenerator.ts +18 -7
  65. package/src/generators/builders/LegacyCalldataGenerator.ts +5 -1
  66. package/src/generators/builders/MineableReward.ts +63 -0
  67. package/src/opnet.ts +5 -0
  68. package/src/transaction/ContractAddress.ts +5 -1
  69. package/src/transaction/TransactionFactory.ts +66 -3
  70. package/src/transaction/browser/WalletConnection.ts +110 -0
  71. package/src/transaction/browser/extensions/UnisatSigner.ts +7 -3
  72. package/src/transaction/browser/extensions/XverseSigner.ts +24 -23
  73. package/src/transaction/browser/types/Xverse.ts +50 -36
  74. package/src/transaction/builders/ChallengeSolutionTransaction.ts +88 -0
  75. package/src/transaction/builders/DeploymentTransaction.ts +46 -3
  76. package/src/transaction/builders/InteractionTransaction.ts +1 -0
  77. package/src/transaction/builders/SharedInteractionTransaction.ts +54 -14
  78. package/src/transaction/builders/TransactionBuilder.ts +3 -0
  79. package/src/transaction/enums/TransactionType.ts +3 -4
  80. package/src/transaction/interfaces/ITransactionParameters.ts +8 -15
  81. package/src/transaction/mineable/ChallengeGenerator.ts +39 -0
  82. package/src/transaction/shared/TweakedTransaction.ts +1 -1
  83. package/src/utxo/interfaces/IUTXO.ts +1 -1
  84. package/src/verification/TapscriptVerificator.ts +3 -18
@@ -4,12 +4,14 @@ import { ICustomTransactionParameters } from './builders/CustomScriptTransaction
4
4
  import { FundingTransaction } from './builders/FundingTransaction.js';
5
5
  import { TransactionBuilder } from './builders/TransactionBuilder.js';
6
6
  import { TransactionType } from './enums/TransactionType.js';
7
- import { IDeploymentParameters, IFundingTransactionParameters, IInteractionParameters } from './interfaces/ITransactionParameters.js';
7
+ import { IChallengeSolutionTransactionParameters, IDeploymentParameters, IFundingTransactionParameters, IInteractionParameters } from './interfaces/ITransactionParameters.js';
8
+ import { ChallengeSolutionTransaction } from './builders/ChallengeSolutionTransaction.js';
8
9
  export interface DeploymentResult {
9
10
  readonly transaction: [string, string];
10
11
  readonly contractAddress: string;
11
12
  readonly contractPubKey: string;
12
13
  readonly p2trAddress: string;
14
+ readonly preimage: string;
13
15
  readonly utxos: UTXO[];
14
16
  }
15
17
  export interface WrapResult {
@@ -25,18 +27,31 @@ export interface FundingTransactionResponse {
25
27
  readonly estimatedFees: bigint;
26
28
  readonly nextUTXOs: UTXO[];
27
29
  }
28
- export interface BitcoinTransferResponse {
30
+ export interface ChallengeSolutionResponse {
31
+ readonly tx: Transaction;
32
+ readonly original: ChallengeSolutionTransaction;
33
+ readonly estimatedFees: bigint;
34
+ readonly nextUTXOs: UTXO[];
35
+ }
36
+ export interface BitcoinTransferBase {
29
37
  readonly tx: string;
30
- readonly original: FundingTransaction;
31
38
  readonly estimatedFees: bigint;
32
39
  readonly nextUTXOs: UTXO[];
33
40
  }
41
+ export interface ChallengeSolution extends BitcoinTransferBase {
42
+ readonly original: ChallengeSolutionTransaction;
43
+ }
44
+ export interface BitcoinTransferResponse extends BitcoinTransferBase {
45
+ readonly original: FundingTransaction;
46
+ }
34
47
  export declare class TransactionFactory {
35
48
  createCustomScriptTransaction(interactionParameters: ICustomTransactionParameters): Promise<[string, string, UTXO[]]>;
36
- signInteraction(interactionParameters: IInteractionParameters): Promise<[string, string, UTXO[]]>;
49
+ signInteraction(interactionParameters: IInteractionParameters): Promise<[string, string, UTXO[], string]>;
37
50
  signDeployment(deploymentParameters: IDeploymentParameters): Promise<DeploymentResult>;
38
51
  createBTCTransfer(parameters: IFundingTransactionParameters): Promise<BitcoinTransferResponse>;
52
+ createChallengeSolution(parameters: IChallengeSolutionTransactionParameters): Promise<ChallengeSolution>;
39
53
  getAllNewUTXOs(original: TransactionBuilder<TransactionType>, tx: Transaction, to: string): UTXO[];
54
+ private _createChallengeSolution;
40
55
  private createFundTransaction;
41
56
  private writePSBTHeader;
42
57
  private getPriorityFee;
@@ -4,6 +4,7 @@ import { DeploymentTransaction } from './builders/DeploymentTransaction.js';
4
4
  import { FundingTransaction } from './builders/FundingTransaction.js';
5
5
  import { InteractionTransaction } from './builders/InteractionTransaction.js';
6
6
  import { TransactionBuilder } from './builders/TransactionBuilder.js';
7
+ import { ChallengeSolutionTransaction } from './builders/ChallengeSolutionTransaction.js';
7
8
  export class TransactionFactory {
8
9
  async createCustomScriptTransaction(interactionParameters) {
9
10
  if (!interactionParameters.to) {
@@ -89,6 +90,7 @@ export class TransactionFactory {
89
90
  ...interactionParameters,
90
91
  utxos: this.getUTXOAsTransaction(signedTransaction.tx, interactionParameters.to, 0),
91
92
  randomBytes: preTransaction.getRndBytes(),
93
+ preimage: preTransaction.getPreimage(),
92
94
  nonWitnessUtxo: signedTransaction.tx.toBuffer(),
93
95
  estimatedFees: preTransaction.estimatedFees,
94
96
  };
@@ -98,6 +100,7 @@ export class TransactionFactory {
98
100
  signedTransaction.tx.toHex(),
99
101
  outTx.toHex(),
100
102
  this.getUTXOAsTransaction(signedTransaction.tx, interactionParameters.from, 1),
103
+ preTransaction.getPreimage().toString('hex'),
101
104
  ];
102
105
  }
103
106
  async signDeployment(deploymentParameters) {
@@ -127,6 +130,7 @@ export class TransactionFactory {
127
130
  ...deploymentParameters,
128
131
  utxos: [newUtxo],
129
132
  randomBytes: preTransaction.getRndBytes(),
133
+ preimage: preTransaction.getPreimage(),
130
134
  nonWitnessUtxo: signedTransaction.toBuffer(),
131
135
  optionalOutputs: [],
132
136
  };
@@ -148,6 +152,7 @@ export class TransactionFactory {
148
152
  contractPubKey: finalTransaction.contractPubKey,
149
153
  p2trAddress: finalTransaction.p2trAddress,
150
154
  utxos: [refundUTXO],
155
+ preimage: preTransaction.getPreimage().toString('hex'),
151
156
  };
152
157
  }
153
158
  async createBTCTransfer(parameters) {
@@ -162,6 +167,18 @@ export class TransactionFactory {
162
167
  nextUTXOs: this.getAllNewUTXOs(resp.original, resp.tx, parameters.from),
163
168
  };
164
169
  }
170
+ async createChallengeSolution(parameters) {
171
+ if (!parameters.from) {
172
+ throw new Error('Field "from" not provided.');
173
+ }
174
+ const resp = await this._createChallengeSolution(parameters);
175
+ return {
176
+ estimatedFees: resp.estimatedFees,
177
+ original: resp.original,
178
+ tx: resp.tx.toHex(),
179
+ nextUTXOs: this.getAllNewUTXOs(resp.original, resp.tx, parameters.from),
180
+ };
181
+ }
165
182
  getAllNewUTXOs(original, tx, to) {
166
183
  const outputs = original.getOutputs();
167
184
  const utxos = [];
@@ -178,6 +195,21 @@ export class TransactionFactory {
178
195
  }
179
196
  return utxos;
180
197
  }
198
+ async _createChallengeSolution(parameters) {
199
+ if (!parameters.to)
200
+ throw new Error('Field "to" not provided.');
201
+ const challengeTransaction = new ChallengeSolutionTransaction(parameters);
202
+ const signedTransaction = await challengeTransaction.signTransaction();
203
+ if (!signedTransaction) {
204
+ throw new Error('Could not sign funding transaction.');
205
+ }
206
+ return {
207
+ tx: signedTransaction,
208
+ original: challengeTransaction,
209
+ estimatedFees: challengeTransaction.estimatedFees,
210
+ nextUTXOs: this.getUTXOAsTransaction(signedTransaction, parameters.to, 0),
211
+ };
212
+ }
181
213
  async createFundTransaction(parameters) {
182
214
  if (!parameters.to)
183
215
  throw new Error('Field "to" not provided.');
@@ -0,0 +1,18 @@
1
+ import { Address } from '../../opnet.js';
2
+ import { UnisatSigner } from './extensions/UnisatSigner.js';
3
+ import { XverseSigner } from './extensions/XverseSigner.js';
4
+ export declare enum SupportedWallets {
5
+ Unisat = "unisat",
6
+ Xverse = "xverse"
7
+ }
8
+ export declare class WalletConnection {
9
+ wallet_type: SupportedWallets | null;
10
+ private unisatSigner;
11
+ private xverseSigner;
12
+ connect(): Promise<void>;
13
+ disconnect(): Promise<void>;
14
+ switchTo(walletType: SupportedWallets): Promise<void>;
15
+ getAddress(): Address;
16
+ getSigner(): UnisatSigner | XverseSigner;
17
+ }
18
+ export default WalletConnection;
@@ -0,0 +1,95 @@
1
+ import { Address } from '../../opnet.js';
2
+ import { UnisatSigner } from './extensions/UnisatSigner.js';
3
+ import { XverseSigner } from './extensions/XverseSigner.js';
4
+ export var SupportedWallets;
5
+ (function (SupportedWallets) {
6
+ SupportedWallets["Unisat"] = "unisat";
7
+ SupportedWallets["Xverse"] = "xverse";
8
+ })(SupportedWallets || (SupportedWallets = {}));
9
+ export class WalletConnection {
10
+ constructor() {
11
+ this.wallet_type = null;
12
+ this.unisatSigner = null;
13
+ this.xverseSigner = null;
14
+ }
15
+ async connect() {
16
+ if (this.wallet_type) {
17
+ throw new Error('Wallet already connected');
18
+ }
19
+ this.unisatSigner = new UnisatSigner();
20
+ this.xverseSigner = new XverseSigner();
21
+ if (window.opnet || window.unisat) {
22
+ try {
23
+ await this.unisatSigner.init();
24
+ this.wallet_type = SupportedWallets.Unisat;
25
+ return;
26
+ }
27
+ catch (error) {
28
+ if (error instanceof Error) {
29
+ throw new Error(error.message);
30
+ }
31
+ throw new Error('Error connecting wallet');
32
+ }
33
+ }
34
+ if (window.BitcoinProvider) {
35
+ try {
36
+ await this.xverseSigner.init();
37
+ this.wallet_type = SupportedWallets.Xverse;
38
+ return;
39
+ }
40
+ catch (error) {
41
+ if (error instanceof Error) {
42
+ throw new Error(error.message);
43
+ }
44
+ throw new Error('Error connecting wallet');
45
+ }
46
+ }
47
+ throw new Error('Wallet not found');
48
+ }
49
+ async disconnect() {
50
+ if (!this.unisatSigner || !this.xverseSigner) {
51
+ throw new Error('Wallet not connected');
52
+ }
53
+ if (this.wallet_type === SupportedWallets.Unisat) {
54
+ this.unisatSigner.unisat.disconnect();
55
+ }
56
+ else {
57
+ await this.xverseSigner.BitcoinProvider.request('wallet_disconnect', null);
58
+ }
59
+ this.wallet_type = null;
60
+ }
61
+ async switchTo(walletType) {
62
+ if (!this.unisatSigner || !this.xverseSigner) {
63
+ throw new Error('Wallet not connected');
64
+ }
65
+ if (this.wallet_type === walletType)
66
+ return;
67
+ if (walletType === SupportedWallets.Unisat) {
68
+ await this.unisatSigner.init();
69
+ this.wallet_type = SupportedWallets.Unisat;
70
+ }
71
+ else {
72
+ await this.xverseSigner.init();
73
+ this.wallet_type = SupportedWallets.Xverse;
74
+ }
75
+ }
76
+ getAddress() {
77
+ if (!this.unisatSigner || !this.xverseSigner) {
78
+ throw new Error('Wallet not connected');
79
+ }
80
+ if (this.wallet_type === SupportedWallets.Unisat) {
81
+ return Address.fromString(this.unisatSigner.getPublicKey().toString('hex'));
82
+ }
83
+ return Address.fromString(this.xverseSigner.getPublicKey().toString('hex'));
84
+ }
85
+ getSigner() {
86
+ if (!this.unisatSigner || !this.xverseSigner) {
87
+ throw new Error('Wallet not connected');
88
+ }
89
+ if (this.wallet_type === SupportedWallets.Unisat) {
90
+ return this.unisatSigner;
91
+ }
92
+ return this.xverseSigner;
93
+ }
94
+ }
95
+ export default WalletConnection;
@@ -1,8 +1,8 @@
1
- import { crypto as bitCrypto, networks, Psbt, script as bitScript, toXOnly, } from '@btc-vision/bitcoin';
1
+ import { crypto as bitCrypto, script as bitScript, networks, Psbt, toXOnly, } from '@btc-vision/bitcoin';
2
2
  import { EcKeyPair } from '../../../keypair/EcKeyPair.js';
3
+ import { canSignNonTaprootInput, isTaprootInput } from '../../../signer/SignerUtils.js';
3
4
  import { CustomKeypair } from '../BrowserSignerBase.js';
4
5
  import { UnisatNetwork } from '../types/Unisat.js';
5
- import { canSignNonTaprootInput, isTaprootInput } from '../../../signer/SignerUtils.js';
6
6
  export class UnisatSigner extends CustomKeypair {
7
7
  constructor() {
8
8
  super();
@@ -67,6 +67,9 @@ export class UnisatSigner extends CustomKeypair {
67
67
  throw new Error(`Invalid network: ${network}`);
68
68
  }
69
69
  const publicKey = await this.unisat.getPublicKey();
70
+ if (publicKey === '') {
71
+ throw new Error('Unlock your wallet first');
72
+ }
70
73
  this._publicKey = Buffer.from(publicKey, 'hex');
71
74
  this._p2wpkh = EcKeyPair.getP2WPKHAddress(this, this.network);
72
75
  this._p2tr = EcKeyPair.getTaprootAddress(this, this.network);
@@ -1,7 +1,7 @@
1
1
  import { networks, Psbt, toXOnly } from '@btc-vision/bitcoin';
2
2
  import { EcKeyPair } from '../../../keypair/EcKeyPair.js';
3
- import { CustomKeypair } from '../BrowserSignerBase.js';
4
3
  import { canSignNonTaprootInput, isTaprootInput, pubkeyInScript, } from '../../../signer/SignerUtils.js';
4
+ import { CustomKeypair } from '../BrowserSignerBase.js';
5
5
  export class XverseSigner extends CustomKeypair {
6
6
  constructor() {
7
7
  super();
@@ -50,7 +50,7 @@ export class XverseSigner extends CustomKeypair {
50
50
  async init() {
51
51
  if (this.isInitialized)
52
52
  return;
53
- const connectResult = (await this.BitcoinProvider.request('wallet_connect', null));
53
+ const connectResult = await this.BitcoinProvider.request('wallet_connect', null);
54
54
  if ('error' in connectResult)
55
55
  throw new Error(connectResult.error.message);
56
56
  const payementAddress = connectResult.result.addresses.find((address) => address.purpose === 'payment');
@@ -120,7 +120,7 @@ export class XverseSigner extends CustomKeypair {
120
120
  const toSignPsbts = [];
121
121
  const options = [];
122
122
  for (const psbt of transactions) {
123
- const hex = psbt.toHex();
123
+ const hex = psbt.toBase64();
124
124
  toSignPsbts.push(hex);
125
125
  const toSignInputs = psbt.data.inputs
126
126
  .map((input, i) => {
@@ -166,10 +166,13 @@ export class XverseSigner extends CustomKeypair {
166
166
  toSignInputs: toSignInputs,
167
167
  });
168
168
  }
169
- const callSign = (await this.BitcoinProvider.request('signPsbt', {
169
+ const toSignInputs = {
170
+ [this.p2wpkh]: options[0].toSignInputs?.map((input) => input.index) || [],
171
+ };
172
+ const callSign = await this.BitcoinProvider.request('signPsbt', {
170
173
  psbt: toSignPsbts[0],
171
- signInputs: options[0].toSignInputs,
172
- }));
174
+ signInputs: toSignInputs,
175
+ });
173
176
  if ('error' in callSign)
174
177
  throw new Error(callSign.error.message);
175
178
  const signedPsbts = Psbt.fromBase64(callSign.result.psbt);
@@ -234,10 +237,13 @@ export class XverseSigner extends CustomKeypair {
234
237
  toSignInputs: toSign.flat(),
235
238
  };
236
239
  const psbt = transaction.toBase64();
237
- const callSign = (await this.BitcoinProvider.request('signPsbt', {
240
+ const toSignInputs = {
241
+ [this.p2wpkh]: opts.toSignInputs?.map((input) => input.index) || [],
242
+ };
243
+ const callSign = await this.BitcoinProvider.request('signPsbt', {
238
244
  psbt,
239
- signInputs: opts.toSignInputs,
240
- }));
245
+ signInputs: toSignInputs,
246
+ });
241
247
  if ('error' in callSign)
242
248
  throw new Error(callSign.error.message);
243
249
  return Psbt.fromBase64(callSign.result.psbt);
@@ -3,12 +3,11 @@ export declare enum XverseNetwork {
3
3
  testnet = "testnet",
4
4
  signet = "Signet"
5
5
  }
6
- export type XverseRPCResponse<T = unknown> = {
6
+ type XverseRPCResponse<T = unknown> = {
7
7
  id: string;
8
8
  jsonrpc: string;
9
9
  result: T;
10
- };
11
- export type XverseRPCError = {
10
+ } | {
12
11
  id: string;
13
12
  jsonrpc: string;
14
13
  error: {
@@ -16,17 +15,29 @@ export type XverseRPCError = {
16
15
  message: string;
17
16
  };
18
17
  };
19
- export type XverseRPCGetAccountResponse = XverseRPCResponse<{
18
+ type XverseRPCGetAccountResponse = XverseRPCResponse<{
20
19
  addresses: {
21
20
  address: string;
22
21
  addressType: string;
23
22
  publicKey: string;
24
- purpose: string;
23
+ purpose: 'stacks' | 'payment' | 'ordinals';
25
24
  }[];
26
- }> | XverseRPCError;
27
- export type XverseRPCSignPsbtResponse = XverseRPCResponse<{
25
+ walletType: string;
26
+ }>;
27
+ type XverseRPCSignPsbtResponse = XverseRPCResponse<{
28
+ psbt: string;
29
+ }>;
30
+ type XverseRPCGetBalanceResponse = XverseRPCResponse<{
31
+ confirmed: string;
32
+ total: string;
33
+ unconfirmed: string;
34
+ }>;
35
+ export type XVersePSBTInput = {
28
36
  psbt: string;
29
- }> | XverseRPCError;
37
+ signInputs: {
38
+ [x: string]: number[];
39
+ } | undefined;
40
+ };
30
41
  interface InscriptionData {
31
42
  address: string;
32
43
  amount: number;
@@ -66,11 +77,14 @@ interface SignedTransactionResult {
66
77
  raw: string;
67
78
  }
68
79
  export interface Xverse {
69
- connect: () => Promise<void>;
80
+ request(method: string, params: unknown): Promise<XverseRPCResponse>;
81
+ request(method: 'wallet_connect' | 'wallet_getAccount', params: null): Promise<XverseRPCGetAccountResponse>;
82
+ request(method: 'wallet_disconnect', params: null): Promise<XverseRPCResponse<null>>;
83
+ request(method: 'getBalance', params: null): Promise<XverseRPCGetBalanceResponse>;
84
+ request(method: 'signPsbt', params: XVersePSBTInput): Promise<XverseRPCSignPsbtResponse>;
70
85
  addListener: (event: string, callback: (...args: unknown[]) => void) => void;
71
86
  createInscription: (data: InscriptionData) => Promise<InscriptionResult>;
72
87
  createRepeatInscriptions: (data: RepeatInscriptionsData) => Promise<InscriptionResult[]>;
73
- request: (method: string, params: unknown) => Promise<XverseRPCResponse>;
74
88
  sendBtcTransaction: (transaction: BtcTransaction) => Promise<TransactionResult>;
75
89
  signMessage: (message: string) => Promise<SignedMessageResult>;
76
90
  signMultipleTransactions: (transactions: BtcTransaction[]) => Promise<SignedTransactionResult[]>;
@@ -0,0 +1,18 @@
1
+ import { TransactionType } from '../enums/TransactionType.js';
2
+ import { IChallengeSolutionTransactionParameters } from '../interfaces/ITransactionParameters.js';
3
+ import { Psbt, PsbtInput, Signer } from '@btc-vision/bitcoin';
4
+ import { TransactionBuilder } from './TransactionBuilder.js';
5
+ import { ECPairInterface } from 'ecpair';
6
+ export declare class ChallengeSolutionTransaction extends TransactionBuilder<TransactionType.CHALLENGE_SOLUTION> {
7
+ readonly type: TransactionType.CHALLENGE_SOLUTION;
8
+ protected amount: bigint;
9
+ protected readonly challengeSolution: Buffer;
10
+ constructor(parameters: IChallengeSolutionTransactionParameters);
11
+ protected buildTransaction(): Promise<void>;
12
+ protected signInput(transaction: Psbt, input: PsbtInput, i: number, signer: Signer | ECPairInterface, reverse?: boolean, errored?: boolean): Promise<void>;
13
+ protected customFinalizerP2SH: (inputIndex: number, input: PsbtInput, scriptA: Buffer, isSegwit: boolean, isP2SH: boolean, isP2WSH: boolean) => {
14
+ finalScriptSig: Buffer | undefined;
15
+ finalScriptWitness: Buffer | undefined;
16
+ };
17
+ protected getSignerKey(): Signer | ECPairInterface;
18
+ }
@@ -0,0 +1,51 @@
1
+ import { TransactionType } from '../enums/TransactionType.js';
2
+ import { getFinalScripts, opcodes, script } from '@btc-vision/bitcoin';
3
+ import { TransactionBuilder } from './TransactionBuilder.js';
4
+ export class ChallengeSolutionTransaction extends TransactionBuilder {
5
+ constructor(parameters) {
6
+ super(parameters);
7
+ this.type = TransactionType.CHALLENGE_SOLUTION;
8
+ this.customFinalizerP2SH = (inputIndex, input, scriptA, isSegwit, isP2SH, isP2WSH) => {
9
+ const inputDecoded = this.inputs[inputIndex];
10
+ if (isP2SH && inputDecoded && inputDecoded.redeemScript) {
11
+ const scriptSig = script.compile([this.challengeSolution, inputDecoded.redeemScript]);
12
+ return {
13
+ finalScriptSig: scriptSig,
14
+ finalScriptWitness: undefined,
15
+ };
16
+ }
17
+ return getFinalScripts(inputIndex, input, scriptA, isSegwit, isP2SH, isP2WSH, false);
18
+ };
19
+ this.amount = parameters.amount;
20
+ this.challengeSolution = parameters.challengeSolution;
21
+ this.internalInit();
22
+ }
23
+ async buildTransaction() {
24
+ if (!this.to) {
25
+ throw new Error('Recipient address is required');
26
+ }
27
+ this.addInputsFromUTXO();
28
+ if (this.isPubKeyDestination) {
29
+ const pubKeyScript = script.compile([
30
+ Buffer.from(this.to.replace('0x', ''), 'hex'),
31
+ opcodes.OP_CHECKSIG,
32
+ ]);
33
+ this.addOutput({
34
+ value: Number(this.amount),
35
+ script: pubKeyScript,
36
+ });
37
+ }
38
+ else {
39
+ this.addOutput({
40
+ value: Number(this.amount),
41
+ address: this.to,
42
+ });
43
+ }
44
+ await this.addRefundOutput(this.amount + this.addOptionalOutputsAndGetAmount());
45
+ }
46
+ async signInput(transaction, input, i, signer, reverse = false, errored = false) {
47
+ }
48
+ getSignerKey() {
49
+ return this.signer;
50
+ }
51
+ }
@@ -4,9 +4,12 @@ import { Payment, Psbt } from '@btc-vision/bitcoin';
4
4
  import { TransactionBuilder } from './TransactionBuilder.js';
5
5
  import { TapLeafScript } from '../interfaces/Tap.js';
6
6
  import { Address } from '../../keypair/Address.js';
7
+ import { IMineableReward } from '../mineable/ChallengeGenerator.js';
7
8
  export declare class DeploymentTransaction extends TransactionBuilder<TransactionType.DEPLOYMENT> {
8
9
  static readonly MAXIMUM_CONTRACT_SIZE: number;
9
10
  type: TransactionType.DEPLOYMENT;
11
+ protected readonly preimage: Buffer;
12
+ protected readonly rewardChallenge: IMineableReward;
10
13
  protected readonly _contractAddress: Address;
11
14
  protected tapLeafScript: TapLeafScript | null;
12
15
  private targetScriptRedeem;
@@ -25,6 +28,7 @@ export declare class DeploymentTransaction extends TransactionBuilder<Transactio
25
28
  get contractAddress(): Address;
26
29
  get p2trAddress(): string;
27
30
  getRndBytes(): Buffer;
31
+ getPreimage(): Buffer;
28
32
  protected contractSignerXOnlyPubKey(): Buffer;
29
33
  protected buildTransaction(): Promise<void>;
30
34
  protected signInputsWalletBased(transaction: Psbt): Promise<void>;
@@ -1,12 +1,13 @@
1
1
  import { TransactionType } from '../enums/TransactionType.js';
2
2
  import { crypto as bitCrypto, toXOnly, } from '@btc-vision/bitcoin';
3
- import { TransactionBuilder } from './TransactionBuilder.js';
3
+ import { MINIMUM_AMOUNT_CA, MINIMUM_AMOUNT_REWARD, TransactionBuilder, } from './TransactionBuilder.js';
4
4
  import { DeploymentGenerator } from '../../generators/builders/DeploymentGenerator.js';
5
5
  import { EcKeyPair } from '../../keypair/EcKeyPair.js';
6
6
  import { BitcoinUtils } from '../../utils/BitcoinUtils.js';
7
7
  import { Compressor } from '../../bytecode/Compressor.js';
8
8
  import { SharedInteractionTransaction } from './SharedInteractionTransaction.js';
9
9
  import { Address } from '../../keypair/Address.js';
10
+ import { ChallengeGenerator } from '../mineable/ChallengeGenerator.js';
10
11
  const p = 0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2fn;
11
12
  export class DeploymentTransaction extends TransactionBuilder {
12
13
  constructor(parameters) {
@@ -24,7 +25,6 @@ export class DeploymentTransaction extends TransactionBuilder {
24
25
  }
25
26
  const scriptSolution = [
26
27
  this.randomBytes,
27
- this.internalPubKeyToXOnly(),
28
28
  input.tapScriptSig[0].signature,
29
29
  input.tapScriptSig[1].signature,
30
30
  ];
@@ -42,10 +42,12 @@ export class DeploymentTransaction extends TransactionBuilder {
42
42
  this.verifyCalldata();
43
43
  }
44
44
  this.randomBytes = parameters.randomBytes || BitcoinUtils.rndBytes();
45
+ this.preimage = parameters.preimage || BitcoinUtils.getSafeRandomValues(128);
46
+ this.rewardChallenge = ChallengeGenerator.generateMineableReward(this.preimage, this.network);
45
47
  this.contractSeed = this.getContractSeed();
46
48
  this.contractSigner = EcKeyPair.fromSeedKeyPair(this.contractSeed, this.network);
47
49
  this.deploymentGenerator = new DeploymentGenerator(Buffer.from(this.signer.publicKey), this.contractSignerXOnlyPubKey(), this.network);
48
- this.compiledTargetScript = this.deploymentGenerator.compile(this.bytecode, this.randomBytes, this.calldata);
50
+ this.compiledTargetScript = this.deploymentGenerator.compile(this.bytecode, this.randomBytes, this.preimage, this.calldata);
49
51
  this.scriptTree = this.getScriptTree();
50
52
  this.internalInit();
51
53
  this._contractPubKey = '0x' + this.contractSeed.toString('hex');
@@ -63,6 +65,9 @@ export class DeploymentTransaction extends TransactionBuilder {
63
65
  getRndBytes() {
64
66
  return this.randomBytes;
65
67
  }
68
+ getPreimage() {
69
+ return this.preimage;
70
+ }
66
71
  contractSignerXOnlyPubKey() {
67
72
  return toXOnly(Buffer.from(this.contractSigner.publicKey));
68
73
  }
@@ -89,10 +94,24 @@ export class DeploymentTransaction extends TransactionBuilder {
89
94
  };
90
95
  this.addInputsFromUTXO();
91
96
  const amountSpent = this.getTransactionOPNetFee();
97
+ let amountToCA;
98
+ if (amountSpent > MINIMUM_AMOUNT_REWARD + MINIMUM_AMOUNT_CA) {
99
+ amountToCA = MINIMUM_AMOUNT_CA;
100
+ }
101
+ else {
102
+ amountToCA = amountSpent;
103
+ }
92
104
  this.addOutput({
93
- value: Number(amountSpent),
105
+ value: Number(amountToCA),
94
106
  address: this.contractAddress.p2tr(this.network),
95
107
  });
108
+ if (amountToCA === MINIMUM_AMOUNT_CA &&
109
+ amountSpent - MINIMUM_AMOUNT_CA > MINIMUM_AMOUNT_REWARD) {
110
+ this.addOutput({
111
+ value: Number(amountSpent - amountToCA),
112
+ address: this.rewardChallenge.address,
113
+ });
114
+ }
96
115
  await this.addRefundOutput(amountSpent + this.addOptionalOutputsAndGetAmount());
97
116
  }
98
117
  async signInputsWalletBased(transaction) {
@@ -6,7 +6,7 @@ export class InteractionTransaction extends SharedInteractionTransaction {
6
6
  this.type = TransactionType.INTERACTION;
7
7
  this.tapLeafScript = null;
8
8
  this.contractSecret = this.generateSecret();
9
- this.compiledTargetScript = this.calldataGenerator.compile(this.calldata, this.contractSecret);
9
+ this.compiledTargetScript = this.calldataGenerator.compile(this.calldata, this.contractSecret, this.preimage);
10
10
  this.scriptTree = this.getScriptTree();
11
11
  this.internalInit();
12
12
  }
@@ -4,6 +4,7 @@ import { TransactionBuilder } from './TransactionBuilder.js';
4
4
  import { TransactionType } from '../enums/TransactionType.js';
5
5
  import { CalldataGenerator } from '../../generators/builders/CalldataGenerator.js';
6
6
  import { SharedInteractionParameters } from '../interfaces/ITransactionParameters.js';
7
+ import { IMineableReward } from '../mineable/ChallengeGenerator.js';
7
8
  export declare abstract class SharedInteractionTransaction<T extends TransactionType> extends TransactionBuilder<T> {
8
9
  static readonly MAXIMUM_CALLDATA_SIZE: number;
9
10
  readonly randomBytes: Buffer;
@@ -11,6 +12,8 @@ export declare abstract class SharedInteractionTransaction<T extends Transaction
11
12
  protected leftOverFundsScriptRedeem: Payment | null;
12
13
  protected abstract readonly compiledTargetScript: Buffer;
13
14
  protected abstract readonly scriptTree: Taptree;
15
+ protected readonly preimage: Buffer;
16
+ protected readonly rewardChallenge: IMineableReward;
14
17
  protected calldataGenerator: CalldataGenerator;
15
18
  protected readonly calldata: Buffer;
16
19
  protected abstract readonly contractSecret: Buffer;
@@ -19,6 +22,7 @@ export declare abstract class SharedInteractionTransaction<T extends Transaction
19
22
  protected constructor(parameters: SharedInteractionParameters);
20
23
  getContractSecret(): Buffer;
21
24
  getRndBytes(): Buffer;
25
+ getPreimage(): Buffer;
22
26
  protected generateSecret(): Buffer;
23
27
  protected scriptSignerXOnlyPubKey(): Buffer;
24
28
  protected generateKeyPairFromSeed(): ECPairInterface;
@@ -32,6 +36,7 @@ export declare abstract class SharedInteractionTransaction<T extends Transaction
32
36
  finalScriptWitness: Buffer<ArrayBufferLike>;
33
37
  };
34
38
  protected signInputsWalletBased(transaction: Psbt): Promise<void>;
39
+ private createMineableRewardOutputs;
35
40
  private signInputsNonWalletBased;
36
41
  private getPubKeys;
37
42
  private generateRedeemScripts;