Skip to main content

Attribute-Based Access Control (ABAC) with OPA

tip

Don't miss How to implement ABAC in Rego for in-depth ABAC Rego examples

Overview

In the ABAC model, the policy decision is informed by further attributes of any of the common entities, subject, action and resource. Here are example attributes that can be relevant to authorization:

Subject

  • group or organization membership (e.g. operator, support technician)
  • entitlements: have they subscribed to premium features?
  • last successful sign-in

Resource

  • public or private
  • enterprise edition or community
  • confidentiality rating

Action

These are less common, but you could imagine:

  • entitlements: is the action available to everyone?
  • destructive or not

Environmental

Furthermore, there can be attributes depending on the current execution environment, such as time-based constraints:

  • only allow access to on-call personnel
  • only allow access for a limited time (such as a 30-minute window)

Where do attributes come from?

To make use of attributes in a policy decision, they need to first be made available to OPA. Depending on the requirements for changing attributes, various sources are possible:

Attributes of the subject and resource often arise naturally in an application. For example, a typical REST API call to an application contains enough information to identify subject, resource and action:

GET /v1/books/4322
Authorization: bearer ${JWT}
  • Subject: claims from JSON Web Token sent along with the request
  • Action: GET => "read"
  • Resource: "book with ID 4322"

To make the concrete attributes of these three entities available to the policy evaluation, the most important characteristic is their rate of change:

  • Attributes of entities that cannot change can be put into the Rego policies as-is.
  • Attributes that can change and can be enumerated can be mirrored in OPA's in-memory store, via push or pull methods (see below).
  • Attributes that change too often, or that belong to entities that come in huge or unknown quantities, such as user attributes, or properties of resources that are never enumerated and cannot be put into a bundle, need to be provided just-in-time:
    • by pulling them in via one of the built-ins for querying external services,
    • or by sending them along with the input to the policy evaluation.

In OPA, external HTTP APIs can be queried using http.send. Enterprise OPA adds the option to use dynamodb.send, sql.send, mongodb.send and others (see our tutorials here).

Out-of-band attribute provisioning

The most clear-cut approach to attributes is providing them out-of-band from the actual policy query: Either OPA pulls them in at query time, or it's provided to OPA via Push (HTTP API) or Pull methods (Bundles for OPA, S3, LDAP, MongoDB and others for Enterprise OPA).

note

Some environmental attributes like the current time are provided by OPA built-ins, like time.now_ns(). While technically also out-of-band, these are not part of this illustration.

Relevant integration points for out-of-band provisioning with OPA are:

  1. Bundles
  2. Pushed data via the Data API

Enterprise OPA can furthermore synchronize its data from multiple other data sources (S3, Git, Kafka, MongoDB, LDAP, and others).

In-band attribute provisioning

Oftentimes, the application service already has access to the available attributes of our core entities:

  • Subject: from JWT claims, or data directly injected by upstream authentication services.
  • Resource: properties of the resource could have been fetched before evaluating authorization, or could be known to the relevant application services already.

What next?

Further Reading