-
Notifications
You must be signed in to change notification settings - Fork 40
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add CLI error where multiple devices match the same short dev id
- Loading branch information
1 parent
9349757
commit 9415f35
Showing
6 changed files
with
162 additions
and
14 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,6 @@ | ||
use std::sync::Arc; | ||
|
||
use libparsec::{tmp_path, LocalDevice, TmpPath}; | ||
use libparsec::{tmp_path, HumanHandle, LocalDevice, TmpPath}; | ||
use predicates::prelude::PredicateBooleanExt; | ||
|
||
use super::bootstrap_cli_test; | ||
|
@@ -93,3 +93,148 @@ async fn missing_option(tmp_path: TmpPath) { | |
.and(predicates::str::contains(&available_devices_string_list)), | ||
); | ||
} | ||
|
||
#[rstest::rstest] | ||
#[tokio::test] | ||
async fn multiple_device_found(tmp_path: TmpPath) { | ||
let config = super::get_testenv_config(); | ||
let url = super::new_environment(&tmp_path, None, config, false) | ||
.await | ||
.unwrap() | ||
.unwrap(); | ||
|
||
let org_id = super::unique_org_id(); | ||
let org_addr = crate::commands::create_organization::create_organization_req( | ||
&org_id, | ||
&url, | ||
crate::testenv_utils::DEFAULT_ADMINISTRATION_TOKEN, | ||
) | ||
.await | ||
.unwrap(); | ||
|
||
let client_config = libparsec::ClientConfig::default(); | ||
let first_available_device = | ||
crate::commands::bootstrap_organization::bootstrap_organization_req( | ||
client_config.clone(), | ||
org_addr, | ||
"dev1".parse().unwrap(), | ||
libparsec::HumanHandle::new("[email protected]", "First").unwrap(), | ||
crate::testenv_utils::DEFAULT_DEVICE_PASSWORD | ||
.to_string() | ||
.into(), | ||
) | ||
.await | ||
.unwrap(); | ||
|
||
let first_device = libparsec::load_device( | ||
&client_config.config_dir, | ||
&libparsec::DeviceAccessStrategy::Password { | ||
key_file: libparsec::get_default_key_file( | ||
&client_config.config_dir, | ||
&first_available_device.device_id, | ||
), | ||
password: crate::testenv_utils::DEFAULT_DEVICE_PASSWORD | ||
.to_string() | ||
.into(), | ||
}, | ||
) | ||
.await | ||
.unwrap(); | ||
|
||
let first_auth_cmds = libparsec::AuthenticatedCmds::new( | ||
&client_config.config_dir, | ||
first_device.clone(), | ||
libparsec::ProxyConfig::default(), | ||
) | ||
.unwrap(); | ||
|
||
let first_dev_id_prefix = &first_device.device_id.hex()[..8]; | ||
|
||
let second_device = create_second_device( | ||
&first_auth_cmds, | ||
&first_device, | ||
client_config, | ||
first_dev_id_prefix, | ||
) | ||
.await | ||
.unwrap(); | ||
|
||
let mut devices = [first_device, second_device]; | ||
devices.sort_by_cached_key(|d| d.device_id.hex()); | ||
|
||
let mut available_devices_string_list = String::new(); | ||
format_device::<3>(&devices, &mut available_devices_string_list).unwrap(); | ||
|
||
crate::assert_cmd_failure!("list-users", "--device", first_dev_id_prefix).stderr( | ||
predicates::str::contains(format!( | ||
"Error: Multiple devices found for `{first_dev_id_prefix}`:" | ||
)) | ||
.and(predicates::str::contains(available_devices_string_list)), | ||
); | ||
} | ||
|
||
async fn create_second_device( | ||
cmds: &libparsec::AuthenticatedCmds, | ||
author: &Arc<LocalDevice>, | ||
client_config: libparsec::ClientConfig, | ||
dev_id_prefix: &str, | ||
) -> anyhow::Result<Arc<LocalDevice>> { | ||
// Create a device id with the same prefix as the first device | ||
let second_device_id = { | ||
let new_id_hex = libparsec::DeviceID::default().hex(); | ||
libparsec::DeviceID::from_hex(&format!( | ||
"{}{}", | ||
&dev_id_prefix, | ||
&new_id_hex[dev_id_prefix.len()..] | ||
)) | ||
.map_err(anyhow::Error::msg) | ||
}?; | ||
|
||
let second_device = Arc::new(LocalDevice::generate_new_device( | ||
cmds.addr().clone(), | ||
libparsec::UserProfile::Standard, | ||
HumanHandle::new("[email protected]", "Second").map_err(anyhow::Error::msg)?, | ||
"second".parse().map_err(anyhow::Error::msg)?, | ||
None, | ||
Some(second_device_id), | ||
None, | ||
None, | ||
)); | ||
|
||
let now = author.now(); | ||
let (user_cert, redacted_user_cert) = crate::testenv_utils::create_new_user( | ||
second_device.clone(), | ||
author.clone(), | ||
libparsec::UserProfile::Standard, | ||
now, | ||
); | ||
let (dev_cert, redacted_dev_cert) = | ||
crate::testenv_utils::create_new_device(second_device.clone(), author.clone(), now); | ||
|
||
match cmds | ||
.send(libparsec::authenticated_cmds::latest::user_create::Req { | ||
device_certificate: dev_cert, | ||
redacted_device_certificate: redacted_dev_cert, | ||
redacted_user_certificate: redacted_user_cert, | ||
user_certificate: user_cert, | ||
}) | ||
.await? | ||
{ | ||
libparsec::authenticated_cmds::latest::user_create::UserCreateRep::Ok => (), | ||
invalid_rep => panic!("Cannot create user: {invalid_rep:?}"), | ||
} | ||
|
||
let key_file = | ||
libparsec::get_default_key_file(&client_config.config_dir, &second_device.device_id); | ||
|
||
let second_dev_access = libparsec::DeviceAccessStrategy::Password { | ||
key_file, | ||
password: crate::testenv_utils::DEFAULT_DEVICE_PASSWORD | ||
.to_string() | ||
.into(), | ||
}; | ||
|
||
libparsec::save_device(std::path::Path::new(""), &second_dev_access, &second_device).await?; | ||
|
||
Ok(second_device) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters