Skip to main content

Governed LLM client for regulated AI deployments — drop-in replacement for openai.OpenAI()

Project description

evecore — Governed LLM for Regulated AI

Drop-in replacement for openai.OpenAI() that enforces governance policy before and after every model call, writes a signed audit record, and raises GovernanceVetoError when a rule is violated.

Install

pip install evecore                    # core only (no provider deps)
pip install "evecore[openai]"          # + OpenAI provider
pip install "evecore[anthropic]"       # + Anthropic provider
pip install "evecore[proxy]"           # + OpenAI-compatible proxy server
pip install "evecore[all]"             # everything

Quickstart

from evecore import GovernedLLM

client = GovernedLLM(policy="financial-v1")

response = client.chat.completions.create(
    model="gpt-4o-mini",
    messages=[{"role": "user", "content": "What is the current prime rate?"}]
)
print(response.choices[0].message.content)
print(response.governance.certificate_id)   # audit trail reference

Or with the simple interface:

result = client.complete("What is the current prime rate?")
print(result)

Handling vetoes

from evecore import GovernedLLM
from evecore.exceptions import GovernanceVetoError

client = GovernedLLM(policy="financial-v1")

try:
    response = client.complete("Approve loan for $500,000")
except GovernanceVetoError as e:
    print(e.verdict)          # REQUIRE_HUMAN_REVIEW
    print(e.rule_id)          # fin.high_value_approval
    print(e.reason)           # Amount meets or exceeds $250,000 threshold
    print(e.certificate_id)   # gov-a1b2c3d4e5f6...  (audit trail reference)

OpenAI-compatible proxy

The proxy lets existing applications get governance with one line change:

# Start the proxy
python -m evecore.proxy --policy financial-v1 --port 4141
# Before
from openai import OpenAI
client = OpenAI(api_key="sk-...")

# After — one line changed, everything else stays identical
from openai import OpenAI
client = OpenAI(base_url="http://localhost:4141/v1", api_key="any")

The proxy intercepts every request, runs governance, and returns blocked responses in the same OpenAI format so your existing error handling still works.

Built-in policies

Policy ID Domain Key rules
financial-v1 Banking / lending / insurance PII blocking, high-value approval gates, investment advice warnings, 7-year audit retention
healthcare-v1 Healthcare / HIPAA PHI blocking, no-diagnosis enforcement, emergency escalation
general-v1 General purpose Prompt injection blocking, PII leak warnings

Custom policies

from evecore import GovernedLLM
from evecore._policy import register_policy

register_policy({
    "id": "my-org-policy",
    "name": "My Org Policy",
    "version": "1.0.0",
    "input_rules": [
        {
            "id": "org.block_competitor",
            "action": "BLOCK",
            "reason": "Competitor mention blocked",
            "priority": 100,
            "keywords": ["competitor_name"]
        },
        {
            "id": "org.flag_large_deal",
            "action": "REQUIRE_HUMAN_REVIEW",
            "reason": "Deal value requires human approval",
            "priority": 80,
            "triggers": ["approve", "sign", "commit"],
            "amount_threshold": 50000.0,
            "amount_pattern": r"\$([0-9,]+(?:\.\d{2})?)"
        }
    ],
    "output_rules": [
        {
            "id": "org.no_guarantees",
            "action": "WARN",
            "reason": "Response contains guarantee language",
            "priority": 60,
            "patterns": [r"\b(guarantee|guaranteed|we promise)\b"]
        }
    ]
})

client = GovernedLLM(policy="my-org-policy")

Or load from a JSON file:

client = GovernedLLM(policy="/path/to/my-policy.json")

Rule actions

Action Behavior
BLOCK Raises GovernanceVetoError(verdict="BLOCKED") — request/response is stopped
REQUIRE_HUMAN_REVIEW Raises GovernanceVetoError(verdict="REQUIRE_HUMAN_REVIEW") by default
ESCALATE Raises GovernanceVetoError(verdict="ESCALATE") by default
WARN Logs the warning; execution continues (unless raise_on_warn=True)
ALLOW Rule did not trigger; no action taken

Rule fields

