use primitives::authorizer::Storage;
use primitives::registrar::{Client, ClientMap};
use code_grant::frontend::{AuthorizationFlow, OwnerAuthorizer};
use std::collections::HashMap;
use super::{CraftedRequest, CraftedResponse, TestGenerator, ToSingleValueQuery};
use super::{Allow, Deny};
use super::defaults::*;
struct AuthorizationSetup {
registrar: ClientMap,
authorizer: Storage<TestGenerator>,
}
impl AuthorizationSetup {
fn new() -> AuthorizationSetup {
let mut registrar = ClientMap::new();
let authorizer = Storage::new(TestGenerator("AuthToken".to_string()));
let client = Client::confidential(EXAMPLE_CLIENT_ID,
EXAMPLE_REDIRECT_URI.parse().unwrap(),
EXAMPLE_SCOPE.parse().unwrap(),
EXAMPLE_PASSPHRASE.as_bytes());
registrar.register_client(client);
AuthorizationSetup {
registrar,
authorizer,
}
}
fn test_silent_error(&mut self, mut request: CraftedRequest) {
let pagehandler = Allow(EXAMPLE_OWNER_ID.to_string());
match AuthorizationFlow::new(&mut self.registrar, &mut self.authorizer).handle(&mut request, &pagehandler) {
Ok(CraftedResponse::Redirect(url))
=> panic!("Redirection without client id {:?}", url),
Ok(resp) => panic!("Response without client id {:?}", resp),
Err(_) => (),
};
}
fn test_error_redirect (&mut self, mut request: CraftedRequest, pagehandler: &OwnerAuthorizer<Request=CraftedRequest>) {
match AuthorizationFlow::new(&mut self.registrar, &mut self.authorizer).handle(&mut request, pagehandler) {
Ok(CraftedResponse::RedirectFromError(ref url))
if url.query_pairs().collect::<HashMap<_, _>>().get("error").is_some()
=> (),
resp
=> panic!("Expected redirect with error set: {:?}", resp),
};
}
}
#[test]
fn auth_request_silent_missing_client() {
let missing_client = CraftedRequest {
query: Some(vec![("response_type", "code")].iter().to_single_value_query()),
urlbody: None,
auth: None,
};
AuthorizationSetup::new().test_silent_error(missing_client);
}
#[test]
fn auth_request_silent_unknown_client() {
let unknown_client = CraftedRequest {
query: Some(vec![("response_type", "code"),
("client_id", "SomeOtherClient"),
("redirect_uri", "https://wrong.client.example/endpoint")]
.iter().to_single_value_query()),
urlbody: None,
auth: None,
};
AuthorizationSetup::new().test_silent_error(unknown_client);
}
#[test]
fn auth_request_silent_mismatching_redirect() {
let mismatching_redirect = CraftedRequest {
query: Some(vec![("response_type", "code"),
("client_id", EXAMPLE_CLIENT_ID),
("redirect_uri", "https://wrong.client.example/endpoint")]
.iter().to_single_value_query()),
urlbody: None,
auth: None,
};
AuthorizationSetup::new().test_silent_error(mismatching_redirect);
}
#[test]
fn auth_request_silent_invalid_redirect() {
let invalid_redirect = CraftedRequest {
query: Some(vec![("response_type", "code"),
("client_id", EXAMPLE_CLIENT_ID),
("redirect_uri", "\\://")]
.iter().to_single_value_query()),
urlbody: None,
auth: None,
};
AuthorizationSetup::new().test_silent_error(invalid_redirect);
}
#[test]
fn auth_request_error_denied() {
let denied_request = CraftedRequest {
query: Some(vec![("response_type", "code"),
("client_id", EXAMPLE_CLIENT_ID),
("redirect_uri", EXAMPLE_REDIRECT_URI)]
.iter().to_single_value_query()),
urlbody: None,
auth: None,
};
AuthorizationSetup::new().test_error_redirect(denied_request, &Deny);
}
#[test]
fn auth_request_error_unsupported_method() {
let unsupported_method = CraftedRequest {
query: Some(vec![("response_type", "other_method"),
("client_id", EXAMPLE_CLIENT_ID),
("redirect_uri", EXAMPLE_REDIRECT_URI)]
.iter().to_single_value_query()),
urlbody: None,
auth: None,
};
AuthorizationSetup::new().test_error_redirect(unsupported_method,
&Allow(EXAMPLE_OWNER_ID.to_string()));
}
#[test]
fn auth_request_error_malformed_scope() {
let malformed_scope = CraftedRequest {
query: Some(vec![("response_type", "code"),
("client_id", EXAMPLE_CLIENT_ID),
("redirect_uri", EXAMPLE_REDIRECT_URI),
("scope", "\"no quotes (0x22) allowed\"")]
.iter().to_single_value_query()),
urlbody: None,
auth: None,
};
AuthorizationSetup::new().test_error_redirect(malformed_scope,
&Allow(EXAMPLE_OWNER_ID.to_string()));
}