【问题标题】:POST from angular.js doesn't work but directly from form works. Why?来自 angular.js 的 POST 不起作用,但直接来自表单的工作。为什么?
【发布时间】:2025-12-27 06:05:13
【问题描述】:

我正在使用 passport.js 和 LocalStrategy 方法在 node.js 中为我的项目进行基本身份验证。它甚至还没有密码验证。帐户存储在 MongoDB 实例中。

我一整天都被困在课程中,我正在通过讲师推荐的将表单数据绑定到 angular 并从那里发送$http.post(),如下所示:

$scope.signIn = function (username, password) {
    $http.post('/login', {username: username, password: password})
        .then(function (res) {
            if(res.data.success) {
                console.log('Logged in');
            } else {
                console.log('error logging in');
            }
        })
};

这是它的路线:

app.post('/login', function (req, res, next) {

    var auth = passport.authenticate('local', function (err, user) {
        if(err) { return next(err); }
        if(!user) { res.send({success: false, user: user}); }

        req.login(user, function (err) {
            if(err) { return next(err); }
            res.render('index', { success: true, user: user });
        });
    });

    auth(req, res, next);
});

除了它总是返回 {success: false, user: false }。经过大量的谷歌搜索后,我决定直接从表单发出 POST 请求:

玉:

.navbar-right(ng-controller='navbarLoginCtrl')
form.navbar-form(action='/login' method='post')
    .form-group
        input.form-control(name='username' placeholder='username', ng-model='username' required)
    .form-group
        input.form-control(name='password' type='password', placeholder='password', ng-model='password' required)
    button.btn.btn-default(type='submit' value="Submit") Sign in

相对于:

.navbar-right(ng-controller='navbarLoginCtrl')
form.navbar-form
    .form-group
        input.form-control(name='username' placeholder='username', ng-model='username' required)
    .form-group
        input.form-control(name='password' type='password', placeholder='password', ng-model='password' required)
    button.btn.btn-default(ng-click='signIn(username, password)') Sign in

提交方法确实有效,但我想保持清洁并使用 Angular 来完成。 我该怎么做?

其他 passport.js 组件供参考:

var User = mongoose.model('User');

passport.serializeUser(function (user, done) {
    if (user) {
        done(null, user._id);
    }
});

passport.deserializeUser(function (id, done) {

    User.findOne({_id: id}).exec(function (err, user) {
        if(user) {
            return done(null, user);
        } else {
            return done(null, false);
        }
    });
});

passport.use(new LocalStrategy(
    function (username, password, done) {
        User.findOne({username: username}, function (err, user) {
            if (user) return done(null, user);
            else return done(null, false);
        });
    }
));

【问题讨论】:

    标签: angularjs post express passport.js


    【解决方案1】:

    您应该检查浏览器发送的内容。

    您的浏览器表单以 username=&password= 的形式发送数据,以 JSON {username:, password:} 的形式发送数据,并且 Content-Type 标头不同。

    如果你想在角度做同样的事情:

     var headers={ 'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8'};         
          return $http.post(BackEndpoint+'/login','username='+username+'&password='+password,
        {headers:headers}).then(function(result){
    });
    

    这是我用来对抗 spring 身份验证的。

    【讨论】:

    • 谢谢,成功了。遗憾的是,即使是 passport.js 文档,也绝对没有提及它。我只是假设 body-parser 会为我解决这个问题。知道为什么它可以在没有明确指定内容类型的情况下在早期版本的 Express/node 中工作吗?
    • 完全不知道我只知道表单发布和角度发布的区别:)
    最近更新 更多