No Result
View All Result
Cloud Reports
  • Home
  • Linux
  • Web development
  • Javascript
  • SQL
  • Ant Design tutorial
  • PC & Laptop
  • Technology & Digital
  • Home
  • Linux
  • Web development
  • Javascript
  • SQL
  • Ant Design tutorial
  • PC & Laptop
  • Technology & Digital
No Result
View All Result
Cloud Reports
No Result
View All Result

NextJs + KoaJs Create custom NextJs server with KoaJs

npn by npn
July 26, 2019
in Web development
Reading Time: 6min read
A A
2
NextJs + KoaJs Create custom NextJs server with KoaJs
ADVERTISEMENT

NextJs provide a routing system that can handle almost popular use cases. Some notables about this routing system:

READ ALSO

Javascript developer should stop for … in for now

Javascript developer should stop for … in for now

December 31, 2020
23
How to display colors (color, bgcolor) in console.log () for javascript developers!

How to display colors (color, bgcolor) in console.log () for javascript developers!

January 22, 2021
21
  • Fully supported for Client Side routing
  • Accept url object
  • Support for both push and replace actions
  • Usable with any element that support onClick event
  • Expose href attribute to child component
  • Shallow Routing
  • Mask Routing

Check out these tutorials about Next.js

Next.js + Ant Design with less – Advanced Nextjs and Ant design scaffolding

Convert HTML template into NextJs app

Create custom self-api Next.js api server

[Tutorial] Create react based server side rendering app with NextJS

NextJs Data fetching – Combine Server Side and Client Side fetching

Cloudreports – Next.js tutorials

