Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added redirects middleware #880

Open
wants to merge 2 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
60 changes: 30 additions & 30 deletions next.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,36 +14,36 @@ const nextConfig = {
// https://vercel.com/docs/projects/environment-variables/system-environment-variables
// basePath: process.env.VERCEL_ENV === 'production' ? '/docs' : '',
basePath: '/docs',
async redirects() {
return [
...updatedRedirectsData,
{
source: `/v/${config.DOCS_LATEST_VERSION}/:slug*`,
destination: `https://sourcegraph.com/docs/:slug*`,
permanent: false
},
{
source: `/@${config.DOCS_LATEST_VERSION}/:slug*`,
destination: `https://sourcegraph.com/docs/:slug*`,
permanent: false
},
{
source: '/v/:version(\\d+\\.\\d+)/:slug*',
destination: 'https://:version.sourcegraph.com/:slug*',
permanent: true
},
{
source: '/@:version(\\d+\\.\\d+)/:slug*',
destination: 'https://:version.sourcegraph.com/:slug*',
permanent: true
},
{
source: '/changelog.rss',
destination: '/technical-changelog.rss',
permanent: true
}
];
}
// async redirects() {
// return [
// ...updatedRedirectsData,
// {
// source: `/v/${config.DOCS_LATEST_VERSION}/:slug*`,
// destination: `https://sourcegraph.com/docs/:slug*`,
// permanent: false
// },
// {
// source: `/@${config.DOCS_LATEST_VERSION}/:slug*`,
// destination: `https://sourcegraph.com/docs/:slug*`,
// permanent: false
// },
// {
// source: '/v/:version(\\d+\\.\\d+)/:slug*',
// destination: 'https://:version.sourcegraph.com/:slug*',
// permanent: true
// },
// {
// source: '/@:version(\\d+\\.\\d+)/:slug*',
// destination: 'https://:version.sourcegraph.com/:slug*',
// permanent: true
// },
// {
// source: '/changelog.rss',
// destination: '/technical-changelog.rss',
// permanent: true
// }
// ];
// }
};

module.exports = async () => {
Expand Down
88 changes: 88 additions & 0 deletions src/middleware.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
import { NextResponse } from 'next/server'
import type { NextRequest } from 'next/server'
import docsConfig from '../docs.config.js'

const { updatedRedirectsData } = require('./data/redirects.ts');

function createRedirectUrl(request: NextRequest, destination: string, path: string): string {
// Handle absolute URLs
if (destination.startsWith('http')) {
// Handle dynamic slug replacements
if (destination.includes(':slug')) {
const slugMatch = path.match(/[^/]+$/)
const slug = slugMatch ? slugMatch[0] : ''
destination = destination.replace(':slug*', slug)
}
// Handle version replacements
if (destination.includes(':version')) {
const versionMatch = path.match(/\d+\.\d+/)
const version = versionMatch ? versionMatch[0] : ''
destination = destination.replace(':version', version)
}

return destination
}

// Handle relative paths
const basePath = '/docs'
return destination.startsWith('/') ?
`${request.nextUrl.origin}${basePath}${destination}` :
`${request.nextUrl.origin}${basePath}/${destination}`
}

export function middleware(request: NextRequest) {
const path = request.nextUrl.pathname
const pathWithoutBase = path.replace('/docs', '')

// Handle base redirects from redirects.ts
const redirect = updatedRedirectsData.find((r: any) => r.source === pathWithoutBase)
if (redirect) {
return NextResponse.redirect(createRedirectUrl(request, redirect.destination, path))
}
// Handle version without slug
const versionOnlyMatch = pathWithoutBase.match(/^\/v\/(\d+\.\d+)$/)
if (versionOnlyMatch) {
return NextResponse.redirect(`https://${versionOnlyMatch[1]}.sourcegraph.com/`)
}
// Handle version-specific redirects
if (pathWithoutBase.startsWith(`/v/${docsConfig.DOCS_LATEST_VERSION}/`)) {
return NextResponse.redirect(createRedirectUrl(
request,
`https://sourcegraph.com/docs/:slug*`,
pathWithoutBase
))
}
if (pathWithoutBase.startsWith(`/@${docsConfig.DOCS_LATEST_VERSION}/`)) {
return NextResponse.redirect(createRedirectUrl(
request,
`https://sourcegraph.com/docs/:slug*`,
pathWithoutBase
))
}
const versionMatch = pathWithoutBase.match(/^\/v\/(\d+\.\d+)\/(.*)/)
if (versionMatch) {
return NextResponse.redirect(createRedirectUrl(
request,
'https://:version.sourcegraph.com/:slug*',
pathWithoutBase
))
}
const atVersionMatch = pathWithoutBase.match(/^\/@(\d+\.\d+)\/(.*)/)
if (atVersionMatch) {
return NextResponse.redirect(createRedirectUrl(
request,
'https://:version.sourcegraph.com/:slug*',
pathWithoutBase
))
}
if (pathWithoutBase === '/changelog.rss')
return NextResponse.redirect(createRedirectUrl(request, '/technical-changelog.rss', path))

return NextResponse.next()
}

export const config = {
matcher: [
'/((?!api|_next/static|_next/image|assets|favicon.ico|sw.js).*)',
],
}
Loading