<?xml version="1.0" encoding="US-ASCII"?>
<!DOCTYPE rfc SYSTEM "rfc2629.dtd">
<?rfc toc="yes"?>
<?rfc tocompact="yes"?>
<?rfc tocdepth="3"?>
<?rfc tocindent="yes"?>
<?rfc symrefs="yes"?>
<?rfc sortrefs="yes"?>
<?rfc comments="yes"?>
<?rfc inline="yes"?>
<?rfc compact="yes"?>
<?rfc subcompact="no"?>
<rfc category="exp" docName="draft-bradley-oauth-jwt-encoded-state-04"
     ipr="trust200902">
  <front>
    <title abbrev="Abbreviated-Title">Encoding claims in the OAuth 2 state parameter using a JWT</title>

    <author fullname="John Bradley" initials="J." role="editor"
            surname="Bradley">
                  <organization abbrev="Ping">Ping Identity</organization>
      <address>
	<email>ve7jtb@ve7jtb.com</email>
	<uri>http://www.thread-safe.com/</uri>
      </address>
      


    </author>

    <author fullname="Dr.-Ing. Torsten Lodderstedt" initials="T."
         surname="Lodderstedt">
      <organization>Deutsche Telekom AG</organization>

      <address>
        <email>torsten@lodderstedt.net</email>

        
      </address>
    </author>

    <author fullname="Hans Zandbelt" initials="H." 
            surname="Zandbelt">
                  <organization abbrev="Ping">Ping Identity</organization>
      <address>
	<email>hzandbelt@pingidentity.com</email>
	<uri>http://hanszandbelt.wordpress.com</uri>
      </address>
      


    </author>


    <date day="21" month="May" year="2015"/>
    
    <keyword>JOSE</keyword>
    <keyword>JSON Web Signature</keyword>
    <keyword>JWS</keyword>
    <keyword>JSON Web Encryption</keyword>
    <keyword>JWE</keyword>
    <keyword>JSON Web Key</keyword>
    <keyword>JWK</keyword>
    <keyword>JSON Web Algorithms</keyword>
    <keyword>JWA</keyword>
    <keyword>JWT</keyword>
    
    <abstract>
      <t>This draft provides a method for a client to encode one or more elements encoding 
      information about the session into the OAuth 2 <spanx
          style="verb">state</spanx> parameter.</t>
    </abstract>

    <note title="Requirements Language">
      <t>The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT",
      "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this
      document are to be interpreted as described in <xref
      target="RFC2119">RFC 2119</xref>.</t>
    </note>
  </front>

  <middle>
    <section title="Introduction">
      <t>In the <xref target="RFC6749">OAuth 2.0 Authorization protocol</xref> , the Authorization server SHOULD 
      perform an exact string comparison of the <spanx style="verb">redirect_uri</spanx>
      parameter with the <spanx style="verb">redirect_uri</spanx> parameter registered by
      by the client.  This is essential for preventing token leakage to third parties in 
      the OAuth implicit flow.</t>
      <t>As a result of this clients can not safely add extra query parameters to the 
      <spanx style="verb">redirect_uri</spanx> parameter that encode additional client state 
      information.</t>
      <t>The Client MUST use the <spanx style="verb">state</spanx> parameter to encode 
      both Cross Site Request Forgery protection and any other state information it wishes
      to preserve for itself regarding the authorization request.</t>
      
      <t>This draft proposes a mechanism whereby multiple state attributes can be  
      encoded into a JSON Web Token <xref target="RFC7519">JWT</xref> for use as the value of the <spanx
          style="verb">state</spanx> parameter.</t>
       <t>The JWT may be sent without integrity protection, with integrity protection 
       <xref target="RFC7515">JWS</xref>,
       or with both integrity and confidentiality protection <xref target="RFC7516">JWE</xref>.  
       The client is free
       to choose the appropriate protection for its use-case as the <spanx
          style="verb">state</spanx> parameter is treated as opaque by the 
          Authorization Server (AS).</t>
    </section>

    <section title="The state JSON Web Token claims">
      <t>The OAuth Authorization request <spanx style="verb">state</spanx> parameter 
      consists of a <xref target="RFC7519">JWT</xref>, optionally
      signed with <xref target="RFC7515">JWS</xref> or encrypted with 
      <xref target="RFC7516">JWE</xref>, whose payload contains claims as defined 
      here.</t>

      <t><list style="hanging">
          <t hangText="rfp">
          <vspace/>
          REQUIRED. string containing a verifiable identifier for the 
          browser session, that cannot be guessed by a third party. The verification of 
          this element by the client protects it from accepting authorization responses 
          generated in response to forged requests generated by third parties.</t>

          <t hangText="kid">
          <vspace/>
          RECOMMENDED if signed or encrypted. Identifier of the key used
          to sign this state token at the issuer. Identifier of the key used
          to encrypt this JWT state token at the issuer.  This SHOULD be included in the 
          <xref target="RFC7516">JWE</xref> header. 
          </t>
          
          <t hangText="iat">
          <vspace/>
          OPTIONAL. Timestamp of when this Authorization Request
          was issued.</t>
          
          <t hangText="exp">
          <vspace/>
          OPTIONAL. The <spanx style="verb">exp</spanx> (expiration time)
          claim identifies the expiration time on or after which the
          JWT MUST NOT be accepted for processing.  The processing
          of the <spanx style="verb">exp</spanx> claim requires that
          the current date/time MUST be before the expiration
          date/time listed in the <spanx style="verb">exp</spanx>
          claim. Implementers MAY provide for some small leeway,
          usually no more than a few minutes, to account for clock skew.
          Its value MUST be a number containing an IntDate value.
          Use of this claim is OPTIONAL.  This is RECOMMENDED if 
          the <xref target="RFC7519">JWT</xref> state token is being produced by the AS.
          </t>


          <t hangText="iss">
          <vspace/>
          OPTIONAL. string identifying the party that issued
          this state value.</t>
          
          <t hangText="aud">
          <vspace/>
          OPTIONAL. string identifying the client that 
          this state value is intended for.</t>

          <t hangText="target_link_uri">
          <vspace/>
          OPTIONAL. URI containing the location the user agent
          is to be redirected to after authorization.</t>
          
          <t hangText="as">
          <vspace/>
          OPTIONAL. string identifying the authorization server that 
          this request was sent to.</t>
          
		  <t hangText="jti">
          <vspace/>
	      RECOMMENDED. The <spanx style="verb">jti</spanx> (JWT ID) claim
	      provides a unique identifier for the JWT.  The identifier
	      value MUST be assigned in a manner that ensures that there
	      is a negligible probability that the same value will be
	      accidentally assigned to a different data object.  The
	      <spanx style="verb">jti</spanx> claim can be used to
	      prevent the JWT from being replayed.
	      The <spanx style="verb">jti</spanx> value is a case-sensitive string.
	      Use of this claim is OPTIONAL.
	      </t>


          <t hangText="at_hash">
		  <vspace/>
		  OPTIONAL. 
		  Access Token hash value.
		  Its value is the base64url encoding of the left-most half of the
		  hash of the octets of the ASCII representation of the
		  <spanx style="verb">access_token</spanx> value,
		  where the hash algorithm used is the hash algorithm
		  used in the <spanx style="verb">alg</spanx> parameter
		  of the State Token's <xref target="RFC7515">JWS</xref> header.
		  For instance, if the <spanx style="verb">alg</spanx> is
		  <spanx style="verb">RS256</spanx>, hash the
		  <spanx style="verb">access_token</spanx> value
		  with SHA-256, then take the left-most 128 bits and base64url encode them.
		  The <spanx style="verb">at_hash</spanx> value is a case sensitive string.
		  This is REQUIRED if 
          the <xref target="RFC7519">JWT</xref> state token is being produced by the AS and 
          issued with a <spanx style="verb">access_token</spanx> in the authorization 
          response.
		</t>
		
		  <t hangText="c_hash">
		  <vspace/>
		  OPTIONAL. 
		  Code hash value.
		  Its value is the base64url encoding of the left-most half of the
		  hash of the octets of the ASCII representation of the
		  <spanx style="verb">code</spanx> value,
		  where the hash algorithm used is the hash algorithm
		  used in the <spanx style="verb">alg</spanx> header parameter
		  of the State Token's <xref target="RFC7515">JWS</xref> header.
		  For instance, if the <spanx style="verb">alg</spanx> is
		  <spanx style="verb">HS512</spanx>, hash the
		  <spanx style="verb">code</spanx> value
		  with SHA-512, then take the left-most 256 bits and base64url encode them.
		  The <spanx style="verb">c_hash</spanx> value is a case sensitive string.
		  This is REQUIRED if 
          the <xref target="RFC7519">JWT</xref> state token is being produced by the AS and 
          issued with a <spanx style="verb">code</spanx> in the authorization 
          response.
		</t>
          
        </list></t>

	  <t>The issuer may add additional claims to the token.
	  The producer and the consumer of the JWT are the same or closely related entities so 
	  collision resistance of claim names should not be a concern.</t>
	  
      <t>The issuer SHOULD sign the <xref target="RFC7519">JWT</xref> with <xref target="RFC7515">JWS</xref> 
      in such a way that it can verify the 
      signature. The <xref target="RFC7518">JWA</xref> algorithm HS256 with a key of 256bits 
      is recommended.</t>

      <t>The issuer MAY sign the <xref target="RFC7519">JWT</xref> with <xref target="RFC7515">JWS</xref> 
      using <xref target="RFC7518">JWA</xref> algorithm <spanx style="verb">none</spanx> if integrity protecting the 
      contents of the <spanx style="verb">state</spanx> parameter is not required.</t>
      
      <t>If the <spanx style="verb">state</spanx> parameter contains information the client 
      doesn't want to disclose to the Authorization server or user, the issuer MAY encrypt
       the <xref target="RFC7519">JWT</xref> with <xref target="RFC7516">JWE</xref>. 
       The <xref target="RFC7518">JWA</xref>
        algorithm ("alg") of "dir" and encryption algorithm ("enc") 
       of "A128CBC-HS256" are recommended for symmetric encryption.</t>
       
       <t>In the case of the <spanx style="verb">state</spanx> value being created
        by the Issuer the <spanx style="verb">iss</spanx> and 
            <spanx style="verb">aud</spanx> claims MUST be included in the JWT. The jwt
            MUST also be signed with <xref target="RFC7515">JWT</xref>. If the State token
            is issued with a code <spanx style="verb">c_hash</spanx> MUST be included.
            If the State Token is issued with a Access Token 
            <spanx style="verb">at_hash</spanx> MUST be included.</t>
            
    </section>

    <section title="Validating the state parameter">
      <t>Upon receiving a state parameter the client must validate its integrity.
      The client parses it as a JWT. It then verifies the
      signature of the JWT (if signed) using <xref target="RFC7515">JWS</xref>.
      The key used to sign the <xref target="RFC7519">JWT</xref>
      MAY be indicated by the kid field. The client MAY use
      other means to validate the JWT and determine its authenticity.</t>

      <t>The client then reads the fields inside the <xref target="RFC7519">JWT</xref>
      and uses these to configure the user experience and security parameters
      of the authorization. </t>
      
      <t>The <spanx style="verb">rfp</spanx> claim MUST be validated by the client by 
      comparing it to the secret
      information that it used to create the <spanx style="verb">rfp</spanx> value.</t>
    </section>

    <section title="Creating a Request Forgery Protection (rfp) claim value.">
      <t>The client MUST create a value that cannot be guessed by a third party
      attacker and used to forge requests.  There are many possible ways to create this
      value. For reference two common ways will be listed.</t>

      <t>It is completely up to the purview of the particular client
      which generation methods, and which claims, they
      will accept.</t>
      
    		<section title="Stateful Clients.">
    		  <t>Many clients that are web servers maintain session state for browsers 
    		  in a server side store.</t>
    		  <t>These clients can generate a random value with sufficient entropy 
    		  that an attacker cannot guess future values.  This value can be stored in 
    		  the server side store and used directly as the value of 
    		  <spanx style="verb">rfp</spanx>.</t>
      		</section>
      		
      		<section title="Stateless Clients.">
      		
      		<t>Some clients that are web servers maintain session state for browsers 
    		  using browser stored cookies or HTML5 local storage.</t>
    		  <t>These clients can generate a hash value based on a HTTPS: bound session 
    		  cookie or other browser side information that is not accessible to third parties.
    		  This hash value can directly as the value of "xsrf".</t>
    		  <t>While OAuth strongly recommends that clients use TLS to secure their endpoints,
    		  if a client is not using TLS it MUST produce the value of 
    		  <spanx style="verb">rfp</spanx> by using
    		  a HMAC algorithm with a secret known only to itself over the browser stored 
    		  information. </t>
      		</section>
       
            <section title="Responses Initiated by the Issuer">
            <t>Some clients may be willing to rely on the Authorization server providing 
            protection for Cross Site Request Forgery.  In Cases where the Authorization
            server and the client have a pre-established relationship, and the client is 
            willing to accept flows initiated by the Authorization server, the string "iss"
            may be used as the value of <spanx style="verb">rfp</spanx>.</t>
            
            </section>

    </section>

    <section anchor="IANA" title="IANA Considerations">
      <t>[ maybe we register the "rfp" claim above? ]</t>

      <t>This document makes no request of IANA.</t>

      <t>Note to RFC Editor: this section may be removed on publication as an
      RFC.</t>
    </section>

    <section anchor="Security" title="Security Considerations">
      <t>Some information in the state JWT such as target_link_uri value for redirecting the user to 
      the application might have some security impact is the user modifies them intentionally
      or unintentionally.
      To prevent tampering with the "state" value the client may integrity protect the 
      contents of the JWT.  </t>

      <t>The client may have information that it wants to protect from disclosure to the 
      Authorization server, in logs, to proxies, or to the user.  In this case encrypting the 
      JWT as a JWE is required to protect the confidentiality of the state information.</t>
    </section>

    <section anchor="Acknowledgements" title="Acknowledgements">
      <t/>
    </section>
  </middle>

  <back>
    <references title="Normative References">
      <?rfc include="http://xml2rfc.tools.ietf.org/public/rfc/bibxml/reference.RFC.2119.xml"?>
      <?rfc include='http://xml2rfc.tools.ietf.org/public/rfc/bibxml/reference.RFC.6749.xml' ?>
      <?rfc include='http://xml2rfc.tools.ietf.org/public/rfc/bibxml/reference.RFC.7515.xml' ?>
      <?rfc include='http://xml2rfc.tools.ietf.org/public/rfc/bibxml/reference.RFC.7516.xml' ?>
      <?rfc include='http://xml2rfc.tools.ietf.org/public/rfc/bibxml/reference.RFC.7518.xml' ?>
      <?rfc include='http://xml2rfc.tools.ietf.org/public/rfc/bibxml/reference.RFC.7519.xml' ?>


    </references>
        <section anchor="History" title="Document History">
      <t>[[ to be removed by the RFC editor before publication as an RFC
      ]]</t>

 

      <t>-04</t>

      <t><list style="symbols">
          <t>Updated references to JOSE/JWT</t>

          
        </list></t>


    </section>
  </back>
</rfc>
