Subject: [OAUTH-WG] draft-fett-oauth-dpop-01 implementation feedback

From: Paul Querna <[email-masked]>
Date: Wed, 1 May 2019 23:32:40 -0700

Hi all,

I recently built a prototype of DPoP using Go, and wanted to provide
some feedback as I went about the implementation.

The implementation is open source: https://github.com/pquerna/dpop

Overall the spec felt functional, though I think the biggest gaps for
a deployment are with the Access Token interactions, but this makes
sense since that seems to be addressed in the future by
<https://tools.ietf.org/html/draft-ietf-oauth-access-token-jwt-00>

Jumping into specific items:

cnf in DPoP-Proof
>   o  "cnf": Confirmation claim as per [RFC7800] containing a member
>      "dpop+jwk", representing the public key chosen by the client in
>      JWK format (REQUIRED for DPoP Binding JWTs, OPTIONAL for DPoP
>      Proof JWTs).

Is there a use case for this being present in the DPoP-Proof JWT?  As
I've implemented DPoP, I didn't see how it was helpful to be sent as a
`cnf` claim of the Proof?

Request Headers vs Parameters
> 5.  Token Request (Binding Tokens to a Public Key)

Placing the DPoP Binding JWT in the HTTP Header `DPoP-Binding` is
different than most other OAuth extensions that I am familiar with.
It is easy in the Go OAuth2 library to add URL / /body params to the
`/token` endpoint, but it is impossible to add an HTTP Header.  Is
there a reason that the binding can't be sent as an OAuth Parameter in
the token request body?

HTTP Request Signing
>   o  "http_method": The HTTP method for the request to which the JWT is
>      attached, in upper case ASCII characters, as defined in [RFC7231]
>      (REQUIRED).
>
>   o  "http_uri": The HTTP URI used for the request, without query and
>      fragment parts (REQUIRED).

HTTP Request signing may be a quagmire that this spec wishes to avoid,
but it seems very hard to avoid "fixing" it for at-scale adoption.
With the Okta-hat on, I think this is one area we would like to see
some iteration on.  I think it would be ideal to not require multiple
client sign() and server validate() PKI operations per request, so
this is where combining DPoP-Proof and a Request Signature start
making sense to me.

Keeping it simple, there are two approaches for DPoP for adding
attesting about the HTTP Request:

  a) Adding parts of the HTTP Request as claims
  b) Adding a hash of an HTTP Request as a claim

For option (b), it seems like part of this could live in a separate spec:
 1) request canonicalization
 2) request hashing

<https://tools.ietf.org/html/draft-cavage-http-signatures-11> does
cover request canonicalization, but the hashing is part of the
specific signature scheme.  From an implementors POV, layering
draft-cavage-http-signatures-11 in addition to DPoP is annoying since
it would take two sign or verify key operations per request.

I'm not sure where the spec-author team wants to take this area, but
am interested in providing feedback.

JWT as AT
>  7.  IANA Considerations
>
>    [[TODO: MIME type registration for at+jwt ]]

Assume this will eventually be done via
<https://tools.ietf.org/html/draft-ietf-oauth-access-token-jwt-00>

Thank you for the work so far, and I'm happy to provide further
feedback as the spec evolves.

Paul

---

From: Benjamin Kaduk <[email-masked]>
Date: Sat, 4 May 2019 12:50:34 -0500

> it would take two sign or verify key operations per request.

I haven't had a chance to read the linked draft, but we've also seen some
activity recently around
https://tools.ietf.org/html/draft-rundgren-json-canonicalization-scheme-05
and linked/related drafts, which are also working in a similar space.

-Ben

---

From: David Waite <[email-masked]>
Date: Sat, 4 May 2019 13:37:21 -0600

> On May 2, 2019, at 12:32 AM, Paul Querna <[email-masked]> wrote:

Discussions with some of the authors makes me think the next draft will change this so that there is no longer a distinction between binding and proof, instead having the key sent outside the DPoP-Proof JWT while binding (possibly as another header). This also allows for more potential flexibility for where the client public key comes from.

Ignoring that, cnf in a proof JWT would allow for debugging/errors to indicate a key mismatch. I think the current language may be a bit ambiguous as to whether a JWK set is allowed as “cnf” as it merely says “JWK format"; if sets are allowed then cnf in the proof would be used for key selection.

