JWT Authentication

This module provides support for verifying (JWT) tokens in client requests. The module implements parts of RFC7519, and the algorithm currently supported is HMAC SHA-256 (“HS256”).

The module does not issue tokens. If token issuing is required, the session JWT issuer module can be used instead or in combination with this module. The alternative is to use an external authentication service that handles token issuing.

Example configuration

{
    "name": "example",
    "host": "example.com",
    "path": "/*",
    "modules": [
        {
            "order": 0,
            "name": "auth-jwt",
            "consumers": {
                "foo": {
                    "issuer": "someissuer",
                    "secret": "somesecret"
                },
                "bar": {
                    "secret": "anothersecret"
                }
            }
        }
    ]
}

Consumer configuration attributes

Attribute Required Type Default Description
secret Yes String The secret key used to verify the JWT signature.
issuer No String The issuer (iss) field in the claims, if it exists, will be compared to this string.

Request headers

Header Required Type Description
Authorization Yes String The client uses the authorization header to deliver its token. The format is Authorization: bearer TOKEN.

Example request with authorization header:

GET / HTTP/1.1
Host: example.com
Authorization: bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYmYiOjE0Nzc5MTY2MTIsInN1YiI6ImZvbyJ9.WvAdZBCDkHTaL7FZQmTFF3-gLBJ8dKcxlQIwBjf7ztE

Response status

Status Description
200 The request was authorized to access the specified resource.
401 Unauthorized.

Response headers

Header Description
X-Auth-Error Any human readable authentication error, if present.
X-Auth-Type The auth type used, will with this module be jwt.
X-Auth-User The username of the authorized user.
X-Auth-ID The id of the token (JTI claim) if present, or the username of the authorized user (Subject claim).

The JWT module will not return detailed information to the client about why a token was rejected. This information can be found in the logs.

Token

The Header should always specify Type JWT and algorithm HS256:

{
    "alg": "HS256",
    "typ": "JWT"
}

Payload

The following Claims are considered from the payload.

Claim Required Type Description
sub Yes String The Subject claim must contain the (user)name of the consumer.
iss No String The Issuer claim may contain a string that is compared with the consumer specific string. It can for example be the secret id.
exp No Int The Expiration Time claim may contain an epoch which specifies the end of the valid period of the token.
nbf No Int The Not Before claim may contain an epoch which specifies the start of the valid period of the token.
jti No String The JWT ID claim may contain a string which identifies this specific token.

Example:

{
    "sub": "foo",
    "nbf": 1477568761,
    "exp": 1477569061,
    "iss": "someissuer"
}

Signature

The signature is generated using

HS256(base64UrlEncode(header) + "." + base64UrlEncode(payload), secret)

The example above would produce the signature 4auzds2CrlQgaj1LLtyJfAZhWHegUmHUq_E9xKSG6gk. The complete token would be:

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiJmb28iLCJuYmYiOjE0Nzc1Njg3NjEsImV4cCI6MTQ3NzU2OTA2MSwiaXNzIjoic29tZWlzc3VlciJ9.4auzds2CrlQgaj1LLtyJfAZhWHegUmHUq_E9xKSG6gk

Examples

API configuration

  1. Define an endpoint.

    POST /endpoints HTTP/1.1
    {
        "name": "example",
        "host": "example.com",
        "path": "/"
    }
    
  2. Enable the JWT module for the endpoint.

    POST /endpoints/example/modules HTTP/1.1
    {
        "name": "auth-jwt"
    }
    
  3. Create a consumer

    POST /consumers HTTP/1.1
    {
        "name": "foo"
    }
    
  4. Enable the consumer in the endpoint

    POST /endpoints/example/auth-jwt/consumers
    {
        "name": "foo"
    }
    
  5. Configure the credentials for the consumer in the endpoint.

    PUT /endpoints/example/modules/auth-jwt/consumers/foo
    {
        "secret": "someSecret",
        "issuer": "someIssuer"
    }
    

Client request using cURL

#!/bin/bash

host="example.com"
path="/"

# Header: {
#     "alg": "HS256",
#     "typ": "JWT"
# }
# 
# Payload: {
#     "sub": "foo",
#     "iss": "someissuer"
# }
# 
# Signature: HMACSHA256(
#     base64UrlEncode(header) + "." +
#     base64UrlEncode(payload),
#     somesecret
# )

token="eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiJmb28iLCJpc3MiOiJzb21laXNzdWVyIn0.upW9rQbwq3Y_uR_1v1TIoVzb1_Lkrc4I9_Nm0XmUPdQ"

curl -i http://localhost:8088${path} \
        -H "Authorization: bearer ${token}" \
        -H "host: ${host}"

®Varnish Software, Wallingatan 12, 111 60 Stockholm, Organization nr. 556805-6203