【问题标题】:Express + Passport session works in Postman but not in browserExpress + Passport 会话在 Postman 中有效,但在浏览器中无效
【发布时间】:2021-04-03 12:41:10
【问题描述】:

我有一个节点 js 服务器在 http://localhost:9000 上运行

还有一个在 http://localhost:3000 上运行 react js 的客户端

我可以通过在端点 http:localhost:9000/api/v1/authenticate 中发出发布请求来验证用户身份,并向客户端发送 cookie,正如您在我的 response header 上看到的那样

Access-Control-Allow-Credentials: true
Access-Control-Allow-Origin: http://localhost:3000
Connection: keep-alive
Content-Length: 51
Content-Security-Policy: default-src 'self';base-uri 'self';block-all-mixed-content;font-src 'self' https: data:;frame-ancestors 'self';img-src 'self' data:;object-src 'none';script-src 'self';script-src-attr 'none';style-src 'self' https: 'unsafe-inline';upgrade-insecure-requests
Content-Type: application/json; charset=utf-8
Date: Fri, 25 Dec 2020 14:03:48 GMT
ETag: W/"33-tyk8lJX6mfHZ8N08Hj//Q3TUtmY"
Expect-CT: max-age=0
Referrer-Policy: no-referrer
Set-Cookie: connect.sid=s%3ALVe2uJLDGv502_M70nCSfjfawWhXG0Zx.zDCxMUAJE54wKO0ecJogSPLWZIQoOdHqF387XEX1A7E; Path=/; Expires=Fri, 08 Jan 2021 14:03:48 GMT; HttpOnly
Strict-Transport-Security: max-age=15552000; includeSubDomains
Vary: Origin
X-Content-Type-Options: nosniff
X-DNS-Prefetch-Control: off
X-Download-Options: noopen
X-Frame-Options: SAMEORIGIN
X-Permitted-Cross-Domain-Policies: none
X-XSS-Protection: 0

现在在我登录并检查用户是否经过身份验证/check-session 之后, 我能够在 POSTMAN 中获取数据并且存在req.session.passport 数据。

但是当我在前端使用axios 发出请求时无法获得相同的结果

export const checkAuthSession = async () => {
    try {
        const req = await axios({
            method: 'GET',
            url: '/check-session',
            withCredentials: true,
        });

        return Promise.resolve(req.data);
    } catch (e) {
        return Promise.reject(e);
    }
}

我希望在前端登录后获得200 状态并获取数据,但我得到了 404。

这些是我使用 axios 发出请求后的 requestresponse 标头:

请求标头

Accept: application/json, text/plain, */*
Accept-Encoding: gzip, deflate, br
Accept-Language: en-US,en;q=0.9
Connection: keep-alive
Cookie: connect.sid=s%3Ag7erGfrj2XWv5jrFXrSk4kJH-qvuCCa7.8e2cnCs1dduo86Ydne1sPDRSoAlYwdiAbGcZJqluZgc
Host: localhost:9000
Origin: http://localhost:3000
Referer: http://localhost:3000/
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-site
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.4280.88 Safari/537.36 Edg/87.0.664.66

响应标头

Access-Control-Allow-Credentials: true
Access-Control-Allow-Origin: http://localhost:3000
Connection: keep-alive
Content-Length: 9
Content-Security-Policy: default-src 'self';base-uri 'self';block-all-mixed-content;font-src 'self' https: data:;frame-ancestors 'self';img-src 'self' data:;object-src 'none';script-src 'self';script-src-attr 'none';style-src 'self' https: 'unsafe-inline';upgrade-insecure-requests
Content-Type: text/plain; charset=utf-8
Date: Fri, 25 Dec 2020 14:17:18 GMT
ETag: W/"9-0gXL1ngzMqISxa6S1zx3F4wtLyg"
Expect-CT: max-age=0
Referrer-Policy: no-referrer
Strict-Transport-Security: max-age=15552000; includeSubDomains
Vary: Origin
X-Content-Type-Options: nosniff
X-DNS-Prefetch-Control: off
X-Download-Options: noopen
X-Frame-Options: SAMEORIGIN
X-Permitted-Cross-Domain-Policies: none
X-XSS-Protection: 0

这就是我在 express 中配置 CORS 的方式:

app.use(cors({
  origin: 'http://localhost:3000',
  credentials: true
}));

【问题讨论】:

  • 显示您为axios设置基本网址的代码
  • 我这样设置基本网址:axios.defaults.baseURL = `${foodieUrl}/api/${foodieApiVersion}`; //http:localhost:9000/api/v1
  • 应该是http://localhost:9000/api/v1
  • @Anatoly 是的,就是这样。

标签: node.js mongodb session cookies axios


【解决方案1】:

终于找到答案了:

在我的 axios 请求中,我只是在我的 /check-session 端点中设置了 withCredentials: true 选项。

要修复它,我必须为所有请求设置凭据。

axios.defaults.withCredentials = true;

正如 MDN 所说:

对于带有凭据的 CORS 请求,为了让浏览器向前端 JavaScript 代码公开响应,服务器(使用 Access-Control-Allow-Credentials 标头)和客户端(通过设置 XHR 的凭据模式) 、Fetch 或 Ajax 请求)必须表明他们选择加入凭据。

【讨论】:

    猜你喜欢
    • 2023-02-01
    • 1970-01-01
    • 1970-01-01
    • 2016-07-11
    • 2020-07-31
    • 2021-11-12
    • 2021-09-19
    • 2018-06-30
    • 1970-01-01
    相关资源
    最近更新 更多