I am new to javascript and node. I followed the guide from passportJS and I am getting the error "local strategy cannot be found". I do not know why. my code, basically taken from the website at this point.
var express = require('express')
, routes = require('./routes')
, user = require('./routes/user')
, http = require('http')
, path = require('path')
, mongoose = require('mongoose')
, passport = require('passport')
, LocalStrategy = require('passport-local').Strategy;
app.use(passport.initialize());
//to configure the passport
app.use(new LocalStrategy({
usernameField: 'username',
passwordField: 'password'
},
function(username, password, done){
console.log(username);
console.log(password);
People.findOne({username:username},
function(err, user){
if(err){return done(err); }
if(!user){
return done(null, false, {message:
'Incorrect username'});
}
if(!user.validPassword(password)){
return done(null, false, {message:
'Incorrect Password'});
}
return done(null, user);
});
}
));
//route to authenticate the user
app.post('/login',
passport.authenticate('local', { successRedirect:'/accessed',
failureRedirect: '/access'})
);
My error is that "local strategy not found", I looked inside the local-strategy module and found the function that defines it. So I assume the error lies somewhere in the way I am attempting to access that variable.
My server is set up like
var app = express();
app.configure(function(){
app.set('port', process.env.PORT || 3000);
app.set('views', __dirname + '/views');
app.set('view engine', 'jade');
app.use(express.favicon());
app.use(express.logger('dev'));
app.use(express.bodyParser());
app.use(express.methodOverride());
app.use(passport.initialize());
app.use(app.router);
app.use(express.static(path.join(__dirname, 'public')));
});
app.configure('development', function(){
app.use(express.errorHandler());
});
Here's a boilerplate for using passport-local. The order in which the middleware is configured matters. It also implements serializeUser/deserializeUser which seem to be missing from your code.
var express = require('express')
, http = require('http')
, path = require('path')
, passport = require('passport')
, LocalStrategy = require('passport-local').Strategy;
var app = express();
passport.use(new LocalStrategy(function(username, password, done) {
// insert your MongoDB check here. For now, just a simple hardcoded check.
if (username === 'foo' && password === 'bar')
{
done(null, { user: username });
}
else
{
done(null, false);
}
}));
passport.serializeUser(function(user, done) {
// please read the Passport documentation on how to implement this. We're now
// just serializing the entire 'user' object. It would be more sane to serialize
// just the unique user-id, so you can retrieve the user object from the database
// in .deserializeUser().
done(null, user);
});
passport.deserializeUser(function(user, done) {
// Again, read the documentation.
done(null, user);
});
app.use(express.bodyParser());
app.use(express.cookieParser());
app.use(express.session({ secret: 'secret' }));
app.use(passport.initialize());
app.use(passport.session());
// route to authenticate the user
app.post('/login', passport.authenticate('local', {
successRedirect: '/accessed',
failureRedirect: '/access'
}));
// app.listen(3012);
When you use curl -v -d "username=foo&password=bar" http://127.0.0.1:3012/login you see you'll get redirected to /accessed, meaning the authentication worked.
Related
I've recently started learning on my own and I am stuck at this and can't get past it.
I'm trying to create a login page and for the first time I'm using middleware
I'm getting an error: throw new TypeError('app.use() requires a middleware function')
TypeError: app.use() requires a middleware function
This is the code down below:
var express = require("express"),
mongoose = require("mongoose"),
passport = require("passport"),
bodyParser = require("body-parser"),
User =require("./models/user"),
LocalStrategy =require("passport-local"),
passportLocalMongoose = require("passport-local-mongoose");
mongoose.connect("mongodb://localhost:27017/auth_demo_app", { useUnifiedTopology: true },{ useNewUrlParser: true });
var app = express();
app.set('view engine', 'ejs');
app.use(bodyParser.urlencoded({extended:true}));
app.use(require("express-session")({
secret: "Neno is the best and cutest dog in the world.",
resave: false,
saveUninitialized: false
}));
app.use(new LocalStrategy(User.authenticate()));
app.use(passport.initialize());
app.use(passport.session());
passport.serializeUser(User.serializeUser()); // Encoding the session
passport.deserializeUser(User.deserializeUser()); // Decoding the session
// =========
// ROUTES
// =========
app.get("/", function(req, res){
res.render("home");
});
app.get("/secret", function(req, res){
res.render("secret");
});
// ===========
// Auth ROUTES
// ===========
// Show Signup Form
app.get("/register", function (req, res){ // req - request / res - response
res.render("register");
});
//handling USER SIGN UP
app.post("/register", function(req, res){
req.body.username
req.body.password
User.register(new User({username: req.body.username}), req.body.password, function(err, user){
if(err) {
console.log(err);
res.render("register");
} else {
passport.authenticate("local")(req, res, function(){
res.redirect("secret");
})
}
});
})
//handling USER LOG IN / LOGIN ROUTES
app.get("/login", function (req, res){
res.render("login");
});
//login logic
//middleware
app.post("/login", passport.authenticate("local", {
successRedirect: "/secret",
failureRedirect: "/login"
}),function(req, res) {
});
app.listen(3000, function (){
console.log("Server Started......");
})
You need to pass strategy to passport, not to the app.
Replace
app.use(new LocalStrategy(User.authenticate()));
With
passport.use(new LocalStrategy(User.authenticate()));
Also I think you need to pass a function new LocalStrategy(User.authenticate) instead of it's result. Unless of course you have implemented it to return a callback (hard to say w/o seeing your code)
I am trying to authenticate the user using passport.I am trying to display message using flash.In the passport-config.js,I wrote the local strategy.When I run the code ,it give an error "req.flash is not a function " in passport-config.js file.This the first time I am using passport and flash.Please help me.Thanks in advance.
app.js
const express = require("express");
const bodyParser = require("body-parser");
const ejs = require("ejs");
const passport = require("passport");
const initializePassport=require('./passport-config')(passport);
const auth=require('./authenticate');
const bcrypt=require('bcrypt');
const session = require('express-session');
const flash = require('express-flash');
const Post=require("./Post");
const User=require('./User');
const app = express();
app.set('view engine', 'ejs');
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({extended: true}));
app.use(express.static("public"));
app.use(session({
secret:"secret",
resave:false, //this means session variables are not resaved if nothing is changed
saveUninitialized:false //this means we dont want to save empty value in session if there is no value
}))
app.use(flash());
app.use(passport.initialize());
app.use(passport.session());
app.use(function(req, res, next) {
// make all error and success flash messages available from all templates
res.locals.error = req.flash("error")
res.locals.success = req.flash("success")
next()
})
app.get("/login",function(req,res){
res.render('login');
})
app.post("/login",passport.authenticate('local',{
successRedirect:'/',
failureRedirect:'/login',
failureFlash:true
}))
passport-config.js
const LocalStrategy = require('passport-local').Strategy;
const mongoose=require('mongoose');
const bcrypt = require('bcrypt');
const User=require('./User');
function initialize(passport) {
const authenticateUser =(req,email, password, done) => {
User.findOne({email:email}).then(user=>{
if(!user){
// req.flash('error','This email is not registered');
return done(null,false,req.flash('error','This email is not registered'));
}
//Match password
bcrypt.compare(password,user.password,(err,isMatch)=>{
if(err){
// req.flash('error','Something went wrong!Please try again.');
throw err;
}
if(isMatch){
return done(null,user);
}
else{
req.flash('error','Password Incorrect');
return done(null,false, req.flash('error','Password Incorrect'));
}
});
}).catch(err=> console.log(err));
}
passport.use(new LocalStrategy({ usernameField: 'email' ,passReqToCallBack: true}, authenticateUser));
passport.serializeUser((user, done) => done(null, user.id));
passport.deserializeUser((id, done) => {
User.findById(id,(err,user)=>{
done(err,user);
})
})
}
module.exports = initialize;
Try putting passport before the flash
app.use(passport.initialize());
app.use(passport.session());
app.use(flash());
passport.use(new LocalStrategy({ usernameField: 'email' , passReqToCallback : true}, authenticateUser));
I just had to add passReqToCallback : true.It works now.
trying first time node with passport for signing to app and can't get any error in command.
after too much load it responds:
No data received
ERR_EMPTY_RESPONSE
can't find any solution for this error.
routes
loginRouter.route('/login')
.get(loginController.getLogin)
.post(loginController.postLogin);
postlogin function :
var postLogin = function(req, res, next){
passport.authenticate('local', {
successRedirect: '/',
failureRedirect: '/auth/login',
failureFlash : true
});
};
passport.js
var passport = require('passport');
var localStrategy = require('passport-local').Strategy;
var bcrypt = require('bcrypt-nodejs');
var User = require('../app/models/model')().User;
module.exports = function(){
passport.use('local',new localStrategy({
usernameField: 'username',
passwordField: 'password',
passReqToCallback : true
},
function (username, password, done){
User.findOne({
where: {
username: username
}
}).then(function(user){
if(!user) {
console.log(user);
done(null, false, req.flash('invalid credentials try again'));
} else if (!bcrypt.compareSync(password, user.password)) {
done(null, false, req.flash('invalid credentials try again'));
} else {
done(null, user);
}
});
}));
passport.serializeUser(function (user,done) {
done(null, user.id);
});
passport.deserializeUser(function (id, done){
User.findOne({where: {id: id}}).then(function(user){
done(null, user);
});
});
};
app.js
var express = require('express'),
session = require('express-session'),
cookieParser = require('cookie-parser'),
bodyParser = require('body-parser'),
passport = require('passport'),
flash = require('express-flash'),
app = express(),
port = 80;
app.use(express.static(__dirname + '/public'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded( { extended: true } ));
app.use(cookieParser());
app.use(session({
secret: 'lirary',
cookie: {
maxage: 1200000
},
resave: true,
saveUninitialized: true
}));
app.use(passport.initialize());
app.use(passport.session());
app.use(flash());
require('./config/passport')();
app.set('views','./resources/views');
app.set('view engine','ejs');
require(__dirname + '/app/routes/routes')(app);
app.listen(port,function(err){
console.log('server running on : '+ port)
if (err) {
throw err;
};
});
Just little change in my route and solved this now.
loginRouter.post('/login',
function (req, res, next) {
console.log(User.validate());
next();
},
passport.authenticate('local',{
successRedirect: '/dashboard',
failureRedirect: '/auth/login',
failureFlash : true
}
));
I am implementing a basic login system with passport but I keep receiving this error when I login with the correct credentials:
Express
500 TypeError: Cannot read property 'passport' of undefined
However works fine when I login with wrong credentials by redirecting back to login page. Help?
app.js
//dependencies
var express = require('express');
var routes = require('./routes');
var http = require('http');
var path = require('path');
var mongoose = require('mongoose');
var passport = require('./auth');
var app = express();
server = require('http').createServer(app),
io = require('socket.io').listen(server);
// all environments
app.use(passport.initialize());
app.use(passport.session());
....
app.use(app.router);
app.use(require('less-middleware')({src: path.join(__dirname, 'public')}));
app.use(express.static(path.join(__dirname, 'public')));
......
//routes
app.get('/login', routes.login);
app.post('/login', passport.authenticate('local', {
failureRedirect: '/login',
successRedirect: '/user'
}));
app.get('/user', routes.user);
index.js
exports.login = function(req, res) {
res.render('login', {title: 'Log in'});
};
exports.user = function(req, res) {
if (req.session.passport.user === undefined) {
res.redirect('/login');
} else {
res.render('user', {title: 'Welcome!',
user: req.user
})
}
};
auth.js
var passport = require('passport'),
LocalStrategy = require('passport-local').Strategy;
passport.use(new LocalStrategy(
function(username, password, done) {
if (username === 'admin' && password === 'lynda') {
return done(null, {username: 'admin'});
}
return done(null, false);
}
));
passport.serializeUser(function(user, done) {
done(null, user.username);
});
passport.deserializeUser(function(username, done) {
done(null, {username: username});
});
module.exports = passport;
You're missing the session declaration, so req.session is undefined
app.use( express.cookieParser() );
app.use(express.session({ secret: 'my secret', cookie: { maxAge : 1200000 } }));
also, you seem to be mixing up the requires:
var passport = require('./auth');
I would change this to:
var auth = require('./auth');
to avoid confusion with the passport library
You don't have a session, so you can't do if (req.session.passport.user === undefined) ...
You probably didn't set the session after login
Some questions:
Is this implementation of Passport for Node.js (Express) secure?
Is it a correct implementation of REST?
Can I store state in the session in this way?
/************************************
* Module dependencies.
************************************/
var express = require('express')
, passport = require('passport')
, BasicStrategy = require('passport-http').BasicStrategy
, crypto = require('crypto')
, http = require('http')
, path = require('path')
, fs = require('fs')
, app = express()
, service = require('./service');
var privateKey = fs.readFileSync('privatekey.pem').toString();
var certificate = fs.readFileSync('certificate.pem').toString();
var credentials = crypto.createCredentials({key: privateKey, cert: certificate});
/************************************
* Passport
************************************/
// User object supplied by MongoDB from the `service` object
//
// {
// id: 1,
// password: 'otherTestPass',
// salesmanId: 'A015',
// email: 'otheruser#email.com'
// }
passport.use(new BasicStrategy(
function(username, password, done) {
User.findOne({ username: username }, function (err, user) {
if (err) { return done(err); }
if (!user) { return done(null, false); }
if (!user.validPassword(password)) { return done(null, false); }
return done(null, user);
});
}
));
passport.serializeUser(function(user, done) {
done(null, user.id);
});
passport.deserializeUser(function(id, done) {
User.findById(id, function(err, user) {
done(err, user);
});
});
/************************************
* Config
************************************/
// all environments
app.set('port', process.env.PORT || 8000);
app.set('views', __dirname + '/views');
app.set('view engine', 'jade');
app.use(express.favicon());
app.use(express.logger('dev'));
app.use(express.cookieParser());
app.use(express.bodyParser());
app.use(express.session({ secret: 'keyboard cat' })); // would normally have a randomly generated string
app.use(passport.initialize());
app.use(passport.session());
app.use(passport.authenticate('basic', {session: true}));
app.use(express.compress());
app.use(app.router);
app.use(express.static(path.join(__dirname, 'dist'))); // backbone SPA that talks to the '/api/' routes
// development only
if ('development' == app.get('env')) {
app.use(express.errorHandler());
}
/************************************
* Routes
************************************/
app.get('/api/session/user', function(req,res){
var user = req.user;
delete user.password;
res.json(user);
});
app.get('/api/customers', function(req,res){
service.findAllCustomersBySalesmanId(req.user.salesmanId, function(result){
res.json(result);
});
});
app.get('/api/products', function(req,res){
service.findAllProducts(function(result){
res.json(result);
});
});
app.get('/api/orders', function(req,res){
service.findAllOrders(function(result){
res.json(result);
});
});
// ... other routes
/************************************
* Server Start
************************************/
http.createServer(app)
.setSecure(credentials)
.listen(app.get('port'), function(){
console.log('Express server listening on port ' + app.get('port'));
}
);
Extra credit to anyone that can suggest:
Good way of moving the api routes to a different file and 'mounting' them at /api/ as part of the middleware configuration.
Internally securing the app by checking if a user is allowed to perform a certain operation.