Node.js 通过 Apache-Redirect 代理进行护照身份验证
Node.js Passport Authentification through Apache-Redirect Proxy
我正在构建一个带有集成护照帐户系统的 node.js 应用程序。因为我在 uberspace.de 上托管,所以我需要像这样在主网络根目录中配置我的 .htaccess:
RewriteEngine On
RewriteRule ^(.*) http://localhost:34457/ [P]
我的快速登录路径是:(可在 /api/auth/login
访问)
router.post('/login', passport.authenticate('login', {
successRedirect: '/account',
failureRedirect: '/login?error=true'
}));
根据我对 Passport 的理解,如果成功登录,我应该被重定向到 /account
,如果没有,则重定向到 /login?error=true
。
但是如果我使用
执行 POST
url --data "email=foo@bar.com&password=test" http://[domain]/api/auth/login
结果是:
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>502 Proxy Error</title>
</head><body>
<h1>Proxy Error</h1>
<p>The proxy server received an invalid
response from an upstream server.<br />
The proxy server could not handle the request <em><a href="/api/auth/login">POST /api/auth/login</a></em>.<p>
Reason: <strong>Error reading from remote server</strong></p></p>
<hr>
<address>Apache/2.2.15 (CentOS) Server at [domain] Port 80</address>
</body></html>
如果我在 Chrome 中通过 html 形式(方法:POST,操作:/api/auth/login
)执行相同的查询,我将被重定向到 /api/auth/login%5E
(显然 returns 一个 404
)。
像这样的简单重定向有效:
router.post('/redirectToHome', function(req, res, next) {
res.redirect(302, '/');
});
但即使我在调用时执行此功能/api/auth/login
router.post('/login', function(req, res, next) {
passport.authenticate('login', function(err, user, info) {
if (err) return next(err);
if (!user) {
console.log(info);
return res.json(401, {success: false});
} else {
console.log(info);
return res.json(200, {success: true});
}
})(req, res, next);
});
我仍然会被重定向到 /api/auth/login%5E
。
我的 login
身份验证策略实现为:
var LocalStrategy = require('passport-local').Strategy;
var User = require('../models/user');
var bCrypt = require('bcrypt-nodejs');
module.exports = function(passport){
passport.use('login', new LocalStrategy({
usernameField: 'email',
passReqToCallback : true
}, function(req, email, password, done) {
// check in mongo if a user with username exists or not
User.findOne({ 'email' : email },
function(err, user) {
// In case of any error, return using the done method
if (err)
return done(err);
// Username does not exist, log the error and redirect back
if (!user){
console.log('User Not Found with email '+email);
return done(null, false, req.flash('message', 'User Not found.'));
}
// User exists but wrong password, log the error
if (!isValidPassword(user, password)){
console.log('Invalid Password');
return done(null, false, req.flash('message', 'Invalid Password')); // redirect back to login page
}
// User and password both match, return user from done method
// which will be treated like success
return done(null, user);
});
}));
var isValidPassword = function(user, password){
return bCrypt.compareSync(password, user.password);
}
}
即使login
-router这样写:
router.post('/login', function(req, res, next) {
passport.authenticate('login', function(err, user, info) {
if (err) return next(err);
if (!user) {
console.log(info);
return res.json(401, {success: false});
} else {
console.log(info);
return res.json(200, {success: true});
}
})(req, res, next);
});
我仍然被重定向到 /api/auth/login%5E
。
我的护照login
-策略是这样实现的:
var LocalStrategy = require('passport-local').Strategy;
var User = require('../models/user');
var bCrypt = require('bcrypt-nodejs');
module.exports = function(passport){
passport.use('login', new LocalStrategy({
usernameField: 'email',
passReqToCallback : true
}, function(req, email, password, done) {
// check in mongo if a user with username exists or not
User.findOne({ 'email' : email },
function(err, user) {
// In case of any error, return using the done method
if (err)
return done(err);
// Username does not exist, log the error and redirect back
if (!user){
console.log('User Not Found with email '+email);
return done(null, false, req.flash('message', 'User Not found.'));
}
// User exists but wrong password, log the error
if (!isValidPassword(user, password)){
console.log('Invalid Password');
return done(null, false, req.flash('message', 'Invalid Password')); // redirect back to login page
}
// User and password both match, return user from done method
// which will be treated like success
return done(null, user);
});
}));
var isValidPassword = function(user, password){
return bCrypt.compareSync(password, user.password);
}
}
有什么问题?
实际上,我的问题是一些不可见的字符,它将我重定向到其他页面,然后导致其他一些事情出错。
我正在构建一个带有集成护照帐户系统的 node.js 应用程序。因为我在 uberspace.de 上托管,所以我需要像这样在主网络根目录中配置我的 .htaccess:
RewriteEngine On
RewriteRule ^(.*) http://localhost:34457/ [P]
我的快速登录路径是:(可在 /api/auth/login
访问)
router.post('/login', passport.authenticate('login', {
successRedirect: '/account',
failureRedirect: '/login?error=true'
}));
根据我对 Passport 的理解,如果成功登录,我应该被重定向到 /account
,如果没有,则重定向到 /login?error=true
。
但是如果我使用
执行 POSTurl --data "email=foo@bar.com&password=test" http://[domain]/api/auth/login
结果是:
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>502 Proxy Error</title>
</head><body>
<h1>Proxy Error</h1>
<p>The proxy server received an invalid
response from an upstream server.<br />
The proxy server could not handle the request <em><a href="/api/auth/login">POST /api/auth/login</a></em>.<p>
Reason: <strong>Error reading from remote server</strong></p></p>
<hr>
<address>Apache/2.2.15 (CentOS) Server at [domain] Port 80</address>
</body></html>
如果我在 Chrome 中通过 html 形式(方法:POST,操作:/api/auth/login
)执行相同的查询,我将被重定向到 /api/auth/login%5E
(显然 returns 一个 404
)。
像这样的简单重定向有效:
router.post('/redirectToHome', function(req, res, next) {
res.redirect(302, '/');
});
但即使我在调用时执行此功能/api/auth/login
router.post('/login', function(req, res, next) {
passport.authenticate('login', function(err, user, info) {
if (err) return next(err);
if (!user) {
console.log(info);
return res.json(401, {success: false});
} else {
console.log(info);
return res.json(200, {success: true});
}
})(req, res, next);
});
我仍然会被重定向到 /api/auth/login%5E
。
我的 login
身份验证策略实现为:
var LocalStrategy = require('passport-local').Strategy;
var User = require('../models/user');
var bCrypt = require('bcrypt-nodejs');
module.exports = function(passport){
passport.use('login', new LocalStrategy({
usernameField: 'email',
passReqToCallback : true
}, function(req, email, password, done) {
// check in mongo if a user with username exists or not
User.findOne({ 'email' : email },
function(err, user) {
// In case of any error, return using the done method
if (err)
return done(err);
// Username does not exist, log the error and redirect back
if (!user){
console.log('User Not Found with email '+email);
return done(null, false, req.flash('message', 'User Not found.'));
}
// User exists but wrong password, log the error
if (!isValidPassword(user, password)){
console.log('Invalid Password');
return done(null, false, req.flash('message', 'Invalid Password')); // redirect back to login page
}
// User and password both match, return user from done method
// which will be treated like success
return done(null, user);
});
}));
var isValidPassword = function(user, password){
return bCrypt.compareSync(password, user.password);
}
}
即使login
-router这样写:
router.post('/login', function(req, res, next) {
passport.authenticate('login', function(err, user, info) {
if (err) return next(err);
if (!user) {
console.log(info);
return res.json(401, {success: false});
} else {
console.log(info);
return res.json(200, {success: true});
}
})(req, res, next);
});
我仍然被重定向到 /api/auth/login%5E
。
我的护照login
-策略是这样实现的:
var LocalStrategy = require('passport-local').Strategy;
var User = require('../models/user');
var bCrypt = require('bcrypt-nodejs');
module.exports = function(passport){
passport.use('login', new LocalStrategy({
usernameField: 'email',
passReqToCallback : true
}, function(req, email, password, done) {
// check in mongo if a user with username exists or not
User.findOne({ 'email' : email },
function(err, user) {
// In case of any error, return using the done method
if (err)
return done(err);
// Username does not exist, log the error and redirect back
if (!user){
console.log('User Not Found with email '+email);
return done(null, false, req.flash('message', 'User Not found.'));
}
// User exists but wrong password, log the error
if (!isValidPassword(user, password)){
console.log('Invalid Password');
return done(null, false, req.flash('message', 'Invalid Password')); // redirect back to login page
}
// User and password both match, return user from done method
// which will be treated like success
return done(null, user);
});
}));
var isValidPassword = function(user, password){
return bCrypt.compareSync(password, user.password);
}
}
有什么问题?
实际上,我的问题是一些不可见的字符,它将我重定向到其他页面,然后导致其他一些事情出错。