> there a reason that the binding can't be sent as an OAuth Parameter in

My understanding is that the goal is to have the proof be applied the same for accessing the token endpoint as when accessing the resources. 

RFC 6750 describes sending the access token as a query parameter or application/x-www-form-urlencoded form parameter, with recommendations of only legacy/last resort use and resources having this as MAY to support. I believe the default position (without strong evidence) is to not carry these forward by defining additional alternatives for DPoP as a query/form parameter.

> it would take two sign or verify key operations per request.

I believe the position at the moment is to keep this close to the bare minimum necessary for operation as proof of possession - the method, origin and path which may be used for routing, to allow for a resource server enforce track one-time-use.

The intersection of HTTP components that intermediaries should or must leave unmodified per spec, and that are useful for http request signing is basically empty. Even method and origin/path are often modified by gateways - in such environments, either the intermediary should be responsible for verifying DPoP or the resource will need knowledge on how to verify the supplied method, origin and path (such as via static knowledge or a header added by the intermediary)

The proof can be extended with additional parameters, which the AS and resource servers in an environment can require. In this manner, DPoP can be extended to meet HTTP request signing use cases. HTTP request signing will always be environment-specific however, and is a big additional ask for a proof of possession specification.

Cavage request verification, for example, could be mapped into a DPoP extension by exposing requirements as extensions against the Bearer authorization request, and embedding the cavage headers and a hash (not digest or signature) of the output into the proof token. Or perhaps the requirements are exposed as AS metadata to cover all resources.

-DW

---

From: Brian Campbell <[email-masked]>
Date: Sun, 5 May 2019 06:55:41 -0600

> <https://tools.ietf.org/html/draft-ietf-oauth-access-token-jwt-00>

This DPoP document should aspire to provide sufficient info on access token
interactions so as not to have any dependency on
draft-ietf-oauth-access-token-jwt. And I sorta doubt that PoP style tokens
will be in scope for draft-ietf-oauth-access-token-jwt at all.

Sections 6[a] and 8[b] of DPoP aim to define access token usage. Is there
specific content that you feel is missing in the draft?

[a] https://tools.ietf.org/html/draft-fett-oauth-dpop-01#section-6
[b] https://tools.ietf.org/html/draft-fett-oauth-dpop-01#section-8

> `cnf` claim of the Proof?

As David alluded to in his reply yesterday, this is an area that is likely
to see some changes in the next revision of the draft - like doing away
with the distinction between binding and proof, moving the proof key out of
the JWT and less inappropriate use of the `cnf` claim.

But in the -01 draft the key is included with the access token via the
`cnf` claim and you're right that it's not particularly helpful to have it
also sent with the Proof.

> there a reason that the binding can't be sent as an OAuth Parameter in

Also as David alluded to in his reply yesterday, there's a goal to have the
proof mechanism be the same for accessing the token endpoint as when
accessing resources. And using application/x-www-form-urlencoded parameters
for resource access is problematic for a litany of reasons.

Very much so, yes.

[snip] I'm not sure where the spec-author team wants to take this area, but
> am interested in providing feedback.

Somehow cleanly allowing for it by extension would be nice from the
perspective of this document. But full treatment of HTTP signing is
explicitly a non-goal of the DPoP draft with the intent that it have only a
minimal set of stuff that's signed so as to facilitate the
proof-of-possession.

JWT as AT
> <https://tools.ietf.org/html/draft-ietf-oauth-access-token-jwt-00>

That's already where it is, no?

> feedback as the spec evolves.

Thanks Paul, it's just a -01 version of an individual draft at this point
(with all the authority thereby bestowed on it
<https://tools.ietf.org/html/draft-abr-twitter-reply-00>) but your
participation would certainly be appreciated as the spec evolves and if
it's something the working group decides to pick up as a working group
item.

-- 
_CONFIDENTIALITY NOTICE: This email may contain confidential and privileged 
material for the sole use of the intended recipient(s). Any review, use, 
distribution or disclosure by others is strictly prohibited.  If you have 
received this communication in error, please notify the sender immediately 
by e-mail and delete the message and any file attachments from your 
computer. Thank you._