react / wstein / node_modules / jest-cli / node_modules / jsdom / node_modules / request / node_modules / hawk / test / server.js
81146 views// Load modules12var Url = require('url');3var Code = require('code');4var Hawk = require('../lib');5var Lab = require('lab');678// Declare internals910var internals = {};111213// Test shortcuts1415var lab = exports.lab = Lab.script();16var describe = lab.experiment;17var it = lab.test;18var expect = Code.expect;192021describe('Hawk', function () {2223describe('server', function () {2425var credentialsFunc = function (id, callback) {2627var credentials = {28id: id,29key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',30algorithm: (id === '1' ? 'sha1' : 'sha256'),31user: 'steve'32};3334return callback(null, credentials);35};3637describe('#authenticate', function () {3839it('parses a valid authentication header (sha1)', function (done) {4041var req = {42method: 'GET',43url: '/resource/4?filter=a',44host: 'example.com',45port: 8080,46authorization: 'Hawk id="1", ts="1353788437", nonce="k3j4h2", mac="zy79QQ5/EYFmQqutVnYb73gAc/U=", ext="hello"'47};4849Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {5051expect(err).to.not.exist();52expect(credentials.user).to.equal('steve');53done();54});55});5657it('parses a valid authentication header (sha256)', function (done) {5859var req = {60method: 'GET',61url: '/resource/1?b=1&a=2',62host: 'example.com',63port: 8000,64authorization: 'Hawk id="dh37fgj492je", ts="1353832234", nonce="j4h3g2", mac="m8r1rHbXN6NgO+KIIhjO7sFRyd78RNGVUwehe8Cp2dU=", ext="some-app-data"'65};6667Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353832234000 - Hawk.utils.now() }, function (err, credentials, artifacts) {6869expect(err).to.not.exist();70expect(credentials.user).to.equal('steve');71done();72});73});7475it('parses a valid authentication header (host override)', function (done) {7677var req = {78method: 'GET',79url: '/resource/4?filter=a',80headers: {81host: 'example1.com:8080',82authorization: 'Hawk id="1", ts="1353788437", nonce="k3j4h2", mac="zy79QQ5/EYFmQqutVnYb73gAc/U=", ext="hello"'83}84};8586Hawk.server.authenticate(req, credentialsFunc, { host: 'example.com', localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {8788expect(err).to.not.exist();89expect(credentials.user).to.equal('steve');90done();91});92});9394it('parses a valid authentication header (host port override)', function (done) {9596var req = {97method: 'GET',98url: '/resource/4?filter=a',99headers: {100host: 'example1.com:80',101authorization: 'Hawk id="1", ts="1353788437", nonce="k3j4h2", mac="zy79QQ5/EYFmQqutVnYb73gAc/U=", ext="hello"'102}103};104105Hawk.server.authenticate(req, credentialsFunc, { host: 'example.com', port: 8080, localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {106107expect(err).to.not.exist();108expect(credentials.user).to.equal('steve');109done();110});111});112113it('parses a valid authentication header (POST with payload)', function (done) {114115var req = {116method: 'POST',117url: '/resource/4?filter=a',118host: 'example.com',119port: 8080,120authorization: 'Hawk id="123456", ts="1357926341", nonce="1AwuJD", hash="qAiXIVv+yjDATneWxZP2YCTa9aHRgQdnH9b3Wc+o3dg=", ext="some-app-data", mac="UeYcj5UoTVaAWXNvJfLVia7kU3VabxCqrccXP8sUGC4="'121};122123Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1357926341000 - Hawk.utils.now() }, function (err, credentials, artifacts) {124125expect(err).to.not.exist();126expect(credentials.user).to.equal('steve');127done();128});129});130131it('errors on missing hash', function (done) {132133var req = {134method: 'GET',135url: '/resource/1?b=1&a=2',136host: 'example.com',137port: 8000,138authorization: 'Hawk id="dh37fgj492je", ts="1353832234", nonce="j4h3g2", mac="m8r1rHbXN6NgO+KIIhjO7sFRyd78RNGVUwehe8Cp2dU=", ext="some-app-data"'139};140141Hawk.server.authenticate(req, credentialsFunc, { payload: 'body', localtimeOffsetMsec: 1353832234000 - Hawk.utils.now() }, function (err, credentials, artifacts) {142143expect(err).to.exist();144expect(err.output.payload.message).to.equal('Missing required payload hash');145done();146});147});148149it('errors on a stale timestamp', function (done) {150151var req = {152method: 'GET',153url: '/resource/4?filter=a',154host: 'example.com',155port: 8080,156authorization: 'Hawk id="123456", ts="1362337299", nonce="UzmxSs", ext="some-app-data", mac="wnNUxchvvryMH2RxckTdZ/gY3ijzvccx4keVvELC61w="'157};158159Hawk.server.authenticate(req, credentialsFunc, {}, function (err, credentials, artifacts) {160161expect(err).to.exist();162expect(err.output.payload.message).to.equal('Stale timestamp');163var header = err.output.headers['WWW-Authenticate'];164var ts = header.match(/^Hawk ts\=\"(\d+)\"\, tsm\=\"([^\"]+)\"\, error=\"Stale timestamp\"$/);165var now = Hawk.utils.now();166expect(parseInt(ts[1], 10) * 1000).to.be.within(now - 1000, now + 1000);167168var res = {169headers: {170'www-authenticate': header171}172};173174expect(Hawk.client.authenticate(res, credentials, artifacts)).to.equal(true);175done();176});177});178179it('errors on a replay', function (done) {180181var req = {182method: 'GET',183url: '/resource/4?filter=a',184host: 'example.com',185port: 8080,186authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="bXx7a7p1h9QYQNZ8x7QhvDQym8ACgab4m3lVSFn4DBw=", ext="hello"'187};188189var memoryCache = {};190var options = {191localtimeOffsetMsec: 1353788437000 - Hawk.utils.now(),192nonceFunc: function (nonce, ts, callback) {193194if (memoryCache[nonce]) {195return callback(new Error());196}197198memoryCache[nonce] = true;199return callback();200}201};202203Hawk.server.authenticate(req, credentialsFunc, options, function (err, credentials, artifacts) {204205expect(err).to.not.exist();206expect(credentials.user).to.equal('steve');207208Hawk.server.authenticate(req, credentialsFunc, options, function (err, credentials, artifacts) {209210expect(err).to.exist();211expect(err.output.payload.message).to.equal('Invalid nonce');212done();213});214});215});216217it('errors on an invalid authentication header: wrong scheme', function (done) {218219var req = {220method: 'GET',221url: '/resource/4?filter=a',222host: 'example.com',223port: 8080,224authorization: 'Basic asdasdasdasd'225};226227Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {228229expect(err).to.exist();230expect(err.output.payload.message).to.not.exist();231done();232});233});234235it('errors on an invalid authentication header: no scheme', function (done) {236237var req = {238method: 'GET',239url: '/resource/4?filter=a',240host: 'example.com',241port: 8080,242authorization: '!@#'243};244245Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {246247expect(err).to.exist();248expect(err.output.payload.message).to.equal('Invalid header syntax');249done();250});251});252253it('errors on an missing authorization header', function (done) {254255var req = {256method: 'GET',257url: '/resource/4?filter=a',258host: 'example.com',259port: 8080260};261262Hawk.server.authenticate(req, credentialsFunc, {}, function (err, credentials, artifacts) {263264expect(err).to.exist();265expect(err.isMissing).to.equal(true);266done();267});268});269270it('errors on an missing host header', function (done) {271272var req = {273method: 'GET',274url: '/resource/4?filter=a',275headers: {276authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'277}278};279280Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {281282expect(err).to.exist();283expect(err.output.payload.message).to.equal('Invalid Host header');284done();285});286});287288it('errors on an missing authorization attribute (id)', function (done) {289290var req = {291method: 'GET',292url: '/resource/4?filter=a',293host: 'example.com',294port: 8080,295authorization: 'Hawk ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'296};297298Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {299300expect(err).to.exist();301expect(err.output.payload.message).to.equal('Missing attributes');302done();303});304});305306it('errors on an missing authorization attribute (ts)', function (done) {307308var req = {309method: 'GET',310url: '/resource/4?filter=a',311host: 'example.com',312port: 8080,313authorization: 'Hawk id="123", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'314};315316Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {317318expect(err).to.exist();319expect(err.output.payload.message).to.equal('Missing attributes');320done();321});322});323324it('errors on an missing authorization attribute (nonce)', function (done) {325326var req = {327method: 'GET',328url: '/resource/4?filter=a',329host: 'example.com',330port: 8080,331authorization: 'Hawk id="123", ts="1353788437", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'332};333334Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {335336expect(err).to.exist();337expect(err.output.payload.message).to.equal('Missing attributes');338done();339});340});341342it('errors on an missing authorization attribute (mac)', function (done) {343344var req = {345method: 'GET',346url: '/resource/4?filter=a',347host: 'example.com',348port: 8080,349authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", ext="hello"'350};351352Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {353354expect(err).to.exist();355expect(err.output.payload.message).to.equal('Missing attributes');356done();357});358});359360it('errors on an unknown authorization attribute', function (done) {361362var req = {363method: 'GET',364url: '/resource/4?filter=a',365host: 'example.com',366port: 8080,367authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", x="3", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'368};369370Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {371372expect(err).to.exist();373expect(err.output.payload.message).to.equal('Unknown attribute: x');374done();375});376});377378it('errors on an bad authorization header format', function (done) {379380var req = {381method: 'GET',382url: '/resource/4?filter=a',383host: 'example.com',384port: 8080,385authorization: 'Hawk id="123\\", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'386};387388Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {389390expect(err).to.exist();391expect(err.output.payload.message).to.equal('Bad header format');392done();393});394});395396it('errors on an bad authorization attribute value', function (done) {397398var req = {399method: 'GET',400url: '/resource/4?filter=a',401host: 'example.com',402port: 8080,403authorization: 'Hawk id="\t", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'404};405406Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {407408expect(err).to.exist();409expect(err.output.payload.message).to.equal('Bad attribute value: id');410done();411});412});413414it('errors on an empty authorization attribute value', function (done) {415416var req = {417method: 'GET',418url: '/resource/4?filter=a',419host: 'example.com',420port: 8080,421authorization: 'Hawk id="", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'422};423424Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {425426expect(err).to.exist();427expect(err.output.payload.message).to.equal('Bad attribute value: id');428done();429});430});431432it('errors on duplicated authorization attribute key', function (done) {433434var req = {435method: 'GET',436url: '/resource/4?filter=a',437host: 'example.com',438port: 8080,439authorization: 'Hawk id="123", id="456", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'440};441442Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {443444expect(err).to.exist();445expect(err.output.payload.message).to.equal('Duplicate attribute: id');446done();447});448});449450it('errors on an invalid authorization header format', function (done) {451452var req = {453method: 'GET',454url: '/resource/4?filter=a',455host: 'example.com',456port: 8080,457authorization: 'Hawk'458};459460Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {461462expect(err).to.exist();463expect(err.output.payload.message).to.equal('Invalid header syntax');464done();465});466});467468it('errors on an bad host header (missing host)', function (done) {469470var req = {471method: 'GET',472url: '/resource/4?filter=a',473headers: {474host: ':8080',475authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'476}477};478479Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {480481expect(err).to.exist();482expect(err.output.payload.message).to.equal('Invalid Host header');483done();484});485});486487it('errors on an bad host header (pad port)', function (done) {488489var req = {490method: 'GET',491url: '/resource/4?filter=a',492headers: {493host: 'example.com:something',494authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'495}496};497498Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {499500expect(err).to.exist();501expect(err.output.payload.message).to.equal('Invalid Host header');502done();503});504});505506it('errors on credentialsFunc error', function (done) {507508var req = {509method: 'GET',510url: '/resource/4?filter=a',511host: 'example.com',512port: 8080,513authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'514};515516var credentialsFunc = function (id, callback) {517518return callback(new Error('Unknown user'));519};520521Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {522523expect(err).to.exist();524expect(err.message).to.equal('Unknown user');525done();526});527});528529it('errors on credentialsFunc error (with credentials)', function (done) {530531var req = {532method: 'GET',533url: '/resource/4?filter=a',534host: 'example.com',535port: 8080,536authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'537};538539var credentialsFunc = function (id, callback) {540541return callback(new Error('Unknown user'), { some: 'value' });542};543544Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {545546expect(err).to.exist();547expect(err.message).to.equal('Unknown user');548expect(credentials.some).to.equal('value');549done();550});551});552553it('errors on missing credentials', function (done) {554555var req = {556method: 'GET',557url: '/resource/4?filter=a',558host: 'example.com',559port: 8080,560authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'561};562563var credentialsFunc = function (id, callback) {564565return callback(null, null);566};567568Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {569570expect(err).to.exist();571expect(err.output.payload.message).to.equal('Unknown credentials');572done();573});574});575576it('errors on invalid credentials (id)', function (done) {577578var req = {579method: 'GET',580url: '/resource/4?filter=a',581host: 'example.com',582port: 8080,583authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'584};585586var credentialsFunc = function (id, callback) {587588var credentials = {589key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',590user: 'steve'591};592593return callback(null, credentials);594};595596Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {597598expect(err).to.exist();599expect(err.message).to.equal('Invalid credentials');600expect(err.output.payload.message).to.equal('An internal server error occurred');601done();602});603});604605it('errors on invalid credentials (key)', function (done) {606607var req = {608method: 'GET',609url: '/resource/4?filter=a',610host: 'example.com',611port: 8080,612authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'613};614615var credentialsFunc = function (id, callback) {616617var credentials = {618id: '23434d3q4d5345d',619user: 'steve'620};621622return callback(null, credentials);623};624625Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {626627expect(err).to.exist();628expect(err.message).to.equal('Invalid credentials');629expect(err.output.payload.message).to.equal('An internal server error occurred');630done();631});632});633634it('errors on unknown credentials algorithm', function (done) {635636var req = {637method: 'GET',638url: '/resource/4?filter=a',639host: 'example.com',640port: 8080,641authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcUyW6EEgUH4jlr7T/wuKe3dKijvTvSos=", ext="hello"'642};643644var credentialsFunc = function (id, callback) {645646var credentials = {647key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',648algorithm: 'hmac-sha-0',649user: 'steve'650};651652return callback(null, credentials);653};654655Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {656657expect(err).to.exist();658expect(err.message).to.equal('Unknown algorithm');659expect(err.output.payload.message).to.equal('An internal server error occurred');660done();661});662});663664it('errors on unknown bad mac', function (done) {665666var req = {667method: 'GET',668url: '/resource/4?filter=a',669host: 'example.com',670port: 8080,671authorization: 'Hawk id="123", ts="1353788437", nonce="k3j4h2", mac="/qwS4UjfVWMcU4jlr7T/wuKe3dKijvTvSos=", ext="hello"'672};673674var credentialsFunc = function (id, callback) {675676var credentials = {677key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',678algorithm: 'sha256',679user: 'steve'680};681682return callback(null, credentials);683};684685Hawk.server.authenticate(req, credentialsFunc, { localtimeOffsetMsec: 1353788437000 - Hawk.utils.now() }, function (err, credentials, artifacts) {686687expect(err).to.exist();688expect(err.output.payload.message).to.equal('Bad mac');689done();690});691});692});693694describe('#header', function () {695696it('generates header', function (done) {697698var credentials = {699id: '123456',700key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',701algorithm: 'sha256',702user: 'steve'703};704705var artifacts = {706method: 'POST',707host: 'example.com',708port: '8080',709resource: '/resource/4?filter=a',710ts: '1398546787',711nonce: 'xUwusx',712hash: 'nJjkVtBE5Y/Bk38Aiokwn0jiJxt/0S2WRSUwWLCf5xk=',713ext: 'some-app-data',714mac: 'dvIvMThwi28J61Jc3P0ryAhuKpanU63GXdx6hkmQkJA=',715id: '123456'716};717718var header = Hawk.server.header(credentials, artifacts, { payload: 'some reply', contentType: 'text/plain', ext: 'response-specific' });719expect(header).to.equal('Hawk mac=\"n14wVJK4cOxAytPUMc5bPezQzuJGl5n7MYXhFQgEKsE=\", hash=\"f9cDF/TDm7TkYRLnGwRMfeDzT6LixQVLvrIKhh0vgmM=\", ext=\"response-specific\"');720done();721});722723it('generates header (empty payload)', function (done) {724725var credentials = {726id: '123456',727key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',728algorithm: 'sha256',729user: 'steve'730};731732var artifacts = {733method: 'POST',734host: 'example.com',735port: '8080',736resource: '/resource/4?filter=a',737ts: '1398546787',738nonce: 'xUwusx',739hash: 'nJjkVtBE5Y/Bk38Aiokwn0jiJxt/0S2WRSUwWLCf5xk=',740ext: 'some-app-data',741mac: 'dvIvMThwi28J61Jc3P0ryAhuKpanU63GXdx6hkmQkJA=',742id: '123456'743};744745var header = Hawk.server.header(credentials, artifacts, { payload: '', contentType: 'text/plain', ext: 'response-specific' });746expect(header).to.equal('Hawk mac=\"i8/kUBDx0QF+PpCtW860kkV/fa9dbwEoe/FpGUXowf0=\", hash=\"q/t+NNAkQZNlq/aAD6PlexImwQTxwgT2MahfTa9XRLA=\", ext=\"response-specific\"');747done();748});749750it('generates header (pre calculated hash)', function (done) {751752var credentials = {753id: '123456',754key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',755algorithm: 'sha256',756user: 'steve'757};758759var artifacts = {760method: 'POST',761host: 'example.com',762port: '8080',763resource: '/resource/4?filter=a',764ts: '1398546787',765nonce: 'xUwusx',766hash: 'nJjkVtBE5Y/Bk38Aiokwn0jiJxt/0S2WRSUwWLCf5xk=',767ext: 'some-app-data',768mac: 'dvIvMThwi28J61Jc3P0ryAhuKpanU63GXdx6hkmQkJA=',769id: '123456'770};771772var options = { payload: 'some reply', contentType: 'text/plain', ext: 'response-specific' };773options.hash = Hawk.crypto.calculatePayloadHash(options.payload, credentials.algorithm, options.contentType);774var header = Hawk.server.header(credentials, artifacts, options);775expect(header).to.equal('Hawk mac=\"n14wVJK4cOxAytPUMc5bPezQzuJGl5n7MYXhFQgEKsE=\", hash=\"f9cDF/TDm7TkYRLnGwRMfeDzT6LixQVLvrIKhh0vgmM=\", ext=\"response-specific\"');776done();777});778779it('generates header (null ext)', function (done) {780781var credentials = {782id: '123456',783key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',784algorithm: 'sha256',785user: 'steve'786};787788var artifacts = {789method: 'POST',790host: 'example.com',791port: '8080',792resource: '/resource/4?filter=a',793ts: '1398546787',794nonce: 'xUwusx',795hash: 'nJjkVtBE5Y/Bk38Aiokwn0jiJxt/0S2WRSUwWLCf5xk=',796mac: 'dvIvMThwi28J61Jc3P0ryAhuKpanU63GXdx6hkmQkJA=',797id: '123456'798};799800var header = Hawk.server.header(credentials, artifacts, { payload: 'some reply', contentType: 'text/plain', ext: null });801expect(header).to.equal('Hawk mac=\"6PrybJTJs20jsgBw5eilXpcytD8kUbaIKNYXL+6g0ns=\", hash=\"f9cDF/TDm7TkYRLnGwRMfeDzT6LixQVLvrIKhh0vgmM=\"');802done();803});804805it('errors on missing artifacts', function (done) {806807var credentials = {808id: '123456',809key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',810algorithm: 'sha256',811user: 'steve'812};813814var header = Hawk.server.header(credentials, null, { payload: 'some reply', contentType: 'text/plain', ext: 'response-specific' });815expect(header).to.equal('');816done();817});818819it('errors on invalid artifacts', function (done) {820821var credentials = {822id: '123456',823key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',824algorithm: 'sha256',825user: 'steve'826};827828var header = Hawk.server.header(credentials, 5, { payload: 'some reply', contentType: 'text/plain', ext: 'response-specific' });829expect(header).to.equal('');830done();831});832833it('errors on missing credentials', function (done) {834835var artifacts = {836method: 'POST',837host: 'example.com',838port: '8080',839resource: '/resource/4?filter=a',840ts: '1398546787',841nonce: 'xUwusx',842hash: 'nJjkVtBE5Y/Bk38Aiokwn0jiJxt/0S2WRSUwWLCf5xk=',843ext: 'some-app-data',844mac: 'dvIvMThwi28J61Jc3P0ryAhuKpanU63GXdx6hkmQkJA=',845id: '123456'846};847848var header = Hawk.server.header(null, artifacts, { payload: 'some reply', contentType: 'text/plain', ext: 'response-specific' });849expect(header).to.equal('');850done();851});852853it('errors on invalid credentials (key)', function (done) {854855var credentials = {856id: '123456',857algorithm: 'sha256',858user: 'steve'859};860861var artifacts = {862method: 'POST',863host: 'example.com',864port: '8080',865resource: '/resource/4?filter=a',866ts: '1398546787',867nonce: 'xUwusx',868hash: 'nJjkVtBE5Y/Bk38Aiokwn0jiJxt/0S2WRSUwWLCf5xk=',869ext: 'some-app-data',870mac: 'dvIvMThwi28J61Jc3P0ryAhuKpanU63GXdx6hkmQkJA=',871id: '123456'872};873874var header = Hawk.server.header(credentials, artifacts, { payload: 'some reply', contentType: 'text/plain', ext: 'response-specific' });875expect(header).to.equal('');876done();877});878879it('errors on invalid algorithm', function (done) {880881var credentials = {882id: '123456',883key: 'werxhqb98rpaxn39848xrunpaw3489ruxnpa98w4rxn',884algorithm: 'x',885user: 'steve'886};887888var artifacts = {889method: 'POST',890host: 'example.com',891port: '8080',892resource: '/resource/4?filter=a',893ts: '1398546787',894nonce: 'xUwusx',895hash: 'nJjkVtBE5Y/Bk38Aiokwn0jiJxt/0S2WRSUwWLCf5xk=',896ext: 'some-app-data',897mac: 'dvIvMThwi28J61Jc3P0ryAhuKpanU63GXdx6hkmQkJA=',898id: '123456'899};900901var header = Hawk.server.header(credentials, artifacts, { payload: 'some reply', contentType: 'text/plain', ext: 'response-specific' });902expect(header).to.equal('');903done();904});905});906907describe('#authenticateMessage', function () {908909it('errors on invalid authorization (ts)', function (done) {910911credentialsFunc('123456', function (err, credentials) {912913var auth = Hawk.client.message('example.com', 8080, 'some message', { credentials: credentials });914delete auth.ts;915916Hawk.server.authenticateMessage('example.com', 8080, 'some message', auth, credentialsFunc, {}, function (err, credentials) {917918expect(err).to.exist();919expect(err.message).to.equal('Invalid authorization');920done();921});922});923});924925it('errors on invalid authorization (nonce)', function (done) {926927credentialsFunc('123456', function (err, credentials) {928929var auth = Hawk.client.message('example.com', 8080, 'some message', { credentials: credentials });930delete auth.nonce;931932Hawk.server.authenticateMessage('example.com', 8080, 'some message', auth, credentialsFunc, {}, function (err, credentials) {933934expect(err).to.exist();935expect(err.message).to.equal('Invalid authorization');936done();937});938});939});940941it('errors on invalid authorization (hash)', function (done) {942943credentialsFunc('123456', function (err, credentials) {944945var auth = Hawk.client.message('example.com', 8080, 'some message', { credentials: credentials });946delete auth.hash;947948Hawk.server.authenticateMessage('example.com', 8080, 'some message', auth, credentialsFunc, {}, function (err, credentials) {949950expect(err).to.exist();951expect(err.message).to.equal('Invalid authorization');952done();953});954});955});956957it('errors with credentials', function (done) {958959credentialsFunc('123456', function (err, credentials) {960961var auth = Hawk.client.message('example.com', 8080, 'some message', { credentials: credentials });962963Hawk.server.authenticateMessage('example.com', 8080, 'some message', auth, function (id, callback) { callback(new Error('something'), { some: 'value' }); }, {}, function (err, credentials) {964965expect(err).to.exist();966expect(err.message).to.equal('something');967expect(credentials.some).to.equal('value');968done();969});970});971});972});973974describe('#authenticatePayloadHash', function () {975976it('checks payload hash', function (done) {977978expect(Hawk.server.authenticatePayloadHash('abcdefg', { hash: 'abcdefg' })).to.equal(true);979expect(Hawk.server.authenticatePayloadHash('1234567', { hash: 'abcdefg' })).to.equal(false);980done();981});982});983});984});985986987