Signing a Transaction
The Magic Eden Wallet support the Sats Connect method of signing a transaction. This requires a base64 encoded PSBT to execute.
Let's take a look at a basic example, where we want to send an arbitrary amount of BTC to another wallet. The top-level function call should look something like this:
async function signWalletTransaction() {
const utxos = await fetchUTXO(nativeSegwitAddress);
if (!utxos) {
alert('No UTXOs found! Please deposit some funds to your wallet.');
return;
}
const selectedUTXO = await selectUTXO(10000, utxos);
const scriptPubKey = await fetchScriptPubKey(selectedUTXO.txid, selectedUTXO.vout);
const psbt = await createPSBT({
utxo: selectedUTXO,
recipientAddress: RECIPIENT_ADDRESS,
changeAddress: nativeSegwitAddress,
amountToSend: 1000,
scriptPubKey,
});
try {
await signTransaction({
payload: {
network: {
type: BitcoinNetworkType.Mainnet,
},
psbtBase64: psbt,
broadcast: true,
message: "tip the author! Don't worry this will not be broadcasted.",
inputsToSign: [
{
address: nativeSegwitAddress!,
signingIndexes: [0],
},
],
},
onFinish: (response) => {
const psbResponse = Psbt.fromBase64(response.psbtBase64);
psbResponse.finalizeAllInputs();
const signedTx = psbResponse.extractTransaction();
const txHex = signedTx.toHex();
},
onCancel: () => {
alert('Request canceled');
},
});
} catch (err) {
console.error(err);
}
}There's a lot going on here, so here's a breakdown of each part.
Understanding UTXOs:
In the world of Bitcoin, the concept of a "balance" operates differently compared to traditional bank accounts or even some other blockchain networks. Rather than representing your funds as a single total amount, your Bitcoin balance is actually the sum of all values from Unspent Transaction Outputs (UTXOs). UTXOs are essentially fragments of Bitcoin left over from previous transactions that you have received but not yet spent.
When someone sends you Bitcoin, the amount is recorded in the blockchain as a UTXO, earmarked for your address. Your wallet then aggregates all UTXOs associated with your address to display your total balance. It's similar to having a wallet full of various bills and coins; each piece has value, and your total wealth is the sum of these individual pieces.
To initiate a Bitcoin transaction, your wallet selects enough UTXOs to cover the amount you wish to send, plus the transaction fee. These selected UTXOs are then consumed and effectively transformed: the amount sent to the recipient becomes a new UTXO linked to their address, and any change not sent to the recipient (the remainder after subtracting the amount sent and the transaction fee) returns to you as a new UTXO, ready to be spent in future transactions.
In this particular example, we are just going with the first UTXO that fits the bill. Actual production implementations should expand on this. An easy way to fetch all UTXO's of an address is utilizing mempool's API
Script
In this example, we are looking at a transaction payment. That makes use of our segwit address instead of our taproot address. In the ME wallet, your main BTC address for sending bitcoin is a native segwit address. SegWit (or Segregated Witness) was introduced to make Bitcoin transactions more efficient and secure
In the context of creating PSBTs, ScriptPubKey and WitnessUTXO are essential for SegWit transactions because they ensure that bitcoins are securely and efficiently sent across the Bitcoin network. ScriptPubKey ensures that only the intended recipient can spend the bitcoins, while WitnessUTXO makes transactions more space-efficient, allowing for faster processing and lower fees.
You can find the given scriptPubKey for a UTXO transaction id from the mempool APIs as well:
Creating PSBTs
Now for the fun part! We've put together all the pieces, now let's create a PSBT that we can actually execute. PSBTs are a flexible, standardized format for Bitcoin transactions that can be partially signed and completed by multiple parties.
This example walks through creating a PSBT for Segwit transactions, but taproot transactions are similar and you can follow the documentation from sats-connect if need be. This example process involves sending Bitcoin from one address to another and returning any leftover balance from the UTXO back to the sender.
This formed PSBT can be decoded and sent back to the original code snippet to be executed in our SignTransaction function we created at the top of this section.
Last updated