2022-11-15 20:10:03 -08:00
|
|
|
import { AnchorProvider } from '@project-serum/anchor';
|
2022-09-27 06:13:53 -07:00
|
|
|
import {
|
|
|
|
AddressLookupTableAccount,
|
2022-11-15 20:10:03 -08:00
|
|
|
MessageV0,
|
2022-11-16 06:11:39 -08:00
|
|
|
Signer,
|
2022-09-27 06:13:53 -07:00
|
|
|
TransactionInstruction,
|
2022-11-15 20:10:03 -08:00
|
|
|
VersionedTransaction,
|
2022-09-27 06:13:53 -07:00
|
|
|
} from '@solana/web3.js';
|
2022-08-12 17:15:12 -07:00
|
|
|
|
|
|
|
export async function sendTransaction(
|
|
|
|
provider: AnchorProvider,
|
2022-09-27 06:13:53 -07:00
|
|
|
ixs: TransactionInstruction[],
|
|
|
|
alts: AddressLookupTableAccount[],
|
2022-08-12 17:15:12 -07:00
|
|
|
opts: any = {},
|
2022-09-29 06:51:09 -07:00
|
|
|
): Promise<string> {
|
2022-08-12 17:15:12 -07:00
|
|
|
const connection = provider.connection;
|
2022-09-05 14:36:42 -07:00
|
|
|
const latestBlockhash = await connection.getLatestBlockhash(
|
|
|
|
opts.preflightCommitment,
|
|
|
|
);
|
2022-10-06 02:25:09 -07:00
|
|
|
|
2022-10-07 05:05:49 -07:00
|
|
|
const payer = (provider as AnchorProvider).wallet;
|
2022-08-12 17:15:12 -07:00
|
|
|
|
2022-11-15 20:10:03 -08:00
|
|
|
const message = MessageV0.compile({
|
|
|
|
payerKey: (provider as AnchorProvider).wallet.publicKey,
|
|
|
|
instructions: ixs,
|
|
|
|
recentBlockhash: latestBlockhash.blockhash,
|
|
|
|
addressLookupTableAccounts: alts,
|
2022-08-12 17:15:12 -07:00
|
|
|
});
|
2022-11-18 11:22:12 -08:00
|
|
|
let vtx = new VersionedTransaction(message);
|
2022-11-15 20:10:03 -08:00
|
|
|
if (opts?.additionalSigners?.length) {
|
|
|
|
vtx.sign([...opts?.additionalSigners]);
|
|
|
|
}
|
|
|
|
|
2022-11-16 06:11:39 -08:00
|
|
|
if (typeof payer.signTransaction === 'function') {
|
2022-11-18 11:22:12 -08:00
|
|
|
vtx = (await payer.signTransaction(
|
|
|
|
vtx as any,
|
|
|
|
)) as unknown as VersionedTransaction;
|
2022-11-16 06:11:39 -08:00
|
|
|
} else {
|
|
|
|
vtx.sign([((provider as AnchorProvider).wallet as any).payer as Signer]);
|
|
|
|
}
|
2022-11-15 20:10:03 -08:00
|
|
|
|
|
|
|
const signature = await connection.sendTransaction(
|
2022-11-16 06:11:39 -08:00
|
|
|
vtx as any as VersionedTransaction,
|
2022-11-15 20:10:03 -08:00
|
|
|
{
|
|
|
|
skipPreflight: true,
|
|
|
|
},
|
|
|
|
);
|
2022-08-12 17:15:12 -07:00
|
|
|
|
|
|
|
if (opts.postSendTxCallback) {
|
|
|
|
try {
|
|
|
|
opts.postSendTxCallback({ txid: signature });
|
|
|
|
} catch (e) {
|
|
|
|
console.warn(`postSendTxCallback error ${e}`);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2022-08-26 12:42:10 -07:00
|
|
|
let status: any;
|
|
|
|
if (
|
2022-09-27 06:13:53 -07:00
|
|
|
latestBlockhash.blockhash != null &&
|
|
|
|
latestBlockhash.lastValidBlockHeight != null
|
2022-08-26 12:42:10 -07:00
|
|
|
) {
|
|
|
|
status = (
|
|
|
|
await connection.confirmTransaction(
|
|
|
|
{
|
|
|
|
signature: signature,
|
2022-09-27 06:13:53 -07:00
|
|
|
blockhash: latestBlockhash.blockhash,
|
|
|
|
lastValidBlockHeight: latestBlockhash.lastValidBlockHeight,
|
2022-08-26 12:42:10 -07:00
|
|
|
},
|
|
|
|
'processed',
|
|
|
|
)
|
|
|
|
).value;
|
|
|
|
} else {
|
|
|
|
status = (await connection.confirmTransaction(signature, 'processed'))
|
|
|
|
.value;
|
|
|
|
}
|
2022-08-12 17:15:12 -07:00
|
|
|
|
|
|
|
if (status.err) {
|
|
|
|
throw new MangoError({
|
|
|
|
txid: signature,
|
|
|
|
message: `Transaction ${signature} failed (${JSON.stringify(status)})`,
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
return signature;
|
|
|
|
}
|
|
|
|
|
|
|
|
class MangoError extends Error {
|
|
|
|
message: string;
|
|
|
|
txid: string;
|
|
|
|
|
|
|
|
constructor({ txid, message }) {
|
|
|
|
super();
|
|
|
|
this.message = message;
|
|
|
|
this.txid = txid;
|
|
|
|
}
|
|
|
|
}
|