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

Next.js 13.4 App Router中如何传递修改后的请求至后续路由?

解决Next.js 13.4 App Router中间件中request.locals.user无法传递的问题

问题描述

基于Next.js 13.4 App Router开发项目时,在中间件中自定义了CustomNextRequest接口,将令牌验证后获取的用户对象存入request.locals.user,但后续API路由处理器中访问该属性时始终返回undefined,无法获取用户数据。

原因分析

  1. Next.js App Router的中间件与路由处理器使用独立的Request实例,直接修改中间件传入的request对象的locals属性,不会自动同步到后续路由处理器的request中。
  2. 若目标路由不在middleware的matcher匹配范围内,中间件根本不会执行,也会导致locals无数据。
  3. TypeScript类型定义的扩展方式不正确,可能导致路由处理器无法识别locals属性。

解决方案

1. 修正中间件的数据传递逻辑

不要直接修改原request对象,而是创建新的Request实例并附加locals数据,通过NextResponse.next()传递给后续路由:

// 替换中间件中原return NextResponse.next();的逻辑
const newRequest = new Request(request.url, request);
// 确保user.user有值,可先打印验证
console.log("待存储的用户数据:", user.user);
newRequest.locals = { user: user.user };
return NextResponse.next({ request: newRequest });

2. 确保目标路由在匹配范围内

检查config.matcher是否包含你的目标路由,若不在则更新匹配规则:

export const config = {
  matcher: ["/api/admin/:path*", "/api/usersales/:path*", "/api/your-target-route/:path*"],
};

3. 规范TypeScript类型扩展

避免自定义独立的CustomNextRequest接口,直接扩展Next.js内置的NextRequest类型:

// middleware.ts中
import { NextRequest } from "next/server";
import { UserAdminInfo, UserPortalInfo } from "./app/libs/types";

type User = UserAdminInfo | UserPortalInfo;

// 扩展NextRequest类型,添加locals属性
declare module "next/server" {
  interface NextRequest {
    locals: {
      user?: User;
    };
  }
}

// 中间件函数参数直接使用扩展后的NextRequest
export default async function middleware(request: NextRequest) {
  // ... 原有验证逻辑
  const newRequest = new Request(request.url, request);
  newRequest.locals = { user: user.user };
  return NextResponse.next({ request: newRequest });
}

路由处理器中直接使用扩展后的NextRequest:

import prisma from "@/app/libs/prismadb";
import { NextRequest, NextResponse } from "next/server";

export async function PUT(
  request: NextRequest,
  { params: { id } }: { params: { id: string } },
) {
  if (request.locals.user) {
    console.log(request.locals.user); // 现在可正常获取用户数据
  }
  // ... 原有业务逻辑
}

4. 验证接口返回数据

确保/api/checktoken接口返回的user.user有有效值,可在中间件中添加日志确认:

const user = await response.json();
console.log("checktoken接口返回数据:", user);

如果user.user本身为undefined,需先修正令牌验证接口的返回格式。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.21 20:23:11