Comment définir un cookie dans le nœud js en utilisant le framework express?

161

Dans mon application, je dois définir un cookie en utilisant le framework express.J'ai essayé le code suivant mais il ne définit pas le cookie.

Quelqu'un peut-il m'aider à faire ça?

var express = require('express'), http = require('http');
var app = express();
app.configure(function(){
      app.use(express.cookieParser());
      app.use(express.static(__dirname + '/public'));

      app.use(function (req, res) {
           var randomNumber=Math.random().toString();
           randomNumber=randomNumber.substring(2,randomNumber.length);
           res.cookie('cokkieName',randomNumber, { maxAge: 900000, httpOnly: true })

           console.log('cookie have created successfully');
      });

});

var server = http.createServer(app);
var io = require('socket.io').listen(server);
server.listen(5555);
sachin
la source
Comment vérifiez-vous que le cookie n'est pas défini? Avez-vous vérifié les en-têtes de réponse du navigateur?
NilsH
@NilsH j'ai ajouté une instruction de journal.Si elle est définie, cela signifie qu'elle s'affichera sous la forme `` cookie créé avec succès '' ..
sachin
1
ok, alors soit votre middleware n'est pas appelé, soit certaines des instructions précédentes donnent une exception.
NilsH
si j'ai supprimé 'app.use (express.static (__ dirname +' / public '));' cette ligne signifie qu'elle a mis le cookie
sachin

Réponses:

216

L'ordre dans lequel vous utilisez le middleware dans Express est important: le middleware déclaré plus tôt sera appelé en premier, et s'il peut gérer une requête, tout middleware déclaré ultérieurement ne sera pas appelé.

Si express.statictraite la demande, vous devez déplacer votre middleware:

// need cookieParser middleware before we can do anything with cookies
app.use(express.cookieParser());

// set a cookie
app.use(function (req, res, next) {
  // check if client sent cookie
  var cookie = req.cookies.cookieName;
  if (cookie === undefined) {
    // no: set a new cookie
    var randomNumber=Math.random().toString();
    randomNumber=randomNumber.substring(2,randomNumber.length);
    res.cookie('cookieName',randomNumber, { maxAge: 900000, httpOnly: true });
    console.log('cookie created successfully');
  } else {
    // yes, cookie was already present 
    console.log('cookie exists', cookie);
  } 
  next(); // <-- important!
});

// let static middleware do its job
app.use(express.static(__dirname + '/public'));

En outre, le middleware doit soit mettre fin à une requête (en renvoyant une réponse), soit transmettre la requête au middleware suivant. Dans ce cas, j'ai fait ce dernier en appelant next()lorsque le cookie a été défini.

Mettre à jour

À partir de maintenant, l'analyseur de cookies est un package npm séparé, donc au lieu d'utiliser

app.use(express.cookieParser());

vous devez l'installer séparément en utilisant npm i cookie-parser, puis l'utiliser comme:

const cookieParser = require('cookie-parser');
app.use(cookieParser());
robertklep
la source
aussi j'ai une autre question comment puis-je vérifier si le cokkie existe ou non avant de définir le cookie
sachin
J'ai modifié ma réponse pour vous montrer comment vérifier si le cookie est déjà défini.
robertklep
1
Vous avez probablement des fichiers JS et / ou CSS sur votre page. Ceux-ci seront gérés par express.static, qui les traitera après votre middleware. Donc pour chaque fichier JS ou CSS, le code sera appelé.
robertklep
1
Il ne place pas le cookie 8 fois, il dit que le cookie existe déjà. Ce qui est à prévoir.
robertklep
14
Notez que l'analyseur de cookies doit maintenant être installé séparément. Voir npmjs.com/package/cookie-parser
Joshua
118

Définir le cookie?

res.cookie('cookieName', 'cookieValue')

Lire le cookie?

req.cookies

Démo

const express('express')
    , cookieParser = require('cookie-parser'); // in order to read cookie sent from client

app.get('/', (req,res)=>{

    // read cookies
    console.log(req.cookies) 

    let options = {
        maxAge: 1000 * 60 * 15, // would expire after 15 minutes
        httpOnly: true, // The cookie only accessible by the web server
        signed: true // Indicates if the cookie should be signed
    }

    // Set cookie
    res.cookie('cookieName', 'cookieValue', options) // options is optional
    res.send('')

})
Wayne Chiu
la source
salut, pourriez-vous dire ce qui est signé: vrai?
titoih le
si vous avez conseillé de définir le cookie comme signe, il est important de noter que req.cookie retournera vide. Vous ne pouvez récupérer le cookie signé que depuis req.signedCookies
Someone Special
38

Je ne réponds pas exactement à votre question, mais je suis tombé sur votre question en cherchant une réponse à un problème que j'avais. Peut-être que cela aidera quelqu'un d'autre.

Mon problème était que les cookies étaient définis dans la réponse du serveur, mais n'étaient pas enregistrés par le navigateur.

La réponse du serveur est revenue avec les cookies définis:

Set-Cookie:my_cookie=HelloWorld; Path=/; Expires=Wed, 15 Mar 2017 15:59:59 GMT 

Voilà comment je l'ai résolu.

J'ai utilisé fetchdans le code côté client. Si vous ne le spécifiez pas credentials: 'include' dans les fetchoptions, les cookies ne sont ni envoyés au serveur ni enregistrés par le navigateur, même si la réponse du serveur définit des cookies.

Exemple:

var headers = new Headers();
headers.append('Content-Type', 'application/json');
headers.append('Accept', 'application/json');

return fetch('/your/server_endpoint', {
    method: 'POST',
    mode: 'same-origin',
    redirect: 'follow',
    credentials: 'include', // Don't forget to specify this if you need cookies
    headers: headers,
    body: JSON.stringify({
        first_name: 'John',
        last_name: 'Doe'
    })
})

J'espère que cela aide quelqu'un.

vert
la source
J'ai inspecté ma demande de publication dans le navigateur mais ce champ ne correspond pas à la demande de publication?
Sunil Garg
Si vous utilisez XHR ou Jquery, utilisez plutôt 'withCredentials: true'
débranché