Feature · Compliance

Compliance, expressed as code.

Six Rego policy packages cover access, suitability, restricted lists, AML, AI actions, and data access. Compliance officers edit rules in a Monaco editor, run tests, and deploy through the same CI as the rest of the platform.

What it does

Policies are first-class artifacts.

The compliance context owns rule definitions, evaluation, and case lifecycle. Rules are not buried in service code; they live in infra/opa/policies/ as Rego packages, are tested by opa test in CI, and are versioned through the same release pipeline as the application code. Six packages ship: access (RBAC), suitability, restricted_list, aml, ai_actions, and data_access.

Cases are structured records of breaches and reviews. Each case has a severity (low / medium / high / breach), a state (open / under_review / pending_action / closed), and a typed payload with the original triggering event, the policy decision, and the supporting evidence. Cases participate in the caseManagementWorkflow in Temporal, which runs SLA timers and auto-escalates up to three times before paging a human.

Restricted-list management is per-tenant and per-jurisdiction. Lists are versioned, with effective-from / effective-to ranges; OPA queries the active version at decision time. Adding an instrument is a UI action that produces a Git-tracked Rego data file via the API — every change has an author and an audit event.

The compliance console (web-compliance) is a dedicated Next.js application: audit explorer, case queue with assignment, and the embedded Monaco-based Rego rule editor. Officers run opa eval from the editor against a sample input before deploying; the deploy runs the same way the engineering team’s Helm rollout does.

The six policies

What ships in the box.

PackageConcernInputsDecisions
accessBase RBAC, scope gatessubject role, action, resource typeallow / deny
suitabilityRisk tolerance vs instrument riskclient risk tier, instrument risk class, account allocationallow / warn / deny + reason
restricted_listSymbol-level blockssymbol, tenant + jurisdiction listsallow / deny + match
amlCash, structuring, jurisdictionamount, history, residency, counterpartyallow / warn / deny + flag
ai_actionsGate AI mutationsactor role, AI use case, target resourceallow / require_approval / deny
data_accessRAG chunk filteringsubject relationships, chunk metadataallow / deny per chunk
Sample policy

Suitability, in code.

modir.suitability
package modir.suitability

import future.keywords.if
import future.keywords.in

# Allow: instrument risk does not exceed client tolerance.
allow if {
  input.instrument.risk_class <= input.client.risk_tolerance_score
}

# Warn: one band higher than tolerance.
warn[reason] if {
  input.instrument.risk_class == input.client.risk_tolerance_score + 1
  reason := "instrument is one risk band above client tolerance"
}

# Deny: more than one band higher.
deny[reason] if {
  diff := input.instrument.risk_class - input.client.risk_tolerance_score
  diff > 1
  reason := sprintf("instrument is %d bands above client tolerance", [diff])
}

# Concentration override: any single position must remain <= 10%.
deny[reason] if {
  pct := (input.position.notional + input.order.notional) / input.account.market_value
  pct > 0.10
  reason := sprintf("post-trade concentration would be %.1f%% (max 10%%)", [pct * 100])
}
Cases

Five-stage lifecycle. SLA-tracked.

  1. 1 · Open

    Case created automatically (policy breach) or manually (analyst report). Severity assigned by triggering event.

  2. 2 · Triaged

    Compliance lead reviews; assigns owner; sets target SLA based on severity. AI triage suggests a category.

  3. 3 · Under review

    Owner gathers evidence, links related cases, requests information from advisor. Every action audited.

  4. 4 · Pending action

    Outcome decided (no action / advisory / restitution / escalation). Action assigned to operations or advisor.

  5. 5 · Closed

    Closure note required. Case becomes part of audit evidence; included in regulator-ready exports.

Capabilities

Six things this context owns.

Rego rule editor

Monaco-based editor in the compliance console. Live test runs against sample inputs.

Restricted lists

Per-tenant, per-jurisdiction; versioned with effective ranges.

Case queue

Auto-assigned by team policy; SLA timers; up-to-three escalations.

Audit explorer

Filter by tenant, actor, action, time. Open evidence files in-place.

Signed exports

Regulator-ready, byte-reproducible, with a verification script.

Periodic reviews

periodicReviewWorkflow daily; suitabilityReviewWorkflow annual.

Compliance case
Compliance walkthrough

Run your hardest case through Modir.

Bring a recent breach. We will reproduce it as a case in Modir, with policies, evidence, and signed export.