zombienet_orchestrator/tx_helper/
runtime_upgrade.rs1use subxt::{dynamic::Value, tx::TxStatus, OnlineClient, SubstrateConfig};
2use subxt_signer::sr25519::Keypair;
3use tracing::{debug, info};
4
5use crate::network::node::NetworkNode;
6
7pub async fn upgrade(
8 node: &NetworkNode,
9 wasm_data: &[u8],
10 sudo: &Keypair,
11) -> Result<(), anyhow::Error> {
12 debug!(
13 "Upgrading runtime, using node: {} with endpoting {}",
14 node.name, node.ws_uri
15 );
16 let api: OnlineClient<SubstrateConfig> = node.wait_client().await?;
17
18 let upgrade = subxt::dynamic::tx(
19 "System",
20 "set_code_without_checks",
21 vec![Value::from_bytes(wasm_data)],
22 );
23
24 let sudo_call = subxt::dynamic::tx(
25 "Sudo",
26 "sudo_unchecked_weight",
27 vec![
28 upgrade.into_value(),
29 Value::named_composite([
30 ("ref_time", Value::primitive(1.into())),
31 ("proof_size", Value::primitive(1.into())),
32 ]),
33 ],
34 );
35
36 let mut tx = api
37 .tx()
38 .sign_and_submit_then_watch_default(&sudo_call, sudo)
39 .await?;
40
41 while let Some(status) = tx.next().await {
44 let status = status?;
45 match &status {
46 TxStatus::InBestBlock(tx_in_block) | TxStatus::InFinalizedBlock(tx_in_block) => {
47 let _result = tx_in_block.wait_for_success().await?;
48 let block_status = if status.as_finalized().is_some() {
49 "Finalized"
50 } else {
51 "Best"
52 };
53 info!(
54 "[{}] In block: {:#?}",
55 block_status,
56 tx_in_block.block_hash()
57 );
58 },
59 TxStatus::Error { message }
60 | TxStatus::Invalid { message }
61 | TxStatus::Dropped { message } => {
62 return Err(anyhow::format_err!("Error submitting tx: {message}"));
63 },
64 _ => continue,
65 }
66 }
67
68 Ok(())
69}