pub struct RevocationState { /* private fields */ }Expand description
Signed epoch floors for one (tenant, subject, scope) tuple.
Implementations§
Source§impl RevocationState
impl RevocationState
Sourcepub fn issue(
issuer: &AccessIssuer,
tenant_id: impl Into<String>,
subject_id: impl Into<String>,
scope: impl Into<String>,
spec: RevocationSpec,
) -> Result<Self, AccessError>
pub fn issue( issuer: &AccessIssuer, tenant_id: impl Into<String>, subject_id: impl Into<String>, scope: impl Into<String>, spec: RevocationSpec, ) -> Result<Self, AccessError>
Issue signed revocation floors for one subject and scope.
Examples found in repository?
examples/enterprise_access.rs (lines 46-57)
11fn main() -> Result<(), Box<dyn std::error::Error>> {
12 let issuer = AccessIssuer::generate("acme-admin")?;
13 let alice = PrincipalKeypair::generate("acme", "alice", PrincipalKind::User, 1)?;
14 let admin = PrincipalKeypair::generate("acme", "admin", PrincipalKind::Administrator, 1)?;
15
16 let alice_audit = RoleKeypair::generate("acme", "audit", "alice-audit", 1)?;
17 let tenant_audit = RoleKeypair::generate("acme", "audit", "tenant-audit", 1)?;
18
19 let alice_grant = AccessGrant::issue(
20 &issuer,
21 alice.principal(),
22 &alice_audit,
23 GrantSpec {
24 grant_id: "alice-audit-v1".into(),
25 scope: "audit".into(),
26 permissions: Permissions::READ | Permissions::WRITE,
27 authorization_epoch: 1,
28 not_before: 1,
29 not_after: u64::MAX,
30 },
31 )?;
32 let admin_grant = AccessGrant::issue(
33 &issuer,
34 admin.principal(),
35 &tenant_audit,
36 GrantSpec {
37 grant_id: "admin-audit-v1".into(),
38 scope: "audit".into(),
39 permissions: Permissions::READ | Permissions::OBSERVE,
40 authorization_epoch: 1,
41 not_before: 1,
42 not_after: u64::MAX,
43 },
44 )?;
45
46 let alice_state = RevocationState::issue(
47 &issuer,
48 "acme",
49 "alice",
50 "audit",
51 RevocationSpec {
52 revision: 1,
53 minimum_authorization_epoch: 1,
54 minimum_role_key_epoch: 1,
55 issued_at: 1,
56 },
57 )?;
58 let admin_state = RevocationState::issue(
59 &issuer,
60 "acme",
61 "admin",
62 "audit",
63 RevocationSpec {
64 revision: 1,
65 minimum_authorization_epoch: 1,
66 minimum_role_key_epoch: 1,
67 issued_at: 1,
68 },
69 )?;
70 let trusted = issuer.trusted();
71 let alice_role = alice_grant.open_role(
72 &alice,
73 &trusted,
74 100,
75 &alice_state.verify(&trusted, "acme", "alice", "audit")?,
76 )?;
77 let admin_role = admin_grant.open_role(
78 &admin,
79 &trusted,
80 100,
81 &admin_state.verify(&trusted, "acme", "admin", "audit")?,
82 )?;
83
84 let policy = TenantPolicy::issue(
85 &issuer,
86 alice.principal(),
87 PolicySpec {
88 revision: 1,
89 previous_hash: [0; 32],
90 authorization_epoch: 1,
91 issued_at: 1,
92 not_before: 1,
93 not_after: u64::MAX,
94 rules: vec![CapabilityRule::new(
95 CapabilityKind::Mcp,
96 "github",
97 Effect::Allow,
98 )?],
99 },
100 )?;
101 let verified = policy.verify(&trusted, "acme", "alice", 100, 1, 1)?;
102 assert_eq!(
103 verified.decision(CapabilityKind::Mcp, "github"),
104 Decision::Allow
105 );
106 assert_eq!(
107 verified.decision(CapabilityKind::Skill, "deploy"),
108 Decision::Deny
109 );
110
111 let author = Author::generate()?;
112 let event = AuditEvent {
113 tenant_id: "acme".into(),
114 subject_id: "alice".into(),
115 session_id: "session-42".into(),
116 sequence: 1,
117 timestamp: 100,
118 kind: AuditEventKind::Request,
119 media_type: "application/json".into(),
120 body: br#"{"tool":"github.search","query":"private"}"#.to_vec(),
121 };
122 let record = seal_audit_event(
123 &author,
124 AuditContext {
125 tenant_id: "acme".into(),
126 subject_id: "alice".into(),
127 stream_id: "session-42".into(),
128 epoch: 1,
129 sequence: 1,
130 },
131 &event,
132 &alice_role,
133 &admin_role,
134 fastest_payload_suite(),
135 )?;
136
137 assert_eq!(
138 open_audit_event(&record, &alice_role, author.public_key())?,
139 event
140 );
141 assert_eq!(
142 open_audit_event(&record, &admin_role, author.public_key())?,
143 event
144 );
145 println!("user and tenant administrator opened the encrypted audit event");
146 Ok(())
147}Sourcepub fn subject_id(&self) -> &str
pub fn subject_id(&self) -> &str
Subject identifier authenticated by the signature.
Sourcepub fn decode(
bytes: &[u8],
limits: &AccessValidationPolicy,
) -> Result<Self, AccessError>
pub fn decode( bytes: &[u8], limits: &AccessValidationPolicy, ) -> Result<Self, AccessError>
Decode, structurally validate, and verify signature math.
Sourcepub fn verify<'a>(
&'a self,
trusted: &TrustedIssuer,
expected_tenant: &str,
expected_subject: &str,
expected_scope: &str,
) -> Result<VerifiedRevocation<'a>, AccessError>
pub fn verify<'a>( &'a self, trusted: &TrustedIssuer, expected_tenant: &str, expected_subject: &str, expected_scope: &str, ) -> Result<VerifiedRevocation<'a>, AccessError>
Verify trust and the exact tuple before exposing epoch floors.
Examples found in repository?
examples/enterprise_access.rs (line 75)
11fn main() -> Result<(), Box<dyn std::error::Error>> {
12 let issuer = AccessIssuer::generate("acme-admin")?;
13 let alice = PrincipalKeypair::generate("acme", "alice", PrincipalKind::User, 1)?;
14 let admin = PrincipalKeypair::generate("acme", "admin", PrincipalKind::Administrator, 1)?;
15
16 let alice_audit = RoleKeypair::generate("acme", "audit", "alice-audit", 1)?;
17 let tenant_audit = RoleKeypair::generate("acme", "audit", "tenant-audit", 1)?;
18
19 let alice_grant = AccessGrant::issue(
20 &issuer,
21 alice.principal(),
22 &alice_audit,
23 GrantSpec {
24 grant_id: "alice-audit-v1".into(),
25 scope: "audit".into(),
26 permissions: Permissions::READ | Permissions::WRITE,
27 authorization_epoch: 1,
28 not_before: 1,
29 not_after: u64::MAX,
30 },
31 )?;
32 let admin_grant = AccessGrant::issue(
33 &issuer,
34 admin.principal(),
35 &tenant_audit,
36 GrantSpec {
37 grant_id: "admin-audit-v1".into(),
38 scope: "audit".into(),
39 permissions: Permissions::READ | Permissions::OBSERVE,
40 authorization_epoch: 1,
41 not_before: 1,
42 not_after: u64::MAX,
43 },
44 )?;
45
46 let alice_state = RevocationState::issue(
47 &issuer,
48 "acme",
49 "alice",
50 "audit",
51 RevocationSpec {
52 revision: 1,
53 minimum_authorization_epoch: 1,
54 minimum_role_key_epoch: 1,
55 issued_at: 1,
56 },
57 )?;
58 let admin_state = RevocationState::issue(
59 &issuer,
60 "acme",
61 "admin",
62 "audit",
63 RevocationSpec {
64 revision: 1,
65 minimum_authorization_epoch: 1,
66 minimum_role_key_epoch: 1,
67 issued_at: 1,
68 },
69 )?;
70 let trusted = issuer.trusted();
71 let alice_role = alice_grant.open_role(
72 &alice,
73 &trusted,
74 100,
75 &alice_state.verify(&trusted, "acme", "alice", "audit")?,
76 )?;
77 let admin_role = admin_grant.open_role(
78 &admin,
79 &trusted,
80 100,
81 &admin_state.verify(&trusted, "acme", "admin", "audit")?,
82 )?;
83
84 let policy = TenantPolicy::issue(
85 &issuer,
86 alice.principal(),
87 PolicySpec {
88 revision: 1,
89 previous_hash: [0; 32],
90 authorization_epoch: 1,
91 issued_at: 1,
92 not_before: 1,
93 not_after: u64::MAX,
94 rules: vec![CapabilityRule::new(
95 CapabilityKind::Mcp,
96 "github",
97 Effect::Allow,
98 )?],
99 },
100 )?;
101 let verified = policy.verify(&trusted, "acme", "alice", 100, 1, 1)?;
102 assert_eq!(
103 verified.decision(CapabilityKind::Mcp, "github"),
104 Decision::Allow
105 );
106 assert_eq!(
107 verified.decision(CapabilityKind::Skill, "deploy"),
108 Decision::Deny
109 );
110
111 let author = Author::generate()?;
112 let event = AuditEvent {
113 tenant_id: "acme".into(),
114 subject_id: "alice".into(),
115 session_id: "session-42".into(),
116 sequence: 1,
117 timestamp: 100,
118 kind: AuditEventKind::Request,
119 media_type: "application/json".into(),
120 body: br#"{"tool":"github.search","query":"private"}"#.to_vec(),
121 };
122 let record = seal_audit_event(
123 &author,
124 AuditContext {
125 tenant_id: "acme".into(),
126 subject_id: "alice".into(),
127 stream_id: "session-42".into(),
128 epoch: 1,
129 sequence: 1,
130 },
131 &event,
132 &alice_role,
133 &admin_role,
134 fastest_payload_suite(),
135 )?;
136
137 assert_eq!(
138 open_audit_event(&record, &alice_role, author.public_key())?,
139 event
140 );
141 assert_eq!(
142 open_audit_event(&record, &admin_role, author.public_key())?,
143 event
144 );
145 println!("user and tenant administrator opened the encrypted audit event");
146 Ok(())
147}Trait Implementations§
Source§impl Clone for RevocationState
impl Clone for RevocationState
Source§fn clone(&self) -> RevocationState
fn clone(&self) -> RevocationState
Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§fn clone_from(&mut self, source: &Self)
fn clone_from(&mut self, source: &Self)
Performs copy-assignment from
source. Read moreSource§impl Debug for RevocationState
impl Debug for RevocationState
impl Eq for RevocationState
Source§impl PartialEq for RevocationState
impl PartialEq for RevocationState
impl StructuralPartialEq for RevocationState
Auto Trait Implementations§
impl Freeze for RevocationState
impl RefUnwindSafe for RevocationState
impl Send for RevocationState
impl Sync for RevocationState
impl Unpin for RevocationState
impl UnsafeUnpin for RevocationState
impl UnwindSafe for RevocationState
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Mutably borrows from an owned value. Read more