_setup.ts 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118
  1. import {
  2. Address,
  3. BaseTransactionMessage,
  4. Commitment,
  5. Rpc,
  6. RpcSubscriptions,
  7. SolanaRpcApi,
  8. SolanaRpcSubscriptionsApi,
  9. TransactionMessageWithBlockhashLifetime,
  10. TransactionMessageWithFeePayer,
  11. TransactionSigner,
  12. airdropFactory,
  13. appendTransactionMessageInstruction,
  14. assertIsSendableTransaction,
  15. createSolanaRpc,
  16. createSolanaRpcSubscriptions,
  17. createTransactionMessage,
  18. generateKeyPairSigner,
  19. getSignatureFromTransaction,
  20. lamports,
  21. pipe,
  22. sendAndConfirmTransactionFactory,
  23. setTransactionMessageFeePayerSigner,
  24. setTransactionMessageLifetimeUsingBlockhash,
  25. signTransactionMessageWithSigners,
  26. } from '@solana/kit';
  27. import {
  28. SYSTEM_PROGRAM_ADDRESS,
  29. getCreateAccountInstruction,
  30. getInitializeNonceAccountInstruction,
  31. getNonceSize,
  32. } from '../src';
  33. type Client = {
  34. rpc: Rpc<SolanaRpcApi>;
  35. rpcSubscriptions: RpcSubscriptions<SolanaRpcSubscriptionsApi>;
  36. };
  37. export const createDefaultSolanaClient = (): Client => {
  38. const rpc = createSolanaRpc('http://127.0.0.1:8899');
  39. const rpcSubscriptions = createSolanaRpcSubscriptions('ws://127.0.0.1:8900');
  40. return { rpc, rpcSubscriptions };
  41. };
  42. export const generateKeyPairSignerWithSol = async (
  43. client: Client,
  44. putativeLamports: bigint = 1_000_000_000n
  45. ) => {
  46. const signer = await generateKeyPairSigner();
  47. await airdropFactory(client)({
  48. recipientAddress: signer.address,
  49. lamports: lamports(putativeLamports),
  50. commitment: 'confirmed',
  51. });
  52. return signer;
  53. };
  54. export const createDefaultTransaction = async (
  55. client: Client,
  56. feePayer: TransactionSigner
  57. ) => {
  58. const { value: latestBlockhash } = await client.rpc
  59. .getLatestBlockhash()
  60. .send();
  61. return pipe(
  62. createTransactionMessage({ version: 0 }),
  63. (tx) => setTransactionMessageFeePayerSigner(feePayer, tx),
  64. (tx) => setTransactionMessageLifetimeUsingBlockhash(latestBlockhash, tx)
  65. );
  66. };
  67. export const signAndSendTransaction = async (
  68. client: Client,
  69. transactionMessage: BaseTransactionMessage &
  70. TransactionMessageWithFeePayer &
  71. TransactionMessageWithBlockhashLifetime,
  72. commitment: Commitment = 'confirmed'
  73. ) => {
  74. const signedTransaction =
  75. await signTransactionMessageWithSigners(transactionMessage);
  76. const signature = getSignatureFromTransaction(signedTransaction);
  77. assertIsSendableTransaction(signedTransaction);
  78. await sendAndConfirmTransactionFactory(client)(signedTransaction, {
  79. commitment,
  80. });
  81. return signature;
  82. };
  83. export const getBalance = async (client: Client, address: Address) =>
  84. (await client.rpc.getBalance(address, { commitment: 'confirmed' }).send())
  85. .value;
  86. export const createNonceAccount = async (
  87. client: Client,
  88. payer: TransactionSigner,
  89. nonce: TransactionSigner,
  90. nonceAuthority: TransactionSigner
  91. ) => {
  92. const space = BigInt(getNonceSize());
  93. const rent = await client.rpc.getMinimumBalanceForRentExemption(space).send();
  94. const createAccount = getCreateAccountInstruction({
  95. payer,
  96. newAccount: nonce,
  97. lamports: rent,
  98. space,
  99. programAddress: SYSTEM_PROGRAM_ADDRESS,
  100. });
  101. const initializeNonceAccount = getInitializeNonceAccountInstruction({
  102. nonceAccount: nonce.address,
  103. nonceAuthority: nonceAuthority.address,
  104. });
  105. await pipe(
  106. await createDefaultTransaction(client, payer),
  107. (tx) => appendTransactionMessageInstruction(createAccount, tx),
  108. (tx) => appendTransactionMessageInstruction(initializeNonceAccount, tx),
  109. (tx) => signAndSendTransaction(client, tx)
  110. );
  111. };