2014-04-02 15 views
5

Ich versuche, passport.js in meiner node.js App zu verwenden, um einen Benutzer mit MongoDB zu authentifizieren. Ich habe nie Erfolg gehabt.Passport-local gibt 400 Fehler zurück, Datenbank nie abfragt

In der Post, ich sende "E-Mail": "[email protected]", "Passwort": "test"

var passport = require('passport') 
    , LocalStrategy = require('passport-local').Strategy; 


app.post('/login', 
    passport.authenticate('local', { successRedirect: '/', 
           failureRedirect: '/fail' }) 
); 

passport.use(new LocalStrategy({ 
     emailField: 'email', 
     passwordField: 'passw', 
    }, 
function (emailField, passwordField, done) { 
    process.nextTick(function() { 
     db.collection(users, function (error, collection) { 
     if (!error) { 
      collection.findOne({ 
       'email': emailField, 
       'password': passwordField 
      }, function (err, user) { 
       if (err) { 
        return done(err); 
       } 
       if (!user) { 
        console.log('this email does not exist'); 
        return done(null, false); 
       } 
        return done(null, user); 
      }); 
     } else { 
      console.log(5, 'DB error'); 
     } 
     }); 
    }); 
})); 

In MongoDB Sammlung 'Benutzer':

{ 
    "_id": { 
     "$oid": "533b5283e4b09d8a1148b4c4" 
    }, 
    "email": "[email protected]", 
    "password": "test" 
} 

Vielleicht verbinde ich mich nicht mit der Datenbank, ich bin mir nicht sicher.

Auch, wenn ich alle über die Funktion loggen, bekomme ich keine Protokolle. Ich bekomme einfach

POST /login 302 7ms - 39b 
GET /fail 404 3ms 

Alle Vorschläge würden sehr geschätzt werden. Ich denke, dass ich etwas vermisse, aber ich bin mir nicht sicher, wie ich das genau strukturiere. In der anderen Funktion, wo ich auf die Datenbank schreibe ich habe zu verwenden:

var uristring = 
process.env.MONGOLAB_URI || 
process.env.MONGOHQ_URL || 
'mongodb://<myurlhere>'; 

mongo.connect(uristring, function (err, db) { 

Hier ist der Code aktualisiert ist

erfordern diese:

, passport = require('passport') 
    , LocalStrategy = require('passport-local').Strategy; 

diese mit :

// all environments 
app.set('port', process.env.PORT || 3000); 
app.set('views', path.join(__dirname, 'views')); 
app.set('view engine', 'ejs'); 
app.use(express.favicon()); 
app.use(express.logger('dev')); 
app.use(express.json()); 
app.use(express.urlencoded()); 
app.use(express.methodOverride()); 
app.use(express.cookieParser()); 
app.use(express.session({ secret: 'keyboard cat'})); 
app.use(logfmt.requestLogger()); 
app.use(express.static(path.join(__dirname, 'public'))); 
app.use(passport.initialize()); 
app.use(passport.session()); 
app.use(app.router); 

// User authentication passport 

passport.use(new LocalStrategy(
    { 
     usernameField: 'email', 
     passwordField: 'passw', 
    }, 
    function (userId, password, done) { 
     // removed process.nextTick 
     console.log('Hey! no more 400 error!'); 
     db.collection(users, function (error, collection) { 
      if (!error) { 
       collection.findOne({ 
        'email': userId, 
        'password': password 
       }, function (err, user) { 
        if (err) { 
         return done(err); 
        } 
        if (!user) { 
         console.log('this email does not exist'); 
         return done(null, false); 
        } 
        return done(null, user); 
       }); 
      } else { 
       console.log(5, 'DB error'); 
      } 
     }); 
    } 
)); 

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

passport.deserializeUser(function(user, done) { 
    done(null, user); 
}); 

app.post('/login', passport.authenticate('local'), function(req, res) { 
    console.log('SUCCESS WOOOO'); 
    // If this function gets called, authentication was successful. 
    // `req.user` contains the authenticated user. 
    //res.redirect('/users/' + req.user.username); 
    }); 

Dieser Code gibt mir immer POST /login 400 10ms beim Posten an/login. Alle meine anderen Routen funktionieren gut.

+0

Ist Ihr Code in einer Datei oder in Module zerlegt? Ich frage, weil die Reihenfolge, in der du die Dinge nennst, von Bedeutung sein kann. Haben Sie den 'process.nextTick' aus einem bestimmten Grund auch in Ihrem Code gelassen? Ich glaube, dass es in dem Beispielcode ist, die Verzögerung eines DB-Aufrufs zu "verspotten", aber tatsächlich nicht benötigt wird. –

+0

Nein, ich habe gerade diese App gestartet und diese Funktion befindet sich derzeit in app.js. Ich plane es zu brechen und mache das modularer, nachdem ich die Authentifizierung funktioniert habe. – Joel

+0

Ich habe so viele Dinge ausprobiert. Momentan bekomme ich einen 404. 'app.post ('/ login', pass.authenticate ('local'), Funktion (req, res) {' 'console.log ('SUCCESS WOOOO');' '// Wenn diese Funktion aufgerufen wird, war die Authentifizierung erfolgreich." '// req.user enthält den authentifizierten Benutzer." '//res.redirect('/users/ '+ req.user.username);' '});' – Joel

Antwort

1

Das endete ein Problem mit Postman (die ich soooo oft ohne Problem verwendet habe).

Sobald ich ein echtes HTML-Formular verwendet hatte, funktionierte es gut. Vielleicht eine Header-Sache?

+0

Ich hatte ähnliche Probleme mit Postman. Selbst wenn die Interceptor-Erweiterung aktiviert ist, scheint sie keine Persistenz der Sitzung zu behalten (über Cookies). –

17

1) Die gefürchtete HTTP 400 Fehler

Passport 400 führt einen HTTP-Fehler, wenn der Benutzername und/oder Passwort nicht gesetzt sind.

Siehe die Quelle um Linie 75, wo Strategy.prototype.authenticate einen Fehler 'missing credentials' wirft.

2)

