vta_cli_common/commands/
credentials.rs1use vta_sdk::prelude::*;
2use vta_sdk::sealed_transfer::SealedPayloadV1;
3
4use super::acl::validate_role;
5use crate::local_keygen::generate_admin_did_key;
6use crate::sealed_producer::{SealedRecipient, emit_sealed_output, seal_for_recipient};
7
8pub async fn cmd_auth_credential_create(
9 client: &VtaClient,
10 role: String,
11 label: Option<String>,
12 contexts: Vec<String>,
13 recipient: SealedRecipient,
14) -> Result<(), Box<dyn std::error::Error>> {
15 validate_role(&role)?;
16
17 let config = client.get_config().await?;
19 let vta_did = config
20 .community_vta_did
21 .clone()
22 .ok_or("VTA DID not configured — cannot mint credential")?;
23 let vta_url = config.public_url.clone();
24
25 let (bundle, did) = generate_admin_did_key(vta_did, vta_url);
29 let mut acl_req =
30 vta_sdk::client::CreateAclRequest::new(&did, &role).contexts(contexts.clone());
31 if let Some(l) = label {
32 acl_req = acl_req.label(l);
33 }
34 client.create_acl(acl_req).await?;
35
36 let sealed = seal_for_recipient(
37 &recipient,
38 &SealedPayloadV1::AdminCredential(Box::new(bundle)),
39 )
40 .await?;
41
42 println!("Credentials generated:");
43 println!(" DID: {did}");
44 println!(" Role: {role}");
45 if !contexts.is_empty() {
46 println!(" Contexts: {}", contexts.join(", "));
47 }
48 if let Some(ref rlabel) = recipient.label {
49 println!(" Recipient: {rlabel}");
50 }
51 println!();
52 emit_sealed_output(&sealed, None)?;
53 Ok(())
54}