Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

@passport-next/passport

Package Overview
Dependencies
Maintainers
3
Versions
9
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@passport-next/passport - npm Package Compare versions

Comparing version 2.1.1 to 3.0.0

reports/coverage/coverage.json

16

CHANGELOG.md
This changelog follows Semantic Versioning https://semver.org/
# 3.0.0 (2019-07-13)
### Major
* Major lint changes, there are no functional changes but due to the massive
amount of code changes this is being marked as a major bump for caution sake
this will hopefully be the last of the changes like this for a while.
### Patch
* Fixed premature redirect in logOut and improved test coverage #20 @rwky
* Removed make-node and replaced with nyc and coveralls @rwky
# 2.1.1 (2019-04-30)

@@ -30,3 +44,3 @@

* Added eslint configuration, and fixed a pletora of lint errors @idurotola
* This change should have been a patch (to 1.0.2) but because of the size of the
This change should have been a patch (to 1.0.2) but because of the size of the
number of lines changed it was made a major.

@@ -33,0 +47,0 @@

838

lib/authenticator.js

@@ -0,1 +1,3 @@

'use strict';
/**

@@ -5,4 +7,2 @@ * Module dependencies.

/* eslint-disable no-underscore-dangle, camelcase, no-proto, no-shadow */
const SessionStrategy = require('./strategies/session');

@@ -14,472 +14,480 @@ const SessionManager = require('./sessionmanager');

