Next.js 13 Page Route Interception
📅 Jan 13, 2025✍️ lllomh
import React from 'react';
import { createCache, extractStyle, StyleProvider } from '@ant-design/cssinjs';
import Document, { Head, Html, Main, NextScript } from 'next/document';
import type { DocumentContext } from 'next/document';
import { parse } from 'cookie';
const MyDocument = () => (
<Html lang="ja">
<Head>
<link rel="apple-touch-icon" sizes="180x180" href="/apple-touch-icon.png" />
<link rel="shortcut icon" href="/favicon.ico" />
<link rel="stylesheet" href="https://use.typekit.net/ucv8pdz.css" />
<link href="https://fonts.cdnfonts.com/css/new-york-extra-large" rel="stylesheet" />
</Head>
<body>
<Main />
<NextScript />
</body>
</Html>
);
const whiteListedRoutes = ['/public', '/member/account', '/contact']; // Whitelisted routes
MyDocument.getInitialProps = async (ctx: DocumentContext) => {
const cache = createCache();
const originalRenderPage = ctx.renderPage;
ctx.renderPage = () =>
originalRenderPage({
enhanceApp: (App) => (props) => (
<StyleProvider cache={cache}>
<App {...props} />
</StyleProvider>
),
});
const initialProps = await Document.getInitialProps(ctx);
const style = extractStyle(cache, true);
const cookies = parse(ctx.req.headers.cookie || '');
const isAuthenticated = cookies['U_S'] !== undefined ? true : false;
// Get the current route
const currentRoute = ctx.pathname;
console.log(currentRoute, 'currentRoute');
console.log(isAuthenticated, 'isAuthenticated');
// Check if the current route is in the whitelist
const isRouteInWhiteList = whiteListedRoutes.includes(currentRoute);
if (!isAuthenticated && isRouteInWhiteList) {
console.log(4444);
ctx.res.writeHead(302, { Location: '/member/login' });
ctx.res.end();
}
return {
...initialProps,
styles: (
<>
{initialProps.styles}
<style dangerouslySetInnerHTML={{ __html: style }} />
</>
),
};
};
// Single export default function (Index)
export default function Index({ authStates }: { authStates: boolean }) {
// Logic for the Index page
return (
<div>
<h1>Welcome to the Index page</h1>
{authStates ? <p>You are authenticated</p> : <p>You are not authenticated</p>}
</div>
);
}
// Multiple export default function (Page)
export function Page({ authStates, data }: { authStates: boolean; data: any[] }) {
// Logic for the Page component
return (
<div>
<h1>Page Data</h1>
{authStates ? <p>You are authenticated</p> : <p>You are not authenticated</p>}
<ul>
{data.map((item, index) => (
<li key={index}>{item}</li>
))}
</ul>
</div>
);
}
export default MyDocument;