1 of 9

AuthZEN Boxcarring Proposal

April 30, 2024

| openid.net

1

1

2 of 9

The current spec

We currently have an API ({{host}}/access/v1/evaluation) that allows:

  • sending a single request and
  • getting a single decision back.

Can Alice do X?

True/False

2

3 of 9

The desire

  • We want to be able to send multiple requests and get multiple decisions back
  • We want as many decisions as there are original requests
  • We want the process to be light on the PEP
    • It should be easy to write a PEP that can handle the logic of creating the request and processing/correlating the decisions that come back in the response

3

4 of 9

Prior Art: XACML & ALFA

  • XACML v3.0 Multiple Decision Profile Version 1.0
  • It defines 4 ways
    • By scope
    • By XPath
    • By repetition of the Attributes category
    • By reference
  • In practice, only the last 2 are used in the wild
    • XPath-based is only interesting if dealing with XML as input
  • Let’s have a look at the repetition and reference examples

4

5 of 9

Multiple Decisions by Repetition (XACML/ALFA)

  • Each category is repeated individually (array).
  • There is no request identifier
  • An attribute can be marked as “IncludeInResult
  • Pros
    • This makes for an efficient way to create multiple requests
    • It avoids having to repeat the same information (e.g. username)
    • It supports a matrix of requests e.g. Alice, Bob, Carol + View, Edit, Delete + doc#123, 124, 125 → 3 x 3 x 3 = 27 requests
  • Cons
    • Processing burden on the PEP
    • The PEP needs to correlate the decision back to the original request (hence the need to include an attribute in the response)
  • Sample request

{

"Request": {

"AccessSubject": {

"Attribute": [{

"AttributeId": "com.acme.user.username", "Value": "Alice"

}]

},

"Action": [{

"Attribute": [{

"AttributeId": "com.acme.action", "Value": "view"

}]

}],

"Resource": [{

"Attribute": [{

"AttributeId": "com.acme.objectType", "Value": "record"

}, {

"AttributeId": "com.acme.record.recordId", "Value": "123",

"IncludeInResult": true

}]

},{

"Attribute": [{

"AttributeId": "com.acme.objectType", "Value": "record"

}, {

"AttributeId": "com.acme.record.recordId", "Value": "124",

"IncludeInResult": true

}]

},{

"Attribute": [{

"AttributeId": "com.acme.objectType", "Value": "record"

}, {

"AttributeId": "com.acme.record.recordId", "Value": "125",

"IncludeInResult": true}]}]}}

5

6 of 9

Multiple Decisions by Reference (Cherry-picking)

  • The request is augmented with a MultiRequests element which contains a set of RequestReference elements which contain AttributesReference.
  • Each category defined in the request must be given an id which the MultiRequests element can reference to in order to create requests.
  • This allows cherry-picking.
    1. You can send Alice, Bob, Carol; view, edit, delete; 123, 124, 125 but only pick a subset of the product
  • While this seems useful in theory, in practice, it is seldom used.

{

"Request": {

"AccessSubject": {

"Attribute": [{

"AttributeId": "com.acme.user.username", "Value": "Alice"

}]

},

"Action": [{

"Attribute": [{

"AttributeId": "com.acme.action", "Value": "view"

}]

}],

"Resource": [{

"Attribute": [{

"AttributeId": "com.acme.objectType", "Value": "record"

}, {

"AttributeId": "com.acme.record.recordId", "Value": "123",

"IncludeInResult": true

}]

},{

"Attribute": [{

"AttributeId": "com.acme.objectType", "Value": "record"

}, {

"AttributeId": "com.acme.record.recordId", "Value": "124",

"IncludeInResult": true

}]

},{

"Attribute": [{

"AttributeId": "com.acme.objectType", "Value": "record"

}, {

"AttributeId": "com.acme.record.recordId", "Value": "125",

"IncludeInResult": true}]}]}}

6

7 of 9

Suggestions for AuthZEN

  • We could simply take the existing interface and convert it to being an array
  • The response would therefore become an array as well
  • Enforcing order is not foolproof; let’s introduce a correlation ID/request ID to allow the PEP to tie a decision back to the request
  • Non-normative examples

{

"subject": {"identity": "Alice"},

"action": {"name": "can_read_user"},

"resource": {

"type": "user",

"userID": "beth@the-smiths.com"

}

}

[{

"identifier": 12345,

"subject": {"identity": "Alice"},

"action": {"name": "can_read_user"},

"resource": {

"type": "user",

"userID": "beth@the-smiths.com"

}

},

{

"identifier": 123456,

"subject": {"identity": "Bob"},

"action": {"name": "can_read_user"},

"resource": {

"type": "user",

"userID": "beth@the-smiths.com"

}}]

7

8 of 9

Suggestions from the 4/30 call

  • Make the response async-able
  • Introduce an identifier so that the PEP can correlate decisions inside the response to requests
    • The identifier frees us from the order and allows async behavior
    • Is UUID sufficient?
  • Also leverage the request-level header identifier
  • Propose another iteration of the multiple request more similar to XACML/JSON that allows for common parts in the request (e.g. context data)

8

9 of 9

Thank you.

Visit: www.OpenID.net

9