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

如何允许跨域访问NextJS API路由?解决/api/revalidate跨域问题

Next.js API端点配置CORS的解决方案

针对你遇到的跨域调用/api/revalidate端点被CORS策略拦截的问题,以下是不同路由模式下的具体配置方案:

一、Pages Router 模式(传统pages/api目录)

方法1:手动设置响应头

直接在API路由文件中添加CORS相关响应头,同时处理预检OPTIONS请求:

// pages/api/revalidate.js
export default async function handler(req, res) {
  // 配置允许的可信域名(建议从环境变量读取)
  const allowedOrigin = process.env.NEXT_PUBLIC_ALLOWED_ORIGIN;
  
  // 验证请求来源并设置允许跨域的域名
  if (req.headers.origin === allowedOrigin) {
    res.setHeader('Access-Control-Allow-Origin', allowedOrigin);
  }
  // 允许的请求方法
  res.setHeader('Access-Control-Allow-Methods', 'GET, POST, OPTIONS');
  // 允许的请求头
  res.setHeader('Access-Control-Allow-Headers', 'Content-Type');

  // 处理浏览器预检OPTIONS请求,直接返回200
  if (req.method === 'OPTIONS') {
    return res.status(200).end();
  }

  // 你的按需缓存重新验证逻辑
  try {
    await res.revalidate('/path-to-revalidate');
    return res.json({ revalidated: true });
  } catch (err) {
    return res.status(500).send('Error revalidating');
  }
}

方法2:使用cors第三方包

先安装依赖:

npm install cors
# 或 yarn add cors

然后在API路由中集成中间件:

// pages/api/revalidate.js
import cors from 'cors';

// 初始化cors中间件,指定允许的域名
const corsMiddleware = cors({
  origin: process.env.NEXT_PUBLIC_ALLOWED_ORIGIN,
  methods: ['GET', 'POST', 'OPTIONS'],
});

export default async function handler(req, res) {
  // 用Promise包装cors中间件,适配Next.js API路由逻辑
  await new Promise((resolve, reject) => {
    corsMiddleware(req, res, (result) => {
      if (result instanceof Error) {
        return reject(result);
      }
      return resolve(result);
    });
  });

  // 处理预检请求
  if (req.method === 'OPTIONS') {
    return res.status(200).end();
  }

  // 你的重新验证逻辑
  try {
    await res.revalidate('/path-to-revalidate');
    return res.json({ revalidated: true });
  } catch (err) {
    return res.status(500).send('Error revalidating');
  }
}

二、App Router 模式(Next.js 13+ app/api目录)

在app/api/revalidate/route.js中分别处理OPTIONS预检请求和业务请求:

// app/api/revalidate/route.js
import { NextResponse, revalidatePath } from 'next/server';

// 处理浏览器OPTIONS预检请求
export async function OPTIONS() {
  const allowedOrigin = process.env.NEXT_PUBLIC_ALLOWED_ORIGIN;
  return NextResponse.json({}, {
    headers: {
      'Access-Control-Allow-Origin': allowedOrigin,
      'Access-Control-Allow-Methods': 'GET, POST, OPTIONS',
      'Access-Control-Allow-Headers': 'Content-Type',
    },
  });
}

// 处理业务请求(以POST为例)
export async function POST(request) {
  const allowedOrigin = process.env.NEXT_PUBLIC_ALLOWED_ORIGIN;
  const origin = request.headers.get('origin');
  
  // 验证请求来源合法性
  if (origin !== allowedOrigin) {
    return NextResponse.json({ error: 'Not allowed' }, { status: 403 });
  }

  // 设置响应CORS头
  const response = NextResponse.json({ revalidated: true });
  response.headers.set('Access-Control-Allow-Origin', allowedOrigin);

  // 执行缓存重新验证逻辑
  try {
    await revalidatePath('/path-to-revalidate');
    return response;
  } catch (err) {
    return NextResponse.json({ error: 'Error revalidating' }, { status: 500 });
  }
}

注意事项

  • 生产环境禁止使用*作为Access-Control-Allow-Origin的值,必须限制为可信域名,避免安全风险
  • 建议将允许的域名配置在环境变量中,方便开发、测试、生产环境的不同配置
  • 必须正确处理OPTIONS预检请求,否则浏览器会直接拦截后续的业务请求

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.10 12:05:22