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

在Next.js 15 Server Actions中通过Express设置Cookie的问题排查

问题解决方案

你的核心问题是:Server Actions 运行在 Next.js 服务端,此时 axios 请求是从 Next.js 服务器发起的,而非浏览器客户端——响应里的 set-cookie 会被 Next.js 服务器接收,不会自动同步到用户的浏览器。需要手动提取响应的 Cookie,再通过 Next.js 的 API 设置到客户端。

sameSite: "none" 要求必须搭配 secure: true(仅 HTTPS 环境生效),否则浏览器会拒绝存储 Cookie。同时要确保 CORS 配置允许携带凭证:

// Express 后端代码
const cors = require('cors');
// 配置 CORS
app.use(cors({
  origin: process.env.NEXT_APP_URL, // 替换为你的 Next.js 地址,如 http://localhost:3000
  credentials: true, // 允许跨域携带 Cookie
}));

// 设置 Cookie 的代码
const date = new Date();
date.setDate(date.getDate() + 1);
res.clearCookie("authToken");
res.cookie("authToken", token, {
  httpOnly: true,
  expires: date,
  path: "/",
  sameSite: process.env.NODE_ENV === "production" ? "none" : "lax", // 开发环境用 lax 避免 HTTPS 限制
  secure: process.env.NODE_ENV === "production", // 生产环境强制 HTTPS
});

在 Server Action 中,从响应头提取 set-cookie 字段,解析后用 Next.js 的 cookies() API 设置到浏览器:

"use server";

import { cookies } from "next/headers";
import axiosInstance from "@/utils/axiosInstance"; // 替换为你的 axios 实例路径

export async function handleSubmit(name, email, password) {
  try {
    const res = await axiosInstance.request({
      url: "/auth/login",
      method: "POST",
      data: { name, email, password },
      withCredentials: true, // 确保 axios 接收响应的 Cookie
    });

    // 提取并解析响应头的 set-cookie
    const setCookieHeaders = res.headers["set-cookie"];
    if (setCookieHeaders) {
      const cookieStore = cookies();
      setCookieHeaders.forEach(cookieStr => {
        const cookieParts = cookieStr.split(";").map(part => part.trim());
        const [keyValue] = cookieParts;
        const [key, value] = keyValue.split("=");
        
        // 提取 Cookie 属性
        const expires = cookieParts.find(part => part.startsWith("expires="))?.split("=")[1];
        const path = cookieParts.find(part => part.startsWith("path="))?.split("=")[1] || "/";
        const sameSite = cookieParts.find(part => part.startsWith("SameSite="))?.split("=")[1] as "strict" | "lax" | "none";
        const secure = cookieParts.includes("Secure");
        const httpOnly = cookieParts.includes("HttpOnly");

        // 设置到客户端 Cookie
        cookieStore.set({
          name: key,
          value: value,
          expires: expires ? new Date(expires) : undefined,
          path,
          sameSite,
          secure,
          httpOnly,
        });
      });
    }

    return res.data;
  } catch(error) {
    console.error("登录错误:", error);
    throw error;
  }
}

步骤3:确保 axios 实例配置正确

你的 axios 实例需要开启 withCredentials,保证请求和响应能处理 Cookie:

// axiosInstance 配置示例
import axios from "axios";

const axiosInstance = axios.create({
  baseURL: process.env.NEXT_PUBLIC_API_URL, // 你的后端地址
  withCredentials: true, // 关键:允许携带凭证
});

export default axiosInstance;

关键注意事项

  • 开发环境下,如果使用 HTTP 而非 HTTPS,sameSite: "none" + secure: true 会导致浏览器拒绝 Cookie,此时建议将 sameSite 设为 "lax",或临时关闭 secure。
  • 必须保证 Next.js 和 Express 后端的域名/端口在 CORS 配置中被允许,否则跨域请求会被拦截。

内容的提问来源于stack exchange,提问作者Nikhil Thadani

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.15 10:42:23