Search code examples
open-policy-agentrego

Is there a way in OPA to only evaluate policies relevant to certain request?


I'm experimenting with OPA and securing HTTP REST API. I want to implement ABAC authorization. My question is if it's possible to create rules in such a way that only those relevant to the request will be evaluated - a kind of Target element in XACML

Consider two policies:

package entity

default allow = false

allow = true {
    input.method == "GET"
    input.path = ["entity", "1"]
    input.subject.location = 1
    input.subject.role = "admin"
    input.resource.location = 2
}

package user

default allow = false

allow = true {
    input.method == "GET"
    input.path = ["users", user]
    input.user = user
}

And a request for decision:

{
  "input": {
    "method": "GET",
    "path": [
      "entity",
      "1"
    ],
    "subject": {
      "location": 1,
      "role": "admin"
    },
    "resource": {
      "location": 2
    }
  }
}

What am I getting:

{
  "result": {
    "entity": {
      "allow": true
    },
    "user": {
      "allow": false
    }
  }
}

What I want to get:

{
  "allow": true
}

In this example, a decision request contains only data relevant to the policy with entity. My question is if there's a way to configure OPA or Rego policies so only the relevant policies are evaluated without specifying the policy in the decision request.


Solution

  • What you get back depends on what you ask for :) When querying OPA through its REST API, this is decided by the path of the request, i.e. /v1/data/entity/allow, or /v1/data/user/allow. If you want to decide dynamically which policy or rule(s) to evaluate, you'd commonly setup a "main" policy, which routes to the relevant policy or rule based on the input data. See this article on dynamic policy composition if that's what you're after.