Skip to content

Edge Middleware

Learn how you can use Edge Middleware to provide speed and personalization to your users

Edge Middleware is code that executes before a request is processed on a site. Based on the request, you can modify the response. Because it runs before the cache, using Middleware is an effective way of providing personalization to statically generated content. Depending on the incoming request, you can execute custom logic, rewrite, redirect, add headers and more, before returning a response.

Note: Edge Middleware runs on every request by default. To run on specific paths instead, use the matcher property of the Middleware config object. Even when using path matching, Edge Middleware runs on all /_next/data/ requests for getServerSideProps and getStaticProps pages for the sake of consistency. For more information, review our docs on Edge Middleware API as well as the Next.js matcher docs.

Edge Middleware allows you to deliver content to your site's visitors with speed and personalization. They are deployed globally on Vercel's Edge Network and enable you to move server-side logic to the Edge, close to your visitor's origin.

Middleware uses the Vercel Edge Runtime, which is built on the same high-performance V8 JavaScript and WebAssembly engine that is used by the Chrome browser. The Edge Runtime exposes and extends a subset of Web Standard APIs such FetchEvent, Response, and Request, to give you more control over how you manipulate and configure a response, based on the incoming requests. To learn more about writing Middleware, see the Middleware API guide.

Edge Middleware location within Vercel infrastructure.

As a developer, Edge Middleware gives you more control over the user experience, without adding additional size to the application, meaning better performance. For your end-users, they experience pre-rendered, personalized content with very low latency because it's running on the edge.

Some common use-cases of Middleware are:

You can use Edge Middleware with any framework. To add Middleware to your app, you need to create a middleware.ts or middleware.js file in the root of your project.

If the Middleware function is a default export, it can be named anything you choose. If you choose to use a named export, it must be named middleware:

middleware.ts
//named export
export function middleware() {}
// default export
export default function custom() {}

The following code snippet shows an example of rewriting a URL, using a matcher config.

Next.js Middleware comes with built in helpers that are based upon the native FetchEvent, Response, and Request objects.

See the next/server documentation for more information.

middleware.ts
import { NextResponse } from 'next/server';
import type { NextRequest } from 'next/server';

// config with custom matcher
export const config = {
  matcher: '/about/:path*',
};

export default function middleware(request: NextRequest) {
  return NextResponse.redirect(new URL('/about-2', request.url));
}

Middleware will be invoked for every route in your project. There are two ways to define which paths the middleware should be run on: with a custom matcher config or with conditional statements.

While the config option is the preferred method, as it does not get invoked on every request, you can also use conditional statements to only run the Middleware when it matches specific paths.

To decide which route the Middleware should be run on, you can use a custom matcher config to filter on specific paths. The matcher property can be used to define either a single path, or using an array syntax, multiple paths.

middleware.ts
export const config = {
  matcher: '/about/:path*',
};
middleware.ts
export const config = {
  matcher: ['/about/:path*', '/dashboard/:path*'],
};

The matcher config has full regex support for cases such as negative lookaheads or character matching.

To match all request paths except for the ones starting with:

  • api (API routes)
  • _next/static (static files)
  • favicon.ico (favicon file)
middleware.ts
export const config = {
  matcher: ['/((?!api|_next/static|favicon.ico).*)'],
};

To match /blog/123 but not /blog/abc:

middleware.ts
export const config = {
  matcher: ['/blog/:slug(\\d{1,})'],
};

For help on writing your own regex path matcher, review Path to regexp.

middleware.ts
import { rewrite } from '@vercel/edge';

export function middleware(request: Request) {
  const url = new URL(request.url);

  if (url.pathname.startsWith('/about')) {
    return rewrite(new URL('/about-2', request.url));
  }

  if (url.pathname.startsWith('/dashboard')) {
    return rewrite(new URL('/dashboard/user', request.url));
  }
}

See the @vercel/edge documentation for more information on using the @vercel/edge package.

To get started with Edge Middleware, see the Quickstart guide.

Edge Middleware includes some limitations that you should be aware of, including:

  • The maximum size for Middleware is 4 MB, including all the code that is bundled in the function. For more information, see the Limitations guide.
  • Native Node.js APIs are not supported. For more information on all API limitations, see Unsupported APIs and Runtime restrictions.

Edge Middleware has full support for the console API, including time, debug, timeEnd, etc. Logs will appear inside your Vercel project by clicking View Functions Logs next to the deployment.