Limit for logs filter. (#2180)
* Limit for logs filter. * Moving limit inside the filter object * Fixing tests
This commit is contained in:
@@ -957,7 +957,7 @@ impl BlockChainClient for Client {
|
||||
}
|
||||
}
|
||||
|
||||
fn logs(&self, filter: Filter, limit: Option<usize>) -> Vec<LocalizedLogEntry> {
|
||||
fn logs(&self, filter: Filter) -> Vec<LocalizedLogEntry> {
|
||||
let blocks = filter.bloom_possibilities().iter()
|
||||
.filter_map(|bloom| self.blocks_with_bloom(bloom, filter.from_block.clone(), filter.to_block.clone()))
|
||||
.flat_map(|m| m)
|
||||
@@ -966,7 +966,7 @@ impl BlockChainClient for Client {
|
||||
.into_iter()
|
||||
.collect::<Vec<u64>>();
|
||||
|
||||
self.chain.read().logs(blocks, |entry| filter.matches(entry), limit)
|
||||
self.chain.read().logs(blocks, |entry| filter.matches(entry), filter.limit)
|
||||
}
|
||||
|
||||
fn filter_traces(&self, filter: TraceFilter) -> Option<Vec<LocalizedTrace>> {
|
||||
|
||||
@@ -67,6 +67,8 @@ pub struct TestBlockChainClient {
|
||||
pub execution_result: RwLock<Option<Result<Executed, CallError>>>,
|
||||
/// Transaction receipts.
|
||||
pub receipts: RwLock<HashMap<TransactionID, LocalizedReceipt>>,
|
||||
/// Logs
|
||||
pub logs: RwLock<Vec<LocalizedLogEntry>>,
|
||||
/// Block queue size.
|
||||
pub queue_size: AtomicUsize,
|
||||
/// Miner
|
||||
@@ -114,6 +116,7 @@ impl TestBlockChainClient {
|
||||
code: RwLock::new(HashMap::new()),
|
||||
execution_result: RwLock::new(None),
|
||||
receipts: RwLock::new(HashMap::new()),
|
||||
logs: RwLock::new(Vec::new()),
|
||||
queue_size: AtomicUsize::new(0),
|
||||
miner: Arc::new(Miner::with_spec(&spec)),
|
||||
spec: spec,
|
||||
@@ -165,6 +168,11 @@ impl TestBlockChainClient {
|
||||
*self.latest_block_timestamp.write() = ts;
|
||||
}
|
||||
|
||||
/// Set logs to return for each logs call.
|
||||
pub fn set_logs(&self, logs: Vec<LocalizedLogEntry>) {
|
||||
*self.logs.write() = logs;
|
||||
}
|
||||
|
||||
/// Add blocks to test client.
|
||||
pub fn add_blocks(&self, count: usize, with: EachBlockWith) {
|
||||
let len = self.numbers.read().len();
|
||||
@@ -390,8 +398,13 @@ impl BlockChainClient for TestBlockChainClient {
|
||||
unimplemented!();
|
||||
}
|
||||
|
||||
fn logs(&self, _filter: Filter, _limit: Option<usize>) -> Vec<LocalizedLogEntry> {
|
||||
Vec::new()
|
||||
fn logs(&self, filter: Filter) -> Vec<LocalizedLogEntry> {
|
||||
let mut logs = self.logs.read().clone();
|
||||
let len = logs.len();
|
||||
match filter.limit {
|
||||
Some(limit) if limit <= len => logs.split_off(len - limit),
|
||||
_ => logs,
|
||||
}
|
||||
}
|
||||
|
||||
fn last_hashes(&self) -> LastHashes {
|
||||
|
||||
@@ -156,7 +156,7 @@ pub trait BlockChainClient : Sync + Send {
|
||||
fn blocks_with_bloom(&self, bloom: &H2048, from_block: BlockID, to_block: BlockID) -> Option<Vec<BlockNumber>>;
|
||||
|
||||
/// Returns logs matching given filter.
|
||||
fn logs(&self, filter: Filter, limit: Option<usize>) -> Vec<LocalizedLogEntry>;
|
||||
fn logs(&self, filter: Filter) -> Vec<LocalizedLogEntry>;
|
||||
|
||||
/// Makes a non-persistent transaction call.
|
||||
fn call(&self, t: &SignedTransaction, block: BlockID, analytics: CallAnalytics) -> Result<Executed, CallError>;
|
||||
|
||||
@@ -142,7 +142,8 @@ fn returns_logs() {
|
||||
to_block: BlockID::Latest,
|
||||
address: None,
|
||||
topics: vec![],
|
||||
}, None);
|
||||
limit: None,
|
||||
});
|
||||
assert_eq!(logs.len(), 0);
|
||||
}
|
||||
|
||||
@@ -156,7 +157,8 @@ fn returns_logs_with_limit() {
|
||||
to_block: BlockID::Latest,
|
||||
address: None,
|
||||
topics: vec![],
|
||||
}, Some(2));
|
||||
limit: Some(2),
|
||||
});
|
||||
assert_eq!(logs.len(), 0);
|
||||
}
|
||||
|
||||
|
||||
@@ -41,6 +41,12 @@ pub struct Filter {
|
||||
/// If None, match all.
|
||||
/// If specified, log must contain one of these topics.
|
||||
pub topics: Vec<Option<Vec<H256>>>,
|
||||
|
||||
/// Logs limit
|
||||
///
|
||||
/// If None, return all logs
|
||||
/// If specified, should only return *last* `n` logs.
|
||||
pub limit: Option<usize>,
|
||||
}
|
||||
|
||||
impl Clone for Filter {
|
||||
@@ -59,7 +65,8 @@ impl Clone for Filter {
|
||||
from_block: self.from_block.clone(),
|
||||
to_block: self.to_block.clone(),
|
||||
address: self.address.clone(),
|
||||
topics: topics[..].to_vec()
|
||||
topics: topics[..].to_vec(),
|
||||
limit: self.limit,
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -117,6 +124,7 @@ mod tests {
|
||||
to_block: BlockID::Latest,
|
||||
address: None,
|
||||
topics: vec![None, None, None, None],
|
||||
limit: None,
|
||||
};
|
||||
|
||||
let possibilities = none_filter.bloom_possibilities();
|
||||
@@ -136,7 +144,8 @@ mod tests {
|
||||
None,
|
||||
None,
|
||||
None,
|
||||
]
|
||||
],
|
||||
limit: None,
|
||||
};
|
||||
|
||||
let possibilities = filter.bloom_possibilities();
|
||||
@@ -154,7 +163,8 @@ mod tests {
|
||||
Some(vec!["ff74e91598aed6ae5d2fdcf8b24cd2c7be49a0808112a305069355b7160f23f9".into()]),
|
||||
None,
|
||||
None,
|
||||
]
|
||||
],
|
||||
limit: None,
|
||||
};
|
||||
|
||||
let possibilities = filter.bloom_possibilities();
|
||||
@@ -181,7 +191,8 @@ mod tests {
|
||||
]),
|
||||
Some(vec!["ff74e91598aed6ae5d2fdcf8b24cd2c7be49a0808112a305069355b7160f23f9".into()]),
|
||||
None
|
||||
]
|
||||
],
|
||||
limit: None,
|
||||
};
|
||||
|
||||
// number of possibilites should be equal 2 * 2 * 2 * 1 = 8
|
||||
@@ -201,7 +212,8 @@ mod tests {
|
||||
Some(vec!["ff74e91598aed6ae5d2fdcf8b24cd2c7be49a0808112a305069355b7160f23fa".into()]),
|
||||
None,
|
||||
None,
|
||||
]
|
||||
],
|
||||
limit: None,
|
||||
};
|
||||
|
||||
let entry0 = LogEntry {
|
||||
|
||||
Reference in New Issue
Block a user