/**
* `Authenticator` constructor.
* The `Authenticator` constructor.
*
* @api public
* @public
*/
function Authenticator() {
this._key = 'passport';
this._strategies = {};
this._serializers = [];
this._deserializers = [];
this._infoTransformers = [];
this._framework = null;
this._userProperty = 'user';
class Authenticator {
constructor() {
this._key = 'passport';
this._strategies = {};
this._serializers = [];
this._deserializers = [];
this._infoTransformers = [];
this._framework = null;
this._userProperty = 'user';
this.init();
}
this.init();
}
/**
* Initialize authenticator.
*
* @api protected
*/
Authenticator.prototype.init = function init() {
this.framework(connect());
this.use(new SessionStrategy(this.deserializeUser.bind(this)));
this._sm = new SessionManager({ key: this._key }, this.serializeUser.bind(this));
};
/**
* Utilize the given `strategy` with optional `name`, overridding the strategy's
* default name.
*
* Examples:
*
* passport.use(new TwitterStrategy(...));
*
* passport.use('api', new http.BasicStrategy(...));
*
* @param {String|Strategy} name
* @param {Strategy} strategy
* @return {Authenticator} for chaining
* @api public
*/
Authenticator.prototype.use = function use(name, strategy) {
if (!strategy) {
strategy = name;
name = strategy.name;
/**
* Initialize authenticator.
* @returns {void}
* @protected
*/
init() {
this.framework(connect());
this.use(new SessionStrategy(this.deserializeUser.bind(this)));
this._sm = new SessionManager({ key: this._key }, this.serializeUser.bind(this));
}
if (!name) { throw new Error('Authentication strategies must have a name'); }
this._strategies[name] = strategy;
return this;
};
/**
* Utilize the given `strategy` with optional `name`, overridding the strategy's
* default name.
*
* @example
*
* passport.use(new TwitterStrategy(...args));
*
* passport.use('api', new http.BasicStrategy(...args));
*
* @param {string|Strategy} name
* @param {Strategy} strategy
* @returns {Authenticator} for chaining
* @public
*/
use(name, strategy) {
if (!strategy) {
strategy = name;
({ name } = strategy);
}
if (!name) { throw new Error('Authentication strategies must have a name'); }
/**
* Un-utilize the `strategy` with given `name`.
*
* In typical applications, the necessary authentication strategies are static,
* configured once and always available. As such, there is often no need to
* invoke this function.
*
* However, in certain situations, applications may need dynamically configure
* and de-configure authentication strategies. The `use()`/`unuse()`
* combination satisfies these scenarios.
*
* Examples:
*
* passport.unuse('legacy-api');
*
* @param {String} name
* @return {Authenticator} for chaining
* @api public
*/
Authenticator.prototype.unuse = function unuse(name) {
delete this._strategies[name];
return this;
};
this._strategies[name] = strategy;
return this;
}
/**
* Setup Passport to be used under framework.
*
* By default, Passport exposes middleware that operate using Connect-style
* middleware using a `fn(req, res, next)` signature. Other popular frameworks
* have different expectations, and this function allows Passport to be adapted
* to operate within such environments.
*
* If you are using a Connect-compatible framework, including Express, there is
* no need to invoke this function.
*
* Examples:
*
* passport.framework(require('hapi-passport')());
*
* @param {Object} name
* @return {Authenticator} for chaining
* @api public
*/
Authenticator.prototype.framework = function framework(fw) {
this._framework = fw;
return this;
};
/**
* Un-utilize the `strategy` with given `name`.
*
* In typical applications, the necessary authentication strategies are static,
* configured once and always available. As such, there is often no need to
* invoke this function.
*
* However, in certain situations, applications may need dynamically configure
* and de-configure authentication strategies. The `use()`/`unuse()`
* combination satisfies these scenarios.
*
* @example
*
* passport.unuse('legacy-api');
*
* @param {string} name
* @returns {Authenticator} for chaining
* @public
*/
unuse(name) {
delete this._strategies[name];
return this;
}
/**
* Passport's primary initialization middleware.
*
* This middleware must be in use by the Connect/Express application for
* Passport to operate.
*
* Options:
* - `userProperty` Property to set on `req` upon login, defaults to _user_
*
* Examples:
*
* app.use(passport.initialize());
*
* app.use(passport.initialize({ userProperty: 'currentUser' }));
*
* @param {Object} options
* @return {Function} middleware
* @api public
*/
Authenticator.prototype.initialize = function initialize(options) {
options = options || {};
this._userProperty = options.userProperty || 'user';
/**
* Setup Passport to be used under framework.
*
* By default, Passport exposes middleware that operate using Connect-style
* middleware using a `fn(req, res, next)` signature. Other popular frameworks
* have different expectations, and this function allows Passport to be adapted
* to operate within such environments.
*
* If you are using a Connect-compatible framework, including Express, there is
* no need to invoke this function.
*
* @example
*
* passport.framework(require('hapi-passport')());
*
* @param {object} fw
* @returns {Authenticator} for chaining
* @public
*/
framework(fw) {
this._framework = fw;
return this;
}
return this._framework.initialize(this, options);
};
/**
* @typedef {Object} AuthenticatorInitializeOptions
* @property {string} [userProperty="user"] Property to set on `req` upon login
*/
/**
* Middleware that will authenticate a request using the given `strategy` name,
* with optional `options` and `callback`.
*
* Examples:
*
* passport.authenticate('local', {
* successRedirect: '/',
* failureRedirect: '/login'
* })(req, res);
*
* passport.authenticate('local', function(err, user) {
* if (!user) { return res.redirect('/login'); }
* res.end('Authenticated!');
* })(req, res);
*
* passport.authenticate('basic', { session: false })(req, res);
*
* app.get('/auth/twitter', passport.authenticate('twitter'), function(req, res) {
* // request will be redirected to Twitter
* });
* app.get('/auth/twitter/callback', passport.authenticate('twitter'), function(req, res) {
* res.json(req.user);
* });
*
* @param {String} strategy
* @param {Object} options
* @param {Function} callback
* @return {Function} middleware
* @api public
*/
Authenticator.prototype.authenticate = function authenticate(strategy, options, callback) {
return this._framework.authenticate(this, strategy, options, callback);
};
/**
* Passport's primary initialization middleware.
*
* This middleware must be in use by the Connect/Express application for
* Passport to operate.
*
* @example
*
* app.use(passport.initialize());
*
* app.use(passport.initialize({ userProperty: 'currentUser' }));
*
* @param {AuthenticatorInitializeOptions} options
* @returns {GenericCallback} middleware
* @public
*/
initialize(options) {
options = options || {};
this._userProperty = options.userProperty || 'user';
/**
* Middleware that will authorize a third-party account using the given
* `strategy` name, with optional `options`.
*
* If authorization is successful, the result provided by the strategy's verify
* callback will be assigned to `req.account`. The existing login session and
* `req.user` will be unaffected.
*
* This function is particularly useful when connecting third-party accounts
* to the local account of a user that is currently authenticated.
*
* Examples:
*
* passport.authorize('twitter-authz', { failureRedirect: '/account' });
*
* @param {String} strategy
* @param {Object} options
* @return {Function} middleware
* @api public
*/
Authenticator.prototype.authorize = function authorize(strategy, options, callback) {
options = options || {};
options.assignProperty = 'account';
return this._framework.initialize(this, options);
}
const fn = this._framework.authorize || this._framework.authenticate;
return fn(this, strategy, options, callback);
};
/**
* Middleware that will authenticate a request using the given `strategy` name,
* with optional `options` and `callback`.
*
* @example
*
* passport.authenticate('local', {
* successRedirect: '/',
* failureRedirect: '/login'
* })(req, res);
*
* passport.authenticate('local', (err, user) => {
* if (err) { next(err); return; }
* if (!user) { res.redirect('/login'); return; }
* res.end('Authenticated!');
* })(req, res);
*
* passport.authenticate('basic', { session: false })(req, res);
*
* app.get('/auth/twitter', passport.authenticate('twitter'), (req, res) => {
* // request will be redirected to Twitter
* });
* app.get('/auth/twitter/callback', passport.authenticate('twitter'), (req, res) => {
* res.json(req.user);
* });
*
* @param {string} strategy
* @param {object} options
* @param {GenericCallback} callback
* @returns {GenericCallback} middleware
* @public
*/
authenticate(strategy, options, callback) {
return this._framework.authenticate(this, strategy, options, callback);
}
/**
* Middleware that will restore login state from a session.
*
* Web applications typically use sessions to maintain login state between
* requests. For example, a user will authenticate by entering credentials into
* a form which is submitted to the server. If the credentials are valid, a
* login session is established by setting a cookie containing a session
* identifier in the user's web browser. The web browser will send this cookie
* in subsequent requests to the server, allowing a session to be maintained.
*
* If sessions are being utilized, and a login session has been established,
* this middleware will populate `req.user` with the current user.
*
* Note that sessions are not strictly required for Passport to operate.
* However, as a general rule, most web applications will make use of sessions.
* An exception to this rule would be an API server, which expects each HTTP
* request to provide credentials in an Authorization header.
*
* Examples:
*
* app.use(connect.cookieParser());
* app.use(connect.session({ secret: 'keyboard cat' }));
* app.use(passport.initialize());
* app.use(passport.session());
*
* @param {Object} options
* @return {Function} middleware
* @api public
*/
Authenticator.prototype.session = function session(options) {
return this.authenticate('session', options);
};
/**
* Middleware that will authorize a third-party account using the given
* `strategy` name, with optional `options`.
*
* If authorization is successful, the result provided by the strategy's verify
* callback will be assigned to `req.account`. The existing login session and
* `req.user` will be unaffected.
*
* This function is particularly useful when connecting third-party accounts
* to the local account of a user that is currently authenticated.
*
* @example
*
* passport.authorize('twitter-authz', { failureRedirect: '/account' });
*
* @param {string} strategy
* @param {object} options
* @param {GenericCallback} callback
* @returns {GenericCallback} middleware
* @public
*/
authorize(strategy, options, callback) {
options = options || {};
options.assignProperty = 'account';
/**
* Sets a custom SessionManager
*
* Examples:
*
* passport.sessionManager = new CustomSessionManager();
*
* @api public
*/
const fn = this._framework.authorize || this._framework.authenticate;
return fn(this, strategy, options, callback);
}
Authenticator.prototype.sessionManager = function sessionManager(mgr) {
this._sm = mgr;
return this;
};
/**
* Middleware that will restore login state from a session.
*
* Web applications typically use sessions to maintain login state between
* requests. For example, a user will authenticate by entering credentials into
* a form which is submitted to the server. If the credentials are valid, a
* login session is established by setting a cookie containing a session
* identifier in the user's web browser. The web browser will send this cookie
* in subsequent requests to the server, allowing a session to be maintained.
*
* If sessions are being utilized, and a login session has been established,
* this middleware will populate `req.user` with the current user.
*
* Note that sessions are not strictly required for Passport to operate.
* However, as a general rule, most web applications will make use of sessions.
* An exception to this rule would be an API server, which expects each HTTP
* request to provide credentials in an Authorization header.
*
* @example
*
* app.use(connect.cookieParser());
* app.use(connect.session({ secret: 'keyboard cat' }));
* app.use(passport.initialize());
* app.use(passport.session());
*
* @param {object} options
* @returns {GenericCallback} middleware
* @public
*/
session(options) {
return this.authenticate('session', options);
}
/**
* Registers a function used to serialize user objects into the session.
*
* Examples:
*
* passport.serializeUser(function(user, done) {
* done(null, user.id);
* });
*
* @api public
*/
/**
* Sets a custom SessionManager
*
* @example
*
* passport.sessionManager = new CustomSessionManager();
*
* @public
*/
// eslint-disable-next-line consistent-return
Authenticator.prototype.serializeUser = function serializeUser(fn, req, done) {
if (typeof fn === 'function') {
return this._serializers.push(fn);
sessionManager(mgr) {
this._sm = mgr;
return this;
}
// private implementation that traverses the chain of serializers, attempting
// to serialize a user
const user = fn;
/**
* Registers a function used to serialize user objects into the session.
*
* @example
*
* passport.serializeUser(function(user, done) {
* done(null, user.id);
* });
*
* @public
*/
// For backwards compatibility
if (typeof req === 'function') {
done = req;
req = undefined;
}
const stack = this._serializers;
// eslint-disable-next-line consistent-return
(function pass(i, err, obj) {
// serializers use 'pass' as an error to skip processing
if (err === 'pass') {
err = undefined;
serializeUser(fn, req, done) {
if (typeof fn === 'function') {
return this._serializers.push(fn);
}
// an error or serialized object was obtained, done
if (err || obj || obj === 0) { return done(err, obj); }
const layer = stack[i];
if (!layer) {
return done(new Error('Failed to serialize user into session'));
}
// private implementation that traverses the chain of serializers, attempting
// to serialize a user
const user = fn;
function serialized(e, o) {
pass(i + 1, e, o);
// For backwards compatibility
if (typeof req === 'function') {
done = req;
req = undefined;
}
try {
const arity = layer.length;
if (arity === 3) {
layer(req, user, serialized);
} else {
layer(user, serialized);
const stack = this._serializers;
// eslint-disable-next-line consistent-return
(function pass(i, err, obj) {
// serializers use 'pass' as an error to skip processing
if (err === 'pass') {
err = undefined;
}
} catch (e) {
return done(e);
}
}(0));
};
// an error or serialized object was obtained, done
if (err || obj || obj === 0) { return done(err, obj); }
/**
* Registers a function used to deserialize user objects out of the session.
*
* Examples:
*
* passport.deserializeUser(function(id, done) {
* User.findById(id, function (err, user) {
* done(err, user);
* });
* });
*
* @api public
*/
const layer = stack[i];
if (!layer) {
return done(new Error('Failed to serialize user into session'));
}
// eslint-disable-next-line consistent-return
Authenticator.prototype.deserializeUser = function deserializeUser(fn, req, done) {
if (typeof fn === 'function') {
return this._deserializers.push(fn);
}
// private implementation that traverses the chain of deserializers,
// attempting to deserialize a user
const obj = fn;
// eslint-disable-next-line jsdoc/require-jsdoc
function serialized(e, o) {
pass(i + 1, e, o);
}
// For backwards compatibility
if (typeof req === 'function') {
done = req;
req = undefined;
try {
const arity = layer.length;
if (arity === 3) {
layer(req, user, serialized);
} else {
layer(user, serialized);
}
} catch (e) {
return done(e);
}
}(0));
}
const stack = this._deserializers;
/**
* Registers a function used to deserialize user objects out of the session.
*
* @example
*
* passport.deserializeUser(function(id, done) {
* User.findById(id, function (err, user) {
* done(err, user);
* });
* });
*
* @public
*/
// eslint-disable-next-line consistent-return
(function pass(i, err, user) {
// deserializers use 'pass' as an error to skip processing
if (err === 'pass') {
err = undefined;
deserializeUser(fn, req, done) {
if (typeof fn === 'function') {
return this._deserializers.push(fn);
}
// an error or deserialized user was obtained, done
if (err || user) { return done(err, user); }
// a valid user existed when establishing the session, but that user has
// since been removed
if (user === null || user === false) { return done(null, false); }
const layer = stack[i];
if (!layer) {
return done(new Error('Failed to deserialize user out of session'));
}
// private implementation that traverses the chain of deserializers,
// attempting to deserialize a user
const obj = fn;
function deserialized(e, u) {
pass(i + 1, e, u);
// For backwards compatibility
if (typeof req === 'function') {
done = req;
req = undefined;
}
try {
const arity = layer.length;
if (arity === 3) {
layer(req, obj, deserialized);
} else {
layer(obj, deserialized);
const stack = this._deserializers;
// eslint-disable-next-line consistent-return
(function pass(i, err, user) {
// deserializers use 'pass' as an error to skip processing
if (err === 'pass') {
err = undefined;
}
} catch (e) {
return done(e);
}
}(0));
};
// an error or deserialized user was obtained, done
if (err || user) { return done(err, user); }
// a valid user existed when establishing the session, but that user has
// since been removed
if (user === null || user === false) { return done(null, false); }
/**
* Registers a function used to transform auth info.
*
* In some circumstances authorization details are contained in authentication
* credentials or loaded as part of verification.
*
* For example, when using bearer tokens for API authentication, the tokens may
* encode (either directly or indirectly in a database), details such as scope
* of access or the client to which the token was issued.
*
* Such authorization details should be enforced separately from authentication.
* Because Passport deals only with the latter, this is the responsiblity of
* middleware or routes further along the chain. However, it is not optimal to
* decode the same data or execute the same database query later. To avoid
* this, Passport accepts optional `info` along with the authenticated `user`
* in a strategy's `success()` action. This info is set at `req.authInfo`,
* where said later middlware or routes can access it.
*
* Optionally, applications can register transforms to proccess this info,
* which take effect prior to `req.authInfo` being set. This is useful, for
* example, when the info contains a client ID. The transform can load the
* client from the database and include the instance in the transformed info,
* allowing the full set of client properties to be convieniently accessed.
*
* If no transforms are registered, `info` supplied by the strategy will be left
* unmodified.
*
* Examples:
*
* passport.transformAuthInfo(function(info, done) {
* Client.findById(info.clientID, function (err, client) {
* info.client = client;
* done(err, info);
* });
* });
*
* @api public
*/
const layer = stack[i];
if (!layer) {
return done(new Error('Failed to deserialize user out of session'));
}
// eslint-disable-next-line consistent-return
Authenticator.prototype.transformAuthInfo = function transformAuthInfo(fn, req, done) {
if (typeof fn === 'function') {
return this._infoTransformers.push(fn);
}
// private implementation that traverses the chain of transformers,
// attempting to transform auth info
const info = fn;
// eslint-disable-next-line jsdoc/require-jsdoc
function deserialized(e, u) {
pass(i + 1, e, u);
}
// For backwards compatibility
if (typeof req === 'function') {
done = req;
req = undefined;
try {
const arity = layer.length;
if (arity === 3) {
layer(req, obj, deserialized);
} else {
layer(obj, deserialized);
}
} catch (e) {
return done(e);
}
}(0));
}
const stack = this._infoTransformers;
/**
* Registers a function used to transform auth info.
*
* In some circumstances authorization details are contained in authentication
* credentials or loaded as part of verification.
*
* For example, when using bearer tokens for API authentication, the tokens may
* encode (either directly or indirectly in a database), details such as scope
* of access or the client to which the token was issued.
*
* Such authorization details should be enforced separately from authentication.
* Because Passport deals only with the latter, this is the responsiblity of
* middleware or routes further along the chain. However, it is not optimal to
* decode the same data or execute the same database query later. To avoid
* this, Passport accepts optional `info` along with the authenticated `user`
* in a strategy's `success()` action. This info is set at `req.authInfo`,
* where said later middlware or routes can access it.
*
* Optionally, applications can register transforms to proccess this info,
* which take effect prior to `req.authInfo` being set. This is useful, for
* example, when the info contains a client ID. The transform can load the
* client from the database and include the instance in the transformed info,
* allowing the full set of client properties to be convieniently accessed.
*
* If no transforms are registered, `info` supplied by the strategy will be left
* unmodified.
*
* @example
*
* passport.transformAuthInfo(function(info, done) {
* Client.findById(info.clientID, function (err, client) {
* info.client = client;
* done(err, info);
* });
* });
*
* @public
*/
// eslint-disable-next-line consistent-return
(function pass(i, err, tinfo) {
// transformers use 'pass' as an error to skip processing
if (err === 'pass') {
err = undefined;
transformAuthInfo(fn, req, done) {
if (typeof fn === 'function') {
return this._infoTransformers.push(fn);
}
// an error or transformed info was obtained, done
if (err || tinfo) { return done(err, tinfo); }
const layer = stack[i];
if (!layer) {
// if no transformers are registered (or they all pass), the default
// behavior is to use the un-transformed info as-is
return done(null, info);
// private implementation that traverses the chain of transformers,
// attempting to transform auth info
const info = fn;
// For backwards compatibility
if (typeof req === 'function') {
done = req;
req = undefined;
}
const stack = this._infoTransformers;
// eslint-disable-next-line consistent-return
(function pass(i, err, tinfo) {
// transformers use 'pass' as an error to skip processing
if (err === 'pass') {
err = undefined;
}
// an error or transformed info was obtained, done
if (err || tinfo) { return done(err, tinfo); }
function transformed(e, t) {
pass(i + 1, e, t);
}
const layer = stack[i];
if (!layer) {
// if no transformers are registered (or they all pass), the default
// behavior is to use the un-transformed info as-is
return done(null, info);
}
try {
const arity = layer.length;
if (arity === 1) {
// sync
const t = layer(info);
transformed(null, t);
} else if (arity === 3) {
layer(req, info, transformed);
} else {
layer(info, transformed);
// eslint-disable-next-line jsdoc/require-jsdoc
function transformed(e, t) {
pass(i + 1, e, t);
}
} catch (e) {
return done(e);
}
}(0));
};
/**
* Return strategy with given `name`.
*
* @param {String} name
* @return {Strategy}
* @api private
*/
Authenticator.prototype._strategy = function _strategy(name) {
return this._strategies[name];
};
try {
const arity = layer.length;
if (arity === 1) {
// sync
const t = layer(info);
transformed(null, t);
} else if (arity === 3) {
layer(req, info, transformed);
} else {
layer(info, transformed);
}
} catch (e) {
return done(e);
}
}(0));
}
/**
* Return strategy with given `name`.
*
* @param {string} name
* @returns {Strategy}
* @private
*/
_strategy(name) {
return this._strategies[name];
}
}

@@ -486,0 +494,0 @@ /**

@@ -0,23 +1,18 @@

'use strict';
/**
* `AuthenticationError` error.
* The `AuthenticationError` error.
*
* @constructor
* @api private
* @private
*/
/* eslint-disable no-proto, no-proto, no-caller, no-restricted-properties */
function AuthenticationError(message, status) {
Error.call(this);
Error.captureStackTrace(this, arguments.callee);
this.name = 'AuthenticationError';
this.message = message;
this.status = status || 401;
class AuthenticationError extends Error {
constructor(message, status) {
super(message);
Error.captureStackTrace(this, AuthenticationError);
this.name = 'AuthenticationError';
this.status = status || 401;
}
}
// Inherit from `Error`.
AuthenticationError.prototype.__proto__ = Error.prototype;
// Expose constructor.
module.exports = AuthenticationError;

@@ -0,5 +1,6 @@

'use strict';
/**
* Module dependencies.
*/
/* eslint-disable camelcase, no-proto, no-shadow */

@@ -16,3 +17,3 @@ const initialize = require('../middleware/initialize');

* @return {Object}
* @api protected
* @protected
*/

@@ -24,4 +25,4 @@

initialize,
authenticate,
authenticate
};
};
/**
* Module dependencies.
*/
'use strict';
// var http = require('http')
// const http = require('http')
// , req = http.IncomingMessage.prototype;
/* eslint-disable no-multi-assign, camelcase, no-proto, no-shadow */
/* eslint-disable no-multi-assign */
const req = exports = module.exports = {};
/* eslint-enable no-multi-assign */
/**
* @typedef {Object} LogInOptions
* @property {boolean} [session] Save login state in session, defaults to _true_
*/
/**
* Initiate a login session for `user`.
*
* Options:
* - `session` Save login state in session, defaults to _true_
*
* Examples:
* @example
*
* req.logIn(user, { session: false });
*
* req.logIn(user, function(err) {
* req.logIn(user, (err) => {
* if (err) { throw err; }

@@ -28,5 +32,6 @@ * // session saved

* @param {User} user
* @param {Object} options
* @param {Function} done
* @api public
* @param {LogInOptions} options
* @param {GenericCallback} done
* @returns {void}
* @public
*/

@@ -49,8 +54,7 @@ req.logIn = function logIn(user, options, done) {

if (!this._passport) { throw new Error('passport.initialize() middleware not in use'); }
if (typeof done !== 'function') { throw new Error('req#login requires a callback function'); }
if (typeof done !== 'function') { throw new TypeError('req#login requires a callback function'); }
const self = this;
// eslint-disable-next-line consistent-return
this._passport.instance._sm.logIn(this, user, (err) => {
if (err) { self[property] = null; return done(err); }
if (err) { this[property] = null; return done(err); }
done();

@@ -68,6 +72,7 @@ });

* Terminate an existing login session.
*
* @api public
* @param {GenericCallback} done
* @returns {void}
* @public
*/
req.logOut = function logOut() {
req.logOut = function logOut(done) {
let property = 'user';

@@ -80,3 +85,3 @@ if (this._passport && this._passport.instance) {

if (this._passport) {
this._passport.instance._sm.logOut(this);
this._passport.instance._sm.logOut(this, done);
}

@@ -90,4 +95,4 @@ };

*
* @return {Boolean}
* @api public
* @returns {boolean}
* @public
*/

@@ -100,3 +105,3 @@ req.isAuthenticated = function isAuthenticated() {

return !!(this[property]);
return Boolean(this[property]);
};

@@ -107,4 +112,4 @@

*
* @return {Boolean}
* @api public
* @returns {boolean}
* @public
*/

@@ -111,0 +116,0 @@ req.isUnauthenticated = function isUnauthenticated() {

@@ -6,2 +6,3 @@ /**

/* eslint-disable no-multi-assign */
'use strict';

@@ -15,3 +16,3 @@ const Passport = require('./authenticator');

*
* @api public
* @public
*/

@@ -18,0 +19,0 @@ exports = module.exports = new Passport();

@@ -0,1 +1,4 @@

/* eslint-disable no-shadow */
'use strict';
/**

@@ -5,4 +8,2 @@ * Module dependencies.

/* eslint-disable camelcase, no-proto, no-shadow */
const http = require('http');

@@ -58,3 +59,3 @@ const AuthenticationError = require('../errors/authenticationerror');

*
* Examples:
* @example
*

@@ -67,7 +68,8 @@ * passport.authenticate('local', { successRedirect: '/', failureRedirect: '/login' });

*
* @param {String|Array} name
* @param {Object} options
* @param {Function} callback
* @return {Function}
* @api public
* @param {Authenticator} passport
* @param {string|Array} name
* @param {object} options
* @param {GenericCallback} callback
* @returns {GenericCallback}
* @public
*/

@@ -102,2 +104,3 @@ module.exports = function authenticate(passport, name, options, callback) {

// eslint-disable-next-line jsdoc/require-jsdoc
function redirect(url) {

@@ -110,3 +113,3 @@ if (req.session && req.session.save && typeof req.session.save === 'function') {

// eslint-disable-next-line consistent-return
// eslint-disable-next-line consistent-return, jsdoc/require-jsdoc
function allFailed() {

@@ -124,5 +127,4 @@ if (callback) {

// message, the first failure will be displayed.
let failure = failures[0] || {};
let challenge = failure.challenge || {};
let msg;
const failure = failures[0] || {};
const challenge = failure.challenge || {};

@@ -134,6 +136,8 @@ if (options.failureFlash) {

}
flash.type = flash.type || 'error';
if (typeof flash !== 'boolean') {
flash.type = flash.type || 'error';
}
const type = flash.type || challenge.type || 'error';
msg = flash.message || challenge.message || challenge;
const msg = flash.message || challenge.message || challenge;
if (typeof msg === 'string') {

@@ -144,3 +148,3 @@ req.flash(type, msg);

if (options.failureMessage) {
msg = options.failureMessage;
let msg = options.failureMessage;
if (typeof msg === 'boolean') {

@@ -165,9 +169,3 @@ msg = challenge.message || challenge;

let rstatus;
let status;
// eslint-disable-next-line no-plusplus
for (let j = 0, len = failures.length; j < len; j++) {
failure = failures[j];
challenge = failure.challenge;
status = failure.status;
failures.forEach(({ challenge, status }) => {
rstatus = rstatus || status;

@@ -177,3 +175,3 @@ if (typeof challenge === 'string') {

}
}
});

@@ -224,3 +222,3 @@ res.statusCode = rstatus || 401;

* @param {Object} info
* @api public
* @public
*/

@@ -242,3 +240,5 @@

}
flash.type = flash.type || 'success';
if (typeof flash !== 'boolean') {
flash.type = flash.type || 'success';
}

@@ -270,3 +270,3 @@ const type = flash.type || info.type || 'success';

// eslint-disable-next-line consistent-return
// eslint-disable-next-line consistent-return, jsdoc/require-jsdoc
function complete() {

@@ -306,5 +306,6 @@ if (options.successReturnToOrRedirect) {

*
* @param {String} challenge
* @param {Number} status
* @api public
* @param {string} challenge
* @param {number} status
* @returns {void}
* @public
*/

@@ -329,5 +330,6 @@ strategy.fail = function fail(challenge, status) {

*
* @param {String} url
* @param {Number} status
* @api public
* @param {string} url
* @param {number} status
* @returns {void}
* @public
*/

@@ -359,3 +361,4 @@ strategy.redirect = function redirect(url, status) {

*
* @api public
* @returns {void}
* @public
*/

@@ -374,3 +377,3 @@ strategy.pass = function pass() {

* @param {Error} err
* @api public
* @public
*/

@@ -377,0 +380,0 @@

@@ -0,1 +1,3 @@

'use strict';
/**

@@ -22,3 +24,3 @@ * Passport initialization.

*
* Examples:
* @example
*

@@ -41,3 +43,3 @@ * app.use(connect.cookieParser());

* @return {Function}
* @api public
* @public
*/

@@ -47,4 +49,4 @@

/* eslint-disable no-proto, no-shadow */
module.exports = function initialize(passport) {
/* eslint-disable-next-line no-shadow */
return function initialize(req, res, next) {

@@ -51,0 +53,0 @@ req._passport = {};

@@ -1,42 +0,43 @@

/* eslint-disable camelcase, no-proto, no-shadow */
'use strict';
function SessionManager(options, serializeUser) {
if (typeof options === 'function') {
serializeUser = options;
options = undefined;
class SessionManager {
constructor(options, serializeUser) {
if (typeof options === 'function') {
serializeUser = options;
options = undefined;
}
options = options || {};
this._key = options.key || 'passport';
this._serializeUser = serializeUser;
}
options = options || {};
this._key = options.key || 'passport';
this._serializeUser = serializeUser;
}
logIn(req, user, cb) {
// eslint-disable-next-line consistent-return
this._serializeUser(user, req, (err, obj) => {
if (err) {
return cb(err);
}
if (!req._passport.session) {
req._passport.session = {};
}
req._passport.session.user = obj;
if (!req.session) {
req.session = {};
}
req.session[this._key] = req._passport.session;
cb();
});
}
SessionManager.prototype.logIn = function logIn(req, user, cb) {
const self = this;
// eslint-disable-next-line consistent-return
this._serializeUser(user, req, (err, obj) => {
if (err) {
return cb(err);
// eslint-disable-next-line class-methods-use-this
logOut(req, cb) {
if (req._passport && req._passport.session) {
delete req._passport.session.user;
}
if (!req._passport.session) {
req._passport.session = {};
}
req._passport.session.user = obj;
if (!req.session) {
req.session = {};
}
req.session[self._key] = req._passport.session;
cb();
});
};
SessionManager.prototype.logOut = function logOut(req, cb) {
if (req._passport && req._passport.session) {
delete req._passport.session.user;
// eslint-disable-next-line no-unused-expressions
cb && cb();
}
// eslint-disable-next-line no-unused-expressions
cb && cb();
};
}
module.exports = SessionManager;

@@ -0,1 +1,2 @@

'use strict';
/**

@@ -5,75 +6,67 @@ * Module dependencies.

/* eslint-disable camelcase, no-proto, no-shadow */
const util = require('util');
const Strategy = require('@passport-next/passport-strategy');
/**
* `SessionStrategy` constructor.
* The `SessionStrategy` constructor.
*
* @api public
* @public
*/
function SessionStrategy(options, deserializeUser) {
if (typeof options === 'function') {
deserializeUser = options;
options = undefined;
class SessionStrategy extends Strategy {
constructor(options, deserializeUser) {
if (typeof options === 'function') {
deserializeUser = options;
options = undefined;
}
options = options || {};
super();
this.name = 'session';
this._deserializeUser = deserializeUser;
}
options = options || {};
Strategy.call(this);
this.name = 'session';
this._deserializeUser = deserializeUser;
}
/**
* Authenticate request based on the current session state.
*
* The session authentication strategy uses the session to restore any login
* state across requests. If a login session has been established, `req.user`
* will be populated with the current user.
*
* This strategy is registered automatically by Passport.
*
* @param {Object} req
* @param {Object} options
* @protected
*/
/**
* Inherit from `Strategy`.
*/
util.inherits(SessionStrategy, Strategy);
// eslint-disable-next-line consistent-return, no-unused-vars
authenticate(req, options) {
if (!req._passport) { return this.error(new Error('passport.initialize() middleware not in use')); }
options = options || {};
/**
* Authenticate request based on the current session state.
*
* The session authentication strategy uses the session to restore any login
* state across requests. If a login session has been established, `req.user`
* will be populated with the current user.
*
* This strategy is registered automatically by Passport.
*
* @param {Object} req
* @param {Object} options
* @api protected
*/
let su;
// eslint-disable-next-line consistent-return, no-unused-vars
SessionStrategy.prototype.authenticate = function authenticate(req, options) {
if (!req._passport) { return this.error(new Error('passport.initialize() middleware not in use')); }
options = options || {};
if (req._passport.session) {
su = req._passport.session.user;
}
const self = this;
let su;
if (req._passport.session) {
su = req._passport.session.user;
if (su || su === 0) {
// eslint-disable-next-line consistent-return
this._deserializeUser(su, req, (err, user) => {
if (err) { return this.error(err); }
if (!user) {
delete req._passport.session.user;
} else {
// TODO: Remove instance access
const property = req._passport.instance._userProperty || 'user';
req[property] = user;
}
this.pass();
});
} else {
this.pass();
}
}
}
if (su || su === 0) {
// eslint-disable-next-line consistent-return
this._deserializeUser(su, req, (err, user) => {
if (err) { return self.error(err); }
if (!user) {
delete req._passport.session.user;
} else {
// TODO: Remove instance access
const property = req._passport.instance._userProperty || 'user';
req[property] = user;
}
self.pass();
});
} else {
self.pass();
}
};
/**

@@ -80,0 +73,0 @@ * Expose `SessionStrategy`.

{
"name": "@passport-next/passport",
"version": "2.1.1",
"description": "Simple, unobtrusive authentication for Node.js.",
"keywords": [
"express",
"connect",
"auth",
"authn",
"authentication"
],
"author": {
"name": "Rowan Wookey",
"email": "admin@rwky.net"
},
"repository": {
"type": "git",
"url": "git://github.com/passport-next/passport.git"
},
"bugs": {
"url": "http://github.com/passport-next/passport/issues"
},
"license": "MIT",
"licenses": [
{
"type": "MIT",
"url": "http://opensource.org/licenses/MIT"
"name": "@passport-next/passport",
"version": "3.0.0",
"description": "Simple, unobtrusive authentication for Node.js.",
"author": {
"name": "Passport Next Developers",
"url": "https://github.com/orgs/passport-next/people"
},
"homepage": "https://github.com/passport-next/passport",
"contributors": [
"Brett Zamir"
],
"bugs": {
"url": "https://github.com/passport-next/passport/issues"
},
"dependencies": {
"@passport-next/passport-strategy": "1.x.x"
},
"devDependencies": {
"@mysticatea/eslint-plugin": "^10.0.3",
"@passport-next/chai-passport-strategy": "1.x.x",
"@passport-next/eslint-config-passport-next": "1.x.x",
"chai": "4.x.x",
"chai-connect-middleware": "0.x.x",
"coveralls": "^3.0.5",
"eslint": "^5.16.0",
"eslint-config-standard": "^12.0.0",
"eslint-plugin-compat": "^3.1.1",
"eslint-plugin-eslint-comments": "^3.1.1",
"eslint-plugin-import": "^2.17.3",
"eslint-plugin-jsdoc": "^8.0.0",
"eslint-plugin-markdown": "^1.0.0",
"eslint-plugin-no-use-extend-native": "^0.4.0",
"eslint-plugin-node": "^9.1.0",
"eslint-plugin-promise": "^4.1.1",
"eslint-plugin-standard": "^4.0.0",
"eslint-plugin-unicorn": "^9.1.0",
"make-node": "^0.4.6",
"mocha": "6.x.x",
"nunjucks": "^3.2.0",
"nyc": "^14.1.1"
},
"engines": {
"node": ">=8.0.0"
},
"keywords": [
"express",
"connect",
"auth",
"authn",
"authentication"
],
"license": "MIT",
"main": "./lib",
"repository": {
"type": "git",
"url": "https://github.com/passport-next/passport"
},
"scripts": {
"templates": "node ./templates/gen.js",
"init-new-project": "node ./templates/gen --init",
"lint": "eslint --max-warnings 0 --ext js,md .",
"lintfix": "eslint --ext js,md . --fix",
"test": "mocha --reporter spec --require test/bootstrap/node test/*.test.js test/**/*.test.js",
"coverage": "nyc --report-dir=var/coverage --reporter=lcov npm test",
"coveralls": "nyc report --report-dir=var/coverage --reporter=text-lcov | coveralls"
}
],
"main": "./lib",
"dependencies": {
"@passport-next/passport-strategy": "1.x.x"
},
"devDependencies": {
"@passport-next/chai-passport-strategy": "1.x.x",
"chai": "4.x.x",
"chai-connect-middleware": "0.x.x",
"eslint": "^5.16.0",
"eslint-config-airbnb-base": "13.x.x",
"eslint-plugin-import": "^2.17.2",
"make-node": "^0.4.6",
"mocha": "6.x.x"
},
"engines": {
"node": ">=6.0.0"
},
"scripts": {
"spec": "node_modules/.bin/mocha --reporter spec --require test/bootstrap/node test/*.test.js test/**/*.test.js",
"lint": "eslint --ext .js . --max-warnings 0",
"lintfix": "eslint --ext .js . --fix",
"test": "npm run lint && npm run spec"
}
}

@@ -1,3 +0,13 @@

# Passport-Next/Passport
# Passport-Next/Passport
Status:
[![NPM version](https://img.shields.io/npm/v/@passport-next/passport.svg)](https://www.npmjs.com/package/@passport-next/passport)
[![Build Status](https://travis-ci.org/passport-next/passport.svg?branch=master)](https://travis-ci.org/passport-next/passport)
[![Coverage Status](https://coveralls.io/repos/github/passport-next/passport/badge.svg?branch=master)](https://coveralls.io/github/passport-next/passport?branch=master)
[![Maintainability](https://api.codeclimate.com/v1/badges/deaf381bf0cff6bf26a5/maintainability)](https://codeclimate.com/github/passport-next/passport/maintainability)
[![Dependencies](https://david-dm.org/passport-next/passport.png)](https://david-dm.org/passport-next/passport)
[![SAST](https://gitlab.com/passport-next/passport/badges/master/pipeline.svg)](https://gitlab.com/passport-next/passport)
## About
Passport-Next/Passport is [Express](http://expressjs.com/)-compatible authentication

@@ -13,34 +23,3 @@ middleware for [Node.js](http://nodejs.org/).

Status:
[![NPM version](https://img.shields.io/npm/v/@passport-next/passport.svg)](https://www.npmjs.com/package/@passport-next/passport)
[![Build Status](https://travis-ci.org/passport-next/passport.svg?branch=master)](https://travis-ci.org/passport-next/passport)
[![Coverage Status](https://coveralls.io/repos/github/passport-next/passport/badge.svg?branch=master)](https://coveralls.io/github/passport-next/passport?branch=master)
[![Maintainability](https://api.codeclimate.com/v1/badges/deaf381bf0cff6bf26a5/maintainability)](https://codeclimate.com/github/passport-next/passport/maintainability)
[![Dependencies](https://david-dm.org/passport-next/passport.png)](https://david-dm.org/passport-next/passport)
[![SAST](https://gitlab.com/passport-next/passport/badges/master/build.svg)](https://gitlab.com/passport-next/passport/badges/master/build.svg)
## Differences between passport and passport-next
[Passport Next](https://github.com/passport-next) was created as a fork of the Passport repositories
when the upstream repositories became stale and stopped working due to changes at the various
authentication providers (e.g. Facebook API deprecation, Tumblr using HTTPS etc.)
Passport Next aims to:
* Keep the modules up to date with the various authentication providers
* Maintain up to date dependencies
* Address any security issues promptly
* Ensure compatibility with the current [supported versions](https://github.com/nodejs/Release) of Node
* Maintain the repositories in an organisation so maintaining isn't the responsibility of one person
* Follow [Semantic Versioning](https://semver.org/)
* Keep an up to date CHANGELOG.md
**Passport Next does not aim to be backwards compatible with the upstream repositories.
The changes required to keep up to date and functioning prohibit that so if you're migrating
from the upstream modules please test your code thouroughly!**
If you wish to join the team please raise an issue and one of the maintainers will assess your
request.
## Install

@@ -52,147 +31,19 @@

## Usage
## Docs
#### Strategies
[Please see the wiki](https://github.com/passport-next/passport/wiki)
Passport uses the concept of strategies to authenticate requests. Strategies
can range from verifying username and password credentials, delegated
authentication using [OAuth](http://oauth.net/) (for example, via [Facebook](http://www.facebook.com/)
or [Twitter](http://twitter.com/)), or federated authentication using [OpenID](http://openid.net/).
## Need help?
Before authenticating requests, the strategy (or strategies) used by an
application must be configured.
Please raise an [issue](https://github.com/passport-next/passport/issues) and/or ask a question on [Stackoverflow](https://stackoverflow.com) with the `passport.js` tag.
```javascript
passport.use(new LocalStrategy(
function(username, password, done) {
User.findOne({ username: username }, function (err, user) {
if (err) { return done(err); }
if (!user) { return done(null, false); }
if (!user.verifyPassword(password)) { return done(null, false); }
return done(null, user);
});
}
));
```
## Support policy
There are 480+ strategies. Find the ones you want at: [passportjs.org](http://passportjs.org)
We support all [node versions](https://github.com/nodejs/Release) supported by the Node Foundation
#### Sessions
Passport will maintain persistent login sessions. In order for persistent
sessions to work, the authenticated user must be serialized to the session, and
deserialized when subsequent requests are made.
Passport does not impose any restrictions on how your user records are stored.
Instead, you provide functions to Passport which implements the necessary
serialization and deserialization logic. In a typical application, this will be
as simple as serializing the user ID, and finding the user by ID when
deserializing.
## Contributing
```javascript
passport.serializeUser(function(user, done) {
done(null, user.id);
});
Please see [CONTRIBUTING.md](https://github.com/passport-next/passport/blob/master/CONTRIBUTING.md)
passport.deserializeUser(function(id, done) {
User.findById(id, function (err, user) {
done(err, user);
});
});
```
#### Middleware
To use Passport in an [Express](http://expressjs.com/) or
[Connect](http://senchalabs.github.com/connect/)-based application, configure it
with the required `passport.initialize()` middleware. If your application uses
persistent login sessions (recommended, but not required), `passport.session()`
middleware must also be used.
```javascript
var app = express();
app.use(require('serve-static')(__dirname + '/../../public'));
app.use(require('cookie-parser')());
app.use(require('body-parser').urlencoded({ extended: true }));
app.use(require('express-session')({ secret: 'keyboard cat', resave: true, saveUninitialized: true }));
app.use(passport.initialize());
app.use(passport.session());
```
#### Authenticate Requests
Passport provides an `authenticate()` function, which is used as route
middleware to authenticate requests.
```javascript
app.post('/login',
passport.authenticate('local', { failureRedirect: '/login' }),
function(req, res) {
res.redirect('/');
});
```
#### Protect Routes When Using Sessions
Passport provides an `isAuthenticated()` function on the request object, which
is used to determine if the user has been authenticated and stored in the
session.
```javascript
app.post('/some/protected/route',
function(req, res, next) {
if(req.isAuthenticated()){
next();
} else {
next(new Error('Unauthorized'));
}
});
```
For a more complete solution to handling unauthenticated users, see
[connect-ensure-login](https://github.com/jaredhanson/connect-ensure-login), a
middleware to ensure login sessions.
## Strategies
Passport has a comprehensive set of **over 480** authentication strategies
covering social networking, enterprise integration, API services, and more.
## Search all strategies
There is a **Strategy Search** at [passportjs.org](http://passportjs.org)
The following table lists commonly used strategies:
|Strategy | Protocol |Developer |
|---------------------------------------------------------------|--------------------------|------------------------------------------------|
|[Local](https://github.com/jaredhanson/passport-local) | HTML form |[Jared Hanson](https://github.com/jaredhanson) |
|[OpenID](https://github.com/jaredhanson/passport-openid) | OpenID |[Jared Hanson](https://github.com/jaredhanson) |
|[BrowserID](https://github.com/jaredhanson/passport-browserid) | BrowserID |[Jared Hanson](https://github.com/jaredhanson) |
|[Facebook](https://github.com/jaredhanson/passport-facebook) | OAuth 2.0 |[Jared Hanson](https://github.com/jaredhanson) |
|[Google](https://github.com/jaredhanson/passport-google) | OpenID |[Jared Hanson](https://github.com/jaredhanson) |
|[Google](https://github.com/jaredhanson/passport-google-oauth) | OAuth / OAuth 2.0 |[Jared Hanson](https://github.com/jaredhanson) |
|[Twitter](https://github.com/jaredhanson/passport-twitter) | OAuth |[Jared Hanson](https://github.com/jaredhanson) |
|[Azure Active Directory](https://github.com/AzureAD/passport-azure-ad) | OAuth 2.0 / OpenID / SAML |[Azure](https://github.com/azuread) |
## Examples
- For a complete, working example, refer to the [example](https://github.com/passport/express-4.x-local-example)
that uses [passport-local](https://github.com/jaredhanson/passport-local).
- **Local Strategy**: Refer to the following tutorials for setting up user authentication via LocalStrategy (`passport-local`):
- Mongo
- Express v3x - [Tutorial](http://mherman.org/blog/2016/09/25/node-passport-and-postgres/#.V-govpMrJE5) / [working example](https://github.com/mjhea0/passport-local-knex)
- Express v4x - [Tutorial](http://mherman.org/blog/2015/01/31/local-authentication-with-passport-and-express-4/) / [working example](https://github.com/mjhea0/passport-local-express4)
- Postgres
- [Tutorial](http://mherman.org/blog/2016/09/25/node-passport-and-postgres/) / [working example](https://github.com/mjhea0/passport-local-knex)
- Koa - [Tutorial](http://mherman.org/blog/2018/01/02/user-authentication-with-passport-and-koa) / [working example](https://github.com/mjhea0/node-koa-api)
- **Social Authentication**: Refer to the following tutorials for setting up various social authentication strategies:
- Express v3x - [Tutorial](http://mherman.org/blog/2013/11/10/social-authentication-with-passport-dot-js/) / [working example](https://github.com/mjhea0/passport-examples)
- Express v4x - [Tutorial](http://mherman.org/blog/2015/09/26/social-authentication-in-node-dot-js-with-passport) / [working example](https://github.com/mjhea0/passport-social-auth)
## Tests
```
$ npm install
$ make test
```
SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc