# Decision Execution Engine Loop

```mermaid
flowchart TD
    subgraph ENGINE["Decision Execution Engine\nservices/trading/engine.py"]
        direction TB
        TASKS["5 Concurrent Async Tasks"]
        T1["_decision_loop()\n60s polling interval"]
        T2["_risk_threshold_monitor()"]
        T3["_performance_loop()"]
        T4["_risk_tier_scheduler()"]
        T5["_rebalance_scheduler()"]
        TASKS --> T1 & T2 & T3 & T4 & T5
    end

    T1 --> POLL["Poll recommendations table\naction IN (act, defer)\nmode IN (simulation_eligible, production_eligible)\ngenerated_at > NOW() − 2h"]

    POLL --> EVAL["evaluate_recommendation()"]

    EVAL --> CHK_A

    subgraph PRETRADE["Pre-Execution Check Sequence\n(first failure short-circuits)"]
        direction TB
        CHK_A["a. Circuit Breaker active?\nservices/trading/circuit_breaker.py\nTriggers: daily_loss, single_commitment, volatility"]
        CHK_B["b. Execution Window?\nis_within_execution_window()"]
        CHK_C["c. Confidence Gate\nconfidence ≥ risk_tier.min_confidence"]
        CHK_D["d. Deduplication\nRec ID in processed set?\nRedis: app:dedupe:execution:*"]
        CHK_E["e. Declining Commitments\n> 50% commitments down > 2%"]
        CHK_F["f. Max Open Commitments\nopen_count ≥ max (default 10)"]

        CHK_A -->|"pass"| CHK_B
        CHK_B -->|"pass"| CHK_C
        CHK_C -->|"pass"| CHK_D
        CHK_D -->|"pass"| CHK_E
        CHK_E -->|"pass"| CHK_F
    end

    CHK_A & CHK_B & CHK_C & CHK_D & CHK_E & CHK_F -->|"fail"| SKIP["ExecutionDecision\ndecision = skip\n+ skip_reason"]

    CHK_F -->|"pass"| SIZER

    subgraph SIZER["Commitment Sizing\nservices/trading/position_sizer.py"]
        direction TB
        SZ1["Base sizing\nrisk_tier.max_commitment_pct × 0.5\n× (confidence / min_confidence)"]
        SZ2["Correlation reduction\nweighted avg corr > 0.8 → reject\n> 0.5 → proportional reduction"]
        SZ3["Sector exposure\ncap at risk_tier.max_sector_pct"]
        SZ4["Diversification bonus\n1.2× for new sector (< 3 sectors)"]
        SZ5["Event proximity\n≤ 1 day → reject\n≤ 3 days → 50% reduction"]
        SZ6["Absolute commitment cap"]
        SZ7["Pool exposure check\nmax_pool_exposure × active_pool"]
        SZ8["Share rounding\nfloor(dollar / price)"]

        SZ1 --> SZ2 --> SZ3 --> SZ4 --> SZ5 --> SZ6 --> SZ7 --> SZ8
    end

    SIZER -->|"rejected"| SKIP
    SIZER -->|"approved"| ACT["ExecutionDecision\ndecision = act\nshares, dollar amount"]

    ACT --> PERSIST_TD["Persist to\nexecution_decisions"]

    ACT --> ORDER["Build execution request\n{entity, action, side,\nquantity, request_type}"]

    ORDER -->|"rpush"| Q_BROKER["app:queue:execution_orders"]

    Q_BROKER --> BROKER["Execution Adapter\nexternal execution API (simulation)\nservices/adapters/broker_adapter.py"]

    BROKER --> AUDIT

    subgraph AUDIT["Audit Trail — PostgreSQL"]
        AU1["execution_requests"]
        AU2["commitments"]
        AU3["pool_snapshots"]
    end

    subgraph CB_DETAIL["Circuit Breaker Detail\nservices/trading/circuit_breaker.py"]
        CB1["daily_loss\npool loss > 5%\ncooldown: volatility_pause_hours"]
        CB2["single_commitment\ncommitment loss > 15%\ncooldown: entity_cooldown_hours (48h)"]
        CB3["volatility\n≥ 3 risk thresholds in 30min\ncooldown: volatility_pause_hours (2h)"]
        CB4["Redis state\napp:execution:circuit_breaker:*"]
    end

    subgraph RESERVE["Reserve Pool\nservices/trading/reserve_pool.py"]
        RP1["Profit siphoning: 20%"]
        RP2["High-water rebalance: 30%"]
        RP3["Emergency liquidation"]
        RP4["reserve_pool_ledger"]
    end

    subgraph RISK_TIER["Risk Tier Auto-Adjustment\nservices/trading/risk_tier_controller.py"]
        RT1["Evaluate: risk-adjusted return ratio,\npeak-to-trough decline, success rate"]
        RT2["conservative → moderate → aggressive"]
        RT3["risk_tier_history"]
    end
```
