diff --git a/rust-libs/modules/duniter-gva/src/entities.rs b/rust-libs/modules/duniter-gva/src/entities.rs index 257aeb8d5051870263d6a4d3b7ab1d63b0a9b47b..b13c292280c4d8913b59350651d5c95bb4075216 100644 --- a/rust-libs/modules/duniter-gva/src/entities.rs +++ b/rust-libs/modules/duniter-gva/src/entities.rs @@ -75,6 +75,8 @@ pub(crate) struct UtxoGva { pub(crate) tx_hash: String, /// Index of output in origin transaction pub(crate) output_index: u32, + /// Written block + pub(crate) written_block: u32, /// Written time pub(crate) written_time: u64, } diff --git a/rust-libs/modules/duniter-gva/src/queries/uds.rs b/rust-libs/modules/duniter-gva/src/queries/uds.rs index 55a6508ac832952624ac9dfd369d47126af345e7..4867a37ce4278b009c7744c431a983965e849826 100644 --- a/rust-libs/modules/duniter-gva/src/queries/uds.rs +++ b/rust-libs/modules/duniter-gva/src/queries/uds.rs @@ -46,6 +46,7 @@ impl UdsQuery { #[graphql(desc = "Ed25519 public key on base 58 representation")] pubkey: String, #[graphql(default)] filter: UdsFilter, #[graphql(desc = "pagination", default)] pagination: PaginationWithIntCursor, + #[graphql(desc = "Amount needed")] amount: Option<i64>, ) -> async_graphql::Result<Connection<usize, UdGva, Sum, EmptyFields>> { let pagination = PaginationWithIntCursor::convert_to_page_info(pagination); @@ -63,29 +64,41 @@ impl UdsQuery { ) = data .dbs_pool .execute(move |dbs| { - let paged_data = match filter { - UdsFilter::All => duniter_dbs_read_ops::uds_of_pubkey::all_uds_of_pubkey( - &dbs.bc_db, - &dbs.gva_db, - pubkey, - pagination, - ), - UdsFilter::Unspent => { - duniter_dbs_read_ops::uds_of_pubkey::unspent_uds_of_pubkey( - &dbs.bc_db, pubkey, pagination, None, None, - ) + if let Some(current_block) = + duniter_dbs_read_ops::get_current_block_meta(&dbs.bc_db)? + { + let paged_data = match filter { + UdsFilter::All => duniter_dbs_read_ops::uds_of_pubkey::all_uds_of_pubkey( + &dbs.bc_db, + &dbs.gva_db, + pubkey, + pagination, + ), + UdsFilter::Unspent => { + duniter_dbs_read_ops::uds_of_pubkey::unspent_uds_of_pubkey( + &dbs.bc_db, + pubkey, + pagination, + None, + amount.map(|amount| { + SourceAmount::new(amount, current_block.unit_base as i64) + }), + ) + } + }?; + let mut times = Vec::with_capacity(paged_data.data.uds.len()); + for (bn, _sa) in &paged_data.data.uds { + times.push( + dbs.gva_db + .blockchain_time() + .get(&U32BE(bn.0))? + .unwrap_or_else(|| unreachable!()), + ); } - }?; - let mut times = Vec::with_capacity(paged_data.data.uds.len()); - for (bn, _sa) in &paged_data.data.uds { - times.push( - dbs.gva_db - .blockchain_time() - .get(&U32BE(bn.0))? - .unwrap_or_else(|| unreachable!()), - ); + Ok::<_, anyhow::Error>((paged_data, times)) + } else { + Err(anyhow::Error::msg("no blockchain")) } - Ok::<_, KvError>((paged_data, times)) }) .await??; diff --git a/rust-libs/modules/duniter-gva/src/queries/utxos.rs b/rust-libs/modules/duniter-gva/src/queries/utxos.rs index 79ff9703b475af4a5a29d40575be1aa9d1ea4625..90bdc3d94c25fe5436c42ed6151d31a437ece6da 100644 --- a/rust-libs/modules/duniter-gva/src/queries/utxos.rs +++ b/rust-libs/modules/duniter-gva/src/queries/utxos.rs @@ -31,6 +31,7 @@ impl UtxosQuery { ctx: &async_graphql::Context<'_>, #[graphql(desc = "DUBP wallet script")] script: String, #[graphql(desc = "pagination", default)] pagination: PaginationWithStrCursor, + #[graphql(desc = "Amount needed")] amount: Option<i64>, ) -> async_graphql::Result<Connection<String, UtxoGva, Sum, EmptyFields>> { let pagination = PaginationWithStrCursor::convert_to_page_info(pagination); @@ -48,23 +49,31 @@ impl UtxosQuery { ) = data .dbs_pool .execute(move |dbs| { - let paged_data = duniter_dbs_read_ops::utxos::find_script_utxos( - &dbs.gva_db, - &dbs.txs_mp_db, - None, - pagination, - &script, - )?; - let mut times = Vec::with_capacity(paged_data.data.utxos.len()); - for (UtxoIdWithBlockNumber(_utxo_id, bn), _sa) in &paged_data.data.utxos { - times.push( - dbs.gva_db - .blockchain_time() - .get(&U32BE(bn.0))? - .unwrap_or_else(|| unreachable!()), - ); + if let Some(current_block) = + duniter_dbs_read_ops::get_current_block_meta(&dbs.bc_db)? + { + let paged_data = duniter_dbs_read_ops::utxos::find_script_utxos( + &dbs.gva_db, + &dbs.txs_mp_db, + amount.map(|amount| { + SourceAmount::new(amount, current_block.unit_base as i64) + }), + pagination, + &script, + )?; + let mut times = Vec::with_capacity(paged_data.data.utxos.len()); + for (UtxoIdWithBlockNumber(_utxo_id, bn), _sa) in &paged_data.data.utxos { + times.push( + dbs.gva_db + .blockchain_time() + .get(&U32BE(bn.0))? + .unwrap_or_else(|| unreachable!()), + ); + } + Ok::<_, anyhow::Error>((paged_data, times)) + } else { + Err(anyhow::Error::msg("no blockchain")) } - Ok::<_, anyhow::Error>((paged_data, times)) }) .await??; @@ -87,6 +96,7 @@ impl UtxosQuery { base: source_amount.base(), tx_hash: utxo_id_with_bn.0.tx_hash.to_hex(), output_index: utxo_id_with_bn.0.output_index as u32, + written_block: (utxo_id_with_bn.1).0, written_time: blockchain_time, }, )