1.0.22 • Published 9 years ago
passport-auth-jwt v1.0.22
passport-auth-jwt
A Passport strategy for authenticating with a JSON Web Token.
This module lets you authenticate endpoints using a JSON web token. It is intended to be used to secure RESTful endpoints without sessions.
Install
npm install passport-auth-jwtUsage
Sorry this is a personal library for locking my system. And I to open the handler requirements.
The flow
User <-> Device <-> Provider
Note:
UserThis is your userDeviceThis is your application/websiteProviderThis is your system, RESTful endpoint
Configure
/**
* Config
*/
var passport = require('passport');
var passportAuthJWT = require('passport-auth-jwt');
config.passport.hook = require('./helper/auth-jwt-hook');
var PassportMoney = new passportAuthJWT(config.passport);
passport.use(PassportMoney.strategy());// config.passport
{
clientId: 'client_id',
extractJwtOpts: {
authScheme: 'AuthJWT',
tokenBodyField: 'access_token',
tokenQueryParameterName: 'access_token'
},
requestTokenEndpoint: '/auth/request-token',
refreshTokenEndpoint: '/auth/refresh-token',
tokenEndpoint: '/auth/token',
ignoreRequestTokenUrl: ['/'],
secret: '5f2c6556-2483-4254-a0e6-d8aec4069caa',
accessTokenExpire: 7 * 86400, // 7 days = 7 * 24 * 3600;
refreshTokenExpire: 10 * 365 * 86400, // 10 year
requestTokenExpire: 3600 // 1h
}// ./helper/auth-jwt-hook
'use strict';
const mongoose = require('mongoose');
const uuid = require('node-uuid');
const jwt = require('jsonwebtoken');
const async = require('async');
const moment = require('moment');
const _ = require('lodash');
const PassportError = function (done, err) {
if (err) {
console.log(err);
}
return done({error: err}, false);
};
const ClientSchema = mongoose.model('ClientKey');
const UserSchema = mongoose.model('User');
const RefreshTokenSchema = mongoose.model('RefreshToken');
const Error = require('../config/error');
// restify get path;
var getPath = function (req) {
return req.route ? req.route.path : req.path;
};
var urlRequireForRequestToken = ['/auth/token', '/facebook-register', '/google-register', '/register', '/forgot-password'];
var AuthJWTHook = {
verify: function (config) {
return function (req, jwt_payload, done) {
console.log('payload', jwt_payload);
// Logic
if (req.authenticate.client === jwt_payload.client_id) {
switch (jwt_payload.type) {
case 'request-token':
AuthJWTHook._verifyRequestToken(req, jwt_payload, done, config);
break;
case 'refresh-token':
AuthJWTHook._verifyRefreshToken(req, jwt_payload, done, config);
break;
case 'access-token':
done(null, jwt_payload);
break;
default:
PassportError(done);
}
} else {
PassportError(done);
}
}
},
// Set userId to req
passportCallback: function (req, res, next) {
return function (err, user, info) {
if (user) {
req.userId = user.userId;
next();
} else {
next(err || info);
}
};
},
requestTokenCallback: function (req, res, next) {
return function (error, token) {
res.send(token);
}
},
/*
more in req
req.authenticate = {
client: '14235l4tjgksdsjdlkfs',
secret: '3o432492rjfksdfjslkdfjsdkl'
};
*/
generateRequestToken: function (req, res, next, config) {
var clientInfo = req.authenticate;
ClientSchema.findOne({
client: clientInfo.client,
secret: clientInfo.secret,
isDisabled: false
}, function (error, client) {
if (client) {
var token = AuthJWTHook._generateJWTToken(
'request-token', config.secret, `${config.requestTokenExpire}s`, {
clientId: client._id,
client_id: client.client
}
);
res.send({status: true, request_token: token});
} else {
res.send({
status: false,
message: Error['OAUTH_ERROR_CLIENT_SECRET_NOT_VALIDATE']
});
}
});
},
generateAccessToken: function (req, res, next, config) {
// Logic for generate token
return function (error, tokenInfo) {
if (tokenInfo && tokenInfo.type === 'request-token') {
var client_id = tokenInfo.client_id;
var clientId = tokenInfo.clientId;
var postData = req.body;
AuthJWTHook._login(clientId, client_id, postData, config, function (error, data) {
if (error) {
res.send({
status: false,
message: error
});
} else {
res.send({
status: true,
access_token: data.access_token,
expire: data.expire,
refresh_token: data.refresh_token
});
}
});
} else {
res.send({
status: false,
message: Error['OAUTH_ERROR_CLIENT_SECRET_NOT_VALIDATE']
});
}
};
},
generateRefreshToken: function (req, res, next, config) {
return function (error, tokenInfo) {
if (tokenInfo && tokenInfo.type === 'refresh-token') {
AuthJWTHook._generateToken(
tokenInfo.clientId,
tokenInfo.client_id,
tokenInfo.userId,
config.secret,
tokenInfo.key,
config,
function (error, results) {
if (error) {
res.send({
status: false,
message: Error['']
});
} else {
res.send({
status: true,
access_token: results.access_token.token,
expire: results.access_token.expire,
refresh_token: results.refresh_token
});
}
},
tokenInfo.deviceKey
);
} else {
res.send({
status: false,
message: Error['OAUTH_ERROR_CLIENT_SECRET_NOT_VALIDATE']
});
}
};
},
_generateToken: function (clientId, client_id, userId, secret, key, config, callback, deviceKey) {
async.parallel({
refresh_token: function (callback) {
AuthJWTHook._createRefreshToken(
clientId, client_id, userId, secret, config, callback, deviceKey
);
},
access_token: function (callback) {
AuthJWTHook._createAccessToken(
clientId, client_id, userId, secret, config, callback, deviceKey
);
},
clean_refresh_token: function (callback) {
if (key) {
AuthJWTHook._cleanRefreshToken(key, callback);
} else {
callback(null, true);
}
}
}, callback);
},
_createRefreshToken: function (clientId, client_id, userId, secret, config, callback, deviceKey) {
var key = uuid.v4();
var token = AuthJWTHook._generateJWTToken('refresh-token', secret, `${config.refreshTokenExpire}s`, {
clientId: clientId,
client_id: client_id,
userId: userId,
key: key,
deviceKey: deviceKey
});
// logic more...
},
_cleanRefreshToken: function (key, callback) {
// Logic for clean refresh token
},
_createAccessToken: function (clientId, client_id, userId, secret, config, callback, deviceKey) {
var attachInfo = {
clientId: clientId,
client_id: client_id,
userId: userId,
code: deviceKey
};
var token = AuthJWTHook._generateJWTToken('access-token', secret, `${config.accessTokenExpire}s`, attachInfo);
callback(null, {
token: token,
expire: AuthJWTHook._getExpire(config.accessTokenExpire)
});
},
_verifyRequestToken: function (req, jwt_payload, done, config) {
if (urlRequireForRequestToken.indexOf(getPath(req)) > -1) {
done(null, jwt_payload);
} else {
PassportError(done);
}
},
_verifyRefreshToken: function (req, jwt_payload, done, config) {
// Valid refresh token
console.log('OK');
if (config.refreshTokenEndpoint === getPath(req) && jwt_payload.deviceKey) {
// Logic for verufy refresh token
} else {
console.log(error);
PassportError(done, error);
}
},
_generateJWTToken: function (type, secret, expire, extraData) {
extraData = extraData || {};
var token_payload = {
type: type,
code: uuid.v4()
};
token_payload = Object.assign(token_payload, extraData);
return jwt.sign(token_payload, secret, {
expiresIn: expire
});
},
_getExpire: function (day) {
return moment().add(day, 's').format('X');
},
_login: function (clientId, client_id, postData, config, callback) {
// Login function....
AuthJWTHook._generateToken(...)
}
};
module.exports = AuthJWTHook;Authenticate requests
Use PassportMoney.authenticate() specifying 'JWT' as the strategy.
app.post('/profile', PassportMoney.authenticate({ session: false}),
function(req, res) {
res.send(req.user.profile);
}
);If you have any questions please create issues on Github. I will try to help
1.0.22
9 years ago
1.0.21
10 years ago
1.0.20
10 years ago
1.0.19
10 years ago
1.0.17
10 years ago
1.0.16
10 years ago
1.0.15
10 years ago
1.0.12
10 years ago
1.0.11
10 years ago
1.0.10
10 years ago
1.0.9
10 years ago
1.0.8
10 years ago
1.0.7
10 years ago
1.0.6
10 years ago
1.0.5
10 years ago
1.0.3
10 years ago
1.0.1
10 years ago
1.0.0
10 years ago
2.0.0
10 years ago