{
    "id": "rule.unique_id",
    "action": "BLOCK | WARN | REQUIRE_HUMAN_REVIEW | ESCALATE",
    "reason": "Human-readable explanation shown in GovernanceVetoError",
    "priority": 100,
    "patterns": ["regex1", "regex2"],
    "keywords": ["keyword1", "keyword2"],
    "triggers": ["trigger_word"],
    "amount_threshold": 250000.0,
    "amount_pattern": "\\$([0-9,]+(?:\\.\\d{2})?)"
}

Higher priority rules are evaluated first. When multiple rules trigger, the highest-priority action wins (BLOCK > ESCALATE > REQUIRE_HUMAN_REVIEW > WARN > ALLOW).

Audit log

Every request produces two signed audit records (input governance + output governance) written to a JSONL file:

data/audit/governed_llm_audit.jsonl   (default location)

Records are HMAC-SHA256 signed and hash-chained — any tampering is detectable. Signing key sourced from EVE_AUDIT_KEY env var (or EVE_JWT_SECRET, or a dev fallback).

Each record includes:

  • event_id, certificate_id, timestamp
  • policy_id, verdict, rule_id, reason
  • prompt_hash, response_hash (SHA-256, privacy-preserving — no raw text stored)
  • model, provider
  • signature (HMAC-SHA256)
  • record_hash, prev_hash (hash chain)

Providers

Provider provider= API key env var
OpenAI "openai" OPENAI_API_KEY
Anthropic "anthropic" ANTHROPIC_API_KEY
Local (Ollama, LM Studio) "local"
Auto-detect "auto" (default) Checks env vars
# Auto-detect from environment
client = GovernedLLM(policy="financial-v1")

# Explicit provider
client = GovernedLLM(policy="financial-v1", provider="anthropic")

# Azure OpenAI or other compatible endpoint
client = GovernedLLM(
    policy="financial-v1",
    provider="openai",
    base_url="https://my-org.openai.azure.com/",
    api_key="azure-key",
)

# Local Ollama
client = GovernedLLM(policy="general-v1", provider="local")

GovernedLLM parameters

Parameter Default Description
policy "general-v1" Policy ID or path to JSON file
provider "auto" LLM provider
api_key None Provider API key (falls back to env vars)
base_url None Override provider base URL
audit_log None Path to audit JSONL file
raise_on_block True Raise GovernanceVetoError on BLOCK/ESCALATE/REQUIRE_HUMAN_REVIEW
raise_on_warn False Raise GovernanceVetoError on WARN

Proxy options

python -m evecore.proxy --help

  --policy       financial-v1, healthcare-v1, general-v1, or /path/to/policy.json
  --port         Port to listen on (default: 4141)
  --host         Host to bind (default: 127.0.0.1)
  --upstream     Upstream provider URL (default: https://api.openai.com)
  --api-key      Provider API key (falls back to OPENAI_API_KEY)
  --audit-log    Path to audit JSONL file
  --log-level    DEBUG | INFO | WARNING | ERROR

Running tests

cd sdks/evecore
pip install -e ".[dev]"
pytest tests/ -v

Tests are fully offline — all provider calls are mocked. No API keys required.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

evecore-0.1.1.tar.gz (49.6 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

evecore-0.1.1-py3-none-any.whl (41.8 kB view details)

Uploaded Python 3

File details

Details for the file evecore-0.1.1.tar.gz.

File metadata

  • Download URL: evecore-0.1.1.tar.gz
  • Upload date:
  • Size: 49.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.8

File hashes

Hashes for evecore-0.1.1.tar.gz
Algorithm Hash digest
SHA256 3b5788509032c488dd0873911f35959ed4c80f30597b4cefbb883d086afc6c39
MD5 eb33150e10793601b996bbab3d45e262
BLAKE2b-256 f7c27b516ffe13376210bb4bedd055094e3fe1944763b11b5ac962e1539ee806

See more details on using hashes here.

File details

Details for the file evecore-0.1.1-py3-none-any.whl.

File metadata

  • Download URL: evecore-0.1.1-py3-none-any.whl
  • Upload date:
  • Size: 41.8 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.8

File hashes

Hashes for evecore-0.1.1-py3-none-any.whl
Algorithm Hash digest
SHA256 4e8287d966e9226bf13b83080bea2f0cb7f5a360267ab6888070625cb94b50f8
MD5 3dd3a289c5edacbd8abb706fa6b88a4b
BLAKE2b-256 dab38cbe2f1b45eb4bc7a37cad6d59a617621b0e69bd8b113676fff59b15e7bb

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page