Restore approved state (tree of 4effcc7 "Added LICENSE")

Roll the working tree back to the last approved shape, before the post-LICENSE span that false-greened the AFI parity matrix with symbol-presence probes and smuggled an unauthorized SQLAlchemy dependency into FastAPI's Shapes binding.

Forward commit, not a history rewrite — the six commits since 4effcc7 stay in the log as the record of what happened.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-06-04 14:59:53 -04:00
parent adcc027894
commit ae684a36cb
126 changed files with 1711 additions and 13265 deletions

View File

@@ -1,80 +1,58 @@
//! Mizan axum HTTP adapter — typed RPC over `mizan-core`'s function registry,
//! riding the shared AFI-common logic (auth/cache/invalidation/SSR/manifest).
//! Mizan axum HTTP adapter — typed RPC over `mizan-core`'s function registry.
//!
//! Usage:
//! ```ignore
//! use axum::Router;
//! use mizan_axum::{router, MizanState};
//! use mizan_axum::router;
//!
//! #[tokio::main]
//! async fn main() {
//! let state = MizanState::builder()
//! .app_state(MyState { /* ... */ })
//! .build();
//! let app = Router::new().nest("/api/mizan", router(state));
//! let app = Router::new().nest("/api/mizan", router());
//! let listener = tokio::net::TcpListener::bind("127.0.0.1:8000").await.unwrap();
//! axum::serve(listener, app).await.unwrap();
//! }
//! ```
//!
//! Exposed endpoints (mirroring `mizan-fastapi` / `mizan-django`):
//! * `GET /session/` — session-init probe (placeholder CSRF token)
//! * `POST /call/` — RPC dispatch (JSON or multipart) + invalidate
//! * `GET /ctx/:name/` — bundled context fetch (origin-cached)
//! * `GET /ws/` — WebSocket RPC transport (`websocket=` fns)
//! * `GET /manifest/` — edge manifest (contexts/render_strategy/mutations)
//! * `GET /psr/:context/` — per-context PSR descriptor (render_strategy)
//! * `GET /shape/:fn/` — typed query projection (Shapes)
//! * `POST /ssr/` — server-side render via the Bun worker
//! * `POST /form/:name/{schema,validate,submit}/` — forms binding
//! * `GET /session/` — session-init probe (placeholder CSRF token)
//! * `POST /call/` — RPC dispatch with invalidate+merge response
//! * `GET /ctx/:name/` — bundled context fetch
mod errors;
mod forms;
mod handlers;
mod ssr;
mod state;
mod ws;
pub use errors::ApiError;
pub use handlers::{context_fetch, function_call, session_init, CallBody, CallResponse};
pub use ssr::{ssr_render, SsrRequest};
pub use state::{AppStateAny, MizanState, MizanStateBuilder};
pub use handlers::{
context_fetch, function_call, session_init, AppStateAny, CallBody, CallResponse,
};
use axum::routing::{get, post};
use axum::Router;
use std::any::Any;
use std::sync::Arc;
/// Build the Mizan router with a fully-configured [`MizanState`] (app state +
/// auth + cache + optional SSR worker). Mount under a prefix:
/// `Router::new().nest("/api/mizan", router(state))`.
pub fn router(state: Arc<MizanState>) -> Router {
/// Build the Mizan router with user-supplied app state. The state is
/// type-erased into an `Arc<dyn Any + Send + Sync>` and threaded into every
/// dispatch via `RequestHandle`. Handlers downcast to their concrete state
/// type.
///
/// Mount under a prefix:
/// `Router::new().nest("/api/mizan", router(my_state))`.
pub fn router<S>(state: S) -> Router
where
S: Any + Send + Sync + 'static,
{
let state: AppStateAny = Arc::new(state);
Router::new()
.route("/session/", get(handlers::session_init))
.route("/call/", post(handlers::function_call))
.route("/ctx/:context_name/", get(handlers::context_fetch))
.route("/ws/", get(ws::ws_handler))
.route("/manifest/", get(handlers::edge_manifest))
.route("/psr/:context_name/", get(handlers::psr_descriptor))
.route("/shape/:fn_name/", get(handlers::shape_projection))
.route("/ssr/", post(ssr::ssr_render))
.route("/form/:form_name/schema/", post(forms::form_schema))
.route("/form/:form_name/validate/", post(forms::form_validate))
.route("/form/:form_name/submit/", post(forms::form_submit))
.with_state(state)
}
/// Router variant for the common case of just an app state, no auth/cache.
pub fn router_with_state<S>(app_state: S) -> Router
where
S: Any + Send + Sync + 'static,
{
router(MizanState::builder().app_state(app_state).build())
}
/// Router variant for callers that have no app state to thread — the dispatch
/// path receives a unit-typed handle. Used by the AFI fixture and stateless
/// test apps.
/// Router variant for callers that have no app state to thread — the
/// dispatch path receives a unit-typed handle. Used by the AFI fixture
/// and other stateless test apps.
pub fn router_stateless() -> Router {
router(MizanState::builder().build())
router(())
}