Skip to content

Commit 9904976

Browse files
committed
fix evaluation issues
Signed-off-by: Sylwester Piskozub <sylwesterpiskozub@gmail.com>
1 parent 14b6391 commit 9904976

4 files changed

Lines changed: 36 additions & 47 deletions

File tree

pkg/policies/engine/engine.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,8 @@ type PolicyEngine interface {
2626
Verify(ctx context.Context, policy *Policy, input []byte, args map[string]any) (*EvaluationResult, error)
2727
// MatchesParameters evaluates the matches_parameters rule to determine if evaluation parameters match expected parameters
2828
MatchesParameters(ctx context.Context, policy *Policy, evaluationParams, expectedParams map[string]string) (bool, error)
29-
// MatchesEvaluation evaluates the matches_evaluation rule using a PolicyEvaluation result and evaluation parameters
30-
MatchesEvaluation(ctx context.Context, policy *Policy, evaluation *EvaluationResult, evaluationParams map[string]string) (bool, error)
29+
// MatchesEvaluation evaluates the matches_evaluation rule using policy violations and expected parameters
30+
MatchesEvaluation(ctx context.Context, policy *Policy, violations []string, expectedParams map[string]string) (bool, error)
3131
}
3232

3333
type EvaluationResult struct {

pkg/policies/engine/rego/rego.go

Lines changed: 24 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -112,7 +112,7 @@ const (
112112
EnvironmentModePermissive EnvironmentMode = 1
113113
inputArgs = "args"
114114
expectedArgs = "expected_args"
115-
evalResult = "evaluation_result"
115+
violationsResult = "violations"
116116
inputElements = "elements"
117117
deprecatedRule = "violations"
118118
mainRule = "result"
@@ -400,8 +400,16 @@ func (r *Engine) MatchesParameters(ctx context.Context, policy *engine.Policy, e
400400

401401
// Create input with policy and expected parameters
402402
inputMap := make(map[string]interface{})
403-
inputMap[inputArgs] = evaluationParams
404-
inputMap[expectedArgs] = expectedParams
403+
if evaluationParams == nil {
404+
inputMap[inputArgs] = map[string]string{}
405+
} else {
406+
inputMap[inputArgs] = evaluationParams
407+
}
408+
if expectedParams == nil {
409+
inputMap[expectedArgs] = map[string]string{}
410+
} else {
411+
inputMap[expectedArgs] = expectedParams
412+
}
405413

406414
// Evaluate matches_parameters rule
407415
matchesParameters, err := r.evaluateMatchingRule(ctx, getRuleName(parsedModule.Package.Path, matchesParametersRule), parsedModule, inputMap)
@@ -414,20 +422,27 @@ func (r *Engine) MatchesParameters(ctx context.Context, policy *engine.Policy, e
414422
}
415423

416424
// MatchesEvaluation evaluates the matches_evaluation rule in a rego policy.
417-
// The function creates an input object with policy parameters and evaluation result.
425+
// The function creates an input object with expected parameters and policy violations.
418426
// Returns true if the policy's matches_evaluation rule evaluates to true, false otherwise.
419-
// If the rule is not found or evaluation fails, it defaults to false.
420-
func (r *Engine) MatchesEvaluation(ctx context.Context, policy *engine.Policy, ev *engine.EvaluationResult, evaluationParams map[string]string) (bool, error) {
427+
func (r *Engine) MatchesEvaluation(ctx context.Context, policy *engine.Policy, violations []string, expectedParams map[string]string) (bool, error) {
421428
policyString := string(policy.Source)
422429
parsedModule, err := ast.ParseModule(policy.Name, policyString)
423430
if err != nil {
424431
return false, fmt.Errorf("failed to parse rego policy: %w", err)
425432
}
426433

427-
// Create input with the policy evaluation data
434+
// Create input expected parameters and policy violations
428435
inputMap := make(map[string]interface{})
429-
inputMap[inputArgs] = evaluationParams
430-
inputMap[evalResult] = ev
436+
if expectedParams == nil {
437+
inputMap[expectedArgs] = map[string]string{}
438+
} else {
439+
inputMap[expectedArgs] = expectedParams
440+
}
441+
if violations == nil {
442+
inputMap[violationsResult] = []string{}
443+
} else {
444+
inputMap[violationsResult] = violations
445+
}
431446

432447
// Evaluate matches_parameters rule
433448
matchesEvaluation, err := r.evaluateMatchingRule(ctx, getRuleName(parsedModule.Package.Path, matchesEvaluationRule), parsedModule, inputMap)

pkg/policies/engine/rego/rego_test.go

Lines changed: 8 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -393,44 +393,25 @@ func TestRego_MatchesEvaluation(t *testing.T) {
393393
}
394394

395395
t.Run("evaluation with violations and high severity matches", func(t *testing.T) {
396-
evaluation := &engine.EvaluationResult{
397-
Violations: []*engine.PolicyViolation{
398-
{Subject: "test", Violation: "test violation"},
399-
},
400-
Skipped: false,
401-
SkipReason: "",
402-
Ignore: false,
403-
}
396+
violations := []string{"test violation"}
404397
evaluationParams := map[string]string{"severity": "high"}
405-
matches, err := r.MatchesEvaluation(context.TODO(), policy, evaluation, evaluationParams)
398+
matches, err := r.MatchesEvaluation(context.TODO(), policy, violations, evaluationParams)
406399
require.NoError(t, err)
407400
assert.True(t, matches)
408401
})
409402

410403
t.Run("evaluation without violations does not match", func(t *testing.T) {
411-
evaluation := &engine.EvaluationResult{
412-
Violations: []*engine.PolicyViolation{},
413-
Skipped: false,
414-
SkipReason: "",
415-
Ignore: false,
416-
}
404+
violations := []string{}
417405
evaluationParams := map[string]string{"severity": "high"}
418-
matches, err := r.MatchesEvaluation(context.TODO(), policy, evaluation, evaluationParams)
406+
matches, err := r.MatchesEvaluation(context.TODO(), policy, violations, evaluationParams)
419407
require.NoError(t, err)
420408
assert.False(t, matches)
421409
})
422410

423411
t.Run("evaluation with violations but wrong severity does not match", func(t *testing.T) {
424-
evaluation := &engine.EvaluationResult{
425-
Violations: []*engine.PolicyViolation{
426-
{Subject: "test", Violation: "test violation"},
427-
},
428-
Skipped: false,
429-
SkipReason: "",
430-
Ignore: false,
431-
}
412+
violations := []string{"test violation"}
432413
evaluationParams := map[string]string{"severity": "low"}
433-
matches, err := r.MatchesEvaluation(context.TODO(), policy, evaluation, evaluationParams)
414+
matches, err := r.MatchesEvaluation(context.TODO(), policy, violations, evaluationParams)
434415
require.NoError(t, err)
435416
assert.False(t, matches)
436417
})
@@ -443,16 +424,9 @@ func TestRego_MatchesEvaluation(t *testing.T) {
443424
})
444425

445426
t.Run("empty evaluation params", func(t *testing.T) {
446-
evaluation := &engine.EvaluationResult{
447-
Violations: []*engine.PolicyViolation{
448-
{Subject: "test", Violation: "test violation"},
449-
},
450-
Skipped: false,
451-
SkipReason: "",
452-
Ignore: false,
453-
}
427+
violations := []string{"test violation"}
454428
evaluationParams := map[string]string{}
455-
matches, err := r.MatchesEvaluation(context.TODO(), policy, evaluation, evaluationParams)
429+
matches, err := r.MatchesEvaluation(context.TODO(), policy, violations, evaluationParams)
456430
require.NoError(t, err)
457431
assert.False(t, matches)
458432
})

pkg/policies/engine/rego/testfiles/matches_evaluation.rego

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,10 @@ package test_matches_evaluation
22

33
matches_evaluation := result {
44
# Check if the evaluation contains violations
5-
count(input.evaluation_result.violations) > 0
5+
count(input.violations) > 0
66

77
# Check if we have the expected parameter
8-
input.args.severity == "high"
8+
input.expected_args.severity == "high"
99

1010
# If both conditions are met, return true
1111
result := true

0 commit comments

Comments
 (0)