Validate configuration with Rego
This feature is tech preview. Tech preview features may be subject to significant changes before they become GA.
Gateway WAF has two guardrail layers: the admission webhook checks raw SecLang at apply time (structural safety); validation policies check the merged result at reconcile time, catching problems only visible once everything's merged. See Validation and enforcement for the matrix and Rego validation for the input schema.
Prerequisites
- Gateway WAF is enabled. See Enable Gateway WAF.
- Cluster-admin rights to create a
GlobalWAFValidationPolicy(it's cluster-scoped). AWAFValidationPolicyonly needs namespace write access. - Rego rules evaluate against the merged config — see Rego validation for the input schema and worked examples.
Enforce guardrails cluster-wide with GlobalWAFValidationPolicy
GlobalWAFValidationPolicy is cluster-scoped, applying to every namespace or a label-selected subset via namespaceSelector. It carries Rego rules and an enforcementMode: Audit (default) records violations while the filter stays programmed; Enforce blocks programming on a critical violation. warning/info violations are always recorded.
-
Write the policy with Rego rules and an
enforcementMode. This one requires the Core Rule Set enabled andBlockmode for namespaces labeledenv: production:apiVersion: applicationlayer.projectcalico.org/v3kind: GlobalWAFValidationPolicymetadata:name: production-requirementsspec:enforcementMode: EnforcenamespaceSelector:matchLabels:env: productionrules:# critical: CRS must be enabled- name: crs-must-be-enabledseverity: criticalrego: |package wafviolations[{"msg": "OWASP CRS must be enabled"}] {input.config.crsState != "Enabled"}# critical: production namespaces must use Block mode- name: block-mode-requiredseverity: criticalrego: |package wafviolations[{"msg": "WAF must be in Block mode for production"}] {input.config.action != "Block"}For more rule patterns — a minimum paranoia level, or inspecting the merged directive list to catch a plugin removing a baseline rule — see Rego validation.
-
Start in
Auditmode, review violations on existingWAFPolicystatus, then switch toEnforce— so you don't block teams whose config predates the policy.Leave
namespaceSelectorempty for cluster-wide, or scope withmatchLabels. Multiple policies can coexist — every matching rule is evaluated, and onecriticalviolation (inEnforce) blocks programming.
Self-check your config with WAFValidationPolicy
WAFValidationPolicy is namespace-scoped and advisory only — violations appear on status but never block programming. Use it as a self-check.
-
Write a
WAFValidationPolicyin your namespace:apiVersion: applicationlayer.projectcalico.org/v3kind: WAFValidationPolicymetadata:name: team-self-checknamespace: platformspec:rules:- name: graphql-plugin-activeseverity: warningrego: |package wafviolations[{"msg": "graphql-waf plugin is not loaded — introspection unguarded"}] {not "graphql-waf" in input.source.namespacePlugins}Being advisory, it's safe to hold yourself to a stricter standard than the baseline — e.g. a higher minimum paranoia level. Violations surface on
WAFPolicystatus without interrupting traffic.
Read violation results
Violations from matching policies appear in the affected WAFPolicy's status conditions.
-
Check the policy status:
kubectl get wafpolicy <name> -n <namespace> -o yamlA blocked policy shows the failing rule:
status:conditions:- type: Readystatus: "False"reason: ValidationFailedmessage: >GlobalWAFValidationPolicy/production-requirements rule "block-mode-required":WAF must be in Block mode for production- type: Acceptedstatus: "True"
An audit violation instead leaves Ready=True and adds a ValidationWarning=True condition, reason AuditViolation, with a message like rce-rules-intact" [warning]: RCE rule removal detected in merged config: SecRuleRemoveById 932100 (the filter stays programmed). See Status conditions for the full reference.
Write Rego against the schema in Rego validation; test locally with opa eval first. A syntax error invalidates the whole policy — status reports which rule failed to parse.
Next steps
- Multi-tenant setup — baseline, plugins, and guardrails working together on a shared cluster.
- Reference — the Rego input schema, worked examples, and status conditions.
- Troubleshooting — diagnose a policy blocked by validation.