In Ihrem Code die Ursache diagnostizieren, haben Sie den Block:

passport.use(new LocalStrategy({ 
     emailField: 'email', 
     passwordField: 'passw', 
    }, 

Aber emailField von Reisepass wird nicht erkannt. Zurück im source code sehen wir, dass Pass sucht:

this._usernameField = options.usernameField || 'username'; 
this._passwordField = options.passwordField || 'password'; 

Aus diesem Grunde ist die HTTP 400 in dieser besonderen Situation geworfen.

4) das Problem zu lösen

ich Ihren ursprünglichen Code zu dem, was ich glaube, bearbeitet habe funktioniert (besser) als das Original. Ich habe beim Bearbeiten etwas Freiheit genommen, um die process.nextTick zu entfernen und ein paar Dinge umbenannt. Ich hoffe, du bist eine vergebende Person.:)

passport.use(new LocalStrategy(
    { 
     usernameField: 'email', 
     passwordField: 'passw', 
    }, 
    function (userId, password, done) { 
     // removed process.nextTick 
     console.log('Hey! no more 400 error!'); 
     db.collection(users, function (error, collection) { 
      if (!error) { 
       collection.findOne({ 
        'email': userId, 
        'password': password 
       }, function (err, user) { 
        if (err) { 
         return done(err); 
        } 
        if (!user) { 
         console.log('this email does not exist'); 
         return done(null, false); 
        } 
        return done(null, user); 
       }); 
      } else { 
       console.log(5, 'DB error'); 
      } 
     }); 
    } 
)); 

5) Einige Schlussnoten:

  • könnten Sie auch die Formulareingabe bearbeiten Attribute Pass erwarteten Vorgaben anzupassen. Siehe die passport documentation für eine Anleitung.
  • Ich kann nicht garantieren, dass der MongoDB-Aufruf funktioniert, aber das sollte Sie über das HTTP 400 hinausbringen. Wenn der Datenbankaufruf Probleme hat, ist das mit ziemlicher Sicherheit eine neue Frage, da ein anderer Satz von Code und Modulen beteiligt sind.
  • Wenn Sie einen Reisepass verwenden, lohnt es sich, die GitHub-Seite des Projekts zu besuchen und die Quelle durchzulesen. Es gibt oft Kommentare in der Quelle, die (a) nicht in den anderen Dokumenten enthalten sind oder (b) nahe an dem Code liegen, den sie beschreiben ... also sind die Dinge für dich geklärt, selbst wenn du kein Programmierguru oder was auch immer bist.
+0

Ich bekomme immer noch eine 400. Wenn ich über die 400 hinaus könnte, könnte ich das wahrscheinlich herausfinden. Ich kann immer noch keine Protokolle bekommen, außer der 400. Ich habe den ursprünglichen Beitrag mit meinen Änderungen aktualisiert. 'POST/login 400 10ms' – Joel

+0

Ich poste auf http: // localhost: 3000/login. Alle meine anderen Routen funktionieren. Ich sende E-Mail und passw – Joel

+0

Ich habe fast alles kopiert, was Sie in eine einseitige App basierend auf dem Pass-lokalen Beispiel für die Arbeit mit Express und Mongo gepostet. Das einzige Mal, wenn ich es auf 400 setzen kann, ist, wenn die Attribute im Login-Formular nicht mit dem übereinstimmen, was der Pass erwartet. Entschuldigung, ich kann nicht mehr tun. Wenn Sie es herausfinden, wäre ich interessiert zu hören, was passiert ist. –

Verwandte Themen