- Documentation
- /
- Rilr
- /
- Phase 2 — Runtime Engine Scope
Phase 2 — Runtime Engine Scope
Phase 1 (built) renders the 16-model schema as an AI-Safe CRUD register:
investigations, regulator requests decomposed into requirements, evidence with
privilege review, response drafts, submissions and production items — browsable,
with a dashboard. But the states are static: the seed shows a request already
received, a submission already issued. Nothing is computed or transitioned
by the system.
Phase 2 is the runtime that makes it live — computing the effective deadlines, enforcing the state machines, running the deadline scans and applying the privilege and submission rules the pack specifies. Same shape as the (built, cluster-proven) orchestrator engine, but single-app.
Everything below is drawn from the pack's workflows.yaml, rules.yaml, the DSL
computed/event blocks and the InvestigationDashboard. It is a scope, not a
design.
A. Computed-field engine
The DSL computed fields are seeded statically today; Phase 2 recomputes them:
| Field | Rule |
|---|---|
RegulatoryRequest.effective_due_at |
coalesce(extended_due_at, due_at) |
RegulatoryRequest.days_remaining |
business-days between now and effective_due_at |
RegulatoryRequest.is_overdue |
effective_due_at < now() AND status ∉ {submitted, acknowledged, closed} |
Requirement.is_overdue |
due_at < now() AND status ∉ {submitted, waived, closed} |
The effective due date (extension overrides base) is the key subtlety — every deadline calculation must use it.
Decisions: compute-on-read vs recompute-on-tick.
B. State machines & guarded actions
The pack defines three workflows. Today a user free-edits status; Phase 2 exposes
each transition as a guarded action.
| Workflow | Notable transitions & guards |
|---|---|
| investigation (draft→active→stayed→closed→archived) | open_investigation requires lead_legal_counsel + regulator_id; close guarded by all requests closed |
| regulatory_request (received→triaged→assigned→collecting→drafting→legal_review→awaiting_approval→submitted→acknowledged→closed) | *→overdue on deadline missed (exception transition) |
| requirement (open→in_progress→evidence_complete→response_drafted→reviewed→approved→submitted→closed) | drives the response lifecycle |
Decisions: UI buttons vs API; role → PIN/RBAC; the request pipeline is long — which steps are explicit actions vs derived.
C. Deadline engine (scheduled scans)
A background tick that watches the effective deadlines — "notices never lapse":
- Tiered warnings at 20 / 10 / 5 / 2 / 1 days before
effective_due_at(rules.yaml → deadlines.warn_days). - Overdue — past
effective_due_atand not submitted → flip request/requirement tooverdueand escalate after 4 hours. - Submission receipt follow-up — chase an issued submission with no receipt
after 24 hours (
submissions.receipt_followup_hours).
Decisions: cadence; business-calendar (AU_QLD) business-day math (pack ships
business_calendars.yaml); exception dedupe.
D. Rules / cross-record automation
From rules.yaml (this app's rules are heavily privilege- and evidence-centric):
- Privilege — require legal review when evidence is
potentially_privileged/privileged; prohibit production when
privilegedorwithheld; require a reason when withheld. - Confidentiality —
highly_confidentialexport requires approval; external share requires legal approval;regulator_onlyrestricts internal distribution. - Evidence integrity —
sha256required for documents/email-exports/data; a produced item is immutable; custodian required. - Submission gate —
issuerequiresapproved_by+approved_at+ at least one requirement; generate a production manifest on issue. - Exception raising — auto-raise on overdue request/requirement, missing owner, missing privilege review, failed submission.
- DSL events —
request.received(triage-required),requirement.overdue(→governance.exception.raise),submission.issued(→ receipt-awaiting).
Decisions: event bus (in-app vs orchestrator); enforce prohibitions hard vs flag; manifest format.
E. Executive dashboard & KPIs
The DSL InvestigationDashboard metrics, wired via the repo KPI framework
(kpi_engine.py + kpis.py): active investigations; overdue requests; open
requirements; potentially-privileged evidence; open exceptions.
How it would be built
- A per-app engine module (mirror
server/lib/orchestrator_engine/): compute pass (A), deadline scanner (C), guarded actions (B), rules/privilege evaluator (D). Opt-in env flag, single worker. - KPIs (E) via the existing framework — quick, independent win.
- Business-calendar underpins the effective-due-date math.
- Tests per workstream (
test_orchestrator_flows.pyis the template).
Suggested sequencing
- KPIs / dashboard (E) — visible, no engine.
- Computed fields (A) — accurate
effective_due_at/is_overdue. - Deadline engine (C) — tiered warnings + overdue escalation.
- Privilege & submission rules (D) — the compliance guardrails (this domain's highest-value automation).
- State machines + guards (B) — governed transitions across the long pipeline.
Each slice is independently shippable and demoable. The orchestrator (built and run live this session) is the working template for the engine, scheduler and tests.