(Check out https://nextjs.org/docs/#routing for more)

This tutorial will be based on basic  example here: https://github.com/cloudreports/my-nextjs/tree/basic

Mask Routing is a great feature, it help display url in any way you want, for example:

import Link from 'next/link';
export default () => (
    <div>
        <Link as="/contact" href="/?page=contact">
            <a>contact</a>
        </Link>{' '}
        to read more
    </div>
);

In above example, browser will use the value of as attribute for rendered a tag without care about Link href attribute ( <a href="/contact"> ). When clicking on “contact” link, the browser will navigate to /contact. It won’t send xhr request because contact component do not existed in pages directory, and you will get 404 page.

This feature is great but it’s also have disadvantages. Imagine, you have above component, then you want to share that page to your friend. By copying domain.com/contact, you are sending broken link to other. Trust me, that is what happen if you use Mask Routing without a custom server. In this post we will find out what is NextJs custom server and how to build one for your own.

NextJs have it own built-in server, this server is running when npm run dev or npm run start is executed. But this server only serve request with path exactly existed in pages directory. If you request a non-existed component page, you will get a 404 error.

Because of this situation, NextJs allow us to add a custom server and serve any custom url in NextJs style.

Install KoaJs and koa-router
npm i koa koa-router -s
Create file server.js at root of project
// Import prerequisite packages
const next = require('next');
const Koa = require('koa');
const Router = require('koa-router');

// Initialize KoaJs server and router
const server = new Koa();
const router = new Router();

// Initialize NextJs instance and expose request handler
const nextApp = next({ dev: true });
const handler = nextApp.getRequestHandler();

(async () => {
    try {
        await nextApp.prepare();
        router.get('/custom-page', async ctx => {
            await nextApp.render(ctx.req, ctx.res, '/myHandlerComponent', ctx.query);
            ctx.respond = false;
        });

        router.get('*', async ctx => {
            await handler(ctx.req, ctx.res);
            ctx.respond = false;
        });

        server.use(router.routes());
        server.listen(3000, _ => console.log('App running on port 3000'));
    } catch (e) {
        console.error(e);
        process.exit();
    }
})();

Let me explain about code inside async block.

First, we need to call NextJs prepare function. Behind this one line of code, NextJs generate and register required routes. NextJs app cannot run without these routes.

  • /_next/static/:path* This route use for serve commons, chunks and assets from build resources
  • /_next/:path* This path is needed because `render()` does a check for `/_next` and the calls the routing again
  • /static/:path* For serving custom static resources
  • /:path* if useFileSystemPublicRoutes are enabled, this path will be used for serving public resources

After preparing NextJs app, we have to define our custom route here. NextJs provide simple api for handle a request, the same as default server:

ADVERTISEMENT
await nextApp.render(request, response, '/handleComponent', query);
  • request is http request object. This object can be exposed from http/https module or expressjs, koajs
  • response is http response
  • handleComponent this is a normal NextJs page component that located at pagesdirectory
  • query is just an object, you can pass any data here, this object can be empty but it will be good practice that we pass query object here
handleComponent file:
import React from 'react'

export default class MyHandlerComponent extends React.Component {
    render() {
        return (
            <div>My Handler component</div>
        )
    }
}
Important part:
router.get('*', async ctx => {
    await handler(ctx.req, ctx.res);
    ctx.respond = false;
});

At this part, we capture all un-handled requests, this is a must-have block, it care about these type of requests:

  • All request to page component: all requests to existed page component will be handled here, if you remove this block, you will got an error even you have the page component
  • Handle not found request

You should write routes in a separated file, in server.js just import route file and add it as a handler

With custom server file, you lose file watching and hot module replacement. This mean, you have to restart nodejs server any time you modify a file

To avoid this inconvenience, you could apply these changes to your project:

Install nodemon:

npm i nodemon -g

(run with sudo if required)

Create nodemon config file: nodemon.json in root of your project

{
    "verbose": true,
    "ignore": ["node_modules", ".next", "static"],
    "watch": [
        "libs/*",
        "libs/**/*",
        "routes/**",
        "routes/**/*",
        "server.js",
        "store.js",
        "next.config.js",
        ".babelrc.js"
    ],
    "ext": "js jsx json"
}

If you work with more files and dirs, add them into watch array

Change your npm scripts:

"scripts": {
    "dev": "nodemon server.js --exec",
    "build": "next build",
    "start": "next start",
    "test": "echo \"Error: no test specified\" && exit 1"
}

Now whenever a file is updated, nodemon will automatically restart node app for you

Github repository: https://github.com/cloudreports/my-nextjs/tree/custom-server-koajs

Thank you for reading and see you in next post!

Tags: Next.js
ShareTweetShare
Previous Post

[Tutorial] Create react based server side rendering app with NextJS

Next Post

How to solve Github import error: “We found an error during import”

npn

npn

Related Posts

Javascript developer should stop for … in for now
Javascript

Javascript developer should stop for … in for now

December 31, 2020
23
How to display colors (color, bgcolor) in console.log () for javascript developers!
Javascript

How to display colors (color, bgcolor) in console.log () for javascript developers!

January 22, 2021
21
What is Unit Test? Introduction and Example about Unit Test
Web development

What is Unit Test? Introduction and Example about Unit Test

December 24, 2020
11
Accelerate your Continuous Integration pipelines with Directed Acyclic Graph (DAG)
Web development

Accelerate your Continuous Integration pipelines with Directed Acyclic Graph (DAG)

December 22, 2020
9
The FUNDAMENTAL model for learning Web Development.
Web development

The FUNDAMENTAL model for learning Web Development.

December 21, 2020
28
UTM Google, know everything to better use them!
Web development

UTM Google, know everything to better use them!

December 18, 2020
17
Next Post
How to solve Github import error: “We found an error during import”

How to solve Github import error: "We found an error during import"

Comments 2

  1. Pingback: NextJs Data fetching - Combine Server Side and Client Side fetching - Cloud Reports
  2. Pingback: Create custom self-api Next.js api server - Cloud Reports

Leave a Reply Cancel reply

Your email address will not be published. Required fields are marked *

No Result
View All Result

Categories

  • Android (1)
  • Ant Design tutorial (7)
  • Javascript (21)
  • Layout and Routing (2)
  • Linux (3)
  • PC & Laptop (88)
  • React (17)
  • SQL (2)
  • Technology & Digital (256)
  • The Basics (5)
  • Web development (38)

Search

No Result
View All Result
No Result
View All Result
  • Home
  • Linux
  • Web development
  • Javascript
  • SQL
  • Ant Design tutorial
  • PC & Laptop
  • Technology & Digital