Skip to content

Commit

Permalink
feat: Allow custom sub-claims in provided Claims types (#331)
Browse files Browse the repository at this point in the history
  • Loading branch information
spencewenski authored Aug 13, 2024
1 parent b20d890 commit 64c51f6
Show file tree
Hide file tree
Showing 5 changed files with 89 additions and 8 deletions.
18 changes: 13 additions & 5 deletions src/middleware/http/auth/jwt/ietf.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ use typed_builder::TypedBuilder;
#[serde_as]
#[derive(Debug, Clone, Deserialize, Serialize, TypedBuilder)]
#[non_exhaustive]
pub struct Claims {
pub struct Claims<C = BTreeMap<String, Value>> {
/// See: <https://www.rfc-editor.org/rfc/rfc7519.html#section-4.1.1>
#[serde(rename = "iss")]
#[builder(default, setter(strip_option))]
Expand Down Expand Up @@ -54,8 +54,7 @@ pub struct Claims {
pub jwt_id: Option<String>,

#[serde(flatten)]
#[builder(default)]
pub custom: BTreeMap<String, Value>,
pub custom: C,
}

#[cfg(test)]
Expand All @@ -65,8 +64,8 @@ mod tests {
use crate::middleware::http::auth::jwt::decode_auth_token;
use crate::util::serde::{UriOrString, Wrapper};
use chrono::{TimeDelta, Utc};
use insta::assert_debug_snapshot;
use jsonwebtoken::{encode, EncodingKey, Header, TokenData};
use serde_json::from_str;
use std::ops::{Add, Sub};
use std::str::FromStr;
use url::Url;
Expand Down Expand Up @@ -144,7 +143,7 @@ mod tests {
#[cfg_attr(coverage_nightly, coverage(off))]
fn deserialize_audience_as_vec() {
let value: Wrapper<Vec<UriOrString>> =
from_str(r#"{"inner": ["https://example.com", "aud2"]}"#).unwrap();
serde_json::from_str(r#"{"inner": ["https://example.com", "aud2"]}"#).unwrap();
assert_eq!(
value.inner,
vec![
Expand All @@ -153,4 +152,13 @@ mod tests {
]
);
}

#[test]
fn deserialize_claims() {
let claims = r#"
exp = 1000
"#;
let claims: Claims = toml::from_str(claims).unwrap();
assert_debug_snapshot!(claims);
}
}
18 changes: 15 additions & 3 deletions src/middleware/http/auth/jwt/openid.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ use crate::util::serde::{deserialize_from_str, serialize_to_str, UriOrString};
#[serde_as]
#[derive(Debug, Clone, Deserialize, Serialize, TypedBuilder)]
#[non_exhaustive]
pub struct Claims {
pub struct Claims<C = BTreeMap<String, Value>> {
#[serde(rename = "iss")]
pub issuer: Url,

Expand Down Expand Up @@ -57,8 +57,7 @@ pub struct Claims {
pub authorized_party: Option<UriOrString>,

#[serde(flatten)]
#[builder(default)]
pub custom: BTreeMap<String, Value>,
pub custom: C,
}

// Intentionally not annotated with `#[non_exhaustive]`
Expand All @@ -80,6 +79,7 @@ pub enum Acr {
mod tests {
use super::*;
use crate::util::serde::Wrapper;
use insta::assert_debug_snapshot;
use serde_json::from_str;
use std::str::FromStr;
use url::Url;
Expand Down Expand Up @@ -119,4 +119,16 @@ mod tests {
let value: Wrapper<Acr> = from_str(r#"{"inner": "invalid-uri"}"#).unwrap();
assert_eq!(value.inner, Acr::String("invalid-uri".to_string()));
}

#[test]
fn deserialize_claims() {
let claims = r#"
iss = "http://example.com"
sub = "1234"
iat = 1000
exp = 2000
"#;
let claims: Claims = toml::from_str(claims).unwrap();
assert_debug_snapshot!(claims);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
---
source: src/middleware/http/auth/jwt/ietf.rs
expression: claims
---
Claims {
issuer: None,
subject: None,
audience: [],
expires_at: 1970-01-01T00:16:40Z,
not_before: None,
issued_at: None,
jwt_id: None,
custom: {},
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
---
source: src/middleware/http/auth/jwt/ietf.rs
expression: claims
---
Claims {
issuer: None,
subject: None,
audience: [],
expires_at: 1970-01-01T00:16:40Z,
not_before: None,
issued_at: None,
jwt_id: None,
custom: {},
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
---
source: src/middleware/http/auth/jwt/openid.rs
expression: claims
---
Claims {
issuer: Url {
scheme: "http",
cannot_be_a_base: false,
username: "",
password: None,
host: Some(
Domain(
"example.com",
),
),
port: None,
path: "/",
query: None,
fragment: None,
},
subject: Int(
1234,
),
audience: [],
expires_at: 1970-01-01T00:33:20Z,
issued_at: 1970-01-01T00:16:40Z,
auth_time: None,
nonce: None,
auth_cxt_class_reference: None,
auth_methods_references: [],
authorized_party: None,
custom: {},
}

0 comments on commit 64c51f6

Please sign in to comment.