Radish alpha
h
Radicle Heartwood Protocol & Stack
Radicle
Git (anonymous pull)
Log in to clone via SSH
cli: add explicit hint to rad-id-unauthorized-delegate error with did aliases
✗ CI failure Adrian Duke committed 4 months ago
commit 6ebb8bffe2afcd2ec28fdef51fd5a11548c08dbf
parent b6d59d9dc7169c9d0a684c700ca1f1cc2b5de36c
1 failed (1 total) View logs
2 files changed +33 -8
modified crates/radicle-cli/examples/rad-id-unauthorized-delegate.md
@@ -3,5 +3,6 @@ Alice has created a new repository `rad:z42hL2jL4XNk6K8oHQaSWfMgCL7ji` with only
``` ~bob (fail)
$ rad id update --repo rad:z42hL2jL4XNk6K8oHQaSWfMgCL7ji --title "Add myself!" --delegate did:key:z6Mkt67GdsW7715MEfRuP4pSZxJRJh6kj6Y48WRqVv4N1tRk --no-confirm
✗ Error: did:key:z6Mkt67GdsW7715MEfRuP4pSZxJRJh6kj6Y48WRqVv4N1tRk is not a delegate, and only delegates are allowed to create a revision
+
✗ Hint: bob (you) is attempting to modify the identity document but isn't a delegate!
```

modified crates/radicle-cli/src/commands/id.rs
@@ -19,6 +19,7 @@ use crate::git::unified_diff::Encode as _;
use crate::git::Rev;
use crate::terminal as term;
use crate::terminal::args::Error;
+
use crate::terminal::format::Author;
use crate::terminal::patch::Message;

pub use args::Args;
@@ -194,7 +195,14 @@ pub fn run(args: Args, ctx: impl term::Context) -> anyhow::Result<()> {
                return Ok(());
            }
            let signer = term::signer(&profile)?;
-
            let revision = update(title, description, proposal, &mut identity, &signer)?;
+
            let revision = update(
+
                title,
+
                description,
+
                proposal,
+
                &mut identity,
+
                &signer,
+
                &profile,
+
            )?;

            if revision.is_accepted() && revision.parent == Some(current.id) {
                // Update the canonical head to point to the latest accepted revision.
@@ -421,6 +429,7 @@ fn update<R, G>(
    doc: Doc,
    current: &mut IdentityMut<R>,
    signer: &Device<G>,
+
    profile: &Profile,
) -> anyhow::Result<Revision>
where
    R: WriteRepository + cob::Store<Namespace = NodeId>,
@@ -429,7 +438,7 @@ where
    if let Some((title, description)) = edit_title_description(title, description)? {
        let id = current
            .update(title, description, &doc, signer)
-
            .map_err(on_identity_err)?;
+
            .map_err(|e| on_identity_err(e, profile))?;
        let revision = current
            .revision(&id)
            .ok_or(anyhow!("update failed: revision {id} is missing"))?;
@@ -440,17 +449,32 @@ where
    }
}

-
fn on_identity_err(e: identity::Error) -> anyhow::Error {
+
fn on_identity_err(e: identity::Error, profile: &Profile) -> anyhow::Error {
    let e = anyhow::Error::from(e);

-
    let apply_err = e
+
    let maybe_author = e
        .chain()
-
        .find_map(|c| c.downcast_ref::<identity::ApplyError>());
+
        .find_map(|c| c.downcast_ref::<identity::ApplyError>())
+
        .and_then(|err| match err {
+
            identity::ApplyError::NonDelegateUnauthorized { author, .. } => {
+
                Some(((*author), err.to_string()))
+
            }
+
            _ => None,
+
        });
+

+
    if let Some((author_did, err_msg)) = maybe_author {
+
        let nid = NodeId::from(author_did);
+
        let auth = Author::new(&nid, profile, false);
+
        let (label1, label2) = auth.labels();

-
    match apply_err {
-
        Some(e @ identity::ApplyError::NonDelegateUnauthorized { .. }) => anyhow!(e.to_string()),
-
        _ => e,
+
        return Error::WithHint {
+
            err: anyhow!(err_msg),
+
            hint: format!("{label1} {label2} is attempting to modify the identity document but isn't a delegate!"),
+
        }
+
        .into();
    }
+

+
    e
}

fn print_diff(