Reputation: 659
I'm trying to implement a passport
authentication strategy to my application, but keep getting the following error after trying to sign in:
TypeError: passport.authenticate is not a function at exports.signin
I'm pretty sure that I have missed something but cannot figure out what could that be. Since there aren't anything related to authentication inside the user
model, I decided not to output it in here.
My folder structure is as follows:
|-- project
|-- .env
|-- index.html
|-- package.json
|-- server.js
|-- app
| |-- config
| | |-- passport.js
| | |-- routes.js
| | |-- test.js
| | |-- passport
| | |-- local.js
| |-- controllers
| | |-- users.js
| |-- models
| |-- user.js
Here's my routes.js
file
/* Config / Routes */
'use strict';
const users = require('../controllers/users');
module.exports = function(app) {
app.post('/login', users.signin);
app.post('/users', users.create);
};
Here's my local.js
for LocalStrategy
:
/* Config / Passport / Local */
'use strict';
const mongoose = require('mongoose');
const LocalStrategy = require('passport-local').Strategy;
const User = mongoose.model('User');
module.exports = new LocalStrategy({
usernameField: 'email'
},
function(email, password, done) {
User.findOne({email: email }, function (err, user) {
if (err)
return done(err);
if (!user)
return done(null, false, { message: 'Unknown user' });
if(!user.validPassword(password))
return done(null, false, { message: 'Invalid password' });
return done(null, user);
});
}
);
Here's my passport.js
file where the LocalStrategy
is assigned to the passport
:
/* Config / Passport */
'use strict';
const mongoose = require('mongoose');
const User = mongoose.model('User');
const local = require('./passport/local');
module.exports = function(passport) {
passport.use(local);
};
Here's my users.js
controller file:
/* Controller / Users */
'use strict';
const mongoose = require('mongoose');
const User = mongoose.model('User');
const only = require('only');
const passport = require('../config/passport');
/* Creates a new user */
exports.create = function(req, res) {
// create a new user object of request body
const user = new User(only(req.body, 'firstName lastName email password'));
// attempting to create a new user
user.save(function (err, user) {
if(err) {
// output validation errors
return res.json(err);
}
// output created user
return res.json(user);
});
};
exports.signin = function(req, res, next) {
passport.authenticate('local', function (err, user, info) {
if (err)
return next(err);
if (!user)
return res.status(401).json({message: info.message});
req.logIn(user, function(err) {
next(err)
});
res.json(req.user);
})(req, res, next)
};
And finally, my server.js
file:
/* Server.js */
'use strict';
const mongoose = require('mongoose');
const bodyParser = require('body-parser');
const config = require('./app/config/test');
const express = require('express');
const passport = require('passport');
const port = process.env.PORT || 3000;
const app = express();
mongoose.Promise = global.Promise;
if(mongoose.connect(config.db)) {
console.log("Connected to a database");
}
/* Database Models */
const User = require('./app/models/user');
app.use(bodyParser.urlencoded({ extended: true }));
app.use(bodyParser.json());
app.use(passport.initialize());
/* Bootstrap Routes */
require('./app/config/passport')(passport);
require('./app/config/routes')(app);
app.listen(port);
console.log('Express app started on port ' + port);
// log the current API version
console.log('Current API version: ' + process.env.API_VERSION);
Upvotes: 0
Views: 9328
Reputation: 1556
In your users.js file, change the below line
const passport = require('../config/passport');
to
const passport = require('passport');
I was facing the same issue. we have to import library, not the passport.js we have created in the config folder.
Upvotes: 4
Reputation: 1134
Maybe you have already found the solution, but it might help someone else in the future.
In your users.js, you are requiring the config/passport.js. But it doesn't return a passport object. It just call the use method.
Upvotes: 2