passport.js not working with manual form-data post request angular

柔情痞子 提交于 2019-12-11 02:16:27

问题


I have created a form in angular, On click of submit button I am hitting a post request with Content-Type header with value application/x-www-form-urlencoded.

onSubmit(user:User) {
    let headers = new Headers();
    // to send data as form data as passport library want it as a form data
    headers.append('Content-Type', 'application/x-www-form-urlencoded');
    return this.http.post('/login', user, { headers: headers }).subscribe((data) => {
      console.log("Data : ", data);
    });
} 

and the model user is of type

// Class to bind user data
class User {
  constructor(private name: string, private password: string) {
  }
}

Here is the server side code

 let userList: User[] = [new User(1, "Sunil"), new User(2, "Sukhi")];

        let app = express();

        // passport library
        let passport = require('passport');
        let LocalStrategy = require('passport-local').Strategy;

        // middlewares
        app.use(express.static("public"));
        app.use(bodyParser.json());
        app.use(bodyParser.urlencoded({ extended: false }));
        app.use(session({ resave: false, saveUninitialized: true, secret: "secretKey123!!" }));

        // passport middleware invoked on every request to ensure session contains passport.user object
        app.use(passport.initialize());

        // load seriliazed session user object to req.user 
        app.use(passport.session());

        // Only during the authentication to specify what user information should be stored in the session.
        passport.serializeUser(function (user, done) {
            console.log("Serializer : ", user)
            done(null, user.userId);
        });

        // Invoked on every request by passport.session
        passport.deserializeUser(function (userId, done) {
            let user = userList.filter(user => userId === user.userId);
            console.log("D-serializer : ", user);
            // only pass if user exist in the session
            if (user.length) {
                done(null, user[0]);
            }
        });
// passport strategy : Only invoked on the route which uses the passport.authenticate middleware.
        passport.use(new LocalStrategy({
            usernameField: 'name',
            passwordField: 'password'
        },
            function (username, password, done) {
                console.log("Strategy : Authenticating if user is valid  :", username)
                let user = userList.filter(user => username === user.userName);
                console.log("Valid user : ",user)
                if (!user) {
                    return done(null, false, { message: 'Incorrect username.' });
                }
                return done(null, user[0]);
            }
));

app.post('/login', passport.authenticate('local', {
     successRedirect: '/done',
     failureRedirect: '/login'
}));
app.get('/done', function (req, res) {
     console.log("Done")
     res.send(req.session)
})


app.get('/login', function (req, res) {
     console.log("login")
     res.send("login")
})

but every time it is returning login


回答1:


In my case, the issue was with the request body. I was sending the user object directly so this was not working. To solve this I have created the body object using URLSearchParams.

let  body = new URLSearchParams();
body.append('name', this.user.name);
body.append('password', this.user.password); 

Here is the onSubmit method

onSubmit() {
    let  body = new URLSearchParams();
    body.append('name', this.user.name);
    body.append('password', this.user.password);

    let headers = new Headers({'Content-Type': 'application/x-www-form-urlencoded'});
    let options = new RequestOptions({headers});

    this.http.post("/services/login", body.toString(), options).subscribe((response)=>{
        let arrUrl = response.url.split("/");
        let url = "/" + arrUrl[arrUrl.length-1];
        this.router.navigate([url]);
    });
}

Second, from the login form, I was not passing the value for password field. So the local strategy's callback(with username and password) was not getting called.

If you don't pass any of the fields then the callback method will not be called and will redirect to the failureRedirect URL.



来源:https://stackoverflow.com/questions/47034310/passport-js-not-working-with-manual-form-data-post-request-angular

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!