Set-Cookie 标头中的 Cookie 未设置

V. *_*itu 14 cookies cross-domain node.js reactjs axios

我使用 axios 从 ReactJS 客户端向 Node.js 服务器发送请求,如下所示。

import axios from 'axios';

const apiClient = axios.create({
  withCredentials: true,
  baseURL: 'http://localhost:8080'
});

async function(payload) {
  try {
    debugger;
    let result = await apiClient.post('/auth/signup/', payload);
    debugger;
    return result;
  } catch (error) {
    debugger;
    throw error;
  }
}
Run Code Online (Sandbox Code Playgroud)

Node.js 端点在响应中设置一个 cookie,如下所示。

const express = require('express');
const bodyParser = require('body-parser');
const cookieParser = require('cookie-parser')
const cors = require('cors');
const jwt = require('jsonwebtoken');

router.use(bodyParser.json());
router.use(bodyParser.urlencoded({ extended: true }));
router.use(cors({ origin: 'http://localhost:3000', credentials: true, exposedHeaders: ['Set-Cookie', 'Date', 'ETag']} ));
router.use(cookieParser());


router.post('/signup', async (req, res, next) => {
  debugger;
  let database = req.app.locals.database;
  try {
    let user = await database.findByUsername(req.body.username);
    let token = await jwt.sign({username: user.username}, config.secret, {expiresIn: "15m"});
    res.cookie('jwt',  token, {
      maxAge: 900,
    });
  } catch (error) {
    debugger;
    return res.status(503).send({ auth: false, message: 'Database error.' });
  }
});

Run Code Online (Sandbox Code Playgroud)

响应的 Set-Cookie 标头包含预期的 cookie。

设置 Cookie 标头

但是,Chrome 似乎没有设置 cookie,因为我在开发者控制台的应用程序窗口中看不到 cookie。

饼干

我查看了以下问题的答案,其中提到{ withCredentials: true }在 axios 配置中进行设置,并且不在 node.js 中对 cors 使用通配符来源,但我已经在执行这两项操作。

Set-Cookie 标头未在 Chrome 中设置 cookie

为跨源请求设置cookie

关于为什么未设置 cookie 以及如何解决此问题有什么想法吗?

小智 4

虽然您将客户端和服务器托管在与 相同的域中http://localhost,但您的端口不同,因此同源策略在这里失败。您可以检查https://developer.mozilla.org/en-US/docs/Web/Security/Same-origin_policy

因此,当您发出 CORS 请求时,请在当前浏览器的开发人员工具中检查网络选项卡,OPTIONS在客户端POST向服务器发送请求之前,您可能会看到预检请求。

服务器必须指定 headers 来接受您下一个请求的来源 - 来自http://localhost:8000with 方法的POST 请求POST,您可以参考https://developer.mozilla.org/en-US/docs/Glossary/Preflight_request

HTTP/1.1 204 No Content
Connection: keep-alive
Access-Control-Allow-Origin: http://localhost:3000
Access-Control-Allow-Methods: POST // Your next request will use POST method
Access-Control-Max-Age: 86400
Access-Control-Allow-Credentials: true // cookies accepted
Run Code Online (Sandbox Code Playgroud)

添加:

在 中Set-CookieMax-Age必须是非零数字根据RFC 文档将其四舍五入为整数。对于express.js,cookie的maxAge属性以毫秒为单位

解决方案将属性设置maxAgesecond * 1000

HTTP/1.1 204 No Content
Connection: keep-alive
Access-Control-Allow-Origin: http://localhost:3000
Access-Control-Allow-Methods: POST // Your next request will use POST method
Access-Control-Max-Age: 86400
Access-Control-Allow-Credentials: true // cookies accepted
Run Code Online (Sandbox Code Playgroud)