Crates.io | atproto-oauth-aip |
lib.rs | atproto-oauth-aip |
version | 0.11.2 |
created_at | 2025-06-18 21:26:18.325727+00 |
updated_at | 2025-08-20 18:54:47.468483+00 |
description | ATProtocol AIP OAuth tools |
homepage | https://tangled.sh/@smokesignal.events/atproto-identity-rs |
repository | https://tangled.sh/@smokesignal.events/atproto-identity-rs |
max_upload_size | |
id | 1717621 |
size | 105,843 |
OAuth AIP (Identity Provider) implementation for AT Protocol.
Complete OAuth 2.0 authorization code flow with PAR, PKCE, token exchange, and AT Protocol session management for identity providers.
This crate does not provide standalone CLI tools. It serves as a library for OAuth AIP implementations.
use atproto_oauth_aip::{OAuthClient, oauth_init, oauth_complete, session_exchange};
use atproto_oauth::storage::MemoryStorage;
#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
// Initialize OAuth client
let client = OAuthClient::new(
"https://your-app.com/client-id".to_string(),
Some("your-client-secret".to_string()),
"https://your-app.com/callback".to_string(),
);
// Initialize storage (use persistent storage in production)
let storage = MemoryStorage::new();
// Start OAuth flow
let (authorization_url, state) = oauth_init(
&client,
"user@example.com", // User identifier
&storage,
).await?;
// Redirect user to authorization_url
println!("Please visit: {}", authorization_url);
// After user authorizes and is redirected back with code and state...
let authorization_code = "received-auth-code";
let returned_state = "returned-state";
// Complete OAuth flow
let access_token = oauth_complete(
&client,
authorization_code,
returned_state,
&storage,
).await?;
// Exchange for AT Protocol session
let session = session_exchange(
&client,
&access_token,
&storage,
).await?;
println!("Authenticated as: {} ({})", session.handle, session.did);
println!("PDS Endpoint: {}", session.pds_endpoint);
Ok(())
}
use atproto_oauth_aip::resources::{oauth_protected_resource, oauth_authorization_server};
// Get OAuth protected resource configuration
let protected_resource = oauth_protected_resource("https://bsky.social").await?;
// Get OAuth authorization server metadata
let auth_server = oauth_authorization_server(&protected_resource).await?;
OAuthClient
: OAuth client credentials and configurationATProtocolSession
: Authenticated session containing DID, handle, and PDS endpointoauth_init()
: Initiates OAuth flow using PARoauth_complete()
: Exchanges authorization code for access tokensession_exchange()
: Converts OAuth access token to AT Protocol sessionoauth_protected_resource()
: Fetch OAuth protected resource metadataoauth_authorization_server()
: Fetch OAuth authorization server metadataThe crate uses typed errors following the AT Protocol error format:
use atproto_oauth_aip::OAuthWorkflowError;
match result {
Err(OAuthWorkflowError::InvalidAuthorizationRequest(e)) => {
// Handle PAR errors
}
Err(OAuthWorkflowError::TokenExchangeFailed(e)) => {
// Handle token exchange errors
}
// ... other error types
}
This crate requires an implementation of the OAuthStorage
trait from atproto-oauth
. For production use, implement persistent storage rather than using MemoryStorage
.
This crate depends on:
atproto-oauth
: Core OAuth implementationatproto-identity
: AT Protocol identity resolutionatproto-record
: Record handlingreqwest
: HTTP clientserde
: Serializationtokio
: Async runtimeMIT License