### Build Transparent Transaction Bundle with librustzcash Source: https://context7.com/zcash/librustzcash/llms.txt This Rust function demonstrates how to construct a transparent Zcash transaction bundle using the `librustzcash` library. It takes a list of unspent transaction outputs (UTXOs), a recipient address, and an amount, then adds inputs and outputs to a `TransparentBuilder`. The function handles basic change calculation but notes that real-world implementations require more sophisticated fee management. Dependencies include `transparent` and `zcash_primitives` crates. ```rust use transparent::bundle::{Bundle, TxIn, TxOut, OutPoint, Authorized}; use transparent::address::TransparentAddress; use transparent::builder::TransparentBuilder; use zcash_primitives::transaction::components::Amount; // Build transparent transaction bundle fn build_transparent_bundle( utxos: Vec<(OutPoint, TxOut, secp256k1::SecretKey)>, recipient: TransparentAddress, amount: Amount, ) -> Result, Box> { let mut builder = TransparentBuilder::empty(); // Add inputs from UTXOs for (outpoint, txout, secret_key) in utxos { builder.add_input(secret_key, outpoint, txout)?; } // Add output to recipient builder.add_output(&recipient, amount)?; // Calculate change (simplified - real code needs fee calculation) let input_total: Amount = builder.inputs_value(); let change = input_total.checked_sub(amount)?; if !change.is_zero() { let change_addr = TransparentAddress::PublicKeyHash([0u8; 20]); // Use real address builder.add_output(&change_addr, change)?; } // Build authorized bundle let bundle = builder.build()?; Ok(bundle) } ``` -------------------------------- ### Zcash PCZT Multi-Party Construction Workflow in Rust Source: https://context7.com/zcash/librustzcash/llms.txt Executes the full PCZT lifecycle: create a builder, convert to PCZT, update metadata, finalize IO, generate zero-knowledge proofs, sign inputs by each participant, finalize spends, and extract a final signed Zcash transaction. Returns a valid transaction and its txid. Requires pczt crate and zcash_primitives types for Builder, keys, anchors, and proof generation. Inputs/outputs must match network parameters and anchor constraints. ```Rust use pczt::{Pczt, roles::*}; use pczt::roles::{creator, updater, io_finalizer, prover, signer, spend_finalizer, tx_extractor}; use zcash_primitives::transaction::builder::{Builder, BuildConfig}; // Complete PCZT workflow: create, update, prove, sign, extract fn pczt_multi_party_workflow() -> Result> { let params = MainNetwork; let target_height = BlockHeight::from_u32(2_000_000); let rng = &mut OsRng; // === PARTY 1: Creator - Initialize transaction structure === let mut builder = Builder::new( params, target_height, BuildConfig::Standard { sapling_anchor: Some(sapling_anchor), orchard_anchor: Some(orchard_anchor), }, ); // Add Party 1's inputs/outputs builder.add_sapling_spend(&party1_fvk, party1_note, party1_path)?; builder.add_sapling_output( Some(party1_ovk), recipient_addr, Amount::from_u64(25_000_000)?, Some(memo), )?; // Build PCZT instead of signed transaction let pczt_result = builder.build_for_pczt(rng, &FeeRule::standard())?; let mut pczt = creator::Creator::build_from_parts(pczt_result.pczt_parts)?; // === PARTY 2: Updater - Add more inputs === let mut party2_updater = updater::Updater::new(pczt); // Add metadata for Party 2's Sapling spend party2_updater.sapling().update_spend_with(0, |spend| { spend.set_proof_generation_key(party2_proof_key); Ok(()) })?; // Add Party 2's Orchard input metadata party2_updater.orchard().update_action_with(0, |action| { action.spend_mut().set_fvk(party2_orchard_fvk); Ok(()) })?; pczt = party2_updater.finish(); // === IO Finalizer: Lock inputs/outputs === pczt = io_finalizer::IoFinalizer::new(pczt).finalize_io()?; // === Prover: Generate zero-knowledge proofs === let mut pczt_prover = prover::Prover::new(pczt); // Create Sapling spend proofs pczt_prover = pczt_prover.create_sapling_spends(&sapling_proving_key)?; // Create Sapling output proofs pczt_prover = pczt_prover.create_sapling_outputs(&sapling_proving_key)?; // Create Orchard proofs (spends and outputs together) pczt_prover = pczt_prover.create_orchard_proof(&orchard_proving_key)?; pczt = pczt_prover.finish(); // === Signer: Each party signs their inputs === let mut party1_signer = signer::Signer::new(pczt)?; // Party 1 signs their Sapling spend party1_signer.sign_sapling(0, &party1_ask)?; pczt = party1_signer.finish(); // Party 2 signs their inputs let mut party2_signer = signer::Signer::new(pczt)?; // Sign transparent input (if any) party2_signer.sign_transparent(0, &party2_transparent_sk)?; // Sign Orchard input party2_signer.sign_orchard(0, &party2_orchard_sk)?; pczt = party2_signer.finish(); // === Spend Finalizer: Complete spend authorization === pczt = spend_finalizer::SpendFinalizer::new(pczt).finalize_spends()?; // === Transaction Extractor: Get final signed transaction === let extractor = tx_extractor::TransactionExtractor::new(pczt); let transaction = extractor.extract()?; // Verify transaction assert!(transaction.txid().is_valid()); Ok(transaction) } // Serialize and parse PCZT for transmission fn serialize_pczt(pczt: &Pczt) -> Vec { pczt.serialize() } fn parse_pczt(bytes: &[u8]) -> Result { Pczt::parse(bytes) } // PCZT combiner: merge multiple PCZTs fn combine_pczt_inputs( pczt1: Pczt, pczt2: Pczt, ) -> Result> { use pczt::roles::combiner::Combiner; let combiner = Combiner::new(); let combined = combiner.combine(pczt1, pczt2)?; Ok(combined) } ``` -------------------------------- ### Build Zcash Transaction with zcash_primitives (Rust) Source: https://context7.com/zcash/librustzcash/llms.txt This snippet demonstrates how to build a Zcash transaction using the zcash_primitives crate. It includes constructing a transaction with both Sapling and Orchard shielded outputs, along with transparent outputs, and calculating transaction fees. ```rust use zcash_primitives::transaction::builder::{Builder, BuildConfig}; use zcash_primitives::transaction::fees::zip317::FeeRule; use zcash_protocol::consensus::{BlockHeight, MainNetwork}; use zcash_primitives::transaction::components::Amount; use zcash_keys::keys::UnifiedSpendingKey; use zip32::AccountId; fn build_transaction() -> Result> { let params = MainNetwork; let target_height = BlockHeight::from_u32(2_000_000); let rng = &mut OsRng; // Initialize builder with anchors for shielded pools let mut builder = Builder::new( params, target_height, BuildConfig::Standard { sapling_anchor: Some(sapling_anchor), orchard_anchor: Some(orchard_anchor), } ); // Add Sapling spend (input from shielded pool) builder.add_sapling_spend( &sapling_fvk, sapling_note, sapling_merkle_path, )?; // Add Orchard spend builder.add_orchard_spend( &orchard_fvk, orchard_note, orchard_merkle_path, )?; // Add Sapling output with memo let value = Amount::from_u64(50_000_000)?; // 0.5 ZEC let memo = MemoBytes::from([0u8; 512]); builder.add_sapling_output( Some(sapling_ovk), recipient_sapling_addr, value, Some(memo.clone()), )?; // Add Orchard output builder.add_orchard_output( Some(orchard_ovk), recipient_orchard_addr, value, Some(memo), )?; // Calculate and verify fee let fee_rule = FeeRule::standard(); // ZIP 317: 5000 zatoshis marginal fee let fee = fee_rule.fee_required( ¶ms, target_height, 0, 0, // transparent in/out 1, 1, // sapling in/out 1, // orchard actions )?; // Build transaction with proofs let build_result = builder.build(rng, &prover)?; let tx = build_result.transaction(); // Access metadata about input/output ordering let sapling_input_order = build_result.sapling_inputs(); let orchard_action_order = build_result.orchard_actions(); Ok(tx.clone()) } ``` -------------------------------- ### Initialize Zcash Wallet Account in Rust Source: https://context7.com/zcash/librustzcash/llms.txt Initializes a new Zcash wallet account using a seed and birthday height. It derives spending and viewing keys and imports the account into the wallet database. Dependencies include zcash_client_backend and zcash_protocol. ```rust use zcash_client_backend::data_api::WalletWrite; use zcash_client_backend::wallet::AccountId; use zcash_primitives::consensus::{BlockHeight, MainNetwork}; use zcash_client_backend::keys::UnifiedSpendingKey; // Initialize wallet account fn create_wallet_account( db: &mut DB, seed: &[u8; 32], birthday_height: BlockHeight, ) -> Result> { let params = MainNetwork; let account = AccountId::try_from(0)?; // Derive keys let usk = UnifiedSpendingKey::from_seed(¶ms, seed, account)?; let ufvk = usk.to_unified_full_viewing_key(); // Create birthday with checkpoint let birthday = AccountBirthday::from_height(birthday_height); // Import account into wallet database let account_id = db.create_account(&usk, &birthday)?; Ok(account_id) } ``` -------------------------------- ### Parse and validate Zcash addresses using zcash_address Rust library Source: https://context7.com/zcash/librustzcash/llms.txt Demonstrates a two-phase approach to parsing Zcash addresses using the zcash_address crate. First parses address strings into generic ZcashAddress objects, then converts them to application-specific MyAddress types with network validation. Handles Unified, Sapling, and Transparent P2PKH addresses, providing receiver decoding with preference ordering. ```rust use zcash_address::{ZcashAddress, TryFromAddress, ConversionError}; use zcash_address::unified::{self, Encoding}; use zcash_protocol::consensus::NetworkType; // Phase 1: Parse any Zcash address from string fn parse_any_address(addr_string: &str) -> Result { addr_string.parse::() .map_err(|e| format!("Invalid address: {}", e)) } // Phase 2: Convert to application-specific type #[derive(Debug)] struct MyAddress { network: NetworkType, kind: AddressKind, } impl TryFromAddress for MyAddress { type Error = ConversionError; fn try_from_unified( network: NetworkType, data: unified::Address, ) -> Result { Ok(MyAddress { network, kind: AddressKind::Unified(data), }) } fn try_from_sapling( network: NetworkType, data: [u8; 43], ) -> Result { Ok(MyAddress { network, kind: AddressKind::Sapling(data), }) } fn try_from_transparent_p2pkh( network: NetworkType, data: [u8; 20], ) -> Result { Ok(MyAddress { network, kind: AddressKind::P2pkh(data), }) } // Implement other address types... } // Complete parsing workflow fn validate_recipient(addr_string: &str) -> Result> { // Parse string to opaque ZcashAddress let addr: ZcashAddress = addr_string.parse()?; // Convert with network validation let validated = addr.convert_if_network::(NetworkType::Main)?; Ok(validated) } // Working with Unified Addresses fn decode_unified_address(ua_string: &str) -> Result, Box> { let (network, ua) = unified::Address::decode(ua_string)?; // Get receivers in preference order (Orchard > Sapling > Transparent) let mut receivers = Vec::new(); for receiver in ua.items() { match receiver { unified::Receiver::Orchard(data) => { receivers.push(format!("Orchard: {:?}", data)); } unified::Receiver::Sapling(data) => { receivers.push(format!("Sapling: {:?}", data)); } unified::Receiver::P2pkh(data) => { receivers.push(format!("P2PKH: {:?}", data)); } unified::Receiver::P2sh(data) => { receivers.push(format!("P2SH: {:?}", data)); } _ => {} } } Ok(receivers) } ``` -------------------------------- ### Create Transparent Output Script with librustzcash Source: https://context7.com/zcash/librustzcash/llms.txt This Rust function generates a script suitable for a transparent Zcash transaction output from a given `TransparentAddress`. It utilizes the `script()` method provided by the `TransparentAddress` type from the `transparent` crate. This script is essential for defining where funds are sent in a transaction. ```rust use transparent::address::TransparentAddress; use zcash_script::Script; // Create transparent output script fn create_output_script(address: &TransparentAddress) -> Script { address.script() } ``` -------------------------------- ### Proptest Seed Case for Zcash Network Address Source: https://github.com/zcash/librustzcash/blob/main/components/zcash_address/proptest-regressions/kind/unified/address.txt This seed case represents a failure scenario involving a Zcash network address with Orchard, P2pkh, and Sapling components. It is used by proptest to re-run specific failure cases before generating new test scenarios. ```Rust cc fd6f22032b9add1319ad27b183de7d522bf9dfa0d6ef56354812bce5a803c11c # shrinks to network = Main, ua = Address([Orchard([0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 101, 7, 48, 33, 241, 53, 105]), P2pkh([104, 47, 211, 146, 155, 136, 129, 215, 137, 152, 117, 157, 55, 4, 199, 123, 69, 12, 133, 89]), Sapling([164, 56, 210, 240, 243, 207, 59, 213, 35, 184, 250, 69, 206, 249, 184, 252, 184, 103, 227, 207, 249, 127, 133, 218, 97, 241, 242, 12, 155, 162, 137, 100, 200, 50, 96, 79, 33, 137, 242, 172, 43, 6, 255])]) ``` -------------------------------- ### Derive Unified Keys and Address from Seed (Rust) Source: https://context7.com/zcash/librustzcash/llms.txt Derives Unified Spending Key (USK), Unified Full Viewing Key (UFVk), and a default Unified Address (UA) from a 32-byte seed and an account index following ZIP 32. It also demonstrates accessing individual key components for transparent, Sapling, and Orchard receivers. ```rust use zcash_keys::keys::{UnifiedSpendingKey, UnifiedFullViewingKey}; use zcash_keys::address::UnifiedAddress; use zcash_protocol::consensus::MainNetwork; use zip32::AccountId; fn derive_unified_keys_from_seed( seed: &[u8; 32], account_index: u32, ) -> Result<(UnifiedSpendingKey, UnifiedFullViewingKey, UnifiedAddress), Box> { let params = MainNetwork; let account = AccountId::try_from(account_index)?; // Derive Unified Spending Key from seed following ZIP 32 let usk = UnifiedSpendingKey::from_seed( ¶ms, seed, account, )?; // Get Unified Full Viewing Key (can derive addresses, cannot spend) let ufvk = usk.to_unified_full_viewing_key(); // Generate default Unified Address with all available receivers let (ua, _diversifier_index) = ufvk.default_address()?; // Access individual key components if let Some(_transparent_key) = usk.transparent() { println!("Has transparent key"); } if let Some(_sapling_key) = usk.sapling() { println!("Has Sapling key"); } if let Some(_orchard_key) = usk.orchard() { println!("Has Orchard key"); } Ok((usk, ufvk, ua)) } ``` -------------------------------- ### Commit Hash and CommitmentTree Data for Proptest Failure Case Source: https://github.com/zcash/librustzcash/blob/main/zcash_primitives/proptest-regressions/merkle_tree.txt This snippet represents a specific failure case generated by proptest. It includes a commit hash for reference and the serialized data of a CommitmentTree, which is used to reproduce the failure. ```text cc ad8649940f45fef5aad3355d7ca193e7d018285b04f9d976197ff8e1fec8687a # shrinks to ct = CommitmentTree { left: Some(Node { repr: [31, 136, 59, 216, 239, 236, 65, 132, 70, 226, 212, 35, 165, 194, 10, 57, 188, 94, 141, 22, 236, 68, 38, 57, 219, 28, 160, 173, 156, 62, 220, 34] }), right: Some(Node { repr: [117, 7, 10, 72, 207, 40, 193, 79, 126, 156, 158, 193, 63, 190, 49, 179, 227, 188, 144, 85, 30, 143, 186, 203, 154, 76, 5, 113, 42, 16, 60, 41] }), parents: [Some(Node { repr: [92, 253, 34, 29, 13, 202, 250, 201, 54, 210, 88, 207, 183, 117, 166, 126, 63, 101, 34, 44, 119, 88, 122, 240, 51, 77, 53, 148, 190, 141, 226, 103] }), Some(Node { repr: [91, 140, 162, 31, 9, 135, 96, 209, 170, 45, 143, 251, 108, 37, 94, 84, 95, 22, 28, 109, 140, 61, 249, 41, 220, 207, 149, 136, 93, 220, 161, 87] }), Some(Node { repr: [21, 173, 87, 125, 78, 242, 185, 197, 174, 47, 114, 229, 189, 35, 154, 221, 164, 232, 181, 26, 232, 216, 228, 244, 81, 127, 222, 10, 22, 241, 134, 106] }), None, Some(Node { repr: [88, 145, 84, 46, 146, 135, 252, 5, 21, 50, 137, 85, 36, 136, 101, 55, 153, 134, 71, 41, 95, 73, 17, 151, 170, 141, 195, 95, 11, 204, 181, 85] }), None, None] } ``` -------------------------------- ### Query Zcash Spendable Account Balance in Rust Source: https://context7.com/zcash/librustzcash/llms.txt Queries the spendable balance of a Zcash account, including Sapling, Orchard, and transparent pools. It also reports pending confirmation values. Requires a WalletRead implementor. ```rust use zcash_client_backend::data_api::WalletRead; use zcash_client_backend::wallet::AccountBalance; use zcash_primitives::consensus::BlockHeight; use zcash_primitives::transaction::components::Amount; // Query account balance fn get_spendable_balance( db: &DB, account_id: AccountId, anchor_height: BlockHeight, ) -> Result> { // Get full account balance let balance: AccountBalance = db.get_wallet_balance(account_id)?; // Query by pool let sapling_balance = balance.sapling_balance(); let orchard_balance = balance.orchard_balance(); let transparent_balance = balance.unshielded_balance(); // Total spendable (confirmed) value let spendable = balance.spendable_value(); // Value pending confirmation let pending = balance.value_pending_spendability(anchor_height); println!("Sapling: {} zatoshis", sapling_balance.spendable_value()); println!("Orchard: {} zatoshis", orchard_balance.spendable_value()); println!("Transparent: {} zatoshis", transparent_balance); println!("Total spendable: {} zatoshis", spendable); println!("Pending: {} zatoshis", pending); Ok(spendable) } ``` -------------------------------- ### Execute Zcash Transaction Proposal in Rust Source: https://context7.com/zcash/librustzcash/llms.txt Executes an approved Zcash transaction proposal by building the transaction using provided spending keys and a transaction prover. It returns the transaction ID upon successful execution. Requires WalletWrite and WalletCommitmentTrees traits. ```rust use zcash_client_backend::chain::TransactionInfo; use zcash_client_backend::data_api::{WalletCommitmentTrees, WalletWrite}; use zcash_client_backend::fees::zip317::{TxProver}; use zcash_client_backend::keys::UnifiedSpendingKey; use zcash_client_backend::proposal::{Proposal, ProposalInput}; use zcash_client_backend::wallet::{Builder, BuildConfig}; use zcash_primitives::consensus::MainNetwork; use zcash_primitives::txid::TxId; use rand::rngs::OsRng; // Execute approved proposal fn execute_proposal( db: &mut DB, proposal: &Proposal, usk: &UnifiedSpendingKey, prover: &impl TxProver, ) -> Result> where DB: WalletWrite + WalletCommitmentTrees, { let params = MainNetwork; let rng = &mut OsRng; // Build transaction from proposal let step = proposal.steps().first() .ok_or("Empty proposal")?; let mut builder = Builder::new( params, step.target_height(), BuildConfig::Standard { sapling_anchor: step.sapling_anchor(), orchard_anchor: step.orchard_anchor(), }, ); // Add inputs from proposal for input in step.inputs() { match input { ProposalInput::Sapling { note, merkle_path, .. } => { builder.add_sapling_spend(usk.sapling_fvk(), note, merkle_path)?; } ProposalInput::Orchard { note, merkle_path, .. } => { } } } // ... rest of the builder configuration and transaction creation // let tx = builder.build(rng, prover)?; // let txid = db.insert_tx(tx)?; // Ok(txid) unimplemented!() } ``` -------------------------------- ### Propose Zcash Transaction with ZIP 317 Fees in Rust Source: https://context7.com/zcash/librustzcash/llms.txt Proposes a Zcash transaction, including selecting inputs (coin selection) and calculating fees according to ZIP 317. It returns a Proposal object containing transaction details. Requires WalletRead and InputSource traits. ```rust use zcash_client_backend::fees::zip317; use zcash_client_backend::proposal::{Proposal, ProposalError}; use zcash_client_backend::wallet::{TransactionRequest, GreedyInputSelector}; use zcash_client_backend::data_api::{InputSource, WalletRead}; use zcash_primitives::consensus::MainNetwork; use zcash_primitives::transaction::components::Amount; // Create transaction proposal with ZIP 317 fees fn propose_transaction( db: &mut DB, account_id: AccountId, recipient: &ZcashAddress, amount: Amount, memo: Option, ) -> Result where DB: WalletRead + InputSource, { let params = MainNetwork; let fee_rule = zip317::FeeRule::standard(); let min_target_height = db.chain_height()? + 1; // Build transaction request let mut request = TransactionRequest::new(); request.add_payment(recipient, amount, memo); // Select notes to spend (coin selection) let input_selector = GreedyInputSelector::new(); let proposal = input_selector.propose_transaction( ¶ms, db, account_id, &fee_rule, min_target_height, request, )?; // Proposal contains: // - Selected inputs (transparent UTXOs, Sapling notes, Orchard notes) // - Requested outputs // - Change outputs // - Calculated fee // - Transaction balance Ok(proposal) } ``` -------------------------------- ### Verify Transparent Transaction Signature with librustzcash Source: https://context7.com/zcash/librustzcash/llms.txt This Rust function verifies the signature of a transparent Zcash transaction input against its corresponding previous output. It uses the `verify_script` function from the `zcash_script` crate, taking the transaction input (`TxIn`), the previous output (`TxOut`), and the consensus branch ID as parameters. This is a critical step in validating the authenticity of transactions. ```rust use transparent::bundle::{TxIn, TxOut}; use zcash_script::verify_script; // Verify transparent signature fn verify_transparent_input( input: &TxIn, prevout: &TxOut, consensus_branch_id: u32, ) -> Result<(), zcash_script::Error> { verify_script( &input.script_sig, &prevout.script_pubkey, consensus_branch_id, input.sequence, )?; Ok(()) } ``` -------------------------------- ### Build Custom Unified Address from Receivers (Rust) Source: https://context7.com/zcash/librustzcash/llms.txt Constructs a Unified Address (UA) by combining optional Orchard, Sapling, and transparent addresses. It then encodes the resulting UA for display and asserts that the UA correctly reflects the presence of the provided receiver types. ```rust use zcash_keys::address::UnifiedAddress; use zcash_protocol::consensus::MainNetwork; use orchard; use sapling; use transparent; fn build_custom_unified_address( orchard_addr: Option, sapling_addr: Option, transparent_addr: Option, ) -> Result> { // Construct UA from available receivers let ua = UnifiedAddress::from_receivers( orchard_addr, sapling_addr, transparent_addr, )?; // Query capabilities assert!(ua.has_orchard() == orchard_addr.is_some()); assert!(ua.has_sapling() == sapling_addr.is_some()); assert!(ua.has_transparent() == transparent_addr.is_some()); // Encode for display let encoded = ua.encode(&MainNetwork); Ok(encoded) } ``` -------------------------------- ### Parse Transparent Zcash Address with librustzcash Source: https://context7.com/zcash/librustzcash/llms.txt This Rust function parses a Zcash address string into a `TransparentAddress` type using the `zcash_address` crate. It handles conversion from a general `ZcashAddress` to the specific `TransparentAddress` and prints the address type (P2PKH or P2SH). This is useful for validating and working with transparent addresses in Zcash transactions. ```rust use transparent::address::TransparentAddress; use zcash_address::{ZcashAddress, TryFromAddress}; // Parse transparent address fn parse_transparent_address(addr_string: &str) -> Result> { let addr: ZcashAddress = addr_string.parse()?; // Convert to transparent address let transparent = addr.convert::()?; // Check address type match transparent { TransparentAddress::PublicKeyHash(hash) => { println!("P2PKH address: {:?}", hash); } TransparentAddress::ScriptHash(hash) => { println!("P2SH address: {:?}", hash); } } Ok(transparent) } ``` -------------------------------- ### Scan Zcash Blockchain for Wallet Transactions in Rust Source: https://context7.com/zcash/librustzcash/llms.txt Scans the Zcash blockchain for wallet transactions using cached blocks and provided ranges. Handles chain reorganizations and allows for limiting the scan. Requires a WalletWrite implementor and a BlockSource. ```rust use zcash_client_backend::data_api::chain::scan_cached_blocks; use zcash_client_backend::data_api::{BlockSource, WalletWrite}; use zcash_primitives::consensus::BlockHeight; // Scan blockchain for wallet transactions fn sync_wallet( db: &mut DB, cache: &Cache, from_height: BlockHeight, limit: Option, ) -> Result<(), Box> where DB: WalletWrite, Cache: BlockSource, { let params = MainNetwork; // Get suggested scan ranges (handles chain reorgs) let scan_ranges = db.suggest_scan_ranges()?; for range in scan_ranges { // Scan cached blocks scan_cached_blocks( ¶ms, cache, db, range.start(), limit, )?; } Ok(()) } ``` -------------------------------- ### Derive Sapling Address and Encode Keys (Rust) Source: https://context7.com/zcash/librustzcash/llms.txt Derives the extended Sapling spending key and viewing key from a seed and account index. It then encodes the spending key for backup and generates the payment address for the default diversifier, returning both encoded strings. This function also shows how to derive additional diversified addresses. ```rust use zcash_keys::keys::sapling; use zcash_keys::encoding::{ encode_extended_spending_key, encode_payment_address, }; use zcash_protocol::constants::mainnet::{HRP_SAPLING_EXTENDED_SPENDING_KEY, COIN_TYPE}; use zip32::AccountId; use zip32::DiversifierIndex; fn derive_sapling_address( seed: &[u8; 32], account_index: u32, ) -> Result<(String, String), Box> { let account = AccountId::try_from(account_index)?; // Derive extended Sapling spending key let extsk = sapling::spending_key(seed, COIN_TYPE, account); // Encode spending key for backup let encoded_sk = encode_extended_spending_key( HRP_SAPLING_EXTENDED_SPENDING_KEY, &extsk, ); // Derive viewing key and find address at default diversifier let extfvk = extsk.to_diversifiable_full_viewing_key(); let (diversifier_index, payment_addr) = extfvk .find_address(DiversifierIndex::new())?; // Encode payment address let encoded_addr = encode_payment_address( "zs", // mainnet Sapling HRP &payment_addr, ); // Can derive additional diversified addresses let _next_index = diversifier_index.increment()?; // let (_, diversified_addr) = extfvk.find_address(next_index)?; Ok((encoded_sk, encoded_addr)) } ``` -------------------------------- ### Define Custom Fee Rule for Zcash Transactions Source: https://context7.com/zcash/librustzcash/llms.txt This Rust function creates a custom `FeeRule` for Zcash transactions, allowing for specific marginal fee, grace actions, and minimum fee values. This is useful for testing fee calculations with non-standard parameters. The function returns a `FeeRule` instance configured with provided values. ```rust use zcash_primitives::transaction::fees::zip317::FeeRule; // Fee rule with custom parameters fn custom_fee_rule() -> FeeRule { // Create fee rule with custom values (for testing) FeeRule::new( 5000, // marginal_fee (zatoshis per logical action) 2, // grace_actions (free actions before fee applies) 10000, // minimum_fee (zatoshis) ) } ``` -------------------------------- ### Calculate Zcash Transaction Fee with ZIP 317 Source: https://context7.com/zcash/librustzcash/llms.txt This Rust function calculates the required transaction fee according to ZIP 317 specifications using `zcash_primitives`. It takes the counts of various transaction components (inputs, outputs, spends, etc.) and a target block height to determine the fee. The function also prints the minimum fee, marginal fee, and the calculated fee for the given transaction structure. Dependencies include `zcash_primitives` and `zcash_protocol`. ```rust use zcash_primitives::transaction::fees::zip317::{FeeRule, MINIMUM_FEE, MARGINAL_FEE}; use zcash_protocol::consensus::{BlockHeight, MainNetwork}; use zcash_primitives::transaction::components::Amount; fn calculate_transaction_fee( transparent_inputs: usize, transparent_outputs: usize, sapling_spends: usize, sapling_outputs: usize, orchard_actions: usize, ) -> Result> { let params = MainNetwork; let target_height = BlockHeight::from_u32(2_000_000); let fee_rule = FeeRule::standard(); // Calculate fee based on transaction structure // ZIP 317: fee = max(10000, 5000 * max(2, logical_actions)) // where logical_actions counts "action" pairs let fee = fee_rule.fee_required( ¶ms, target_height, transparent_inputs, transparent_outputs, sapling_spends, sapling_outputs, orchard_actions, )?; println!("Minimum fee: {} zatoshis", MINIMUM_FEE); println!("Marginal fee per action: {} zatoshis", MARGINAL_FEE); println!("Required fee for this tx: {} zatoshis", fee); Ok(fee) } ``` -------------------------------- ### CommitmentTree Seed for Proptest Failure Cases (Rust) Source: https://github.com/zcash/librustzcash/blob/main/zcash_primitives/proptest-regressions/merkle_tree/incremental.txt A Rust CommitmentTree structure representing a specific state that caused a failure during property-based testing (proptest). This seed is used to reproduce the failure. It includes nested Node structures with byte array representations of their state. ```Rust cc f6df6e3a7a1641029b9f39a671046ba39745ded73de8d7444e7c27a8f73e1365 # shrinks to t = CommitmentTree { left: Some(Node { repr: [36, 96, 18, 1, 228, 118, 68, 158, 142, 67, 253, 219, 85, 192, 179, 142, 230, 218, 145, 73, 159, 211, 208, 58, 182, 136, 108, 95, 137, 166, 232, 10] }), right: Some(Node { repr: [10, 211, 222, 223, 94, 55, 180, 62, 79, 50, 38, 55, 73, 152, 245, 181, 157, 40, 89, 177, 51, 96, 154, 78, 185, 74, 118, 11, 54, 188, 151, 181] }), parents: [None, None, Some(Node { repr: [99, 240, 35, 62, 160, 23, 150, 46, 3, 226, 153, 214, 59, 25, 19, 85, 247, 234, 174, 75, 93, 165, 99, 116, 194, 243, 103, 155, 166, 131, 10, 68] }), Some(Node { repr: [106, 249, 220, 118, 49, 239, 102, 59, 121, 101, 110, 82, 194, 242, 72, 24, 209, 160, 24, 225, 124, 138, 138, 52, 157, 6, 43, 180, 212, 8, 117, 3] })] } ```