2017-09-08 4 views
0

Je cours des tests pour le contrôleur de connexion, il continue à donner le mauvais code d'état (401) au lieu de 200 comme je l'ai programmé pour être. Je m'attends à ce qu'il utilise les données stockées lorsqu'un utilisateur s'inscrit et le renvoie si l'entrée donnée est correcte. Cela fonctionne parfaitement dans le facteur mais comme j'écris des tests, il jette l'erreur 401. Il est comme il ne trouve pas l'utilisateurJavascript - Donner le mauvais statut Code au cours des tests

C'est bloc d'essai pour le signe:

it('it should signin a new user', (done) => { 
     request(app) 
     .post('/api/users/signin') 
     .send({ 
     username: "Charles",   
     password: "challenger",    
     }) 
     .expect(200) 
     .end((err, res) => { 
     if (err) { 
      return done(err); 
     }   

     done() 
     }); 
    }); 

Ceci est mon contrôleur pour la connexion:

signin(req, res) { 

    const username = req.body.username.toLowerCase().trim(); 
    // const email = req.body.email.trim(); 

    if(!username) { 
     return res.status(401) 
     .send(
     {status: false, 
      message: "Username cannot be empty" 
     }); 
    } 
    else if (!req.body.password) { 
     return res.status(401) 
     .send({ 
     status: false, 
     message: "Password field cannot be empty" 
     }); 
    } 
    return User.findOne({ 
     where: { 
     username, 
     } 
    }) 
    .then((user) =>{  

     if(!user) { 
     return res.status(401).send({message: "User is not registered"}) 
     } 
     else if(!user.validPassword(req.body.password)){ 
     return res.status(401) 
     .send({ 
      message: "The password is incorrect" 
     }) 
     } 
     const token = user.generateAuthToken(); 
     res.header('x-auth', token).status(200).send({ 
     statusCode: 200, 
     message: `Welcome back, ${user.username}`, 
     user 
    }); 
    }) 
    .catch(error => {return res.status(400).send(error)}) 
    }, 

Ceci est l'erreur i obtenez:

1) Testing API routes POST /api/users/ it should signin a new user: 
    Error: expected 200 "OK", got 401 "Unauthorized" 
     at Test._assertStatus (node_modules\supertest\lib\test.js:266:12) 
     at Test._assertFunction (node_modules\supertest\lib\test.js:281:11) 
     at Test.assert (node_modules\supertest\lib\test.js:171:18) 
     at Server.assert (node_modules\supertest\lib\test.js:131:12) 
     at emitCloseNT (net.js:1552:8) 
     at _combinedTickCallback (internal/process/next_tick.js:77:11) 
     at process._tickCallback (internal/process/next_tick.js:104:9) 
+0

Le 400 est causé par une erreur javascript quelque part dans la dernière clause then().Essayez de sortir la valeur de "erreur" dans votre bloc catch à la fin, cela vous dira ce qui a échoué. –

+0

@DuncanThacker désolé, il donne une erreur 401 pas une erreur de 400. L'utilisateur peut se connecter correctement sur le facteur, mais mon test échoue toujours. L'erreur se produit s'il n'y a pas d'utilisateur – letmebe

+1

Quel message envoie-t-il avec le 401? Cela devrait aider à déterminer quel morceau du code ne va pas. –

Répondre

0

je mettrais un tas de console.log() là-bas pour voir ExAC TLY dont le code est mise à feu puisque vous avez 4 chances de tirer le 401.

est un code pour vous ici pour examiner:

// I don't understand enough context, so I have to re-write this 
// to show you how it could be an async function which will 
// return a promise, but will also allow you to await. 

