Skip to content

Commit

Permalink
idk
Browse files Browse the repository at this point in the history
  • Loading branch information
zbuc committed Aug 20, 2024
1 parent 96f0543 commit 44bff17
Show file tree
Hide file tree
Showing 4 changed files with 203 additions and 134 deletions.
13 changes: 0 additions & 13 deletions crates/core/app/tests/common/ibc_tests/node.rs
Original file line number Diff line number Diff line change
Expand Up @@ -191,19 +191,6 @@ impl TestNodeWithIBC {
)?)
}

pub async fn get_prev_counterparty_consensus_state(
&self,
client_id: &ClientId,
height: &Height,
) -> Result<Option<(Height, ConsensusState)>> {
// TODO: this probably shouldn't reach into storage directly huh
self.storage
.clone()
.latest_snapshot()
.prev_verified_consensus_state(client_id, height)
.await
}

// TODO: maybe move to an IBC extension trait for TestNode?
// or maybe the Block has everything it needs to produce this?
pub fn create_tendermint_header(
Expand Down
274 changes: 197 additions & 77 deletions crates/core/app/tests/common/ibc_tests/relayer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ use {
client::v1::{QueryClientStateRequest, QueryConsensusStateRequest},
connection::v1::QueryConnectionRequest,
},
ibc_types::lightclients::tendermint::client_state::ClientState as TendermintClientState,
ibc_types::{
core::{
client::{
Expand Down Expand Up @@ -376,9 +377,10 @@ impl MockRelayer {
// tell chain b about chain a
pub async fn _build_and_send_update_client_b(&mut self, target_height: Height) -> Result<()> {
tracing::info!(
"send update client for chain {} to chain {}",
"send update client for chain {} to chain {} about height {}",
self.chain_a_ibc.chain_id,
self.chain_b_ibc.chain_id
self.chain_b_ibc.chain_id,
target_height
);
// reverse these because we're sending to chain B
let chain_a_ibc = &mut self.chain_b_ibc;
Expand All @@ -390,9 +392,10 @@ impl MockRelayer {
// helper function to build UpdateClient to send to chain A
pub async fn _build_and_send_update_client_a(&mut self, target_height: Height) -> Result<()> {
tracing::info!(
"send update client for chain {} to chain {}",
"send update client for chain {} to chain {} about height {}",
self.chain_b_ibc.chain_id,
self.chain_a_ibc.chain_id
self.chain_a_ibc.chain_id,
target_height
);
let chain_a_ibc = &mut self.chain_a_ibc;
let chain_b_ibc = &mut self.chain_b_ibc;
Expand Down Expand Up @@ -655,8 +658,15 @@ impl MockRelayer {
// Send an update to both sides to ensure they are up to date
// Build message(s) for updating client on source
// chain B needs to know about chain A at the proof height
let proof_height = connection_of_b_on_a_response.proof_height.clone().unwrap();
self._build_and_send_update_client_b(proof_height.try_into()?)
let proofs_height_on_a: Height = connection_of_b_on_a_response
.proof_height
.clone()
.unwrap()
.try_into()?;
// the proof was included in proof_height, but the root for the proof
// will be available in the next block's header, so we need to increment
let proofs_height_on_a = proofs_height_on_a.increment();
self._build_and_send_update_client_b(proofs_height_on_a.try_into()?)
.await?;
println!(
"client state target height: {:?}",
Expand All @@ -675,6 +685,8 @@ impl MockRelayer {

// d01e8818de18fb050c7aff28a59d430db07802f91c14c4370cf8be785381d4c7 is trusted (for height 6)
// but the proof comes in for ae0565596d0d8fb9019815400868ecf002b3aa48f4e0134e116f3184cfa49c4a (height 7)
self.chain_a_ibc.node.block().execute().await?;
self.chain_b_ibc.node.block().execute().await?;
println!(
"chain b latest height: {:?}",
self.chain_b_ibc.get_latest_height().await?
Expand All @@ -694,14 +706,23 @@ impl MockRelayer {
.unwrap(),
)?;

// chain b needs to know about chain a at the proof height
let proofs_height_on_a = connection_of_b_on_a_response
.proof_height
.expect("proof height")
.try_into()?;
self._build_and_send_update_client_b(proofs_height_on_a)
.await?;
self._sync_chains().await?;

let cs: TendermintClientState = client_state_of_b_on_a_response
.clone()
.client_state
.unwrap()
.try_into()?;
// let cs = ibc_types::lightclients::tendermint::client_state::ClientState::try_from(
// client_state_of_b_on_a_response
// .clone()
// .client_state
// .unwrap(),
// )?;
println!("cs: {:?}", cs);
println!("before send cs latest height: {}", cs.latest_height);
let plan = {
// This mocks the relayer constructing a connection open try message on behalf
// of the counterparty chain.
Expand Down Expand Up @@ -766,6 +787,9 @@ impl MockRelayer {
// "8b741a3cfb2bcd4cf665780d3f9e18a6b954f15912591c1acc6d21de015848dc".to_string()
// );

self.chain_a_ibc.node.block().execute().await?;
self.chain_b_ibc.node.block().execute().await?;

// execute the transaction containing the opentry message
self.chain_b_ibc
.node
Expand Down Expand Up @@ -799,6 +823,7 @@ impl MockRelayer {
self.chain_b_ibc.connection = Some(connection);
}

self._sync_chains().await?;
Ok(())
}

Expand Down Expand Up @@ -909,86 +934,39 @@ async fn _build_and_send_update_client(
chain_b_ibc: &mut TestNodeWithIBC,
target_height: Height,
) -> Result<()> {
let consensus_state = chain_b_ibc
.ibc_client_query_client
.consensus_state(QueryConsensusStateRequest {
client_id: chain_a_ibc.client_id.to_string(),
revision_number: target_height.revision_number,
revision_height: target_height.revision_height,
latest_height: false,
})
.await?
.into_inner();

if let Some(consensus_state) = consensus_state.consensus_state {
tracing::info!("consensus state already exists at height {target_height}, skipping update");
tracing::trace!(?consensus_state, "consensus state");
return Ok(());
}

let mut src_application_latest_height = chain_a_ibc.get_latest_height().await?;
// Wait for the source network to produce block(s) & reach `target_height`.
while src_application_latest_height < target_height {
// advance both blocks
chain_a_ibc.node.block().execute().await?;
chain_b_ibc.node.block().execute().await?;
src_application_latest_height = chain_a_ibc.get_latest_height().await?;
}
let chain_b_height = chain_b_ibc.get_latest_height().await?;
println!("chain_b latest height: {:?}", chain_b_height);
let chain_b_latest_block: penumbra_proto::util::tendermint_proxy::v1::GetBlockByHeightResponse =
chain_b_ibc
.tendermint_proxy_service_client
.get_block_by_height(GetBlockByHeightRequest {
height: chain_b_height.revision_height.try_into()?,
})
.await?
.into_inner();

// Get the latest client state on destination.
let client_state_of_a_on_b_response = chain_b_ibc
// Look up the last recorded consensus state for the counterparty client on chain A
// to determine the last trusted height.
let client_state_of_b_on_a_response = chain_a_ibc
.ibc_client_query_client
.client_state(QueryClientStateRequest {
client_id: chain_a_ibc.client_id.to_string(),
client_id: chain_b_ibc.client_id.to_string(),
})
.await?
.into_inner();

let client_latest_height =
ibc_types::lightclients::tendermint::client_state::ClientState::try_from(
client_state_of_a_on_b_response
client_state_of_b_on_a_response
.clone()
.client_state
.unwrap(),
)?
.latest_height;
let trusted_height = if client_latest_height < target_height {
client_latest_height
} else {
panic!("unsupported, no sending updates to the past");
};

if trusted_height >= target_height {
tracing::warn!(
"skipping update: trusted height ({}) >= chain target height ({})",
trusted_height,
target_height
);

return Ok(());
}

println!("target chain b height: {:?}", target_height);
let chain_b_latest_block: penumbra_proto::util::tendermint_proxy::v1::GetBlockByHeightResponse =
chain_b_ibc
.tendermint_proxy_service_client
.get_block_by_height(GetBlockByHeightRequest {
height: target_height.revision_height.try_into()?,
})
.await?
.into_inner();

// Look up the last recorded consensus state for the counterparty client on chain A
// to determine the last trusted height.
// let prev_counterparty_consensus_state =
// ConsensusState::try_from(consensus_state.consensus_state.unwrap())?;
// let prev_counterparty_consensus_state = self
// .chain_a_ibc
// .get_prev_counterparty_consensus_state(&self.chain_a_ibc.client_id, &chain_b_height)
// .await?;
let trusted_height = client_latest_height;
println!(
"Telling chain a about chain b latest block: {}",
hex::encode(chain_b_latest_block.clone().block_id.unwrap().hash)
"Telling chain a about chain b latest block: {} and trusted height: {}",
hex::encode(chain_b_latest_block.clone().block_id.unwrap().hash),
trusted_height
);
// println!(
// "header: {:?}",
Expand Down Expand Up @@ -1055,5 +1033,147 @@ async fn _build_and_send_update_client(
.with_data(vec![tx.encode_to_vec()])
.execute()
.await?;
// let consensus_state = chain_b_ibc
// .ibc_client_query_client
// .consensus_state(QueryConsensusStateRequest {
// client_id: chain_a_ibc.client_id.to_string(),
// revision_number: target_height.revision_number,
// revision_height: target_height.revision_height,
// latest_height: false,
// })
// .await?
// .into_inner();

// if let Some(consensus_state) = consensus_state.consensus_state {
// tracing::info!("consensus state already exists at height {target_height}, skipping update");
// tracing::trace!(?consensus_state, "consensus state");
// return Ok(());
// }

// let mut src_application_latest_height = chain_a_ibc.get_latest_height().await?;
// // Wait for the source network to produce block(s) & reach `target_height`.
// while src_application_latest_height < target_height {
// // advance both blocks
// chain_a_ibc.node.block().execute().await?;
// chain_b_ibc.node.block().execute().await?;
// src_application_latest_height = chain_a_ibc.get_latest_height().await?;
// }

// // Get the latest client state on destination.
// let client_state_of_a_on_b_response = chain_b_ibc
// .ibc_client_query_client
// .client_state(QueryClientStateRequest {
// client_id: chain_a_ibc.client_id.to_string(),
// })
// .await?
// .into_inner();

// let client_latest_height =
// ibc_types::lightclients::tendermint::client_state::ClientState::try_from(
// client_state_of_a_on_b_response
// .clone()
// .client_state
// .unwrap(),
// )?
// .latest_height;
// let trusted_height = if client_latest_height < target_height {
// client_latest_height
// } else {
// panic!("unsupported, no sending updates to the past");
// };

// if trusted_height >= target_height {
// tracing::warn!(
// "skipping update: trusted height ({}) >= chain target height ({})",
// trusted_height,
// target_height
// );

// return Ok(());
// }

// println!("target chain b height: {:?}", target_height);
// let chain_b_latest_block: penumbra_proto::util::tendermint_proxy::v1::GetBlockByHeightResponse =
// chain_b_ibc
// .tendermint_proxy_service_client
// .get_block_by_height(GetBlockByHeightRequest {
// height: target_height.revision_height.try_into()?,
// })
// .await?
// .into_inner();

// // Look up the last recorded consensus state for the counterparty client on chain A
// // to determine the last trusted height.
// // let prev_counterparty_consensus_state =
// // ConsensusState::try_from(consensus_state.consensus_state.unwrap())?;
// println!(
// "Telling chain a about chain b latest block: {}",
// hex::encode(chain_b_latest_block.clone().block_id.unwrap().hash)
// );
// // println!(
// // "header: {:?}",
// // chain_b_latest_block.block.clone().unwrap().header.unwrap()
// // );
// println!(
// "chain_id {}, height {}, last_commit_hash: {}",
// chain_b_latest_block
// .block
// .clone()
// .unwrap()
// .header
// .unwrap()
// .chain_id,
// chain_b_latest_block
// .block
// .clone()
// .unwrap()
// .header
// .unwrap()
// .height,
// hex::encode(
// chain_b_latest_block
// .block
// .clone()
// .unwrap()
// .header
// .unwrap()
// .last_commit_hash
// )
// );
// let plan = {
// let ibc_msg = IbcRelay::UpdateClient(MsgUpdateClient {
// signer: chain_b_ibc.signer.clone(),
// client_id: chain_a_ibc.client_id.clone(),
// client_message: chain_b_ibc
// // The TendermintHeader is derived from the Block
// // and represents chain B's claims about its current state.
// .create_tendermint_header(Some(trusted_height), chain_b_latest_block)?
// .into(),
// })
// .into();
// TransactionPlan {
// actions: vec![ibc_msg],
// // Now fill out the remaining parts of the transaction needed for verification:
// memo: None,
// detection_data: None, // We'll set this automatically below
// transaction_parameters: TransactionParameters {
// chain_id: chain_a_ibc.chain_id.clone(),
// ..Default::default()
// },
// }
// };
// let tx = chain_a_ibc
// .client()
// .await?
// .witness_auth_build(&plan)
// .await?;

// // Execute the transaction, applying it to the chain state.
// chain_a_ibc
// .node
// .block()
// .with_data(vec![tx.encode_to_vec()])
// .execute()
// .await?;
Ok(())
}
Loading

0 comments on commit 44bff17

Please sign in to comment.