Rust Create Canister / Inter-Canister Calls

Does anyone know how to use the Rust CDK call function?

I’m trying to call the management canister to create a new canister from wasm. It looks like I just need to implement the ArgumentEncoder trait on my struct, but it feels a bit laborious to do that for all my types.

ArgumentEncoder is implemented for all tuple types (T1, T2, ...), where Ti: CandidType. If you have a custom struct, you only need to #[derive(CandidType, Deserialize)], then pass in args as a tuple, for example (your_struct, 42, "Text").

1 Like

Hey @chenyan - I’m having issues with ArgumentDecoder now. If its not too much hassle, could share an example of just calling a canister, and getting the result?

let (first_result, second_result) : (first_result_type, second_result_type) = 
  api::call::call(canister_id, "method", (first_arg, second_arg)).await?;

Both argument and return types are tuples. The type annotation on return type is required, as it cannot be inferred by Rust.

Thanks, let me give that a shot! Just so I make sure I understand

(first_result_type, second_result_type) (candid::Nat, candid::Principle)

That’s the return type of your method. If you are not sure, can you post the did file for that method?

1 Like

@chenyan - sorry for the confusion here is a full example

let canister : (candid::Principal) = ic_cdk::api::call(candid::Principal::management_canister(), "create_canister", ()).await?;

Yields the following error:

the trait `for<'a> ArgumentDecoder<'a>` is not implemented for `ic_types::Principal`

The return type is a tuple, even if it has only one value, so this will work:
let (canister,) : (candid::Principal,)

1 Like

:man_facepalming: DOH! Yes its working now. Thank you!!