Skip to content

Commit

Permalink
alter callback_results example to have a unit result callback
Browse files Browse the repository at this point in the history
  • Loading branch information
itegulov committed Feb 21, 2022
1 parent c3054ed commit a22248e
Show file tree
Hide file tree
Showing 2 changed files with 41 additions and 13 deletions.
Binary file modified examples/callback-results/res/callback_results.wasm
Binary file not shown.
54 changes: 41 additions & 13 deletions examples/callback-results/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,21 +12,24 @@ pub trait ExtCrossContract {
fn a() -> Promise;
fn b(fail: bool) -> &'static str;
fn c(value: u8) -> u8;
fn d(value: u8);
fn handle_callbacks(
#[callback_unwrap] a: u8,
#[callback_result] b: Result<String, PromiseError>,
#[callback_result] c: Result<u8, PromiseError>,
#[callback_result] d: Result<(), PromiseError>,
) -> (bool, bool, bool);
}

#[near_bindgen]
impl Callback {
/// Call functions a, b, and c asynchronously and handle results with `handle_callbacks`.
pub fn call_all(fail_b: bool, c_value: u8) -> Promise {
let gas_per_promise = env::prepaid_gas() / 5;
pub fn call_all(fail_b: bool, c_value: u8, d_value: u8) -> Promise {
let gas_per_promise = env::prepaid_gas() / 7;
ext::a(env::current_account_id(), 0, gas_per_promise)
.and(ext::b(fail_b, env::current_account_id(), 0, gas_per_promise))
.and(ext::c(c_value, env::current_account_id(), 0, gas_per_promise))
.and(ext::d(d_value, env::current_account_id(), 0, gas_per_promise))
.then(ext::handle_callbacks(env::current_account_id(), 0, gas_per_promise))
}

Expand All @@ -51,18 +54,25 @@ impl Callback {
value
}

/// Panics if value is 0.
#[private]
pub fn d(value: u8) {
require!(value > 0, "Value must be positive");
}

/// Receives the callbacks from the other promises called.
#[private]
pub fn handle_callbacks(
#[callback_unwrap] a: u8,
#[callback_result] b: Result<String, PromiseError>,
#[callback_result] c: Result<u8, PromiseError>,
) -> (bool, bool) {
#[callback_result] d: Result<(), PromiseError>,
) -> (bool, bool, bool) {
require!(a == A_VALUE, "Promise returned incorrect value");
if let Ok(s) = b.as_ref() {
require!(s == "Some string");
}
(b.is_err(), c.is_err())
(b.is_err(), c.is_err(), d.is_err())
}
}

Expand All @@ -89,38 +99,56 @@ mod tests {
// No failures
let res = contract
.call(&worker, "call_all")
.args_json((false, 1u8))?
.args_json((false, 1u8, 1u8))?
.gas(300_000_000_000_000)
.transact()
.await?;
assert_eq!(res.json::<(bool, bool)>()?, (false, false));
assert_eq!(res.json::<(bool, bool, bool)>()?, (false, false, false));

// Fail b
let res = contract
.call(&worker, "call_all")
.args_json((true, 1u8))?
.args_json((true, 1u8, 1u8))?
.gas(300_000_000_000_000)
.transact()
.await?;
assert_eq!(res.json::<(bool, bool)>()?, (true, false));
assert_eq!(res.json::<(bool, bool, bool)>()?, (true, false, false));

// Fail c
let res = contract
.call(&worker, "call_all")
.args_json((false, 0u8))?
.args_json((false, 0u8, 1u8))?
.gas(300_000_000_000_000)
.transact()
.await?;
assert_eq!(res.json::<(bool, bool, bool)>()?, (false, true, false));

// Fail d
let res = contract
.call(&worker, "call_all")
.args_json((false, 1u8, 0u8))?
.gas(300_000_000_000_000)
.transact()
.await?;
assert_eq!(res.json::<(bool, bool, bool)>()?, (false, false, true));

// Fail b and c
let res = contract
.call(&worker, "call_all")
.args_json((true, 0u8, 1u8))?
.gas(300_000_000_000_000)
.transact()
.await?;
assert_eq!(res.json::<(bool, bool)>()?, (false, true));
assert_eq!(res.json::<(bool, bool, bool)>()?, (true, true, false));

// Fail both b and c
// Fail all
let res = contract
.call(&worker, "call_all")
.args_json((true, 0u8))?
.args_json((true, 0u8, 0u8))?
.gas(300_000_000_000_000)
.transact()
.await?;
assert_eq!(res.json::<(bool, bool)>()?, (true, true));
assert_eq!(res.json::<(bool, bool, bool)>()?, (true, true, true));

Ok(())
}
Expand Down

0 comments on commit a22248e

Please sign in to comment.