Removes a circular dependency between pijul::identity
and pijul::remote
, and is the final hurdle preventing them being spun off into their own crates.
5Z2Y7VGVHJ7A6UPSEAPFVMIB5J7YHSI6WWHUUUYVLDJ56XSNCXKQC
ABQDWHNGSBF2REQDCGXSBFAU4RUMXYAF2KHJ5O3D32M7Z3A3FEDAC
Y2Y4OOIECVVLL5KIUVHIWJTGPADACCZZHUFGHTLSWHXS5UJ5FD4QC
32G3GOK752NTSULBH6KYGD3ZC2YC4B2X7O73G7BT3AJVMIUIFHXQC
MU5GSJAW65PEG3BRYUKZ7O37BPHW3MOX3S5E2RFOXKGUOJEEDQ5AC
L4JXJHWXYNCL4QGJXNKKTOKKTAXKKXBJUUY7HFZGEUZ5A2V5H34QC
SXEYMYF7P4RZMZ46WPL4IZUTSQ2ATBWYZX7QNVMS3SGOYXYOHAGQC
4RV7T4SRYIQLBW3EZFWBO5G65QAVG2GHPI4KMDDZERCX65KQWSPQC
4KJ45IJLTIE35KQZUSFMFS67RNENG4P2FZMKMULJLGGYMKJUVRSQC
4OJWMSOWWNT5N4W4FDMKBZB5UARCLGV3SRZVKGR4EFAYFUMUHM7AC
44RUBHREQUNI4B36WSV7CUK5CVVIKG2AQOQJQZ7HU3BHY6W6AUEQC
BV4PLHOVPSA5UKF43TL6EC57I7XHYWKZWV6LXI7YTGS2K3SQMY2AC
YV63XF6Z3S3GJKCOXPOLFRR7E5JH3QX6PIWXDMFFDTOOUXGOBWNQC
Y6TBQN7MFWX4SKJM2UGDGR4UMMDEO4TPNNJZKZWHEBTW7MPX4WWQC
LZOGKBJXRQJKXHYNNENJFGNLP5SHIXGSV6HDB7UVOP7FSA5EUNCQC
6FRPUHWKBAWIYN6B6YDFQG2SFWZ6MBBYOYXFUN6DRZ4HPDSKFANQC
IKZBGTGQ7GJMRPYJPLL66DMND6J2JBP6I23U4GGCB5CMDG4FUHLAC
}
/// Associate a generated key with a remote identity. Patches authored
/// by unproven keys will only display the key as the author.
pub async fn prove(
identity: &Complete,
origin: Option<&str>,
no_cert_check: bool,
) -> Result<(), anyhow::Error> {
let remote = origin.unwrap_or(&identity.config.author.origin);
let mut stderr = std::io::stderr();
writeln!(
stderr,
"Linking identity `{}` with {}@{}",
&identity.name, &identity.config.author.username, remote
)?;
let mut remote = if let Ok(repo) = Repository::find_root(None) {
repository(
&repo,
None,
Some(&identity.config.author.username),
&remote,
libpijul::DEFAULT_CHANNEL,
no_cert_check,
false,
)
.await?
} else {
unknown_remote(
None,
Some(&identity.config.author.username),
&remote,
libpijul::DEFAULT_CHANNEL,
no_cert_check,
false,
)
.await?
};
let (key, _password) = identity
.credentials
.clone()
.unwrap()
.decrypt(&identity.name)?;
remote.prove(key).await?;
Ok(())
if Confirm::new()?
.with_prompt("Do you want to link this identity to a remote?")
.with_default(true)
.interact()?
{
new_identity.prompt_remote().await?;
// There are 3 cases that require re-proving:
// 1: new identity (replace_current == None)
// 2: new secret key
// 3. new username/origin
if !will_replace
|| self.secret_key() != new_identity.secret_key()
|| (&self.config.author.origin, &self.config.author.username)
!= (
&new_identity.config.author.origin,
&new_identity.config.author.username,
)
if link_remote {
if Confirm::new()?
.with_prompt("Do you want to link this identity to a remote?")
.with_default(true)
.interact()?
// Prove the identity to the server
if link_remote
&& new_identity
.prove(None, *NO_CERT_CHECK.get_or_init(|| false))
.await
.is_err()
{
error!("Could not prove identity `{}`. Please check your credentials & network connection. If you are on an enterprise network, perhaps try running with `--no-cert-check`. Your data is safe but will not be connected to {} without runnning `pijul identity prove {}`", new_identity.name, new_identity.config.author.origin, new_identity.name);
}
new_identity.prompt_remote().await?;
} else {
// The user wants an 'offline' identity, so make sure not to store login info
new_identity.config.key_path = None;
new_identity.config.author.username = String::new();
new_identity.config.author.origin = String::new();
/// Associate a generated key with a remote identity. Patches authored
/// by unproven keys will only display the key as the author.
pub async fn prove(
&self,
origin: Option<&str>,
no_cert_check: bool,
) -> Result<(), anyhow::Error> {
let remote = origin.unwrap_or(&self.config.author.origin);
let mut stderr = std::io::stderr();
writeln!(
stderr,
"Linking identity `{}` with {}@{}",
&self.name, &self.config.author.username, remote
)?;
let mut remote = if let Ok(repo) = Repository::find_root(None) {
remote::repository(
&repo,
None,
Some(&self.config.author.username),
&remote,
libpijul::DEFAULT_CHANNEL,
no_cert_check,
false,
)
.await?
} else {
crate::remote::unknown_remote(
None,
Some(&self.config.author.username),
&remote,
libpijul::DEFAULT_CHANNEL,
no_cert_check,
false,
)
.await?
};
let (key, _password) = self.credentials.clone().unwrap().decrypt(&self.name)?;
remote.prove(key).await?;
Ok(())
}
if let Err(_) = remote::prove(&identity, None, self.no_cert_check).await {
warn!("Could not prove identity `{}`. Please check your credentials & network connection. If you are on an enterprise network, perhaps try running with `--no-cert-check`. Your data is safe but will not be connected to {} without runnning `pijul identity prove {}`", identity.name, identity.config.author.origin, identity.name);
} else {
info!("Identity `{}` was proved to the server", identity);
}
Complete::load(&identity_name.unwrap_or(choose_identity_name(no_prompt).await?))?
.prove(server.as_deref(), self.no_cert_check)
.await?;
let identity_name =
&identity_name.unwrap_or(choose_identity_name(no_prompt).await?);
let loaded_identity = Complete::load(identity_name)?;
remote::prove(&loaded_identity, server.as_deref(), self.no_cert_check).await?;
old_identity.replace_with(new_identity)?;
old_identity.clone().replace_with(new_identity.clone())?;
// There are 2 cases that require re-proving:
// 1: new secret key
// 2. new username/origin
if !options.no_link {
if new_identity.secret_key() != old_identity.secret_key()
|| old_identity.config.author != new_identity.config.author
{
let prove_result =
remote::prove(&new_identity, None, self.no_cert_check).await;
if let Err(_) = prove_result {
warn!("Could not prove identity `{}`. Please check your credentials & network connection. If you are on an enterprise network, perhaps try running with `--no-cert-check`. Your data is safe but will not be connected to {} without runnning `pijul identity prove {}`", new_identity.name, new_identity.config.author.origin, new_identity.name);
} else {
info!("Identity `{}` was proved to the server", new_identity);
}
}
}