Easy to use universal dynamic routes for Next.js

Usage no npm install needed!

<script type="module">
  import vlzhNextRoutes from 'https://cdn.skypack.dev/@vlzh/next-routes';


Dynamic Routes for Next.js

NOTICE: This is a fork of @yolkai/next-routes.

npm (scoped)

Easy to use universal dynamic routes for Next.js

  • Express-style route and parameters matching
  • Request handler middleware for express & co
  • Link and Router that generate URLs by route definition

How to use


npm install @vlzh/next-routes --save

Create routes.js inside your project:

const newRoutes = require('@vlzh/next-routes').newRoutes

// Or, if using ES modules:
// import {newRoutes} from '@vlzh/next-routes'

                                                    // Name   Page      Pattern
const routes = newRoutes()                          // ----   ----      -----
  .add({name: 'beta', pattern: '/v3', page: 'v3'})  // beta   v3        /v3

module.exports = routes

// Or, if using ES modules:
// export default routes

This file is used both on the server and the client.


  • nextRoutes.add({name: 'name', pattern: '/name', page: 'name'})


  • name - Route name
  • pattern - Route pattern (like express, see path-to-regexp)
  • page - Page inside ./pages to be rendered

The page component receives the matched URL parameters merged into query

export default class Blog extends React.Component {
  static async getInitialProps ({query}) {
    // query.slug
  render () {
    // this.props.url.query.slug

On the server

// server.js
const next = require('next')
const routes = require('./routes')
const app = next({dev: process.env.NODE_ENV !== 'production'})
const handler = routes.getRequestHandler(app)

// With express
const express = require('express')
app.prepare().then(() => {

// Without express
const {createServer} = require('http')
app.prepare().then(() => {

Optionally you can pass a custom handler, for example:

const handler = routes.getRequestHandler(app, ({req, res, route, query}) => {
  app.render(req, res, route.page, query)

Make sure to use server.js in your package.json scripts:

"scripts": {
  "dev": "node server.js",
  "build": "next build",
  "start": "NODE_ENV=production node server.js"

On the client

Import Link and Router from your routes.js file to generate URLs based on route definition:

Link example

// pages/index.js
import routes from '../routes'

const { Link } = routes

export default () => (
    <div>Welcome to Next.js!</div>
    <Link route='blog' params={{slug: 'hello-world'}}>
      <a>Hello world</a>
    <Link route='/blog/hello-world'>
      <a>Hello world</a>


  • <Link route='name'>...</Link>
  • <Link route='name' params={params}> ... </Link>
  • <Link route='/path/to/match'> ... </Link>


  • route - Route name or URL to match (alias: to)
  • params - Optional parameters for named routes

It generates the URLs for href and as and renders next/link. Other props like prefetch will work as well.

Router example

// pages/blog.js
import React from 'react'
import routes from '../routes'

const { Router } = routes

export default class Blog extends React.Component {
  handleClick () {
    // With route name and params
    Router.pushRoute('blog', {slug: 'hello-world'})
    // With route URL
  render () {
    return (
        <button onClick={this.handleClick}>Home</button>


  • Router.pushRoute(route)
  • Router.pushRoute(route, params)
  • Router.pushRoute(route, params, options)


  • route - Route name or URL to match
  • params - Optional parameters for named routes
  • options - Passed to Next.js

The same works with .replaceRoute() and .prefetchRoute()

It generates the URLs and calls next/router

Optionally you can provide custom Link and Router objects, for example:

const nextRoutes = require('@vlzh/next-routes').default

const routes = nextRoutes({
  Link: require('./my/link')
  Router: require('./my/router')

module.exports = routes

Related links