// This example protects all routes including api/trpc routes
// Please edit this to allow other routes to be public as needed.
// See https://clerk.com/docs/references/nextjs/auth-middleware for more information about configuring your Middleware
export default clerkMiddleware((auth, req) => {
if (isPublicRoute(req)) {
return NextResponse.next();
}
//rewrite for domains
const url = req.nextUrl
const searchParams = url.searchParams.toString()
let hostname = req.headers
// Your custom logic here, for example:
// if (someCondition) {
// return NextResponse.redirect(new URL('/custom-page', req.url));
// }
// If not a public route, protect it
auth().protect();
},
)
export const config = {
matcher: [
// Skip Next.js internals and all static files, unless found in search params
'/((?!_next|[^?]\.(?:html?|css|js(?!on)|jpe?g|webp|png|gif|svg|ttf|woff2?|ico|csv|docx?|xlsx?|zip|webmanifest)).)',
'/',
// Always run for API routes
'/(api|trpc)(.*)',
],
};
// import { clerkMiddleware, createRouteMatcher } from '@clerk/nextjs/server';
// import { NextResponse } from 'next/server';
the original code ./src/middleware.ts file uses authMiddleware which has been deprecated by Clerk, updated to clerkMiddlware
here is what I have come with, it does not work too well, and /agency page gives me this error:
Error: Clerk: auth() was called but Clerk can't detect usage of clerkMiddleware() (or the deprecated authMiddleware()). Please ensure the following:
For more details, see https://clerk.com/docs/quickstarts/nextjs
here is my clerkMiddlware solutions:
import { clerkMiddleware, createRouteMatcher } from '@clerk/nextjs/server'; import { NextResponse } from 'next/server';
const isPublicRoute = createRouteMatcher(['/site', '/api/uploadthing']);
// This example protects all routes including api/trpc routes // Please edit this to allow other routes to be public as needed. // See https://clerk.com/docs/references/nextjs/auth-middleware for more information about configuring your Middleware export default clerkMiddleware((auth, req) => { if (isPublicRoute(req)) { return NextResponse.next(); }
//rewrite for domains const url = req.nextUrl const searchParams = url.searchParams.toString() let hostname = req.headers
const pathWithSearchParams =
${url.pathname}${ searchParams.length > 0 ?
?${searchParams}: '' }
//if subdomain exists const customSubDomain = hostname .get('host') ?.split(
${process.env.NEXT_PUBLIC_DOMAIN}
) .filter(Boolean)[0]if (customSubDomain) { return NextResponse.rewrite( new URL(
/${customSubDomain}${pathWithSearchParams}
, req.url) ) }if (url.pathname === '/sign-in' || url.pathname === '/sign-up') { return NextResponse.redirect(new URL(
/agency/sign-in
, req.url)) }if ( url.pathname === '/' || (url.pathname === '/site' && url.host === process.env.NEXT_PUBLIC_DOMAIN) ) { return NextResponse.rewrite(new URL('/site', req.url)) }
if ( url.pathname.startsWith('/agency') || url.pathname.startsWith('/subaccount') ) { return NextResponse.rewrite(new URL(
${pathWithSearchParams}
, req.url)) }// Your custom logic here, for example: // if (someCondition) { // return NextResponse.redirect(new URL('/custom-page', req.url)); // }
// If not a public route, protect it auth().protect(); }, )
export const config = { matcher: [ // Skip Next.js internals and all static files, unless found in search params '/((?!_next|[^?]\.(?:html?|css|js(?!on)|jpe?g|webp|png|gif|svg|ttf|woff2?|ico|csv|docx?|xlsx?|zip|webmanifest)).)', '/', // Always run for API routes '/(api|trpc)(.*)', ], };
// import { clerkMiddleware, createRouteMatcher } from '@clerk/nextjs/server'; // import { NextResponse } from 'next/server';
// const isPublicRoute = createRouteMatcher(['/site(.)', '/api/uploadthing(.)']);
// export default clerkMiddleware((auth, req) => { // const url = req.nextUrl; // const searchParams = url.searchParams.toString(); // let hostname = req.headers;
// const pathWithSearchParams =
${url.pathname}${ // searchParams.length > 0 ?
?${searchParams}: '' // }
;// // if subdomain exists // const customSubDomain = hostname // .get('host') // ?.split(
${process.env.NEXT_PUBLIC_DOMAIN}
) // .filter(Boolean)[0];// console.log('Custom Subdomain:', customSubDomain); // console.log('Path with Search Params:', pathWithSearchParams); // console.log('URL Pathname:', url.pathname);
// if (customSubDomain) { // console.log('Rewriting to:',
/${customSubDomain}${pathWithSearchParams}
); // return NextResponse.rewrite( // new URL(/${customSubDomain}${pathWithSearchParams}
, req.url) // ); // }// if (url.pathname === '/sign-in' || url.pathname === '/sign-up') { // console.log('Redirecting to:',
/agency/sign-in
); // return NextResponse.redirect(new URL(/agency/sign-in
, req.url)); // }// if ( // url.pathname === '/' || // (url.pathname === '/site' && url.host === process.env.NEXT_PUBLIC_DOMAIN) // ) { // console.log('Rewriting to:', '/site'); // return NextResponse.rewrite(new URL('/site', req.url)); // }
// if ( // url.pathname.startsWith('/agency') || // url.pathname.startsWith('/subaccount') // ) { // console.log('Rewriting to:',
${pathWithSearchParams}
); // return NextResponse.rewrite(new URL(${pathWithSearchParams}
, req.url)); // }// // Protect all routes except public ones // if (!isPublicRoute(req)) { // console.log('Protecting route:', url.pathname); // auth().protect(); // } // });
// export const config = { // matcher: [ // '/((?!_next|[^?]\.(?:html?|css|js(?!on)|jpe?g|webp|png|gif|svg|ttf|woff2?|ico|csv|docx?|xlsx?|zip|webmanifest)).)', // '/(api|trpc)(.*)', // ], // };