Skip to main content

Extracting findings to Rego

Objective

Turn reviewed findings into a Rego policy with zift extract, and validate the extracted policy with opa test.

Concept

Once you have reviewed a scan's findings, Zift extracts them to policy. A scan writes findings to a file; zift extract reads that file and emits Rego (for OPA or Enterprise OPA) or Cedar.

# Scan and capture findings, then extract them to policy.
zift scan ./src --deep
zift extract findings.json

Extraction is a translation, not magic. Each embedded check becomes an explicit rule. The three checks from lesson 1 come out like this:

  • The requireRole(...) middleware and the inline if user.role == "admin" check become a role table: role to the set of actions it permits.
  • The ownership guard if doc.owner_id == user.id becomes a second allow rule keyed on ownership.

Two properties matter in the output, and both are visible in the lab policy.

First, the policy is default-deny. default allow := false means the policy denies unless a rule explicitly allows. An unknown role does not match the role table, the right-hand side is undefined, and allow stays false. Default-deny is what turns "we forgot to guard this route" from a silent grant into a denial.

Second, extraction preserves the intent of the original checks, including the parts that are easy to get wrong. In the source service, owning a document let you read and write it but not delete it, and delete stayed role-gated. The extracted policy keeps that: the ownership allow rule lists only read and write, so an owner still cannot delete. If extraction had widened ownership to cover delete, that would be a false allow, and a deny test is what catches it.

After extraction, you do not trust the policy because Zift produced it. You test it. The extracted Rego ships with a test suite, and opa test is the gate.

git clone https://github.com/EnforceAuth/university-labs.git
cd university-labs
opa test courses/assess-with-zift -v

Extraction is where assess hands off to govern. The Rego Zift produces is what Writ, the control plane, later signs, promotes, and deploys from Git. But that is a later course; here your job is to read the extracted policy and prove it is correct.

Hands-on lab

The lab in courses/assess-with-zift ships the policy Zift extracted from the document service with its two allow decision rules removed. Your job is to author them. Open ../lab/policy.rego, find the # TODO(learner) block, and implement the role-based path and the ownership path so the graded test suite passes.

From the cloned university-labs repo:

git clone https://github.com/EnforceAuth/university-labs.git
cd university-labs
opa test courses/assess-with-zift -v

The starter reports PASS: 4/8 (the four allow tests fail because nothing grants yet). Implement the two rules until you reach PASS: 8/8. Read ../lab/policy_test.rego first and predict every result. Pay attention to test_owner_cannot_delete_own_doc: that is the deny test guarding the "ownership does not grant delete" intent, so your ownership rule must allow read and write only. Follow ../lab/README.md for the full exercise, and check your keep iterating until opa test is green.

Check for understanding

  1. What does default allow := false do when a request arrives with a role that is not in the role table?
  2. In the extracted policy, why is delete absent from the ownership allow rule, and what bug would including it introduce?
  3. You add a rule and one allow test passes. Why is that not enough evidence that the policy is correct?