allframe_core/lib.rs
1//! # AllFrame Core
2//!
3//! [](https://crates.io/crates/allframe-core)
4//! [](https://docs.rs/allframe-core)
5//! [](https://github.com/all-source-os/all-frame)
6//!
7//! **The Composable Rust API Framework** - Protocol-agnostic routing, CQRS/ES,
8//! resilience patterns, and beautiful API documentation.
9//!
10//! AllFrame is the first Rust web framework designed, built, and evolved
11//! exclusively through **Test-Driven Development (TDD)** with 500+ tests.
12//!
13//! ## Features at a Glance
14//!
15//! | Feature | Description |
16//! |---------|-------------|
17//! | 🔀 **Protocol-Agnostic** | Write once, expose via REST, GraphQL, and gRPC |
18//! | 📖 **Auto Documentation** | Scalar UI, GraphiQL, gRPC Explorer built-in |
19//! | 🔄 **CQRS/Event Sourcing** | 85% boilerplate reduction with CommandBus, Projections, Sagas |
20//! | 🛡️ **Resilience Patterns** | Retry, Circuit Breaker, Rate Limiting |
21//! | 🔒 **Security Utilities** | Safe logging, credential obfuscation |
22//! | 💉 **Compile-time DI** | Dependency injection resolved at compile time |
23//! | 📊 **OpenTelemetry** | Automatic tracing and metrics |
24//! | 📱 **Offline-First** | SQLite event store, sync engine, zero network deps |
25//!
26//! ## Quick Start
27//!
28//! Add to your `Cargo.toml`:
29//!
30//! ```toml
31//! [dependencies]
32//! allframe = "0.1"
33//! tokio = { version = "1", features = ["full"] }
34//! ```
35//!
36//! ### Basic Router Example
37//!
38//! ```rust
39//! use allframe_core::router::{Router, RestAdapter, ProtocolAdapter};
40//!
41//! #[tokio::main]
42//! async fn main() {
43//! // Create a router
44//! let mut router = Router::new();
45//!
46//! // Register handlers - works with any protocol!
47//! router.register("get_users", || async {
48//! r#"[{"id": 1, "name": "Alice"}]"#.to_string()
49//! });
50//!
51//! router.register("create_user", || async {
52//! r#"{"id": 2, "name": "Bob"}"#.to_string()
53//! });
54//!
55//! // Expose via REST
56//! let mut rest = RestAdapter::new();
57//! rest.route("GET", "/users", "get_users");
58//! rest.route("POST", "/users", "create_user");
59//!
60//! println!("Router configured with {} handlers", 2);
61//! }
62//! ```
63//!
64//! ### Protocol-Agnostic Handler
65//!
66//! ```rust
67//! use allframe_core::router::{Router, RestAdapter, GraphQLAdapter, GrpcAdapter};
68//!
69//! // Same handler, multiple protocols!
70//! let mut router = Router::new();
71//! router.register("get_user", || async {
72//! r#"{"id": 42, "name": "John"}"#.to_string()
73//! });
74//!
75//! // REST: GET /users/42
76//! let mut rest = RestAdapter::new();
77//! rest.route("GET", "/users/:id", "get_user");
78//!
79//! // GraphQL: query { user(id: 42) { name } }
80//! let mut graphql = GraphQLAdapter::new();
81//! graphql.query("user", "get_user");
82//!
83//! // gRPC: UserService.GetUser
84//! let mut grpc = GrpcAdapter::new();
85//! grpc.unary("UserService", "GetUser", "get_user");
86//! ```
87//!
88//! ## Feature Flags
89//!
90//! AllFrame uses feature flags to minimize binary size. Only enable what you
91//! need:
92//!
93//! | Feature | Description | Default |
94//! |---------|-------------|---------|
95//! | `router` | Protocol-agnostic routing | ✅ |
96//! | `router-graphql` | GraphQL adapter with async-graphql | ❌ |
97//! | `router-grpc` | gRPC adapter with tonic | ❌ |
98//! | `di` | Compile-time dependency injection | ✅ |
99//! | `cqrs` | CQRS + Event Sourcing infrastructure | ✅ |
100//! | `otel` | OpenTelemetry tracing | ✅ |
101//! | `health` | Health check endpoints | ✅ |
102//! | `resilience` | Retry, Circuit Breaker, Rate Limiting | ❌ |
103//! | `security` | Safe logging, credential obfuscation | ❌ |
104//! | `cqrs-sqlite` | SQLite event store (WAL mode) | ❌ |
105//! | `offline` | Full offline bundle (cqrs + sqlite + di + security) | ❌ |
106//!
107//! ### Feature Examples
108//!
109//! ```toml
110//! # Minimal REST API
111//! allframe = { version = "0.1", default-features = false, features = ["router"] }
112//!
113//! # Full-stack with resilience
114//! allframe = { version = "0.1", features = ["resilience", "security"] }
115//!
116//! # Multi-protocol gateway
117//! allframe = { version = "0.1", features = ["router-graphql", "router-grpc"] }
118//!
119//! # Offline desktop app (zero network deps)
120//! allframe = { version = "0.1", features = ["offline"] }
121//! ```
122//!
123//! ## Module Overview
124//!
125//! - [`router`] - Protocol-agnostic request routing (REST, GraphQL, gRPC)
126//! - [`shutdown`] - Graceful shutdown utilities
127//! - [`cache`] - Caching infrastructure
128//! - `cqrs` - CQRS + Event Sourcing (requires `cqrs` feature)
129//! - `resilience` - Retry, Circuit Breaker, Rate Limiting (requires
130//! `resilience` feature)
131//! - `security` - Safe logging and credential obfuscation (requires `security`
132//! feature)
133//! - `di` - Compile-time dependency injection (requires `di` feature)
134//! - `otel` - OpenTelemetry instrumentation (requires `otel` feature)
135//! - `health` - Health check infrastructure (requires `health` feature)
136//!
137//! ## Examples
138//!
139//! See the [examples directory](https://github.com/all-source-os/all-frame/tree/main/crates/allframe-core/examples)
140//! for complete working examples:
141//!
142//! - `scalar_docs.rs` - REST API with Scalar documentation
143//! - `graphql_docs.rs` - GraphQL API with GraphiQL playground
144//! - `resilience.rs` - Retry, Circuit Breaker, Rate Limiting
145//! - `graceful_shutdown.rs` - Production shutdown handling
146//!
147//! ## Learn More
148//!
149//! - [GitHub Repository](https://github.com/all-source-os/all-frame)
150//! - [Feature Flags Guide](https://github.com/all-source-os/all-frame/blob/main/docs/guides/FEATURE_FLAGS.md)
151//! - [CQRS Documentation](https://github.com/all-source-os/all-frame/blob/main/docs/phases/PHASE5_COMPLETE.md)
152
153#![deny(warnings)]
154#![deny(missing_docs)]
155#![deny(unsafe_code)]
156// Enable doc_cfg for showing feature requirements on docs.rs
157#![cfg_attr(docsrs, feature(doc_cfg))]
158
159/// Domain layer contracts and business logic primitives.
160/// This module provides the building blocks for Clean Architecture domain
161/// layers, including resilience contracts, business rules, and domain models.
162pub mod domain;
163
164/// Application layer orchestration and use case implementations.
165/// This module provides the orchestration layer that coordinates between
166/// domain logic and infrastructure, including resilience orchestration,
167/// transaction management, and business workflow coordination.
168pub mod application;
169
170/// Clean Architecture enforcement with compile-time dependency injection.
171///
172/// The `arch` module provides traits and utilities for enforcing Clean
173/// Architecture patterns in your application. Use the `#[inject]` macro to wire
174/// up dependencies.
175///
176/// # Example
177///
178/// ```rust,ignore
179/// use allframe::arch::*;
180///
181/// #[inject]
182/// struct MyService {
183/// repo: Arc<dyn UserRepository>,
184/// }
185/// ```
186#[cfg(feature = "di")]
187#[cfg_attr(docsrs, doc(cfg(feature = "di")))]
188pub mod arch;
189
190/// CQRS + Event Sourcing infrastructure with 85% boilerplate reduction.
191///
192/// This module provides production-ready CQRS primitives:
193/// - [`cqrs::CommandBus`] - Type-safe command dispatch (90% less code)
194/// - [`cqrs::EventStore`] - Event storage with replay capability
195/// - [`cqrs::ProjectionRegistry`] - Automatic projection updates (90% less
196/// code)
197/// - [`cqrs::SagaOrchestrator`] - Distributed transaction handling (75% less
198/// code)
199///
200/// # Example
201///
202/// ```rust,ignore
203/// use allframe::cqrs::{CommandBus, Event, EventStore};
204///
205/// #[derive(Clone)]
206/// struct CreateUser { name: String }
207///
208/// let bus = CommandBus::new();
209/// bus.dispatch(CreateUser { name: "Alice".into() }).await?;
210/// ```
211#[cfg(feature = "cqrs")]
212#[cfg_attr(docsrs, doc(cfg(feature = "cqrs")))]
213pub mod cqrs;
214
215/// OpenTelemetry automatic instrumentation for distributed tracing.
216///
217/// Use the `#[traced]` macro to automatically instrument your functions:
218///
219/// ```rust,ignore
220/// use allframe::otel::traced;
221///
222/// #[traced]
223/// async fn fetch_user(id: &str) -> User {
224/// // Automatically creates a span with function name
225/// }
226/// ```
227#[cfg(feature = "otel")]
228#[cfg_attr(docsrs, doc(cfg(feature = "otel")))]
229pub mod otel;
230
231/// Cache abstraction with in-memory and Redis backends.
232///
233/// Provides a unified caching interface with configurable TTL and eviction.
234pub mod cache;
235
236/// Compile-time dependency injection infrastructure.
237///
238/// Build dependency graphs that are resolved at compile time for zero runtime
239/// overhead.
240///
241/// # Example
242///
243/// ```rust,ignore
244/// use allframe::di::{ContainerBuilder, Provider};
245///
246/// let container = ContainerBuilder::new()
247/// .register::<DatabasePool>()
248/// .register::<UserRepository>()
249/// .build();
250/// ```
251#[cfg(feature = "di")]
252#[cfg_attr(docsrs, doc(cfg(feature = "di")))]
253pub mod di;
254
255/// Health check infrastructure for Kubernetes-ready services.
256///
257/// Provides liveness and readiness probes with dependency health aggregation.
258///
259/// # Example
260///
261/// ```rust,ignore
262/// use allframe::health::{HealthServer, HealthCheck};
263///
264/// let server = HealthServer::new()
265/// .add_check("database", db_check)
266/// .add_check("cache", cache_check);
267///
268/// server.serve(8080).await;
269/// ```
270#[cfg(feature = "health")]
271#[cfg_attr(docsrs, doc(cfg(feature = "health")))]
272pub mod health;
273
274/// Protocol-agnostic request routing for REST, GraphQL, and gRPC.
275///
276/// Write handlers once, expose them via any protocol:
277///
278/// # Example
279///
280/// ```rust
281/// use allframe_core::router::{Router, RestAdapter, GraphQLAdapter, GrpcAdapter};
282///
283/// let mut router = Router::new();
284/// router.register("get_user", || async { r#"{"id": 1}"#.to_string() });
285///
286/// // Same handler, three protocols!
287/// let mut rest = RestAdapter::new();
288/// rest.route("GET", "/users/:id", "get_user");
289///
290/// let mut graphql = GraphQLAdapter::new();
291/// graphql.query("user", "get_user");
292///
293/// let mut grpc = GrpcAdapter::new();
294/// grpc.unary("UserService", "GetUser", "get_user");
295/// ```
296///
297/// Also includes documentation generators:
298/// - `scalar_html` - Scalar UI for REST APIs
299/// - `graphiql_html` - GraphiQL playground for GraphQL
300/// - `grpc_explorer_html` - gRPC Explorer
301pub mod router;
302
303/// Graceful shutdown utilities for production services.
304///
305/// Handle SIGTERM/SIGINT signals and coordinate clean shutdown across tasks.
306///
307/// # Example
308///
309/// ```rust,ignore
310/// use allframe::shutdown::{ShutdownSignal, GracefulShutdownExt};
311///
312/// let signal = ShutdownSignal::new();
313///
314/// // In your main loop
315/// tokio::select! {
316/// _ = server.run() => {},
317/// _ = signal.recv() => {
318/// server.perform_shutdown().await;
319/// }
320/// }
321/// ```
322pub mod shutdown;
323
324/// Resilience patterns: Retry, Circuit Breaker, and Rate Limiting.
325///
326/// Production-ready patterns for fault-tolerant microservices:
327///
328/// # Example
329///
330/// ```rust,ignore
331/// use allframe::resilience::{RetryExecutor, CircuitBreaker, RateLimiter};
332///
333/// // Retry with exponential backoff
334/// let retry = RetryExecutor::new(RetryConfig::default());
335/// let result = retry.execute("api_call", || async {
336/// external_api.call().await
337/// }).await;
338///
339/// // Circuit breaker for fail-fast
340/// let cb = CircuitBreaker::new("payments", CircuitBreakerConfig::default());
341/// let result = cb.call(|| payment_service.charge()).await;
342///
343/// // Rate limiting
344/// let limiter = RateLimiter::new(100, 10); // 100 RPS, burst of 10
345/// if limiter.check().is_ok() {
346/// process_request().await;
347/// }
348/// ```
349#[cfg(feature = "resilience")]
350#[cfg_attr(docsrs, doc(cfg(feature = "resilience")))]
351pub mod resilience;
352
353/// Security utilities for safe logging and credential obfuscation.
354///
355/// Prevent accidental credential leaks in logs:
356///
357/// # Example
358///
359/// ```rust,ignore
360/// use allframe::security::{obfuscate_url, Sensitive};
361///
362/// let url = "https://user:password@api.example.com/v1/users";
363/// println!("Connecting to: {}", obfuscate_url(url));
364/// // Output: "Connecting to: https://api.example.com"
365///
366/// let api_key = Sensitive::new("sk_live_abcd1234");
367/// println!("Using key: {:?}", api_key);
368/// // Output: "Using key: ***"
369/// ```
370#[cfg(feature = "security")]
371#[cfg_attr(docsrs, doc(cfg(feature = "security")))]
372pub mod security;
373
374/// gRPC server infrastructure with TLS support.
375///
376/// Production-ready gRPC server with health checks and reflection.
377#[cfg(feature = "router-grpc")]
378#[cfg_attr(docsrs, doc(cfg(feature = "router-grpc")))]
379pub mod grpc;
380
381/// Authentication primitives with layered feature flags.
382///
383/// This module provides authentication infrastructure that can be used
384/// independently or integrated with your web framework:
385///
386/// - **`auth`**: Core traits only (zero dependencies)
387/// - **`auth-jwt`**: JWT validation with HS256/RS256 support
388/// - **`auth-axum`**: Axum extractors and middleware
389/// - **`auth-tonic`**: gRPC interceptors
390///
391/// # Example
392///
393/// ```rust,ignore
394/// use allframe_core::auth::{JwtValidator, JwtConfig, Authenticator};
395///
396/// let validator = JwtValidator::<Claims>::new(
397/// JwtConfig::hs256("secret").with_issuer("my-app")
398/// );
399///
400/// let claims = validator.authenticate("eyJ...").await?;
401/// ```
402#[cfg(feature = "auth")]
403#[cfg_attr(docsrs, doc(cfg(feature = "auth")))]
404pub mod auth;
405
406// ============================================================================
407// Re-exported dependencies
408// ============================================================================
409// These re-exports allow consumers to use common dependencies without adding
410// them explicitly to their Cargo.toml. This ensures version consistency and
411// reduces boilerplate in downstream crates.
412
413// ============================================================================
414// Re-exported macros
415// ============================================================================
416/// Re-export circuit_breaker attribute macro
417#[cfg(feature = "resilience")]
418pub use allframe_macros::circuit_breaker;
419/// Re-export rate_limited attribute macro
420#[cfg(feature = "resilience")]
421pub use allframe_macros::rate_limited;
422/// Re-export retry attribute macro
423#[cfg(feature = "resilience")]
424pub use allframe_macros::retry;
425/// Re-export GrpcError derive macro for automatic tonic::Status conversion
426#[cfg(feature = "router-grpc")]
427pub use allframe_macros::GrpcError;
428/// Re-export HealthCheck derive macro for automatic health check implementation
429#[cfg(feature = "di")]
430pub use allframe_macros::HealthCheck;
431/// Re-export Obfuscate derive macro for safe logging
432#[cfg(feature = "security")]
433pub use allframe_macros::Obfuscate;
434/// Re-export async_graphql for GraphQL support
435#[cfg(feature = "router-graphql")]
436pub use async_graphql;
437/// Re-export async_graphql_parser for GraphQL parsing
438#[cfg(feature = "router-graphql")]
439pub use async_graphql_parser;
440/// Re-export async_trait for async trait definitions
441pub use async_trait;
442/// Re-export backoff for retry/resilience patterns
443#[cfg(feature = "resilience")]
444pub use backoff;
445/// Re-export chrono for date/time handling
446#[cfg(feature = "utils")]
447pub use chrono;
448/// Re-export dashmap for concurrent hash maps
449#[cfg(feature = "cache-memory")]
450pub use dashmap;
451/// Re-export futures for async utilities
452#[cfg(feature = "router-grpc")]
453pub use futures;
454/// Re-export governor for rate limiting
455#[cfg(feature = "rate-limit")]
456pub use governor;
457/// Re-export hyper for HTTP primitives
458#[cfg(feature = "health")]
459pub use hyper;
460/// Re-export moka for high-performance caching
461#[cfg(feature = "cache-memory")]
462pub use moka;
463/// Re-export opentelemetry for full observability
464#[cfg(feature = "otel-otlp")]
465pub use opentelemetry;
466/// Re-export opentelemetry_otlp for OTLP exporter
467#[cfg(feature = "otel-otlp")]
468pub use opentelemetry_otlp;
469/// Re-export opentelemetry_sdk for SDK configuration
470#[cfg(feature = "otel-otlp")]
471pub use opentelemetry_sdk;
472/// Re-export parking_lot for efficient synchronization primitives
473#[cfg(feature = "utils")]
474pub use parking_lot;
475/// Re-export prometheus for metrics
476#[cfg(feature = "metrics")]
477pub use prometheus;
478/// Re-export prost for protobuf support
479#[cfg(feature = "router-grpc")]
480pub use prost;
481/// Re-export prost_types for well-known protobuf types
482#[cfg(feature = "router-grpc")]
483pub use prost_types;
484/// Re-export rand for random number generation
485#[cfg(feature = "utils")]
486pub use rand;
487/// Re-export redis for Redis client
488#[cfg(feature = "cache-redis")]
489pub use redis;
490/// Re-export reqwest for HTTP client functionality
491#[cfg(feature = "http-client")]
492pub use reqwest;
493/// Re-export serde for serialization
494pub use serde;
495/// Re-export serde_json for JSON handling
496pub use serde_json;
497/// Re-export tokio for async runtime
498pub use tokio;
499/// Re-export tokio_stream for async streams
500#[cfg(feature = "router-grpc")]
501pub use tokio_stream;
502/// Re-export tonic for gRPC support
503#[cfg(feature = "router-grpc")]
504pub use tonic;
505/// Re-export tonic_reflection for gRPC reflection
506#[cfg(feature = "router-grpc")]
507pub use tonic_reflection;
508/// Re-export tracing for observability
509#[cfg(feature = "otel")]
510pub use tracing;
511/// Re-export tracing_opentelemetry for tracing integration
512#[cfg(feature = "otel-otlp")]
513pub use tracing_opentelemetry;
514/// Re-export tracing_subscriber for log configuration
515#[cfg(feature = "otel-otlp")]
516pub use tracing_subscriber;
517/// Re-export url for URL parsing
518#[cfg(feature = "utils")]
519pub use url;
520
521/// Prelude module for convenient imports
522///
523/// Commonly used imports for AllFrame applications
524pub mod prelude {
525 /// Re-export cache utilities
526 pub use crate::cache::{Cache, CacheConfig, CacheKey, MemoryCache};
527 /// Re-export DI utilities
528 #[cfg(feature = "di")]
529 pub use crate::di::{
530 AsyncInit, AsyncInitWith, ContainerBuilder, DependencyError, DependencyRegistry, FromEnv,
531 Provider, Scope,
532 };
533 /// Re-export gRPC server utilities
534 #[cfg(feature = "router-grpc")]
535 pub use crate::grpc::{GrpcServer, GrpcServerBuilder, GrpcServerError, TlsConfig};
536 /// Re-export health check utilities
537 #[cfg(feature = "health")]
538 pub use crate::health::{
539 Dependency, DependencyStatus, HealthCheck, HealthReport, HealthServer, OverallStatus,
540 SimpleHealthCheck,
541 };
542 pub use crate::router::{
543 GraphQLAdapter, GrpcAdapter, GrpcRequest, GrpcStatus, Method, ProtocolAdapter, RestAdapter,
544 RestRequest, RestResponse, RouteMetadata, Router, State, ToJsonSchema,
545 };
546 #[cfg(feature = "router")]
547 pub use crate::router::{GraphQLConfig, GrpcConfig, RestConfig, RouterConfig, ServerConfig};
548 /// Re-export shutdown utilities
549 pub use crate::shutdown::{
550 GracefulShutdown, GracefulShutdownExt, ShutdownAwareTaskSpawner, ShutdownSignal,
551 ShutdownToken,
552 };
553 /// Re-export GrpcError for convenient error handling
554 #[cfg(feature = "router-grpc")]
555 pub use crate::GrpcError;
556}
557
558#[cfg(test)]
559mod tests {
560 #[test]
561 fn test_allframe_core_exists() {
562 // This test verifies the crate compiles
563 assert!(true);
564 }
565}