跳转到主文档

定制 Web Server

有些开发场景下,需要定制特殊的服务端逻辑,例如用户鉴权、请求预处理、添加页面渲染骨架等,这时,可以通过对 Modern.js 内置的 Web Server 进行扩展实现相应需求。

创建定制 Web Server

在项目根目录执行 pnpm run new 命令,按照如下选择,开启「Server 自定义」功能:

? 请选择你想要的操作: 创建工程元素
? 创建工程元素: 新建「Server 自定义」源码目录
? 请选择运行时框架: Express/Koa/Egg/Nest

目前 Modern.js 默认支持 4 种主流的 Node.js Server 框架:ExpressKoaEgg.jsNest,选择运行时框架时,可根据自身偏好进行选择。

执行命令后,项目目录下会新建 server/index.ts 文件,自定义逻辑在这个文件中编写。

框架差异

由于不同框架 API 的差异性,自定义逻辑的写法也有所不同。假设有以下场景:当请求的 cookies 中包含 login-token 时,认为用户已登录,正常返回页面;否则返回 404 状态码。下面就以此场景为例,演示不同框架下如何实现定制 Web Server 逻辑。

目前 Modern.js 只支持前置中间件的扩展。

Express

import { hook } from '@modern-js/runtime/server';
import type { Request, Response, NextFunction } from 'express';

export default hook(({ addMiddleware }) => {
addMiddleware((request: Request, response: Response, next: NextFunction) => {
if (request.headers.cookies['login-token']) {
return next();
} else {
response.status = 401;
response.end();
}
});
});

Koa

import { hook } from '@modern-js/runtime/server';
import type { Context, Next } from 'koa';

export default hook(({ addMiddleware }) => {
addMiddleware(async (ctx: Context, next: Next) => {
if (ctx.cookies['login-token']) {
await next();
} else {
ctx.status = 401;
}
});
});

Egg

Egg 添加中间件的方式与 Koa 相同。

import { hook } from '@modern-js/runtime/server';
import type { Context, Next } from 'koa';

export default hook(({ addMiddleware }) => {
addMiddleware(async (ctx: Context, next: Next) => {
if (ctx.cookies['login-token']) {
await next();
} else {
ctx.status = 401;
}
});
});

Nest

Nest 支持添加两种类型的内容:Express 的函数中间件和 Nest 中的 Module

Express 的函数中间件的添加与 Express 部分的示例相同,同时这里使用 Module 来为 Web Server 添加一条新的路由。

import { hook } from '@modern-js/runtime/server';
import { Module, Injectable, Controller, Get } from '@nestjs/common';

@Controller('cats')
export class CatsController {
constructor(private readonly catsService: CatsService) {}

@Get()
getHello() {
return this.catsService.getHello();
}
}

@Injectable()
class CatsService {
getHello(): string {
return '<div>Hello world!</div>';;
}
}

@Module({
controllers: [CatsController],
providers: [CatsService],
})
class CatsModule {}

export default hook(({ addMiddleware }) => {
addMiddleware((request: Request, response: Response, next: NextFunction) => {
if (request.headers.cookies['login-token']) {
return next();
} else {
response.status = 401;
response.end();
}
});

addMiddleware(CatsModule);
});

Modern.js 中 Web Server 与应用是一体的,在开发调试、生产部署阶段都无需单独运维。