Update pairing tests
This commit is contained in:
parent
a919c6d83d
commit
40dbc1b2ba
153
tests/pairing.rs
153
tests/pairing.rs
@ -2,15 +2,15 @@ use std::collections::HashMap;
|
||||
use std::str::FromStr;
|
||||
|
||||
use sdk_client::api::{
|
||||
create_device_from_sp_wallet, create_new_process, create_response_prd, create_update_message, dump_device, get_address, get_update_proposals, pair_device, parse_cipher, reset_device, restore_device, set_process_cache, set_shared_secrets, setup, validate_state
|
||||
create_device_from_sp_wallet, create_new_process, create_response_prd, create_update_message, dump_device, get_address, pair_device, parse_cipher, reset_device, restore_device, set_process_cache, set_shared_secrets, setup, update_process_state, validate_state
|
||||
};
|
||||
use sdk_common::crypto::AnkSharedSecretHash;
|
||||
use sdk_common::log::debug;
|
||||
use sdk_common::pcd::{Member, Pcd};
|
||||
use sdk_common::sp_client::bitcoin::hex::DisplayHex;
|
||||
use sdk_common::pcd::{Member, Pcd, RoleDefinition};
|
||||
use sdk_common::secrets::SecretsStore;
|
||||
use sdk_common::sp_client::bitcoin::hex::FromHex;
|
||||
use sdk_common::sp_client::bitcoin::OutPoint;
|
||||
use serde_json::{json, Value};
|
||||
use serde_json::{json, Map, Value};
|
||||
|
||||
use wasm_bindgen_test::*;
|
||||
|
||||
@ -97,6 +97,8 @@ fn test_pairing() {
|
||||
let mut bob_process_cache = HashMap::new();
|
||||
let mut alice_secrets_store = SecretsStore::new();
|
||||
let mut bob_secrets_store = SecretsStore::new();
|
||||
let mut alice_diff_cache = Vec::new();
|
||||
let mut bob_diff_cache = Vec::new();
|
||||
|
||||
debug!("==============================================\nStarting test_pairing\n==============================================");
|
||||
|
||||
@ -163,6 +165,7 @@ fn test_pairing() {
|
||||
"key_parity": true, // This allows us to use a 32 bytes array in serialization
|
||||
});
|
||||
|
||||
debug!("Alice creates the pairing process");
|
||||
let create_process_return = create_new_process(pairing_init_state.to_string(), RELAY_ADDRESS.to_owned(), 1).unwrap();
|
||||
|
||||
let commit_msg = create_process_return.commit_to_send.unwrap();
|
||||
@ -184,12 +187,18 @@ fn test_pairing() {
|
||||
let updated_process = create_process_return.updated_process.unwrap();
|
||||
alice_process_cache.insert(updated_process.commitment_tx, updated_process.current_process);
|
||||
|
||||
// Alice keeps track of the change she needs to validate
|
||||
let create_process_diffs = updated_process.new_diffs;
|
||||
|
||||
let new_state_id = &create_process_diffs.get(0).unwrap().new_state_merkle_root;
|
||||
|
||||
alice_diff_cache.extend(create_process_diffs.iter());
|
||||
|
||||
// We send the commit_msg to the relay we got the address from
|
||||
|
||||
// now we create prd update for this new process
|
||||
debug!("Alice sends an update prd to Bob");
|
||||
let root = <Value as Pcd>::create_merkle_tree(&commit_msg.pcd_commitment).unwrap().root().unwrap();
|
||||
let create_update_return = create_update_message(updated_process.commitment_tx.to_string(), root.to_lower_hex_string()).unwrap();
|
||||
debug!("Alice creates an update prd to Bob");
|
||||
let create_update_return = create_update_message(updated_process.commitment_tx.to_string(), new_state_id.clone()).unwrap();
|
||||
|
||||
let updated_process = create_update_return.updated_process.unwrap();
|
||||
alice_process_cache.insert(updated_process.commitment_tx, updated_process.current_process);
|
||||
@ -212,11 +221,40 @@ fn test_pairing() {
|
||||
|
||||
let updated_process = bob_parsed_return.updated_process.unwrap();
|
||||
|
||||
let parsed_prd_diffs = updated_process.new_diffs;
|
||||
|
||||
// debug!("Bob creates process {} with state {}", updated_process.commitment_tx, new_state_id);
|
||||
bob_process_cache.insert(updated_process.commitment_tx, updated_process.current_process);
|
||||
|
||||
let prd_confirm_cipher = bob_parsed_return.ciphers_to_send.iter().next().unwrap();
|
||||
// Bob also keeps track of changes
|
||||
|
||||
debug!("Bob sends a Confirm Prd to Alice");
|
||||
bob_diff_cache.extend(parsed_prd_diffs.into_iter());
|
||||
|
||||
debug!("Bob can now fetch the data from storage using the hashes");
|
||||
// We have to cheat here and let Bob access Alice process cache
|
||||
let process = alice_process_cache.get(&updated_process.commitment_tx).unwrap();
|
||||
|
||||
let state = process.get_state_for_commitments_root(&new_state_id).unwrap();
|
||||
|
||||
let hash2values: Map<String, Value> = bob_diff_cache.iter()
|
||||
.filter(|diff| diff.new_state_merkle_root == *new_state_id)
|
||||
.map(|diff| {
|
||||
let encrypted_value = state.encrypted_pcd.as_object().unwrap().get(&diff.field).unwrap();
|
||||
(diff.value_commitment.clone(), encrypted_value.clone())
|
||||
})
|
||||
.collect();
|
||||
let update_process_res = update_process_state(updated_process.commitment_tx.to_string(), new_state_id.clone(), serde_json::to_string(&Value::Object(hash2values)).unwrap()).unwrap();
|
||||
|
||||
let updated_process = update_process_res.updated_process.unwrap();
|
||||
|
||||
let parsed_prd_diffs = updated_process.new_diffs;
|
||||
|
||||
bob_process_cache.insert(updated_process.commitment_tx, updated_process.current_process);
|
||||
|
||||
bob_diff_cache.extend(parsed_prd_diffs);
|
||||
|
||||
// We can also prune the old diffs from the cache
|
||||
bob_diff_cache.retain(|diff| diff.new_value != Value::Null);
|
||||
|
||||
// this is only for testing, as we're playing both parts
|
||||
let bob_device = dump_device().unwrap();
|
||||
@ -227,34 +265,23 @@ fn test_pairing() {
|
||||
set_process_cache(serde_json::to_string(&alice_process_cache).unwrap()).unwrap();
|
||||
set_shared_secrets(serde_json::to_string(&alice_secrets_store).unwrap()).unwrap();
|
||||
|
||||
debug!("Alice receives the Confirm Prd");
|
||||
let alice_parsed_confirm = parse_cipher(prd_confirm_cipher.clone()).unwrap();
|
||||
let commitment_outpoint = alice_process_cache.keys().next().unwrap();
|
||||
|
||||
debug!(
|
||||
"Alice parsed Bob's Confirm Prd: {:#?}",
|
||||
alice_parsed_confirm
|
||||
);
|
||||
debug!("Alice can validate the new state of the process");
|
||||
let relevant_process = alice_process_cache.get(&commitment_outpoint).unwrap();
|
||||
|
||||
// Alice simply shoots back the return value in the ws
|
||||
let bob_received_pcd = alice_parsed_confirm.ciphers_to_send[0].clone();
|
||||
let commit_msg = alice_parsed_confirm.commit_to_send.unwrap();
|
||||
|
||||
// Take the relevant state out of the process
|
||||
let relevant_process = alice_process_cache.get(&OutPoint::from_str(&commit_msg.init_tx).unwrap()).unwrap();
|
||||
|
||||
let concurrent_states = relevant_process.get_latest_concurrent_states().unwrap();
|
||||
let relevant_state = concurrent_states.into_iter().find(|s| s.pcd_commitment == commit_msg.pcd_commitment).unwrap();
|
||||
|
||||
let root = <Value as Pcd>::create_merkle_tree(&relevant_state.pcd_commitment).unwrap().root().unwrap();
|
||||
for diff in alice_diff_cache {
|
||||
debug!("User validate diff: {:#?}", diff);
|
||||
}
|
||||
|
||||
// Alice can also sign her response and send it to Bob
|
||||
let validate_state_return = validate_state(commit_msg.init_tx, root.to_lower_hex_string()).unwrap();
|
||||
let validate_state_return = validate_state(commitment_outpoint.to_string(), new_state_id.clone()).unwrap();
|
||||
|
||||
let updated_process = validate_state_return.updated_process.unwrap();
|
||||
|
||||
alice_process_cache.insert(updated_process.commitment_tx, updated_process.current_process);
|
||||
|
||||
let alice_response = create_response_prd(updated_process.commitment_tx.to_string(), root.to_lower_hex_string()).unwrap();
|
||||
let alice_response = create_response_prd(updated_process.commitment_tx.to_string(), new_state_id.clone()).unwrap();
|
||||
|
||||
// ======================= Bob
|
||||
reset_device().unwrap();
|
||||
@ -262,77 +289,31 @@ fn test_pairing() {
|
||||
set_process_cache(serde_json::to_string(&bob_process_cache).unwrap()).unwrap();
|
||||
set_shared_secrets(serde_json::to_string(&bob_secrets_store).unwrap()).unwrap();
|
||||
|
||||
debug!("Bob parses Alice's pcd");
|
||||
let bob_parsed_pcd_return = parse_cipher(bob_received_pcd).unwrap();
|
||||
|
||||
let updated_process = bob_parsed_pcd_return.updated_process.unwrap();
|
||||
|
||||
// Here we would update our database
|
||||
bob_process_cache.insert(
|
||||
updated_process.commitment_tx,
|
||||
updated_process.current_process
|
||||
);
|
||||
|
||||
// At this point, user must validate the pairing proposal received from Alice
|
||||
// We decrypt the content of the pcd so that we can display to user what matters
|
||||
let alice_proposal = get_update_proposals(updated_process.commitment_tx.to_string()).unwrap().decrypted_pcds;
|
||||
|
||||
debug!("Alice proposal: {:#?}", alice_proposal);
|
||||
|
||||
let (pcd_commitment_root, proposal) = alice_proposal.iter().next().unwrap();
|
||||
|
||||
// debug!("proposal: {:#?}", proposal);
|
||||
|
||||
// get the roles from the proposal
|
||||
let roles = proposal.extract_roles().unwrap();
|
||||
|
||||
// we check that the proposal contains only one member
|
||||
assert!(roles.len() == 1);
|
||||
assert!(roles["owner"].members.len() == 1);
|
||||
|
||||
// we get all the addresses of the members of the proposal
|
||||
let proposal_members = roles
|
||||
.iter()
|
||||
.flat_map(|(_, members)| members.members.iter().flat_map(|m| m.get_addresses()))
|
||||
.collect::<Vec<String>>();
|
||||
|
||||
// we can automatically check that a pairing member contains local device address + the one that sent the proposal
|
||||
assert!(proposal_members.contains(&alice_address));
|
||||
assert!(proposal_members.contains(&bob_address));
|
||||
assert!(proposal_members.len() == 2); // no free riders
|
||||
|
||||
// We remove the local address, but maybe that's the responsibility of the Member type
|
||||
let proposal_members = proposal_members
|
||||
.into_iter()
|
||||
.filter(|m| m != &bob_address)
|
||||
.collect::<Vec<String>>();
|
||||
|
||||
debug!("proposal_members: {:?}", proposal_members);
|
||||
|
||||
// we can now show all the addresses to the user on device to prompt confirmation
|
||||
debug!("Pop-up: User confirmation");
|
||||
for diff in &bob_diff_cache {
|
||||
if diff.need_validation {
|
||||
debug!("Pop-up: User confirmation");
|
||||
debug!("{:#?}", diff);
|
||||
}
|
||||
}
|
||||
|
||||
// If user is ok, we can add our own validation token
|
||||
// Get the whole commitment from the process
|
||||
let bob_validated_process = validate_state(updated_process.commitment_tx.to_string(), pcd_commitment_root.to_string()).unwrap();
|
||||
let bob_validated_process = validate_state(updated_process.commitment_tx.to_string(), new_state_id.clone()).unwrap();
|
||||
|
||||
let updated_process = bob_validated_process.updated_process.unwrap();
|
||||
|
||||
bob_process_cache.insert(updated_process.commitment_tx, updated_process.current_process);
|
||||
|
||||
let bob_response = create_response_prd(updated_process.commitment_tx.to_string(), pcd_commitment_root.to_string()).unwrap();
|
||||
let bob_response = create_response_prd(updated_process.commitment_tx.to_string(), new_state_id.clone()).unwrap();
|
||||
|
||||
let ciphers = bob_response.ciphers_to_send; // We would send it to Alice to let her know we agree
|
||||
|
||||
debug!("Bob pairs device with Alice");
|
||||
pair_device(updated_process.commitment_tx.to_string(), proposal_members).unwrap();
|
||||
let roles: HashMap<String, RoleDefinition> = serde_json::from_value(bob_diff_cache.iter().find(|diff| diff.field == "roles").unwrap().new_value.clone()).unwrap();
|
||||
let owner = roles.get("owner").unwrap();
|
||||
let members_to_pair: Vec<String> = owner.members.iter().flat_map(|m| m.get_addresses()).collect();
|
||||
pair_device(updated_process.commitment_tx.to_string(), members_to_pair).unwrap();
|
||||
|
||||
// We can also check alice response
|
||||
let parsed_alice_response = parse_cipher(alice_response.ciphers_to_send[0].clone()).unwrap();
|
||||
|
||||
debug!("parsed_alice_response: {:#?}", parsed_alice_response.updated_process.unwrap());
|
||||
|
||||
// Since we have enough validation we can send it directly to relay for commitment
|
||||
|
||||
// login();
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user