Skip to main content

saml_rs/api/
options.rs

1use crate::browser::{LogoutBinding, SsoRequestBinding, SsoResponseBinding};
2use crate::model::RelayStateParam;
3
4/// Explicit `ForceAuthn` value for outbound AuthnRequests.
5#[derive(Debug, Clone, Copy, PartialEq, Eq)]
6pub enum ForceAuthn {
7    /// Emit `ForceAuthn="true"`.
8    Required,
9    /// Emit `ForceAuthn="false"`.
10    NotRequired,
11}
12
13impl ForceAuthn {
14    pub(super) fn as_bool(self) -> bool {
15        match self {
16            Self::Required => true,
17            Self::NotRequired => false,
18        }
19    }
20}
21
22/// Options for starting SP-initiated Web SSO.
23#[derive(Debug, Clone)]
24pub struct StartSso {
25    pub(super) binding: SsoRequestBinding,
26    pub(super) response_binding: Option<SsoResponseBinding>,
27    pub(super) relay_state: RelayStateParam,
28    pub(super) force_authn: Option<ForceAuthn>,
29    pub(super) acs_index: Option<u16>,
30}
31
32impl StartSso {
33    /// Start SSO with HTTP-Redirect AuthnRequest dispatch.
34    pub fn redirect() -> Self {
35        Self::new(SsoRequestBinding::Redirect)
36    }
37
38    /// Start SSO with HTTP-POST AuthnRequest dispatch.
39    pub fn post() -> Self {
40        Self::new(SsoRequestBinding::Post)
41    }
42
43    /// Start SSO with HTTP-POST-SimpleSign AuthnRequest dispatch.
44    pub fn simple_sign() -> Self {
45        Self::new(SsoRequestBinding::SimpleSign)
46    }
47
48    fn new(binding: SsoRequestBinding) -> Self {
49        Self {
50            binding,
51            response_binding: None,
52            relay_state: RelayStateParam::absent(),
53            force_authn: None,
54            acs_index: None,
55        }
56    }
57
58    /// Set the expected SAML Response binding.
59    pub fn response_binding(mut self, binding: SsoResponseBinding) -> Self {
60        self.response_binding = Some(binding);
61        self
62    }
63
64    /// Set exact RelayState state for the outbound request.
65    pub fn relay_state(mut self, relay_state: RelayStateParam) -> Self {
66        self.relay_state = relay_state;
67        self
68    }
69
70    /// Set the exact `ForceAuthn` value.
71    pub fn force_authn(mut self, force_authn: ForceAuthn) -> Self {
72        self.force_authn = Some(force_authn);
73        self
74    }
75
76    /// Select an AssertionConsumerServiceIndex.
77    pub fn assertion_consumer_service_index(mut self, acs_index: u16) -> Self {
78        self.acs_index = Some(acs_index);
79        self
80    }
81}
82
83/// Options for issuing SAML Responses from an IdP.
84#[derive(Debug, Clone)]
85pub struct RespondSso {
86    pub(super) binding: SsoResponseBinding,
87    pub(super) relay_state: Option<RelayStateParam>,
88}
89
90impl RespondSso {
91    /// Respond with HTTP-POST.
92    pub fn post() -> Self {
93        Self::new(SsoResponseBinding::Post)
94    }
95
96    /// Respond with HTTP-POST-SimpleSign.
97    pub fn simple_sign() -> Self {
98        Self::new(SsoResponseBinding::SimpleSign)
99    }
100
101    fn new(binding: SsoResponseBinding) -> Self {
102        Self {
103            binding,
104            relay_state: None,
105        }
106    }
107
108    /// Set exact RelayState state for the response.
109    ///
110    /// When omitted for a response to a received request, the received
111    /// RelayState is echoed. Pass [`RelayStateParam::absent`] to suppress echo.
112    pub fn relay_state(mut self, relay_state: RelayStateParam) -> Self {
113        self.relay_state = Some(relay_state);
114        self
115    }
116}
117
118/// Explicit signing choice for typed Single Logout messages.
119#[derive(Debug, Clone, Copy, PartialEq, Eq)]
120pub enum LogoutSigning {
121    /// Use the local typed logout policy.
122    FollowLocalPolicy,
123    /// Sign this logout message.
124    Sign,
125    /// Send unsigned logout for an explicit compatibility exception.
126    DoNotSignForCompatibility,
127}
128
129/// Options for issuing a LogoutRequest.
130#[derive(Debug, Clone)]
131pub struct StartSlo {
132    pub(super) binding: LogoutBinding,
133    pub(super) relay_state: RelayStateParam,
134    pub(super) signing: LogoutSigning,
135}
136
137impl StartSlo {
138    /// Start SLO with HTTP-Redirect.
139    pub fn redirect() -> Self {
140        Self::new(LogoutBinding::Redirect)
141    }
142
143    /// Start SLO with HTTP-POST.
144    pub fn post() -> Self {
145        Self::new(LogoutBinding::Post)
146    }
147
148    /// Start SLO with HTTP-POST-SimpleSign.
149    pub fn simple_sign() -> Self {
150        Self::new(LogoutBinding::SimpleSign)
151    }
152
153    fn new(binding: LogoutBinding) -> Self {
154        Self {
155            binding,
156            relay_state: RelayStateParam::absent(),
157            signing: LogoutSigning::FollowLocalPolicy,
158        }
159    }
160
161    /// Set exact RelayState state for the logout request.
162    pub fn relay_state(mut self, relay_state: RelayStateParam) -> Self {
163        self.relay_state = relay_state;
164        self
165    }
166
167    /// Set logout request signing behavior.
168    pub fn signing(mut self, signing: LogoutSigning) -> Self {
169        self.signing = signing;
170        self
171    }
172}
173
174/// Options for issuing a LogoutResponse.
175#[derive(Debug, Clone)]
176pub struct RespondSlo {
177    pub(super) binding: LogoutBinding,
178    pub(super) relay_state: Option<RelayStateParam>,
179    pub(super) signing: LogoutSigning,
180}
181
182impl RespondSlo {
183    /// Respond with HTTP-Redirect.
184    pub fn redirect() -> Self {
185        Self::new(LogoutBinding::Redirect)
186    }
187
188    /// Respond with HTTP-POST.
189    pub fn post() -> Self {
190        Self::new(LogoutBinding::Post)
191    }
192
193    /// Respond with HTTP-POST-SimpleSign.
194    pub fn simple_sign() -> Self {
195        Self::new(LogoutBinding::SimpleSign)
196    }
197
198    fn new(binding: LogoutBinding) -> Self {
199        Self {
200            binding,
201            relay_state: None,
202            signing: LogoutSigning::FollowLocalPolicy,
203        }
204    }
205
206    /// Set exact RelayState state for the logout response.
207    ///
208    /// When omitted, the received LogoutRequest RelayState is echoed. Pass
209    /// [`RelayStateParam::absent`] to suppress echo.
210    pub fn relay_state(mut self, relay_state: RelayStateParam) -> Self {
211        self.relay_state = Some(relay_state);
212        self
213    }
214
215    /// Set logout response signing behavior.
216    pub fn signing(mut self, signing: LogoutSigning) -> Self {
217        self.signing = signing;
218        self
219    }
220}