supabase-jwt
English | 简体中文
A lightweight, framework-agnostic Rust library for validating Supabase Auth JWTs, with JWKS caching support.
Table of Contents
- ✨ Features
- 🚀 Quick Start
- 🔧 Installation
- 🧩 Framework Integration Examples
- 📖 API Overview
- 🏛️ Design Philosophy
- ✅ Testing and Quality
- 🤝 Contributing
- 📜 License
✨ Features
- 🚀 High-performance: Smart JWKS caching to reduce network requests.
- 🔒 Secure: Optimized for the Supabase Auth ES256 algorithm.
- 🎯 Simple: Framework-agnostic with a simple API design for easy integration.
- ⚡ Asynchronous: Purely asynchronous design based on
tokio
. - 🛡️ Reliable: Thoroughly tested with >94% code coverage.
🚀 Quick Start
use ;
async
🔧 Installation
Add the following to your Cargo.toml
:
[]
= "0.1.0" # Please check for the latest version on crates.io
= { = "1.47.0", = ["full"] }
🧩 Framework Integration Examples
Axum
It's recommended to use axum-extra
to elegantly extract the Bearer Token.
use ;
use ;
use TypedHeader;
use ;
use Arc;
async : ,
)
/*
// Set the state in your application
async fn run_app() {
let jwks_cache = Arc::new(JwksCache::new("..."));
let app = Router::new()
.route("/protected", get(protected_handler))
.with_state(jwks_cache);
// Start the server...
}
*/
Actix Web
In Actix Web, you can manually extract the token from the request headers.
use ;
use ;
async
📖 API Overview
The Claims
struct provides convenient methods to access standard and custom information in the JWT.
// Basic information
let user_id = claims.user_id; // User ID (sub)
let email = claims.email; // Email (email)
let role = claims.role; // Role (role)
let phone = claims.phone; // Phone number (phone)
let is_anon = claims.is_anonymous; // Whether the user is anonymous (is_anonymous)
// Timestamps
let issued_at = claims.issued_at; // Issued at (iat)
let expires_at = claims.expires_at; // Expires at (exp)
// Metadata
// Assuming user_metadata = {"custom_field": "value"}
let custom_field: = claims.get_user_metadata;
// Assuming app_metadata = {"feature_enabled": true}
let app_setting: = claims.get_app_metadata;
JwksCache
provides a smart key caching mechanism to efficiently validate tokens.
let jwks_cache = new;
// Automatically fetch JWKS from cache or network
let jwks = jwks_cache.get_jwks.await?;
// Find a specific key (usually called internally by from_token)
let key = jwks_cache.find_key.await?;
For more details, please refer to the full API documentation on docs.rs.
🚀 Advanced Usage
Error Handling
It's good practice to handle different authentication errors gracefully. from_bearer_token
returns a detailed AuthError
enum.
use ;
async
Cache Behavior
JwksCache
is designed for high availability and performance with a built-in smart caching strategy, requiring no manual configuration:
- Normal Cache: JWKS are cached for 24 hours.
- Fallback Cache: If fetching new keys fails (e.g., due to a network error), the cache will continue to serve the last known valid keys for up to 7 days. This prevents your application from failing if the Supabase Auth service is temporarily unavailable.
- Network Timeout: All network requests to the JWKS endpoint have a 5-second timeout to prevent your application from hanging.
🏛️ Design Philosophy
This library is based on the design philosophy of "Trust Supabase Auth, focus on parsing stability":
- Trust Upstream: Trust the legality of the token format and content generated by Supabase Auth.
- Focus on Parsing: Focus on ensuring the stability and performance of the parsing process.
- Fail Fast: Immediately reject abnormal tokens to avoid excessive validation.
- Cache Optimization: Smart JWKS caching to reduce network overhead.
✅ Testing and Quality
We take code quality and reliability very seriously and ensure it through a comprehensive testing strategy.
- Test Coverage: Achieved >94% code coverage using
cargo-tarpaulin
. - Test Cases: Over 100 test cases covering core logic, edge cases, and integration scenarios.
- Mock Services: Use
wiremock
to simulate the Supabase Auth API, ensuring test stability and independence.
You can run the tests with the following commands:
# Run all tests
# Calculate code coverage
🤝 Contributing
Issues and Pull Requests are welcome! Before contributing, please ensure:
- Run
cargo fmt
to format the code. - Run
cargo clippy
to check code quality. - Run
cargo test
to ensure all tests pass.
📜 License
This project is dual-licensed under MIT or Apache-2.0. See LICENSE-MIT and LICENSE-APACHE for details.