Skip to content

Hawk authentication session

Thomas edited this page Feb 21, 2018 · 17 revisions

What is Hawk and when do I need it?

Hawk is an authentication mechanism, famous because of its replay attack protection.

It is a way to prevent users to tamper with request content or to replay the same request multiple times.

This is especially useful in games where you don't want users to publish fake scores or if you call costly API's (send SMS, trigger a costly lambda job, etc)

Hawk credentials management

What are Hawk credentials?

Hawk credentials looks like a record with the following keys:

{
   'id': 'hawk-id',
   'key': 'hawk-secret',
   'algorithm': 'sha256',
}

How do I retrieve my Hawk credentials?

Because we don't want people to be able to read the credentials in clear through the network we use a mechanism to share them between the server and the client.

For this to happen we use the Hawk-Session-Token header.

The Hawk-Session-Token is a random string of 32 bytes rendered as hexadecimal characters:

Hawk-Session-Token: 47d5616e561443e79d0db605771db46234a984629a6e681059b76657f790583b

You can retrieve this string for your user on a Kinto server, if the account and the hawk plugins are enabled by calling the POST /accounts/(user_id)/hawk-sessions endpoint below. Note that you need to use your account userID and password for Basic Authentication. Once you are using your session for HAWK authentication, you will no longer need to use your account credentials:

$ http POST https://kinto.dev.mozaws.net/v1/accounts/userID/hawk-sessions -v --auth (userID):(password)
POST /v1/accounts/userID/hawk-sessions HTTP/1.1
Host: kinto.dev.mozaws.net


HTTP/1.1 201 Created
Hawk-Session-Token: 47d5616e561443e79d0db605771db46234a984629a6e681059b76657f790583b

How do I use the Hawk-Session-ID to authenticate with Hawk?

In order to get the hawk credentials from the Hawk-Session-Token for the client to use them you will need to use the HKDF derivation function with the following parameters:

  • secret: The Hawk-Session-Token value
  • salt: '' (Empty string)
  • info: 'identity.mozilla.com/picl/v1/sessionToken'
  • length: 64 (2*32) The first 32 bytes for the ID, The last 32 bytes for the Key
  1. Do an HKDF derivation on the given Hawk-Session-ID. With the following parameters:

     key_material = HKDF(hawk_session, "", 'identity.mozilla.com/picl/v1/sessionToken', 32*2)
    
  2. The key material you’ll get out of the HKDF need to be separated into two parts, the first 32 bytes are the Hawk ID, and the next 32 ones are the Hawk key.

    Credentials:

     credentials = {
         'id': codecs.encode(keyMaterial[0:32], 'hex_codec'),
         'key': codecs.encode(keyMaterial[32:64], 'hex_codec'),
         'algorithm': 'sha256',
     }
    

If you are writing a client, you might find these resources useful:

How do I remove all of my Hawk credentials?

You can remove all current sessions to your account by calling DELETE /accounts/(user_id)/hawk-sessions. This endpoint requires HAWK authentication.

$ http DELETE https://kinto.dev.mozaws.net/v1/accounts/userID/hawk-sessions -v
Authorization: Hawk id="...", ts="...", nonce="...", mac="..."
DELETE /v1/accounts/userID/hawk-sessions HTTP/1.1
Host: kinto.dev.mozaws.net


HTTP/1.1 204 No Content

Hawk Session expiry

It is possible to define the hawk_session.ttl_seconds in the Kinto server configuration:

kinto.hawk_session.ttl_seconds = 86400  # 24 hours in seconds 

Its value defaults to 24 hours in seconds (86400)

Each time the Hawk session is used, we delay the session expiration for ttl_seconds more, so that the Hawk session keeps being valid as long as it is used. With the default settings, users will have to reconnect after they stop to use their session for 24h.

It is possible to disconnect all session by removing all of them using DELETE https://kinto.dev.mozaws.net/v1/accounts/userID/hawk-sessions

It is possible to disconnect the current session by using it and calling DELETE https://kinto.dev.mozaws.net/v1/accounts/userID/hawk-sessions/current

Requests to remove sessions require HAWK authentication.