ホームページ > 記事 > ウェブフロントエンド > Node.js でのバックエンド ルートの自動読み込みに関する簡単な説明
難易度
バックグラウンド
router.post('/user/login', user.login);
ユーザー情報の取得インターフェース
router.get ('/user/info', checkAuth, user.xxx);
この書き方は非常に一般的で、最初にルートを登録し、後で実行するミドルウェアのメソッドを指定します。
しかし、インターフェイスが増えていくと、たとえばインターフェイスが 1,000 個になると、このように 1,000 回登録する必要があり、インターフェイスの数が増えると、非常に面倒で面倒なことになると思います。
##koa&express ルーティングの登録例const express = require('express');
const router = express.Router();
const user = require('../../controllers/user');
const tokenCheck = require('../../middleware/token_check_api');
//用户注册
router.post('/user/register', user.register);
//用户登录
router.post('/user/login', user.login);
router.post('xxx', tokenCheck, user.xxx);
...假装还有有1000个
eggjs ルート登録例'use strict';
// egg-router extends koa-router
import { Application } from 'egg';
export default (app: Application) => {
const { router, controller, middleware } = app;
router.get('/', middleware.special(), controller.home.index);
router.get('/1', middleware.special(), controller.home.index1);
....
router.get('/error', controller.home.error);
};
**この種のプロジェクトが拡大すると、この構成は非常に冗長に見えると思うので、ルートの自動読み込み機構を実装する必要があります。それを改善し、最適化するためです。
1. 効率の向上
2. よりエレガントな記述
共通ルートの自動読み込み1. think シリーズ
最初のシリーズは thinkPHP と thinkjs、参考リンクthinkjs.org/zh-cn/doc /3…
両者の関係は、thinkjs が thinkPHP の考え方に従って設計、開発されたということです。 他の 2 つのルートの自動読み込みはファイルベースです。つまり、コントローラー名とメソッド名を書き込んだ後は、追加の構成を行わずにルートに直接アクセスできます。
1. Thinkphp のルーティングは自動的にロードされますtp はモジュール/コントローラー/メソッドのファイル名に従って自動的にロードされます module?/controller/Action
たとえば、 Adminモジュールに続きます 次に、AdlistController.class.phpのindexメソッド
彼のルートは、
## としてロードされます。 #コントローラ ファイルの自動ロード ロジック
1)、アプリケーションの初期化、インスタンスの作成....
2)、コントローラ ディレクトリのトラバース、コントローラのロードディレクトリ ファイルに対応するエクスポートされたクラスのマップを取得します。
たとえば、Controller ディレクトリ内で
彼はモジュール、コントローラー、メソッドをロードし、アプリにハングします。
{ '/order': [class default_1 extends default_1], '/user': [class default_1 extends default_1] }
3. コントローラーのマッチング部分
前のステップは、thinkjs アプリケーションの起動フェーズ中に実行されます。
このステップ コントローラーのマッチング部分 は、リクエストが受信されたときに実行されることです。
つまり、リクエストが来ると、それが最初に通過し、Think-router はモジュール、コントローラー、アクションを解析して ctx にハングします。
ここでは、ctx 上のこのリクエストのモジュール、コントローラー、アクションを取得し、起動時にアプリにハングしているモジュール、コントローラー、アクション、リストと照合し、存在する場合はそれを実行します。 think-controller のマッチング ロジックの詳細については、
1. think-router が解析した後、think-controller はマッチングを実行します。これは動的マッチングです。
2. koa-router がルートと一致した後、koa-compose を使用して小さなオニオン リングを組み立てて
#概要: thinkjs は最初にコントローラーとメソッドを読み込み、最後にリクエストが到着すると、think-controller
#デコレータは Java spring のアノテーションと同様に記述されます node框架中 1、 控制器装饰器 @controller('/order') 2、方法装饰器 @Get('/export')、 @Post('/list') get接口 就是 post的接口 就是 3、装饰器路由统一注册 这里统一按egg的方法循环注册路由 通过如上比较,相信你对think系列框架堵文件的路由自动加载和装饰器的路由加载,有了一定了解, 还有我认为装饰器的路由写起来,比较优雅, 不知道各位小伙伴怎么看,评论区说说? 更多node相关知识,请访问:nodejs 教程!nestjs
和midwayjs
已经全面拥抱了装饰器路由。
home.ts
,
那你控制器注册也写 @controller('/home')
来保持一致。'use strict';
import { Context } from 'egg';
import BaseController from './base';
import { formatDate } from '~/app/lib/utils';
import { SelfController, Get } from './../router'
@SelfController('/home')
export default class HomeController extends BaseController {
[x: string]: any;
@validate()
@Get("/")
public async index(): Promise<void> {}
}</void>
@Get()
@Post()
@Get("/")
public async index(): Promise<void> {}
@Post("/update")
public async update(): Promise<void> {}</void></void>
'use strict';
import { Application, Context } from 'egg';
import 'reflect-metadata';
const CONTROLLER_PREFIX: string = '';
const methodMap: Map<string> = new Map<string>();
const rootApiPath: string = '';
interface CurController {
pathName: string;
fullPath: string;
}
/**
* controller 装饰器,设置api公共前缀
* @param pathPrefix {string}
* @constructor
*/
export const SelfController = (pathPrefix?: string): ClassDecorator => (targetClass): void => {
// 在controller上定义pathPrefix的元数据
// https://github.com/rbuckton/reflect-metadata
(Reflect as any).defineMetadata(CONTROLLER_PREFIX, pathPrefix, targetClass);
};
const methodWrap = (path: string, requestMethod: string): MethodDecorator => (target, methodName): void => {
// 路由装饰器参数为空时,路由为方法名
const key = path ? `${requestMethod}·${path}·${String(methodName)}` : `${requestMethod}·${String(methodName)}·/${String(methodName)}`;
methodMap.set(key, target);
};
// Post 请求
export const Post = (path: string = ''): MethodDecorator => methodWrap(path, 'post');
// Get 请求
export const Get = (path: string = ''): MethodDecorator => methodWrap(path, 'get');
export default (app: Application): void => {
const { router } = app;
// 遍历methodMap, 注册路由
methodMap.forEach((curController: CurController, configString: string) => {
// 请求方法, 请求路径, 方法名
const [ requestMethod, path, methodName ] = configString.split(`·`);
// 获取controller装饰器设置的公共前缀
// 如果controller没有添加SelfController装饰器,则取文件名作为路径
let controllerPrefix: string | undefined | null = (Reflect as any).getMetadata(CONTROLLER_PREFIX, curController.constructor);
if (!(Reflect as any).hasMetadata(CONTROLLER_PREFIX, curController.constructor)) {
controllerPrefix = `/${curController.pathName.split(`.`).reverse()[0]}`;
}
const func: (this: Context, ...args: any[]) => Promise<any> = async function (...args: any[]): Promise<any> {
return new (curController.constructor as any)(this)[methodName](...args);
};
// 注册路由
router[requestMethod](rootApiPath + controllerPrefix + path, func);
});
};</any></any></string></string>
建议使用node写服务直接上midwayjs或者nestjs
总结
他们的这种设计思想值得学习吧
, 希望对你有所启发。
以上がNode.js でのバックエンド ルートの自動読み込みに関する簡単な説明の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。