@@ -38,7 +38,8 @@ pub struct OAuthTokenIntrospectAccess {
38
38
39
39
#[ derive( Debug , Clone , Deserialize ) ]
40
40
pub struct OAuthTokenIntrospect {
41
- pub active : bool ,
41
+ #[ serde( default ) ]
42
+ pub active : Option < bool > ,
42
43
pub scope : Option < String > ,
43
44
pub client_id : Option < String > ,
44
45
pub username : Option < String > ,
@@ -72,10 +73,14 @@ impl<'de> serde::de::Visitor<'de> for AudVisitor {
72
73
Ok ( Some ( vec ! [ value. to_string( ) ] ) )
73
74
}
74
75
76
+ fn visit_string < E : serde:: de:: Error > ( self , value : String ) -> Result < Self :: Value , E > {
77
+ Ok ( Some ( vec ! [ value] ) )
78
+ }
79
+
75
80
fn visit_seq < A : serde:: de:: SeqAccess < ' de > > ( self , mut value : A ) -> Result < Self :: Value , A :: Error > {
76
81
let mut values = vec ! [ ] ;
77
- while let Some ( elm) = value. next_element :: < & str > ( ) ? {
78
- values. push ( elm. to_string ( ) ) ;
82
+ while let Some ( elm) = value. next_element :: < std :: borrow :: Cow < ' de , str > > ( ) ? {
83
+ values. push ( elm. into_owned ( ) ) ;
79
84
}
80
85
Ok ( Some ( values) )
81
86
}
@@ -432,26 +437,56 @@ impl OAuthClient {
432
437
pub async fn verify_token < ' a , R > ( & self , token : & str , role : R ) -> Result < OAuthTokenIntrospect , VerifyTokenError >
433
438
where R : Into < Option < & ' a str > >
434
439
{
435
- let i = self . introspect_token ( token) . await ?;
440
+ let keys = self . jwks ( ) . await ?;
441
+ let wk = self . well_known ( ) . await ?;
436
442
437
- if !i. active {
438
- return Err ( VerifyTokenError :: Forbidden ) ;
439
- }
443
+ let validations = vec ! [
444
+ alcoholic_jwt:: Validation :: Audience ( self . config. client_id. clone( ) ) ,
445
+ alcoholic_jwt:: Validation :: Issuer ( wk. issuer. clone( ) ) ,
446
+ alcoholic_jwt:: Validation :: NotExpired ,
447
+ alcoholic_jwt:: Validation :: SubjectPresent ,
448
+ ] ;
449
+
450
+ let kid = match match alcoholic_jwt:: token_kid ( token) {
451
+ Ok ( k) => k,
452
+ Err ( e) => return Err ( VerifyTokenError :: InternalServerError ( format ! ( "{:?}" , e) ) )
453
+ } {
454
+ Some ( k) => k,
455
+ None => return Err ( VerifyTokenError :: InternalServerError ( "no token kid" . to_string ( ) ) )
456
+ } ;
457
+
458
+ let key = match keys. find ( & kid) {
459
+ Some ( k) => k,
460
+ None => return Err ( VerifyTokenError :: InternalServerError ( "unable to find key" . to_string ( ) ) )
461
+ } ;
462
+
463
+ let token = match alcoholic_jwt:: validate ( token, key, validations) {
464
+ Ok ( k) => k,
465
+ Err ( e) => {
466
+ return Err ( VerifyTokenError :: Forbidden )
467
+ }
468
+ } ;
469
+
470
+ let data: OAuthTokenIntrospect = match serde_json:: from_value ( token. claims ) {
471
+ Ok ( c) => c,
472
+ Err ( e) => {
473
+ return Err ( VerifyTokenError :: InternalServerError ( format ! ( "{:?}" , e) ) )
474
+ }
475
+ } ;
440
476
441
477
if let Some ( r) = role. into ( ) {
442
- match ( & i. aud , & i. resource_access ) {
443
- ( Some ( aud) , Some ( resource_access) ) => {
444
- if !aud. contains ( & self . config . client_id ) ||
445
- !resource_access. contains_key ( & self . config . client_id ) ||
478
+ match & data. resource_access {
479
+ Some ( resource_access) => {
480
+ if !resource_access. contains_key ( & self . config . client_id ) ||
446
481
!resource_access. get ( & self . config . client_id ) . unwrap ( ) . roles . contains ( & r. to_owned ( ) ) {
447
482
return Err ( VerifyTokenError :: Forbidden ) ;
448
483
}
449
- Ok ( i )
484
+ Ok ( data )
450
485
}
451
486
_ => Err ( VerifyTokenError :: Forbidden )
452
487
}
453
488
} else {
454
- Ok ( i )
489
+ Ok ( data )
455
490
}
456
491
}
457
492
0 commit comments