You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

跨域HttpOnly Cookie配置咨询:本地与生产环境实现方案

问题描述

我有一个部署在localhost:3000的网站,用户完成登录后,服务器会创建HttpOnly refresh token Cookie,随后用户被重定向至部署在localhost:5000的仪表盘(仪表盘与服务器均部署在localhost:5000)。

需求是让localhost:5000能利用该refresh token生成access token。目前服务器端创建Cookie的配置如下:

res.cookie('token', token, {
  httpOnly: true,
  domain: '.localhost',
  path: '/',
  maxAge: 1000 * 60 * 60 * 24 * 7,
})

localhost:5000的前端用受保护路由包裹所有路由,代码如下:

import { useEffect } from 'react'
import styles from './style.module.scss'
import { Outlet } from 'react-router-dom'
import { useDispatch, useSelector } from 'react-redux'
import actions from '../../actions'

let isMounted = true
function AuthorizationRouter() {
  const { isAuth, error, user } = useSelector((state) => 
  state.isLoggedIn)

const dispatch = useDispatch()

useEffect(() => {
   isMounted && dispatch(actions.users.isUserLoggedIn())
   return () => {
   isMounted = false
 }
}, [])

if (error) {
   console.log('🚀AuthorizationRouter ~ error:', error)
   window.location.href = 'http://localhost:3000/login'
}

if (isAuth) {
   console.log('🚀AuthorizationRouter ~ user:', user)
   return <Outlet />
}

return (
  <div className={styles.authorizationRouter}>
   <div className={styles.container}>
    <div className={styles.logo}>
      <img src='/images/light_blue.png' alt='logo' />
    </div>
    <div className={styles.progress}>
      <div className={styles.progress__bar}>
        <div className={styles.progress__value}></div>
      </div>
    </div>
  </div>
</div>
)}

export default AuthorizationRouter

当前为开发模式,生产模式下主网站部署在主域名,仪表盘部署在子域名,需实现与开发模式一致的Cookie共享效果。


解决方案

一、开发环境(localhost跨端口共享Cookie)

浏览器对localhost的Domain处理有特殊逻辑,.localhost这类带前缀的配置多数浏览器不支持,调整如下:

  1. 修改服务器端Cookie配置:
    移除domain字段,让浏览器默认绑定到localhost(不区分端口),同时设置sameSite属性适配跨端口请求:

    res.cookie('token', token, {
      httpOnly: true,
      path: '/',
      maxAge: 1000 * 60 * 60 * 24 * 7,
      sameSite: 'Lax', // 若需跨站请求可设为'None',但None必须配合secure(开发环境http下不能用)
    })
    
  2. 确保前端请求携带Cookie:
    前端调用isUserLoggedIn接口时,必须配置请求携带凭证:

    • 若用axios,给实例添加withCredentials: true:
      const api = axios.create({
        baseURL: 'http://localhost:5000',
        withCredentials: true,
      })
      
    • 若用fetch,设置credentials: 'include':
      fetch('/api/isUserLoggedIn', {
        credentials: 'include',
      })
      

    这样浏览器会自动将localhost下的Cookie发送到localhost:5000的服务器,后端就能读取refresh token生成access token。

二、生产环境(主域名与子域名共享Cookie)

假设主站域名为example.com,仪表盘部署在dashboard.example.com,配置如下:

  1. 服务器端Cookie配置:
    设置domain为.example.com(前缀点匹配所有子域名),同时开启secure(仅HTTPS下生效,生产环境必须):

    res.cookie('token', token, {
      httpOnly: true,
      domain: '.example.com',
      path: '/',
      maxAge: 1000 * 60 * 60 * 24 * 7,
      secure: true,
      sameSite: 'Lax', // 按需调整为'None'(需配合secure)
    })
    
  2. 前端请求配置:
    同开发环境,确保请求携带凭证(axioswithCredentials: true/fetchcredentials: 'include'),浏览器会自动将.example.com的Cookie发送到子域名服务器。

三、核心注意点

  • HttpOnly Cookie无法被前端读取:这是安全设计,前端无需直接获取refresh token,由后端接口读取Cookie并生成access token返回。
  • SameSite属性:同站场景(主域与子域)用Lax即可;跨顶级域名场景需设为None,但必须配合secure: true。
  • 端口不影响域名匹配:localhost跨端口属于同域名范畴,只要请求携带凭证,浏览器就会自动传递Cookie。

内容的提问来源于stack exchange,提问作者Ahmed Abdelrahman

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.23 02:02:06