Records are Leo’s primitive for representing owned, private data on the Aleo blockchain. They are similar to UTXOs (Unspent Transaction Outputs) in Bitcoin - each record has a unique owner and can only be consumed once.
Records are consumed when used as function inputs:
fn transfer_private( sender: token, // Consumes this record receiver: address, amount: u64) -> (token, token) { // Creates two new records let difference: u64 = sender.amount - amount; // Create new record for sender with remaining balance let remaining: token = token { owner: sender.owner, amount: difference, }; // Create new record for receiver let transferred: token = token { owner: receiver, amount: amount, }; return (remaining, transferred);}
Once a record is consumed, it cannot be used again. The old record is destroyed and new records are created to represent the updated state.
The owner field determines who can spend the record:
record token { owner: address, // Only this address can spend the token amount: u64,}// Mint a token for a specific ownerfn mint_private(receiver: address, amount: u64) -> token { return token { owner: receiver, // receiver becomes the owner amount: amount, };}
// Convert private record to public balancefn transfer_private_to_public( sender: token, public receiver: address, public amount: u64) -> (token, Final) { let difference: u64 = sender.amount - amount; // Private record for sender let remaining: token = token { owner: sender.owner, amount: difference, }; // Public operation for receiver return (remaining, final { finalize_transfer_private_to_public(receiver, amount) });}final fn finalize_transfer_private_to_public( public receiver: address, public amount: u64) { // Update public state let current_amount: u64 = Mapping::get_or_use(account, receiver, 0u64); Mapping::set(account, receiver, current_amount + amount);}
// Convert public balance to private recordfn transfer_public_to_private( public receiver: address, public amount: u64) -> (token, Final) { // Private record for receiver let transferred: token = token { owner: receiver, amount: amount, }; // Deduct from public balance return (transferred, final { finalize_transfer_public_to_private(self.caller, amount) });}final fn finalize_transfer_public_to_private( public sender: address, public amount: u64) { // Update public state let current_amount: u64 = Mapping::get_or_use(account, sender, 0u64); Mapping::set(account, sender, current_amount - amount);}
// The token record represents a private fungible token.// Each token has an owner and an amount.record token { owner: address, amount: u64,}// A ticket for participating in the lottery.// Tickets are issued to players and consumed when checking results.record Ticket { owner: address,}