`KeychainTxOutIndex` should try and avoid "all" kind of queries. There may be subranges of interest. If the user wants "all" they can just query "..".
105 lines
3.3 KiB
Rust
105 lines
3.3 KiB
Rust
use bdk_chain::{indexed_tx_graph::Indexer, SpkTxOutIndex};
|
|
use bitcoin::{absolute, transaction, Amount, OutPoint, ScriptBuf, Transaction, TxIn, TxOut};
|
|
|
|
#[test]
|
|
fn spk_txout_sent_and_received() {
|
|
let spk1 = ScriptBuf::from_hex("001404f1e52ce2bab3423c6a8c63b7cd730d8f12542c").unwrap();
|
|
let spk2 = ScriptBuf::from_hex("00142b57404ae14f08c3a0c903feb2af7830605eb00f").unwrap();
|
|
|
|
let mut index = SpkTxOutIndex::default();
|
|
index.insert_spk(0, spk1.clone());
|
|
index.insert_spk(1, spk2.clone());
|
|
|
|
let tx1 = Transaction {
|
|
version: transaction::Version::TWO,
|
|
lock_time: absolute::LockTime::ZERO,
|
|
input: vec![],
|
|
output: vec![TxOut {
|
|
value: Amount::from_sat(42_000),
|
|
script_pubkey: spk1.clone(),
|
|
}],
|
|
};
|
|
|
|
assert_eq!(index.sent_and_received(&tx1, ..), (0, 42_000));
|
|
assert_eq!(index.sent_and_received(&tx1, ..1), (0, 42_000));
|
|
assert_eq!(index.sent_and_received(&tx1, 1..), (0, 0));
|
|
assert_eq!(index.net_value(&tx1, ..), 42_000);
|
|
index.index_tx(&tx1);
|
|
assert_eq!(
|
|
index.sent_and_received(&tx1, ..),
|
|
(0, 42_000),
|
|
"shouldn't change after scanning"
|
|
);
|
|
|
|
let tx2 = Transaction {
|
|
version: transaction::Version::ONE,
|
|
lock_time: absolute::LockTime::ZERO,
|
|
input: vec![TxIn {
|
|
previous_output: OutPoint {
|
|
txid: tx1.txid(),
|
|
vout: 0,
|
|
},
|
|
..Default::default()
|
|
}],
|
|
output: vec![
|
|
TxOut {
|
|
value: Amount::from_sat(20_000),
|
|
script_pubkey: spk2,
|
|
},
|
|
TxOut {
|
|
script_pubkey: spk1,
|
|
value: Amount::from_sat(30_000),
|
|
},
|
|
],
|
|
};
|
|
|
|
assert_eq!(index.sent_and_received(&tx2, ..), (42_000, 50_000));
|
|
assert_eq!(index.sent_and_received(&tx2, ..1), (42_000, 30_000));
|
|
assert_eq!(index.sent_and_received(&tx2, 1..), (0, 20_000));
|
|
assert_eq!(index.net_value(&tx2, ..), 8_000);
|
|
}
|
|
|
|
#[test]
|
|
fn mark_used() {
|
|
let spk1 = ScriptBuf::from_hex("001404f1e52ce2bab3423c6a8c63b7cd730d8f12542c").unwrap();
|
|
let spk2 = ScriptBuf::from_hex("00142b57404ae14f08c3a0c903feb2af7830605eb00f").unwrap();
|
|
|
|
let mut spk_index = SpkTxOutIndex::default();
|
|
spk_index.insert_spk(1, spk1.clone());
|
|
spk_index.insert_spk(2, spk2);
|
|
|
|
assert!(!spk_index.is_used(&1));
|
|
spk_index.mark_used(&1);
|
|
assert!(spk_index.is_used(&1));
|
|
spk_index.unmark_used(&1);
|
|
assert!(!spk_index.is_used(&1));
|
|
spk_index.mark_used(&1);
|
|
assert!(spk_index.is_used(&1));
|
|
|
|
let tx1 = Transaction {
|
|
version: transaction::Version::TWO,
|
|
lock_time: absolute::LockTime::ZERO,
|
|
input: vec![],
|
|
output: vec![TxOut {
|
|
value: Amount::from_sat(42_000),
|
|
script_pubkey: spk1,
|
|
}],
|
|
};
|
|
|
|
spk_index.index_tx(&tx1);
|
|
spk_index.unmark_used(&1);
|
|
assert!(
|
|
spk_index.is_used(&1),
|
|
"even though we unmark_used it doesn't matter because there was a tx scanned that used it"
|
|
);
|
|
}
|
|
|
|
#[test]
|
|
fn unmark_used_does_not_result_in_invalid_representation() {
|
|
let mut spk_index = SpkTxOutIndex::default();
|
|
assert!(!spk_index.unmark_used(&0));
|
|
assert!(!spk_index.unmark_used(&1));
|
|
assert!(!spk_index.unmark_used(&2));
|
|
assert!(spk_index.unused_spks(..).collect::<Vec<_>>().is_empty());
|
|
}
|