Skip to main content

Policy Behavior

Compliance Policy Configuration

The compliance controls check specific headers or text that a regulation cares about. This page documents the two controls that have no page of their own, gdpr-compliance and eu-ai-act, and points to the others.

A configured control, or a coverage report, does not make you compliant with a regulation. Each control does one narrow check. Test that check.

TaskStart here
Require a consent marker that your application setsgdpr-compliance
Require a verified identity and MFA assuranceCJIS Mode
Find health identifiersHIPAA PHI Detector
Block phrases in model answersFinancial Compliance, Healthcare Compliance, or Legal Privilege
List your controls against EU AI Act articleseu-ai-act (reporting only)

Syntax​

This file blocks every request without a non-empty consent header. Save it as policy-config.yaml in a new directory:

policy-config.yaml
pack:
  name: consent-marker-test
  version: 1.0.0
  enabled: true
policies:
  chain:
    - gdpr-compliance
policy:
  gdpr-compliance:
    consent_required: true
    consent_header: X-User-Consent-Token
testing:
  suites:
    - name: consent-marker
      cases:
        - name: missing-marker
          input:
            messages:
              - role: user
                content: Hello
          expected:
            verdict: block
            reason_code: gdpr.consent_missing
        - name: present-marker
          input:
            headers:
              X-User-Consent-Token: docs-test
            messages:
              - role: user
                content: Hello
          expected:
            verdict: allow
            reason_code: ok
verdictan policy lint --file policy-config.yaml
verdictan policy test --json

Both cases pass: the request without the header is blocked, and the one with it is allowed. The control checks only that the header has a value. It does not validate consent, call a consent service, or check a signature. Your trusted application must validate consent before it sets the header.

Fields​

gdpr-compliance block​

An input check that blocks a request whose consent header is missing or empty.

FieldTypeRuntime defaultDescription
consent_requiredbooleanfalseBlocks a request without the consent header
consent_headerstringX-User-Consent-TokenHeader name. Case does not matter.
data_categoriesarray of strings[]Categories recorded in the policy details

The schema shows different defaults (consent_required: true, consent_header: x-consent-token, and three categories). Set the fields explicitly. A blocked request has reason code gdpr.consent_missing.

The control records an X-Erasure-Request header in the policy details, but it does not process the erasure. Lint rejects the removed fields consent_verification_endpoint, retention_days, and erasure_webhook.

eu-ai-act block​

A reporting-only control. POST /verdictan/compliance/report reads this block and reports which of your configured controls relate to the requested EU AI Act articles.

FieldTypeDefaultDescription
risk_classminimal, limited, high, or unacceptablehighRisk class in the report
articlesarray of integers[9, 10, 11, 12, 13, 14, 15]Articles that the report evaluates
actionblock, warn, or auditwarnAccepted by the schema. Has no effect.

Keep eu-ai-act out of policies.chain. There, it blocks every request with reason code policy.reporting_only. Put the executable controls for Articles 9 to 15 in the chain instead, such as prompt-injection, gdpr-compliance, pii-detector, audit-logger, human-oversight, and quality-scorer. The report fields fully_covered and gap_count describe your control inventory, not legal compliance or correct operation.

cjis-mode block​

See CJIS Mode for its identity requirements, accepted proof, and fields. Identity headers from the caller do not authorize access.

Output compliance controls​

These run on the complete response and have their own pages: MNPI Filter, Financial Compliance, Healthcare Compliance, Legal Privilege, and UPL Filter. Send requests through them with stream: false.

Examples​

After the local test passes, add the control to the configuration of your test agent. Send the same request with and without X-User-Consent-Token, with normal gateway authentication. The runtime event for the request without the header shows gdpr.consent_missing.

EU AI Act report with executable controls​

Inside policy-config.yaml
policies:
  chain:
    - audit-logger
    - prompt-injection
    - gdpr-compliance
    - pii-detector
    - quality-scorer
    - human-oversight

policy:
  eu-ai-act:
    risk_class: high
    articles: [9, 10, 12, 13, 14, 15]

human-oversight escalates every response it receives. Use it only on a route where every response needs review.

CJIS access rules​

Follow CJIS Mode. Test with two identities: one with enough assurance and one without.

Finance output chain​

Use MNPI Filter for private-information phrases and Financial Compliance for output phrases and disclaimers. Test a synthetic matching phrase and a normal answer with stream: false.

Healthcare output chain​

Test HIPAA PHI Detector and Healthcare Compliance each on their own first, then together. Check that the returned text is redacted. An example configuration is not a certification.

Legal Privilege blocks configured markers. UPL Filter blocks phrases or adds a disclaimer. Neither replaces legal review.

Export control input chain​

ITAR/EAR Filter, Entity List Filter, and Dual-Use Filter match the rules that you configure. Test with synthetic terms from your list and harmless near-matches. None of them supplies an official screening list.

Limits and failure behavior​

  • A policy.<kind> block runs only when the control is also in policies.chain, except for eu-ai-act, which must never be there.
  • gdpr-compliance checks only for a non-empty header. It does not validate the token, process erasure requests, or schedule deletion.
  • gdpr-compliance and cjis-mode check input. financial-compliance, healthcare-compliance, legal-privilege, upl-filter, and mnpi-filter check the buffered output.
  • To apply an input control to some paths, models, or tenants only, use conditional chain entries. Output controls ignore when, so use routes for them.

Next steps​