如何使用middleware.ts文件在Next.js中使用多个中间件?

tpxzln5u  于 2023-10-18  发布在  其他
关注(0)|答案(1)|浏览(294)

我正在做一个Next.js项目,并试图在我的应用程序中实现多个中间件。虽然我已经找到了在Next.js中使用**next-connect包的单个中间件的示例,但我更喜欢在不依赖任何外部包的情况下实现这一点。
我有一个
middleware.ts文件,我想在其中定义和使用多个中间件。下面是我的middleware.ts**文件中的代码片段:

import { NextResponse, NextRequest } from 'next/server';

export function middleware(request: NextRequest) {

  const userId = request.cookies.get('userId')

  if (!userId) {
    return NextResponse.redirect(new URL('/auth/login', request.nextUrl.origin).href);
  }
  return NextResponse.next();
}

export const config = {
    matcher:'/profile/:path*',
};

她就是我所尝试的:

import { NextResponse, NextRequest } from "next/server";

export function profileMiddleware(request: NextRequest) {
  const userId = request.cookies.get("userId");

  if (!userId) {
    return NextResponse.redirect(
      new URL("/auth/login", request.nextUrl.origin).href
    );
  }
  return NextResponse.next();
}

export function authMiddleware(request: NextRequest) {
  const userId = request.cookies.get("userId");

  if (userId) {
    return NextResponse.redirect(
      new URL("/", request.nextUrl.origin).href
    );
  }
  return NextResponse.next();
}

export default {
  middleware: [
    {
      matcher: '/profile/:path*',
      handler: profileMiddleware,
    },
    {
      matcher: '/auth/:path*',
      handler: authMiddleware,
    },
  ],
};
smtd7mpg

smtd7mpg1#

您可以使用中间件链接来实现此目的。以下是您可以实现这一点的方法:
1.在src文件夹中创建一个名为middlewares的文件夹。
1.在middlewares文件夹中创建一个名为stackHandler.ts的文件,并将以下内容粘贴到其中:

import {
  NextMiddleware,
  NextResponse
} from "next/server";

export function stackMiddlewares(functions: MiddlewareFactory[] = [], index = 0): NextMiddleware {
  const current = functions[index];
  if (current) {
    const next = stackMiddlewares(functions, index + 1);
    return current(next);
  }
  return () => NextResponse.next();
}

1.创建另一个名为withUser.ts的文件,并将以下内容粘贴到其中:

import {
  NextFetchEvent,
  NextRequest,
  NextResponse
} from "next/server";

function getSearchParam(param: string, url: any) {
  return url.searchParams.get(param);
}

export const withUser: MiddlewareFactory = (next) => {
  return async(request: NextRequest, _next: NextFetchEvent) => {
    const pathname = request.nextUrl.pathname;

    if (["/profile"]?.some((path) => pathname.startsWith(path))) {
      const userId = request.cookies.get("userId");
      if (!userId) {
        const url = new URL(`/auth/login`, request.url);
        return NextResponse.redirect(url);
      }
    }
    return next(request, _next);
  };
};

1.最后在您的middleware.ts文件夹中的src文件中粘贴此内容:

import {
  stackMiddlewares
} from "@/middlewares/stackHandler";
import {
  withUser
} from "@/middlewares/withUser";

const middlewares = [withEditPost];
export default stackMiddlewares(middlewares);

注意事项

如下定义MiddlewareFactory类型(如果不使用Typescript,请忽略此内容):

import {
  NextMiddleware
} from "next/server";

export type MiddlewareFactory = (middleware: NextMiddleware) => NextMiddleware;

注意事项

您可以创建任意数量的中间件,如withUser,方法是创建它们,然后将它们导入middlewares.ts并将它们推入middlewares数组。

相关问题