backbone-accounting 0.9.28

GL, journals, ledger, reconciliation (extracted from bersihir)
Documentation
//! Accounting Module Routes
//!
//! Generated by metaphor-schema. Do not edit manually.
//!
//! This module provides route composition with dual pattern support:
//! - Stateless routes: `create_stateless_routes()` -> `Router<()>`
//! - Stateful routes: `create_stateful_routes()` -> `Router<AppState>`

use axum::Router;
use std::sync::Arc;

// Import handlers
use crate::presentation::http::{
    create_account_routes,
    create_account_read_routes,
    create_accounting_post_routes,
    create_accounting_post_read_routes,
    create_cost_center_routes,
    create_cost_center_read_routes,
    create_financial_statement_routes,
    create_financial_statement_read_routes,
    create_fiscal_period_routes,
    create_fiscal_period_read_routes,
    create_journal_routes,
    create_journal_read_routes,
    create_journal_line_routes,
    create_journal_line_read_routes,
    create_ledger_routes,
    create_ledger_read_routes,
    create_reconciliation_routes,
    create_reconciliation_read_routes,
    create_reconciliation_item_routes,
    create_reconciliation_item_read_routes
};

// Import AppState for stateful routes
use crate::handlers::AppState;

// ============================================================
// PATTERN 1: STATELESS ROUTES
// ============================================================

/// Create stateless routes for the Accounting module.
///
/// These routes don't require shared state and are simpler to use.
/// Use this when you only need standard CRUD operations.
///
/// # Example
///
/// ```ignore
/// let module = AccountingModule::builder().with_database(pool).build()?;
/// let routes = create_stateless_routes(&module);
/// let app = Router::new().merge(routes);
/// ```
pub fn create_stateless_routes(module: &crate::AccountingModule) -> Router<()> {
    Router::new()
        .merge(create_account_routes(module.account_service.clone()))
        .merge(create_accounting_post_routes(module.accounting_post_service.clone()))
        .merge(create_cost_center_routes(module.cost_center_service.clone()))
        .merge(create_financial_statement_routes(module.financial_statement_service.clone()))
        .merge(create_fiscal_period_routes(module.fiscal_period_service.clone()))
        .merge(create_journal_routes(module.journal_service.clone()))
        .merge(create_journal_line_routes(module.journal_line_service.clone()))
        .merge(create_ledger_routes(module.ledger_service.clone()))
        .merge(create_reconciliation_routes(module.reconciliation_service.clone()))
        .merge(create_reconciliation_item_routes(module.reconciliation_item_service.clone()))
}

/// Read-only routes for the Accounting module — every entity mounted READ-ONLY (the guarded base).
///
/// The generic `create_stateless_routes` exposes full mutable CRUD with no domain
/// validation; this exposes only reads, so generic mutation can't bypass a write
/// service's invariants. Extend it: `create_readonly_accounting_routes(m).merge(my_validated_writes)`.
pub fn create_readonly_accounting_routes(module: &crate::AccountingModule) -> Router<()> {
    Router::new()
        .merge(create_account_read_routes(module.account_service.clone()))
        .merge(create_accounting_post_read_routes(module.accounting_post_service.clone()))
        .merge(create_cost_center_read_routes(module.cost_center_service.clone()))
        .merge(create_financial_statement_read_routes(module.financial_statement_service.clone()))
        .merge(create_fiscal_period_read_routes(module.fiscal_period_service.clone()))
        .merge(create_journal_read_routes(module.journal_service.clone()))
        .merge(create_journal_line_read_routes(module.journal_line_service.clone()))
        .merge(create_ledger_read_routes(module.ledger_service.clone()))
        .merge(create_reconciliation_read_routes(module.reconciliation_service.clone()))
        .merge(create_reconciliation_item_read_routes(module.reconciliation_item_service.clone()))
}

/// Get all routes (stateless) for the Accounting module.
///
/// This is a convenience function that wraps routes with API versioning.
pub fn get_routes(module: &crate::AccountingModule) -> Router<()> {
    Router::new()
        .nest("/api/v1", create_stateless_routes(module))
}

// ============================================================
// PATTERN 2: STATEFUL ROUTES (WITH APPSTATE)
// ============================================================

/// Create stateful routes for the Accounting module.
///
/// These routes require AppState and support custom handlers
/// that need access to services via dependency injection.
///
/// # Example
///
/// ```ignore
/// let module = AccountingModule::builder().with_database(pool).build()?;
/// let state = AppState::from_module(&module);
/// let routes = create_stateful_routes();
/// let app = Router::new().merge(routes).with_state(state);
/// ```
pub fn create_stateful_routes() -> Router<AppState> {
    Router::new()
        // Add custom handlers here that need AppState
        // .route("/custom", get(custom_handler))
}

/// Create combined routes (stateless CRUD + stateful custom handlers).
///
/// This merges both stateless CRUD routes and stateful custom routes.
pub fn create_combined_routes(module: &crate::AccountingModule) -> Router<AppState> {
    // First create stateless routes
    let crud_routes: Router<()> = create_stateless_routes(module);

    // Convert to stateful by adding state requirement
    // Note: The CRUD routes don't actually use the state,
    // but this allows them to be merged with stateful routes.
    let crud_routes_stateful: Router<AppState> = crud_routes.with_state(()).into();

    // Merge with stateful routes
    Router::new()
        .merge(crud_routes_stateful)
        .merge(create_stateful_routes())
}

/// Get all routes (stateful) for the Accounting module.
///
/// This is a convenience function that wraps routes with API versioning.
pub fn get_routes_with_state(module: &crate::AccountingModule) -> Router<AppState> {
    Router::new()
        .nest("/api/v1", create_combined_routes(module))
}

// ============================================================
// CUSTOM HANDLERS
// ============================================================

// <<< CUSTOM HANDLERS START >>>
// Add custom route handlers here
// Example:
//
// use axum::extract::State;
// use axum::response::IntoResponse;
//
// pub async fn custom_handler(
//     State(state): State<AppState>,
// ) -> impl IntoResponse {
//     // Use state.user_service, etc.
//     "Custom response"
// }
// <<< CUSTOM HANDLERS END >>>