File size: 3,543 Bytes
e5034c3 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 | use std::collections::HashMap;
use derive_more::{Deref, From};
use url::Url;
use super::{
ApiKey, AuthorizationCode, DeviceCode, OAuthConfig, PkceVerifier, State, URLParam,
URLParamSpec, URLParamValue, UserCode,
};
#[derive(Debug, Clone, PartialEq, Deref, From)]
pub struct URLParameters(HashMap<URLParam, URLParamValue>);
// API Key Flow
/// Request parameters for API key authentication
#[derive(Debug, Clone)]
pub struct ApiKeyRequest {
pub required_params: Vec<URLParamSpec>,
pub existing_params: Option<URLParameters>,
pub api_key: Option<ApiKey>,
}
/// Response containing API key and URL parameters
#[derive(Debug, Clone)]
pub struct ApiKeyResponse {
pub api_key: ApiKey,
pub url_params: HashMap<URLParam, URLParamValue>,
}
// Authorization Code Flow
/// Authorization code OAuth authentication flow
#[derive(Debug, Clone)]
pub struct CodeAuthFlow;
/// Request parameters for authorization code flow
#[derive(Debug, Clone)]
pub struct CodeRequest {
pub authorization_url: Url,
pub state: State,
pub pkce_verifier: Option<PkceVerifier>,
pub oauth_config: OAuthConfig,
}
/// Response containing authorization code
#[derive(Debug, Clone)]
pub struct CodeResponse {
pub code: AuthorizationCode,
}
// Device Code Flow
/// Device code OAuth authentication flow
#[derive(Debug, Clone)]
pub struct DeviceCodeAuthFlow;
/// Request parameters for device code flow
#[derive(Debug, Clone)]
pub struct DeviceCodeRequest {
pub user_code: UserCode,
pub device_code: DeviceCode,
pub verification_uri: Url,
pub verification_uri_complete: Option<Url>,
pub expires_in: u64,
pub interval: u64,
pub oauth_config: OAuthConfig,
}
/// Response for device code flow
#[derive(Debug, Clone)]
pub struct DeviceCodeResponse;
/// Generic container that pairs a request with its corresponding response
#[derive(Debug, Clone)]
pub struct AuthContext<Request, Response> {
pub request: Request,
pub response: Response,
}
/// Represents different types of authentication requests
#[derive(Debug, Clone)]
pub enum AuthContextRequest {
ApiKey(ApiKeyRequest),
DeviceCode(DeviceCodeRequest),
Code(CodeRequest),
}
/// Represents completed authentication flows with their request/response pairs
#[derive(Debug, Clone)]
pub enum AuthContextResponse {
ApiKey(AuthContext<ApiKeyRequest, ApiKeyResponse>),
DeviceCode(AuthContext<DeviceCodeRequest, DeviceCodeResponse>),
Code(AuthContext<CodeRequest, CodeResponse>),
}
impl AuthContextResponse {
/// Creates an API key authentication context
pub fn api_key(
request: ApiKeyRequest,
api_key: impl ToString,
url_params: HashMap<String, String>,
) -> Self {
Self::ApiKey(AuthContext {
request,
response: ApiKeyResponse {
api_key: api_key.to_string().into(),
url_params: url_params
.into_iter()
.map(|(k, v)| (k.into(), v.into()))
.collect(),
},
})
}
/// Creates a device code authentication context
pub fn device_code(request: DeviceCodeRequest) -> Self {
Self::DeviceCode(AuthContext { request, response: DeviceCodeResponse })
}
/// Creates an authorization code authentication context
pub fn code(request: CodeRequest, code: impl ToString) -> Self {
Self::Code(AuthContext {
request,
response: CodeResponse { code: code.to_string().into() },
})
}
}
|