Skip to main content

ic_auth_wire/
lib.rs

1//! Controlled portable-session transport. No endpoint installation, authority,
2//! cryptography, session storage or delivery/retry policy is supplied here.
3pub mod model;
4use ic_auth_protocol_types::limits::{MAX_LABEL_BYTES, MAX_SESSION_SCOPES};
5pub use ic_wire as wire;
6use ic_wire::{Limits, List, Text};
7use model::{LogoutResult, PortableCredential};
8
9/// Admission narrowing accompanies the exact opaque signed credential.
10#[derive(Clone, Debug, Eq, PartialEq, serde::Serialize, serde::Deserialize)]
11#[cfg_attr(feature = "typescript", derive(ic_wire::Wire))]
12pub struct SessionInput {
13    pub credential: PortableCredential,
14    pub scopes: List<Text<MAX_LABEL_BYTES>, MAX_SESSION_SCOPES>,
15    pub ttl_secs: Option<u64>,
16}
17/// A receiver's authenticated local reply, never a transferable authorization.
18#[derive(Clone, Debug, Eq, PartialEq, serde::Serialize, serde::Deserialize)]
19#[cfg_attr(feature = "typescript", derive(ic_wire::Wire))]
20pub struct SessionView {
21    pub caller: ic_wire::Bytes<29>,
22    pub issuer: ic_wire::Bytes<29>,
23    pub subject: ic_wire::Bytes<29>,
24    pub expires_at_ns: u64,
25}
26const CREDENTIAL_LIMITS: Limits = Limits {
27    bytes: 524288,
28    allocation: 2097152,
29    nodes: 65536,
30    depth: 32,
31};
32const REPLY_LIMITS: Limits = Limits {
33    bytes: 4096,
34    allocation: 16384,
35    nodes: 128,
36    depth: 8,
37};
38const EMPTY_LIMITS: Limits = Limits {
39    bytes: 11,
40    allocation: 128,
41    nodes: 8,
42    depth: 4,
43};
44
45/// Data-envelope identity, not a callable issuer method or signing format.
46pub struct CredentialEnvelope;
47impl CredentialEnvelope {
48    pub const ID: u64 = 0x415554480001;
49    pub const NAME: &'static str = "credential";
50    pub const REQUEST_LIMITS: Limits = CREDENTIAL_LIMITS;
51    pub const RESPONSE_LIMITS: Limits = CREDENTIAL_LIMITS;
52    pub fn encode_request(value: &PortableCredential) -> Result<Vec<u8>, ic_wire::Error> {
53        ic_wire::native::encode_request(Self::ID, value, Self::REQUEST_LIMITS)
54    }
55    pub fn decode_request(bytes: &[u8]) -> Result<PortableCredential, ic_wire::Error> {
56        ic_wire::native::decode_request(Self::ID, bytes, Self::REQUEST_LIMITS)
57    }
58    pub fn encode_response(value: &PortableCredential) -> Result<Vec<u8>, ic_wire::Error> {
59        ic_wire::native::encode_response(Self::ID, value, Self::RESPONSE_LIMITS)
60    }
61    pub fn decode_response(bytes: &[u8]) -> Result<PortableCredential, ic_wire::Error> {
62        ic_wire::native::decode_response(Self::ID, bytes, Self::RESPONSE_LIMITS)
63    }
64}
65/// Controlled admission contract; consumers bind it to their own update export.
66pub struct EstablishSession;
67impl EstablishSession {
68    pub const ID: u64 = 0x415554480012;
69    pub const NAME: &'static str = "establish_portable_session";
70    pub const REQUEST_LIMITS: Limits = CREDENTIAL_LIMITS;
71    pub const RESPONSE_LIMITS: Limits = REPLY_LIMITS;
72    pub fn encode_request(value: &SessionInput) -> Result<Vec<u8>, ic_wire::Error> {
73        ic_wire::native::encode_request(Self::ID, value, Self::REQUEST_LIMITS)
74    }
75    pub fn decode_request(bytes: &[u8]) -> Result<SessionInput, ic_wire::Error> {
76        ic_wire::native::decode_request(Self::ID, bytes, Self::REQUEST_LIMITS)
77    }
78    pub fn encode_response(
79        value: &Result<SessionView, model::AdmissionRefusal>,
80    ) -> Result<Vec<u8>, ic_wire::Error> {
81        ic_wire::native::encode_response(Self::ID, value, Self::RESPONSE_LIMITS)
82    }
83    pub fn decode_response(
84        bytes: &[u8],
85    ) -> Result<Result<SessionView, model::AdmissionRefusal>, ic_wire::Error> {
86        ic_wire::native::decode_response(Self::ID, bytes, Self::RESPONSE_LIMITS)
87    }
88}
89/// Proof-free local read contract; the runtime caller selects the session.
90pub struct ReadSession;
91impl ReadSession {
92    pub const ID: u64 = 0x415554480003;
93    pub const NAME: &'static str = "portable_session_read";
94    pub const REQUEST_LIMITS: Limits = EMPTY_LIMITS;
95    pub const RESPONSE_LIMITS: Limits = REPLY_LIMITS;
96    pub fn encode_request(value: &()) -> Result<Vec<u8>, ic_wire::Error> {
97        ic_wire::native::encode_request(Self::ID, value, Self::REQUEST_LIMITS)
98    }
99    pub fn decode_request(bytes: &[u8]) -> Result<(), ic_wire::Error> {
100        ic_wire::native::decode_request(Self::ID, bytes, Self::REQUEST_LIMITS)
101    }
102    pub fn encode_response(
103        value: &Result<SessionView, Text<256>>,
104    ) -> Result<Vec<u8>, ic_wire::Error> {
105        ic_wire::native::encode_response(Self::ID, value, Self::RESPONSE_LIMITS)
106    }
107    pub fn decode_response(bytes: &[u8]) -> Result<Result<SessionView, Text<256>>, ic_wire::Error> {
108        ic_wire::native::decode_response(Self::ID, bytes, Self::RESPONSE_LIMITS)
109    }
110}
111/// Caller-authenticated logout; no submitted proof or caller identity is trusted.
112pub struct Logout;
113impl Logout {
114    pub const ID: u64 = 0x415554480004;
115    pub const NAME: &'static str = "logout_portable_session";
116    pub const REQUEST_LIMITS: Limits = EMPTY_LIMITS;
117    pub const RESPONSE_LIMITS: Limits = REPLY_LIMITS;
118    pub fn encode_request(value: &()) -> Result<Vec<u8>, ic_wire::Error> {
119        ic_wire::native::encode_request(Self::ID, value, Self::REQUEST_LIMITS)
120    }
121    pub fn decode_request(bytes: &[u8]) -> Result<(), ic_wire::Error> {
122        ic_wire::native::decode_request(Self::ID, bytes, Self::REQUEST_LIMITS)
123    }
124    pub fn encode_response(value: &LogoutResult) -> Result<Vec<u8>, ic_wire::Error> {
125        ic_wire::native::encode_response(Self::ID, value, Self::RESPONSE_LIMITS)
126    }
127    pub fn decode_response(bytes: &[u8]) -> Result<LogoutResult, ic_wire::Error> {
128        ic_wire::native::decode_response(Self::ID, bytes, Self::RESPONSE_LIMITS)
129    }
130}