Skip to content

Instantly share code, notes, and snippets.

@goodylili
Created July 22, 2025 13:54
Show Gist options
  • Select an option

  • Save goodylili/bc65e7dece3430991721d4ba01e7c321 to your computer and use it in GitHub Desktop.

Select an option

Save goodylili/bc65e7dece3430991721d4ba01e7c321 to your computer and use it in GitHub Desktop.
Sponsored Transaction for the same transaction
import { Transaction } from '@mysten/sui/transactions';
import { Ed25519Keypair } from '@mysten/sui/keypairs/ed25519';
import { SuiClient, getFullnodeUrl } from '@mysten/sui/client';
async function main() {
// Initialize client
const client = new SuiClient({ url: getFullnodeUrl('testnet') });
// Create a keypair from your secret
const userKeypair = Ed25519Keypair.fromSecretKey(
'suiprivkey1qqrv8zds2k24ky47u7gx5v3zjuxugr7kjqesz33fn32qe08vs50rutflk9v'
);
// Sponsor keypair (your provided key)
const sponsorKeypair = Ed25519Keypair.fromSecretKey(
'suiprivkey1qq9r6rkysny207t5vr7m5025swh7w0wzra9p0553paprhn8zshqsx2rz64r'
);
// Create a single new programmable transaction
const tx = new Transaction();
// Define multiple transfers and the amounts
const transfers = [
{ to: '0x83ecd81fdd132d4fb4f9ae2608656b000df13c4c3c5b10490d48ee981bc8f433', amount: 500000 },
{ to: '0x1b2e893cb5164f2f48bd65f77ea76c14d025d8577ab89f2b40a7af0376a8584c', amount: 40000 },
];
// Split gas coin into exact amounts for transfers
const coins = tx.splitCoins(
tx.gas,
transfers.map((transfer) => transfer.amount)
);
// Transfer each split coin to its corresponding address
transfers.forEach((transfer, index) => {
tx.transferObjects([coins[index]], transfer.to);
});
// Build KIND bytes (no gas owner yet)
const kindBytes = await tx.build({
client,
onlyTransactionKind: true,
});
// Sponsor modifies transaction
const sponsoredTx = Transaction.fromKind(kindBytes);
sponsoredTx.setSender(userKeypair.getPublicKey().toSuiAddress());
sponsoredTx.setGasOwner(sponsorKeypair.getPublicKey().toSuiAddress());
// Build final transaction bytes
const builtBytes = await sponsoredTx.build({ client });
// ✍️ User signs first
const { signature: userSignature } = await userKeypair.signTransaction(builtBytes);
// ✍️ Sponsor signs
const { signature: sponsorSignature } = await sponsorKeypair.signTransaction(builtBytes);
// 🚀 Execute with both signatures
const result = await client.executeTransactionBlock({
transactionBlock: builtBytes,
signature: [userSignature, sponsorSignature], // ✅ Two signatures required
options: {
showEffects: true,
showEvents: true,
},
});
console.log('Sponsored Transaction Successful!');
console.log('Digest:', result.digest);
}
main().catch(console.error);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment