use std::future::Future; use std::collections::HashMap; use kittybox_indieauth::{ AuthorizationRequest, TokenData }; pub use kittybox_util::auth::EnrolledCredential; type Result = std::io::Result; pub mod fs; pub use fs::FileBackend; pub trait AuthBackend: Clone + Send + Sync + 'static { /// Initialize self from URL, possibly performing initialization. fn new(url: &'_ url::Url) -> impl Future> + Send; // Authorization code management. /// Create a one-time OAuth2 authorization code for the passed /// authorization request, and save it for later retrieval. /// /// Note for implementors: the [`AuthorizationRequest::me`] value /// is guaranteed to be [`Some(url::Url)`][Option::Some] and can /// be trusted to be correct and non-malicious. fn create_code(&self, data: AuthorizationRequest) -> impl Future> + Send; /// Retreive an authorization request using the one-time /// code. Implementations must sanitize the `code` field to /// prevent exploits, and must check if the code should still be /// valid at this point in time (validity interval is left up to /// the implementation, but is recommended to be no more than 10 /// minutes). fn get_code(&self, code: &str) -> impl Future>> + Send; // Token management. fn create_token(&self, data: TokenData) -> impl Future> + Send; fn get_token(&self, website: &url::Url, token: &str) -> impl Future>> + Send; fn list_tokens(&self, website: &url::Url) -> impl Future>> + Send; fn revoke_token(&self, website: &url::Url, token: &str) -> impl Future> + Send; // Refresh token management. fn create_refresh_token(&self, data: TokenData) -> impl Future> + Send; fn get_refresh_token(&self, website: &url::Url, token: &str) -> impl Future>> + Send; fn list_refresh_tokens(&self, website: &url::Url) -> impl Future>> + Send; fn revoke_refresh_token(&self, website: &url::Url, token: &str) -> impl Future> + Send; // Password management. /// Verify a password. #[must_use] fn verify_password(&self, website: &url::Url, password: String) -> impl Future> + Send; /// Enroll a password credential for a user. Only one password /// credential must exist for a given user. fn enroll_password(&self, website: &url::Url, password: String) -> impl Future> + Send; /// List currently enrolled credential types for a given user. fn list_user_credential_types(&self, website: &url::Url) -> impl Future>> + Send; // WebAuthn credential management. #[cfg(feature = "webauthn")] /// Enroll a WebAuthn authenticator public key for this user. /// Multiple public keys may be saved for one user, corresponding /// to different authenticators used by them. /// /// This function can also be used to overwrite a passkey with an /// updated version after using /// [webauthn::prelude::Passkey::update_credential()]. fn enroll_webauthn(&self, website: &url::Url, credential: webauthn::prelude::Passkey) -> impl Future> + Send; #[cfg(feature = "webauthn")] /// List currently enrolled WebAuthn authenticators for a given user. fn list_webauthn_pubkeys(&self, website: &url::Url) -> impl Future>> + Send; #[cfg(feature = "webauthn")] /// Persist registration challenge state for a little while so it /// can be used later. /// /// Challenges saved in this manner MUST expire after a little /// while. 10 minutes is recommended. fn persist_registration_challenge( &self, website: &url::Url, state: webauthn::prelude::PasskeyRegistration ) -> impl Future> + Send; #[cfg(feature = "webauthn")] /// Retrieve a persisted registration challenge. /// /// The challenge should be deleted after retrieval. fn retrieve_registration_challenge( &self, website: &url::Url, challenge_id: &str ) -> impl Future> + Send; #[cfg(feature = "webauthn")] /// Persist authentication challenge state for a little while so /// it can be used later. /// /// Challenges saved in this manner MUST expire after a little /// while. 10 minutes is recommended. /// /// To support multiple authentication options, this can return an /// opaque token that should be set as a cookie. fn persist_authentication_challenge( &self, website: &url::Url, state: webauthn::prelude::PasskeyAuthentication ) -> impl Future> + Send; #[cfg(feature = "webauthn")] /// Retrieve a persisted authentication challenge. /// /// The challenge should be deleted after retrieval. fn retrieve_authentication_challenge( &self, website: &url::Url, challenge_id: &str ) -> impl Future> + Send; }