Skip to content

v1.35.0

Choose a tag to compare

@koponen-styra koponen-styra released this 15 Aug 12:04
· 46 commits to main since this release

OPA v1.2.0
Regal v0.31.1

This release includes a fix for ref heads in evaluation (see upstream issue) and includes various dependency bumps.

rego.compile and test helpers for data policy testing

This release features a new built-in function, rego.compile, that mirrors the extended Compile API of Enterprise OPA. It is intended for data filter policy testing.

It is accompanied by a helper function, data.system.eopa.utils.tests.v1.filter.helper that allows for exemplary data policy testing.

With a data policy like this, filters.rego,

package filters

# METADATA
# scope: document
# custom:
# unknowns: ["input.tickets", "input.users"]
include if input.users.name == input.username

you can use the helper to create a test that actually filters some tables:

package filters

import data.system.eopa.utils.tests.v1.filter

tickets_table := [
	{"id": 0, "description": "bluetooth icon is green", "assignee": "a"},
	{"id": 1, "description": "yellow pages are purple", "assignee": "a"},
	{"id": 2, "description": "bluegrass sounds orange", "assignee": "b"},
]

users_table := [
	{"id": "a", "name": "jane"},
	{"id": "b", "name": "john"},
]

test_assignee_can_see_their_tickets if {
	filtered := filter.helper(
		"data.filters.include",
		"SELECT tickets.description, users.name as assignee FROM tickets LEFT JOIN users ON tickets.assignee = users.id",
		{"tables": {
			"tickets": tickets_table,
			"users": users_table,
		}},
	) with input.username as "jane"
	count(filtered) == 2
	{"description": "bluetooth icon is green", "assignee": "jane"} in filtered
	{"description": "yellow pages are purple", "assignee": "jane"} in filtered
}

The low-level built-in method rego.compile can be used to write unit tests for the generated filter queries, like

package filters

test_generated_where_clause if {
	conditions := rego.compile({
		"query": "data.filters.include",
		"target": "sql+postgresql",
	}) with input.username as "jane"
	conditions.sql == "WHERE users.name = E'jane'"
}