Skip to content

Commit

Permalink
Updating examples to discuss signing key strength
Browse files Browse the repository at this point in the history
  • Loading branch information
Robert committed Jul 13, 2016
1 parent 35b447a commit 5edb076
Show file tree
Hide file tree
Showing 3 changed files with 46 additions and 11 deletions.
46 changes: 40 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,14 @@ is allowed to do.

JWTs should be signed, otherwise you can't verify that they were created by you.
Our library expects that you give us a highly random signing key for
signing tokens. We use the `HS256` algorithm by default.
signing tokens. We use the `HS256` algorithm by default, and the byte length of
the signing key should match that of the signing algorithm, to ensure cryptographic
security.

While the library will accept strings for signing keys, we suggest you use a
Buffer instead. Using buffers makes it easy to do other operations, like
convert your signing key to Base64URL encoding, if you need to transmit your
key to other systems.

While the claims are completely up to you, we do recommend setting the "Subject"
and "Audience" fields.
Expand All @@ -30,23 +37,30 @@ JWTs commonly contain the `iat` and `exp` claims, which declare the time the
token was issued and when it expires. Our library will create these for you,
with a default expiration of 1 hour.

Here is a simple example that shows you how to create a secure byte string for
your signing key, and then use that key to sign a JWT with some claims that you
provide:

````javascript
var uuid = require('uuid');
var nJwt = require('njwt');
var signingKey = uuid.v4(); // For example purposes
var secureRandom = require('secure-random');

var signingKey = secureRandom(256, {type: 'Buffer'}); // Create a highly random byte array of 256 bytes

var claims = {
iss: "http://myapp.com/", // The URL of your service
sub: "users/user1234", // The UID of the user in your system
scope: "self, admins"
}

var jwt = nJwt.create(claims,signingKey)
var jwt = nJwt.create(claims,signingKey);

````

Once you have created the JWT, you can look at its internal structure by
logging it to the console. This is our internal representation of the token,
this is not what you'll send to your end user:

````javascript
console.log(jwt);
````
Expand All @@ -71,8 +85,9 @@ unique for every token. You can use this if you want to create a database of
tokens that have been issued to the user.

When you are ready to give the token to your end user, you need to compact it.
This will turn it into a Base64 URL encoded string, so it'll be safe to pass
around in browsers without getting any strange formatting applied to it.
This will turn it into a Base64 URL encoded string, making it safe to pass
around in browsers without any unexpected formatting applied to it.

````javascript
var token = jwt.compact();
console.log(token);
Expand All @@ -81,6 +96,25 @@ console.log(token);
eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJmb28iOiJiYXIiLCJpYXQiOjE0MzQ0Nzk4ODN9.HQyx15jWm1upqsrKSf89X_iP0sg7N46a9pqBVGPMYdiqZeuU_ZZOdU-zizHJoIHMIJxtEWzpSMaVubJW0AJsTqjqQf6GoJ4cmFAfmfUFXmMC4Xv5oc4UqvGizpoLjfZedd834PcwbS-WskZcL4pVNmBIGRtDXkoU1j2X1P5M_sNJ9lYZ5vITyqe4MYJovQzNdQziUNhcMI5wkXncV7XzGInBeQsPquASWVG4gb3Y--k1P3xWA4Df3rKeEQBbInDKXczvDpfIlTojx4Ch8OM8vXWWNxW-mIQrV31wRrS9XtNoig7irx8N0MzokiYKrQ8WP_ezPicHvVPIHhz-InOw
````

This is the JWT that the client application will retain, and use for authentication.

Your server application will also need to persist the signing key that was used
to sign the token, and when the client tries to use this token for
authentication, you will need to use the same signing key for verification.

The Buffer needs to be converted to a string so that it can be persisted in a
database, and you can do so like this:

```
var base64SigningKey = signingKey.toString('base64');
```

If you are going to use multiple signing keys, it is common practice to create a
random ID which identifies the key, and store that ID with the key in your
database. When you create JWTs, set the `kid` field of the header to be this ID.
Then when verifying JWTs, this `kid` field will tell you which signing key should
be used for verification.

### Verifying Signed JWTs

The end user will use their JWT to authenticate themselves with your service.
Expand Down
7 changes: 4 additions & 3 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -27,12 +27,13 @@
"uuid": "^2.0.1"
},
"devDependencies": {
"mocha": "^2.2.3",
"chai": "^2.2.0",
"ursa": "^0.8.4",
"coveralls": "^2.11.2",
"istanbul": "^0.3.15",
"jsonwebtoken": "^5.0.2",
"jwt-simple": "^0.3.0",
"coveralls": "^2.11.2"
"mocha": "^2.2.3",
"secure-random": "^1.1.1",
"ursa": "^0.8.4"
}
}
4 changes: 2 additions & 2 deletions test/verifier.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
var fs = require('fs');
var path = require('path');
var uuid = require('uuid');
var secureRandom = require('secure-random');
var assert = require('chai').assert;

var nJwt = require('../');
Expand Down Expand Up @@ -155,7 +156,6 @@ describe('Verifier().verify() ',function(){


before(function(done){
debugger
verifier.verify(jwt.compact(),function(err,res){
result = [err,res];
done();
Expand Down Expand Up @@ -216,7 +216,7 @@ describe('Verifier().verify() ',function(){
});

describe('when configured to expect signature verification',function(){
var key = uuid.v4();
var key = secureRandom(256,{type: 'Buffer'});

var verifier = new nJwt.Verifier()
.setSigningAlgorithm('HS256')
Expand Down

0 comments on commit 5edb076

Please sign in to comment.