// async function sign(req, res) { 
const sign = async (req, res) => { // This is same as above line 

    const username = req.body.username.toLowerCase().trim(); 
    // const email = req.body.email.trim(); 

    if (!username) { 
     console.log('username was empty') 
     return res.status(401).send({ 
      status: false, 
      message: "Username cannot be empty" 
     }); 
    } 

    if (!req.body.password) { 
     console.log('password was empty') 
     return res.status(401).send({ 
      status: false, 
      message: "Password field cannot be empty" 
     }); 
    } 

    return await User.findOne({ where: { username } }) 
     // I'm making this one async also to ensure user.generateAuthToken() 
     // has a value before it proceeds to res.send() 
     .then(async (user) => {  
      if (!user) { 
       console.log('couldnt find user') 
       return res.status(401).send({ 
        message: "User is not registered" 
       }) 
      } 

      else if (!user.validPassword(req.body.password)){ 
       console.log('password was incorrect') 
       return res.status(401).send({ 
        message: "The password is incorrect" 
       }) 
      } 

      const token = await user.generateAuthToken(); 
      // I added a return here 
      return res.header('x-auth', token).status(200).send({ 
       statusCode: 200, 
       message: `Welcome back, ${user.username}`, 
       user 
      }); 
     }) 
     .catch((error) => { 
      console.log('lets put data in here: ' + error) 
      return res.status(400).send(error) 
     }) 
}, 

Je remarque la recherche MongoDB User.findOne({ where: { username } }). Je ne me souviens pas si cela doit être $where. Je pense que la syntaxe MongoDB utilise un $. Cela pourrait être votre problème, et cela déclenchera console.log('couldnt find user') si c'est le cas. Cela pourrait être seulement pour le pilote MongoDB natif. J'ai juste googlé et trouvé que la syntaxe pourrait également être: User.findOne({ username }) qui est un raccourci pour User.findOne({ username: username }).

Certaines personnes vous diront qu'il est superflu de faire return await fn() et omettre le await, mais il jetteront un rejet de la promesse non prise en charge si la promesse est rejetée. Il sera pris si l'attente est là. Cela fait partie de l'architecture de gestion des erreurs de l'instance supérieure.

Je recommande de regarder des tutoriels async/wait, car je vous vois mixer dans un peu de sauce callback. Votre code est assez bon, mais je pense que vous pouvez le prendre au prochain niveau. On dirait que tu es prêt.

Anecdote, vous pouvez également omettre { et } si votre déclaration if n'a qu'une seule expression, à savoir:

if (err) { 
    throw err; 
} 

peut être raccourci:

if (err) throw err; 

Cela peut aller un long chemin à aider à nettoyer le code, mais la syntaxe async/wait avec les blocs try/catch utilisés correctement avec throw apportera des améliorations incroyables au code synchrone avec une imbrication minimale.

Voici comment vous pouvez ré-écrire une partie de cela, parce que je veux vous montrer comment nous pouvons nous débarrasser de l'imbrication qui ajoute la confusion à votre contrôle de flux:

const sign = async (req, res) => { 
    try { 
     const username = req.body.username.toLowerCase().trim() 
     if (!username) throw 'noUsername' 
     if (!req.body.password) throw 'noPassword' 

     const foundUser = await User.findOne({ username }) 
     if (!foundUser.username) throw 'notFound' 

     // I assume this returns Boolean 
     const validPassword = await user.validPassword(req.body.password) 
     if (!validPassword) throw 'invalidPassword' 

     // Alter generateAuthToken() to throw 'badToken' if it fails 
     const token = await user.generateAuthToken() 
     return res.header('x-auth', token).status(200).send({ 
      statusCode: 200, 
      message: `Welcome back, ${user.username}`, 
      user 
     }) 
    } catch (error) { 
     // errors are manually thrown into here, and rejected promises 
     // are automatically thrown into here 
     if (error === 'noUsername') return res.status(401).send({ 
      status: false, 
      message: 'Username cannot be empty' 
     }) 

     if (error === 'noPassword') return res.status(401).send({ 
      status: false, 
      message: 'Password field cannot be empty' 
     }) 

     if (error === 'notFound') return res.status(401).send({ 
      message: 'User is not registered' 
     }) 

     if (error === 'invalidPassword') return res.status(401).send({ 
      message: 'The password is incorrect' 
     }) 

     if (error === 'badToken') return res.status(403).send({ 
      message: 'User is not authorized' 
     }) 

     return res.status(400).send(error) 
    } 
} 

sign(req, res).then((response) => console.log(response)) 

Il faut espérer que cela a été utile :) et désolé je n'utilise pas de points-virgules.