← Concepts

阅读中文版本

Policy as Code: Guardrails You Can Test and Version

Policy as code expresses security and compliance rules as versioned, testable artifacts that gate pipelines and reconcile live systems instead of living in a wiki.

operations

Definition

Policy as code is the practice of defining organizational rules, such as allowed regions, required labels, or forbidden public buckets, in a machine-readable language that is versioned, reviewed, tested, and enforced automatically at admission time or in CI.

Context and scope

Manual review does not scale to thousands of resources and hundreds of teams, and spreadsheets of exceptions decay faster than the systems they describe.

Common misconceptions

  • Policy as code means writing YAML — the value is automated evaluation, not the file format
  • Policies should block everything risky — overly strict gates get bypassed or disabled
  • One policy engine covers every layer — admission, CI, cloud APIs, and runtime each need their own hooks

Anti-patterns

  • Shipping policies with no tests or dry-run period
  • Granting broad exceptions that quietly become permanent
  • Enforcing policy only at deploy time and never reconciling existing resources

Related concepts

Related examples

Authoritative source

https://www.openpolicyagent.org/docs/latest/

Rules as artifacts

Policy as code turns organizational intent into files: which regions may host data, which labels every workload must carry, which storage classes cannot be public. Because the rules live in a repository, they get history, review, and tests. The point is not the syntax; it is that a rule can be executed against real inputs and produce a deterministic answer.

What belongs in code

Encode rules that are objective and checkable: naming, required metadata, encryption settings, network exposure, image provenance. Keep judgment-heavy exceptions in a review process with an expiry date. A policy that needs a paragraph of context to apply is usually a design decision, not a guardrail.

Testing before enforcing

Every policy needs fixtures: resources that should pass and resources that should fail. Without them, a typo silently allows everything or blocks a legitimate deployment at the worst time. Roll out in audit mode first, count violations, fix the policy or the workloads, and only then switch to enforcement.

deny[msg] {
  input.kind == "Deployment"
  not input.metadata.labels.owner
  msg := "Deployment must declare an owner label"
}

Enforcement points

Admission control blocks non-compliant resources at creation. CI catches issues earlier but can be bypassed. Cloud-native policy engines evaluate existing resources continuously, which is the only way to catch drift. Mature programs use several hooks with the same rule source, so a rule is written once and evaluated everywhere.

Compared to manual review

Manual review depends on reviewer memory and availability, and it leaves no record of what was checked. Policy as code is faster, consistent, and auditable, but it is also literal: a badly written rule blocks good work at scale. Treat policies like software, with tests, owners, and a rollback plan, or the guardrail becomes the outage.