Rust-based Movie API with production grade features: clean architecture, observability, comprehensive testing, and passwordless authentication with WebAuthn/Passkeys.
This project demonstrates real-world patterns for building and evolving backend services with Rust:
- Dependency Inversion (DIP) - Domain defines abstract trait contracts (Repository, Metrics); infrastructure provides concrete implementations (PostgresRepository, PrometheusMetrics)
- Stateless service design - horizontally scalable with externalized state (PostgreSQL, Redis)
- Observability - Prometheus metrics, health checks, structured logging
- Comprehensive testing - 57 integration tests with real services, not mocks
- CI parity - local development matches CI exactly
- PostgreSQL - ACID-compliant storage with foreign key constraints and migrations
- Redis - High-performance caching, session storage, ephemeral challenge data
- Registration - Create passkey credentials with authenticators (WebAuthn)
- Authentication - Login using biometrics or hardware keys
- Credential Management - List and delete registered passkeys
- Replay Attack Prevention - Cryptographic counter validation
- Multi-device Support - Multiple passkeys per account
- Health Checks - Light and full modes with Redis connectivity validation
- Prometheus Metrics - HTTP request duration, status codes, business metrics (movie creation events)
- Structured Logging - Tracing instrumentation with configurable levels and span events
- Movies API - Full create, read, update, delete with validation
- Hash-based IDs - Deterministic key generation from normalized data
- Input Sanitization - Whitespace normalization, range validation
# Start all services (PostgreSQL + Redis)
source ./scripts/startup.sh
# Run the server
cargo run
# Server running at http://localhost:3000
# Stop all services when done
./scripts/shutdown.sh# Copy environment config
cp .env.example .env
# Start services (PostgreSQL + Redis)
docker compose up -d
# Run database migrations
cargo install sqlx-cli --no-default-features --features postgres
sqlx migrate run
# Start API server
cargo run
# Server running at http://localhost:3000- Rust toolchain (install via rustup)
- Docker & Docker Compose
sqlx-clifor database migrations
cargo install sqlx-cli --no-default-features --features postgres# Format code
cargo fmt
# Lint
cargo clippy --all-targets --all-features -- -D warnings
# Build
cargo build
# Watch mode (requires cargo-watch)
cargo watch -x runContributing: See CONTRIBUTING.md
GET /- HTML landing page with version and endpoint listingGET /health- Health check (light mode by default)GET /health?mode=full- Full health check including Redis connectivityGET /metrics- Prometheus metrics in text exposition format
GET /movies/get/{id}- Fetch movie by ID (200 OK or 404 Not Found)POST /movies/add- Create movie (201 Created or 409 Conflict if duplicate)PUT /movies/update/{id}- Update movie (200 OK, allows overwrite)DELETE /movies/delete/{id}- Delete movie (204 No Content or 404 Not Found)
POST /webauthn/register/start- Begin passkey registration with challenge generationPOST /webauthn/register/finish- Complete passkey registration and store credentialPOST /webauthn/auth/start- Begin passkey authentication with challengePOST /webauthn/auth/finish- Complete passkey authentication and create sessionGET /webauthn/credentials- List user's registered passkeys (requires Bearer token)DELETE /webauthn/credentials/{id}- Delete specific passkey (requires Bearer token)
Architecture details: See docs/webauthn-architecture.md
| Variable | Default | Description |
|---|---|---|
REDIS_URL |
(required) | Redis connection string |
DATABASE_URL |
(required) | PostgreSQL connection string |
API_BIND_ADDR |
(required) | Server bind address |
AXUM_METRICS_TYPE |
noop |
Metrics backend (prom for Prometheus or noop) |
AXUM_LOG_LEVEL |
debug |
Log level (trace, debug, info, warn, error) |
AXUM_SPAN_EVENTS |
close |
Tracing span events (full, enter_exit, close) |
AXUM_DB_RETRY_COUNT |
50 |
Database connection retry attempts during startup |
AXUM_DB_ACQUIRE_TIMEOUT_SEC |
30 |
Database connection pool acquire timeout (seconds) |
Note: PostgreSQL is required for WebAuthn functionality. Copy .env.example to .env and customize as needed.
Run the complete test suite (matches CI exactly):
./scripts/test-all.shIndividual test suites:
./scripts/run-unit-tests.sh- Unit tests, linting, format checks, doctests./scripts/run-integration-tests.sh- Integration tests with Docker services./scripts/ci-local.sh- Local CI simulation usingact
Test Coverage: 57 tests across unit, integration, and WebAuthn flows. See scripts for detailed breakdowns.
Five WebAuthn tests are currently ignored due to upstream test utility limitations:
- 2 registration tests (
test_register_finish_*) - 3 authentication tests (
test_auth_start_*)
These tests require injectable WebAuthn verifier instances for full end-to-end verification. The current implementation validates:
- ✅ Database operations (user/credential CRUD)
- ✅ Challenge storage and expiry in Redis
- ✅ Counter validation and replay prevention
- ✅ Session creation and validation
⚠️ WebAuthn signature verification (requires browser automation)
Full verification requires browser-based E2E tests (planned for Phase 5).
Framework & Runtime:
- Rust 1.92.0 (pinned for sqlx-cli 0.8.2 compatibility) with Axum 0.8 web framework
- Tokio async runtime
- SQLx for compile-time verified queries
Data Layer:
- PostgreSQL 16 for persistent storage
- Redis 7 for sessions, caching, and ephemeral data
Authentication:
webauthn-rs- WebAuthn protocol implementation- Public key cryptography (ECDSA, EdDSA)
- FIDO2/WebAuthn specification compliance
Testing & CI:
- Docker Compose for integration test services
- GitHub Actions CI/CD with caching
- Local CI runner using
act
axum-quickstart/
├── src/
│ ├── domain/ # Business logic (Repository trait, models)
│ ├── infrastructure/ # Implementation (PostgreSQL, Redis, WebAuthn)
│ ├── handlers/ # HTTP handlers (WebAuthn, CRUD, health)
│ └── lib.rs # Public API gateway (EMBP)
├── tests/ # Integration tests
├── migrations/ # SQLx database migrations
├── scripts/ # Development and CI scripts
├── docs/ # Architecture and setup guides
└── docker-compose.yml # PostgreSQL + Redis services
Architecture: Follows EMBP (Explicit Module Boundary Pattern) and Clean Architecture principles.
Dependencies flow inward: Domain defines contracts, Infrastructure provides implementations, Application orchestrates handlers. No database or transport types leak into domain logic.
The project follows clean architecture with explicit boundaries:
- Domain — business logic and trait contracts (Repository, User, Credential, Movie)
- Infrastructure — concrete implementations (PostgreSQL, Redis, WebAuthn, Metrics)
- Application — Axum handlers and HTTP routing
Dependencies flow inward; implementations never leak outward. The service is designed for horizontal scalability: all persistent state (PostgreSQL) and ephemeral state (Redis) are externalized, keeping application instances stateless.
Key architectural patterns:
- Dependency Inversion Principle (DIP) via trait-based contracts
- Dependency injection via AppState
- EMBP (Explicit Module Boundary Pattern) for module organization
- Integration testing against real services, not mocks
Authentication:
- Phishing-resistant authentication - WebAuthn's cryptographic challenge-response prevents phishing
- Replay attack prevention - Signature counters validated on every authentication
- Session expiry - Redis automatically expires sessions (7 days) and challenges (5 minutes)
- Generic error messages - Prevent username enumeration attacks
Data Integrity:
- ACID-compliant storage - PostgreSQL ensures data integrity with foreign key constraints
- Foreign key constraints - Credentials cannot exist without users; cascade deletion enforced
- Atomic operations - Redis GETDEL ensures single-use challenges
- Input validation - All user inputs sanitized and validated before processing
The following phases demonstrate incremental addition of WebAuthn/Passkeys to the existing REST API foundation. This showcases how modern authentication capabilities are integrated into real systems rather than built in isolation.
- Users and Credentials tables with foreign key constraints
- Repository pattern with Clean Architecture
- Counter tracking for replay prevention
- Multiple credentials per user (multi-device support)
- 9 unit tests + 1 schema test
- Registration endpoints (
/webauthn/register/start,/webauthn/register/finish) - Redis-backed challenge storage with automatic expiry
- webauthn-rs integration for protocol implementation
- 6 integration tests (2 ignored - Issue #33)
- Authentication endpoints (
/webauthn/auth/start,/webauthn/auth/finish) - Session token generation with 7-day TTL
- Counter validation to prevent replay attacks
- Generic error messages to prevent username enumeration
- 6 integration tests (3 ignored - Issue #33)
- Credential listing endpoint (
GET /webauthn/credentials) - Credential deletion endpoint (
DELETE /webauthn/credentials/:id) - Session-based authentication with Bearer tokens
- Ownership verification for secure deletion
- 7 integration tests
- Browser-based E2E tests with Playwright
- Full WebAuthn signature verification
- Production deployment guide
- Enhanced flow diagrams
WebAuthn:
- Browser-based E2E testing with Playwright for full signature verification
- Production deployment guide with HTTPS requirements
General Improvements:
- Enhanced documentation with architecture flow diagrams
- Additional API feature demonstrations
- Performance benchmarking suite
- WebAuthn Architecture - Implementation details
- WebAuthn Specification - W3C standard
- SQLx Offline Mode - CI/CD guide
MIT