Enterprise API¶
Multi-tenant scoring isolation, declarative policy rules, and audit logging. These modules are lazy-loaded — importing director_ai does not pull them in until accessed.
PII Redaction¶
PIIRedactor masks sensitive values before prompts, responses, or audit
payloads leave the tenant boundary. The default path is dependency-free regex
PII detection with the Rust scanner used automatically when the
backfire-kernel wheel is present. Presidio can still be added as an optional
detector for named-entity enrichment in regulated deployments; the committed
PII benchmark records Director and Presidio span-level precision/recall on the
same labelled corpus so operators can compare detector behavior before enabling
the optional stack.
from director_ai.enterprise import PIIRedactor
redactor = PIIRedactor()
report = redactor.redact_with_report(
"Email jane.doe@example.com, call +1 415 555 0101, card 4111-1111-1111-1111."
)
assert report.redacted_text == "Email [EMAIL], call [PHONE], card [CARD]."
assert report.category_counts == {"card": 1, "email": 1, "phone": 1}
audit_payload = report.to_dict()
assert audit_payload["privacy"] == {
"payload_classification": "tenant_safe",
"raw_payload_included": False,
}
The structured report exposes detector name, category, offsets, replacement
token, score, and category counts. It never serialises the raw matched value,
so the report can be stored in tenant-safe audit metadata. Stable replacement
tokens are [EMAIL], [PHONE], [CARD], [SSN], [IBAN], [IPV4],
[PASSPORT], [PERSON], and [PHI]; unknown detector categories fall back to
an uppercase bracketed token.
Content Moderation Wrapper¶
ContentModerator is the commercial wrapper for moderation enforcement. It
combines PII redaction with toxicity detection and returns one decision:
allow, redact, warn, or block. The default deployment path redacts PII
with the dependency-free detector stack and blocks keyword toxicity; operators
can inject stronger model-backed detectors or switch toxicity handling to
warn-only mode.
from director_ai.enterprise import ContentModerator, ModerationAction
moderator = ContentModerator(toxicity_action=ModerationAction.BLOCK)
result = moderator.moderate("Email jane@example.com, then go kill yourself.")
assert result.blocked is True
assert result.safe_text == "Email [EMAIL], then go kill yourself."
audit_payload = result.to_dict()
assert audit_payload["privacy"] == {
"payload_classification": "tenant_safe",
"raw_input_included": False,
}
The wrapper's metadata contains detector names, categories, offsets, actions,
scores, replacement tokens, and aggregate category counts. It does not serialise
raw matched values. Use the lower-level RegexPIIDetector,
PresidioPIIDetector, KeywordToxicityDetector, or DetoxifyDetector only
when building a custom moderation policy.
Custom Rules DSL¶
CustomRuleset loads strict operator-owned JSON or YAML policy documents and
compiles them into the existing runtime Policy engine. Unknown fields,
duplicate rule identifiers, invalid regex patterns, invalid actions, invalid
thresholds, and non-positive numeric limits are rejected before a policy can be
registered.
version: director.rules.v1
name: tenant-alpha.safety
rules:
- id: no-passwords
kind: forbidden
value: share passwords
name: No password disclosure
action: block
source: security-baseline.md#L10
- id: ticket-redaction
kind: pattern
value: "TICKET-\\d{6}"
name: Ticket reference
action: redact
- id: length-cap
kind: max_length
value: 800
- id: citations
kind: required_citations
value: 2
from director_ai.enterprise import CustomRuleset
ruleset = CustomRuleset.from_file("tenant-alpha.rules.yaml")
policy = ruleset.to_policy()
violations = policy.check("share passwords in TICKET-123456")
assert {violation.rule for violation in violations} == {
"forbidden",
"pattern:Ticket reference",
"required_citations",
}
Supported rule kinds are forbidden, pattern, max_length, and
required_citations; supported actions are block, warn, and redact.
CustomRuleset.to_policy_bundle(version=...) returns the immutable compiler
bundle when operators need deterministic registry hot-swap behaviour.
TenantRouter¶
Isolates scoring configuration per tenant. Each tenant gets its own CoherenceScorer instance with independent thresholds, knowledge bases, and caching.
from director_ai.enterprise import TenantRouter
router = TenantRouter()
# Tenants are provisioned implicitly: get_scorer returns a per-tenant
# CoherenceScorer, created on first use with the given threshold.
scorer_a = router.get_scorer("tenant_a", threshold=0.7, use_nli=True)
scorer_b = router.get_scorer("tenant_b", threshold=0.5, use_nli=False)
approved, score = scorer_a.review(query, response)
Policy¶
Declarative rule engine for content filtering. Runs before coherence scoring.
from director_ai.enterprise import Policy
policy = Policy(
forbidden=[r"(buy|sell|short)\s+(stock|shares)"],
patterns=[{"name": "ssn", "regex": r"\b(SSN|social security)\b", "action": "block"}],
max_length=4000,
)
violations = policy.check(response_text)
for violation in violations:
print(f"Policy violation: {violation.rule} — {violation.detail}")
AuditLogger¶
SQLite-backed audit logging for compliance. Records every review decision with full context.
from director_ai.enterprise import AuditLogger
logger = AuditLogger(path="/var/log/director-ai/audit.db")
logger.log_review(query, response, approved=True, score=0.91, tenant_id="tenant_a")
# Verify the tamper-evident hash chain
ok, error = logger.verify_chain()
assert ok, error
License Matrix¶
The enterprise module is part of the Advanced & Labs tier, licensed under BUSL-1.1 (source-available).
| Use Case | License Required |
|---|---|
| Evaluation / prototyping | BUSL-1.1 (free) |
| Non-production internal use | BUSL-1.1 (free) |
| Production deployment | Commercial license |
| Hosted / SaaS product | Commercial license |
The Apache-2.0 core, by contrast, is free in production. See Licensing for pricing and terms.
Full API¶
director_ai.core.tenant.TenantRouter
¶
Routes requests to tenant-isolated GroundTruthStores.
Thread-safe: stores are created lazily on first access. Supports per-tenant fine-tuned model selection.
get_store
¶
Get or create an isolated store for this tenant.
add_fact
¶
Add a fact to a specific tenant's store.
remove_tenant
¶
Remove a tenant and all its data. Returns True if existed.
get_vector_store
¶
get_vector_store(tenant_id: str, backend_type: str = 'memory', **kwargs: Any) -> VectorGroundTruthStore
Get or create a tenant-isolated VectorGroundTruthStore.
Supported backend_type values: "memory", "chroma", "pinecone", "qdrant". Extra kwargs are forwarded to the backend constructor.
set_model
¶
set_model(tenant_id: str, model_id: str, model_path: str, balanced_accuracy: float = 0.0, regression_pp: float = 0.0, recommendation: str = '', dataset_hash: str = '') -> ModelVersion
Register a fine-tuned model for a tenant.
activate_model
¶
Activate a specific model version for a tenant. Deactivates others.
rollback_model
¶
Deactivate all models for a tenant (revert to baseline).
get_active_model
¶
Return the active model for a tenant, or None for baseline.
list_models
¶
List all model versions for a tenant.
delete_model
¶
Remove a model version. Cannot delete active models.
get_scorer
¶
Build a CoherenceScorer scoped to this tenant's KB and model.
save_manifest
¶
Save all tenant model metadata to a JSON manifest.
load_manifest
¶
Load tenant model metadata from a JSON manifest. Returns count loaded.
director_ai.core.safety.audit.AuditLogger
¶
AuditLogger(path: str | Path | None = None, logger_name: str = 'DirectorAI.Audit', hmac_secret: str | None = None)
Structured audit logger with file and logging sinks.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
path
|
str | Path | None — JSONL file path. None = logging-only.
|
|
None
|
logger_name
|
str — Python logger name for audit events.
|
|
'DirectorAI.Audit'
|
add_sink
¶
Add an external consumer for audit records (e.g. PostgresAuditSink).
log_review
¶
log_review(query: str, response: str, approved: bool, score: float, h_logical: float = 0.0, h_factual: float = 0.0, policy_violations: list[str] | None = None, tenant_id: str = '', halt_reason: str = '', latency_ms: float = 0.0, kb_snapshot: dict[str, Any] | None = None) -> AuditEntry
Record a review decision.
verify_chain
¶
Re-derive the on-disk hash chain and report the first tampered entry.
Returns (ok, first_bad_index). ok is False when any record's
payload was altered (content hash mismatch), the chain linkage was broken
(a record deleted, reordered, or its prev_hash edited), or a tag fails
(HMAC mismatch — needs the same secret that wrote the log).
first_bad_index is the 0-based line index, None on success.
director_ai.enterprise.redactor.PIIRedactor
¶
PIIRedactor(enabled: bool = True, *, detectors: Sequence[ModerationDetector] | None = None, prefer_rust: bool = True)
Enterprise redaction pipeline for sensitive string values.
redact_with_report
¶
Redact PII and return a tenant-safe structured report.
director_ai.enterprise.redactor.PIIRedactionReport
dataclass
¶
PII redaction result and tenant-safe metadata.
director_ai.enterprise.moderation.ContentModerator
¶
ContentModerator(*, enable_pii: bool = True, toxicity_action: ModerationAction = ModerationAction.BLOCK, toxicity_detectors: Sequence[ModerationDetector] | None = None, prefer_rust: bool = True)
Production wrapper for PII redaction and toxicity moderation.
moderate
¶
Moderate text and return the safe text plus tenant-safe metadata.
director_ai.enterprise.moderation.ContentModerationResult
dataclass
¶
ContentModerationResult(action: ModerationAction, safe_text: str, findings: tuple[ContentModerationFinding, ...])
Result of a content moderation pass.
director_ai.enterprise.rules_dsl.CustomRuleset
¶
Bases: BaseModel
Versioned JSON/YAML ruleset with strict schema validation.