HTTP маршрутизатор для Node.js на основе префиксного дерева
|
|
7 months ago | |
|---|---|---|
| .husky | 1 year ago | |
| dist | 11 months ago | |
| examples | 1 year ago | |
| src | 1 year ago | |
| .c8rc | 1 year ago | |
| .commitlintrc | 1 year ago | |
| .editorconfig | 1 year ago | |
| .gitignore | 1 year ago | |
| .mocharc.cjs | 1 year ago | |
| .prettierrc | 1 year ago | |
| LICENSE | 1 year ago | |
| README-ru.md | 1 year ago | |
| README.md | 1 year ago | |
| build-cjs.js | 1 year ago | |
| eslint.config.js | 1 year ago | |
| package.json | 7 months ago | |
| tsconfig.json | 1 year ago |
English | Русский
HTTP роутер для Node.js на основе префиксного дерева (trie).
cookie.preHandler и postHandler
хуков.Требуется Node.js 16 и выше.
npm install @e22m4u/js-trie-router
Модуль поддерживает ESM и CommonJS стандарты.
ESM
import {TrieRouter} from '@e22m4u/js-trie-router';
CommonJS
const {TrieRouter} = require('@e22m4u/js-trie-router');
Базовый пример создания экземпляра роутера, объявления маршрута и передачи слушателя запросов HTTP серверу.
import http from 'http';
import {TrieRouter} from '@e22m4u/js-trie-router';
const server = new http.Server(); // создание экземпляра HTTP сервера
const router = new TrieRouter(); // создание экземпляра роутера
router.defineRoute({
method: 'GET', // метод запроса "GET", "POST" и т.д.
path: '/', // шаблон пути, пример "/user/:id"
handler(ctx) { // обработчик маршрута
return 'Hello world!';
},
});
server.on('request', router.requestListener); // подключение роутера
server.listen(3000, 'localhost'); // прослушивание запросов
// Open in browser http://localhost:3000
Первый параметр обработчика маршрута принимает экземпляр класса
RequestContext с набором свойств, содержащих разобранные
данные входящего запроса.
container: ServiceContainer экземпляр сервис-контейнераreq: IncomingMessage нативный поток входящего
запросаres: ServerResponse нативный поток ответа сервераparams: ParsedParams объект ключ-значение с параметрами
путиquery: ParsedQuery объект ключ-значение с параметрами
строки запросаheaders: ParsedHeaders объект ключ-значение с
заголовками запросаcookie: ParsedCookie объект ключ-значение разобранного
заголовка cookiemethod: string метод запроса в верхнем регистре,
например GET, POST и т.д.path: string путь включающий строку запроса, например
/myPath?foo=barpathname: string путь запроса, например
/myMathbody: unknown тело запросаПример доступа к контексту из обработчика маршрута.
router.defineRoute({
method: 'GET',
path: '/users/:id',
handler(ctx) {
// GET /users/10?include=city
// Cookie: foo=bar; baz=qux;
console.log(ctx.req); // IncomingMessage
console.log(ctx.res); // ServerResponse
console.log(ctx.params); // {id: 10}
console.log(ctx.query); // {include: 'city'}
console.log(ctx.headers); // {cookie: 'foo=bar; baz=qux;'}
console.log(ctx.cookie); // {foo: 'bar', baz: 'qux'}
console.log(ctx.method); // "GET"
console.log(ctx.path); // "/users/10?include=city"
console.log(ctx.pathname); // "/users/10"
// ...
},
});
Возвращаемое значение обработчика маршрута используется в качестве
ответа сервера. Тип значения влияет на представление возвращаемых
данных. Например, если результатом будет являться тип
object, то такое значение автоматически сериализуется в
JSON.
| value | content-type |
|---|---|
string |
text/plain |
number |
application/json |
boolean |
application/json |
object |
application/json |
Buffer |
application/octet-stream |
Stream |
application/octet-stream |
Пример возвращаемого значения обработчиком маршрута.
router.defineRoute({ // регистрация маршрута
// ...
handler(ctx) { // обработчик входящего запроса
return {foo: 'bar'}; // ответ будет представлен в виде JSON
},
});
Контекст запроса ctx содержит нативный экземпляр класса
ServerResponse модуля http, который может быть
использован для ручного управления ответом.
router.defineRoute({
// ...
handler(ctx) {
res.statusCode = 404;
res.setHeader('content-type', 'text/plain; charset=utf-8');
res.end('404 Not Found', 'utf-8');
},
});
Определение маршрута методом defineRoute позволяет
задать хуки для отслеживания и перехвата входящего запроса и ответа
конкретного маршрута.
preHandler выполняется перед вызовом обработчикаpostHandler выполняется после вызова обработчикаПеред вызовом обработчика маршрута может потребоваться выполнение
таких операции как авторизация и проверка параметров запроса. Для этого
можно использовать хук preHandler.
router.defineRoute({ // регистрация маршрута
// ...
preHandler(ctx) {
// перед обработчиком маршрута
console.log(`Incoming request ${ctx.method} ${ctx.path}`);
// > incoming request GET /myPath
},
handler(ctx) {
return 'Hello world!';
},
});
Если хук preHandler возвращает значение отличное от
undefined и null, то такое значение будет
использовано в качестве ответа сервера, а вызов обработчика маршрута
будет пропущен.
router.defineRoute({ // регистрация маршрута
// ...
preHandler(ctx) {
// возвращение ответа сервера
return 'Are you authorized?';
},
handler(ctx) {
// данный обработчик не будет вызван, так как
// хук "preHandler" уже отправил ответ
},
});
Возвращаемое значение обработчика маршрута передается вторым
аргументом хука postHandler. По аналогии с
preHandler, если возвращаемое значение отличается от
undefined и null, то такое значение будет
использовано в качестве ответа сервера. Это может быть полезно для
модификации возвращаемого ответа.
router.defineRoute({
// ...
handler(ctx) {
return 'Hello world!';
},
postHandler(ctx, data) {
// после обработчика маршрута
return data.toUpperCase(); // HELLO WORLD!
},
});
Экземпляр роутера TrieRouter позволяет задать глобальные
хуки, которые имеют более высокий приоритет перед хуками маршрута, и
вызываются в первую очередь.
preHandler выполняется перед вызовом обработчика
каждого маршрутаpostHandler выполняется после вызова обработчика
каждого маршрутаДобавить глобальные хуки можно методом addHook
экземпляра роутера, где первым параметром передается название хука, а
вторым его функция.
router.addHook('preHandler', (ctx) => {
// перед обработчиком маршрута
});
router.addHook('postHandler', (ctx, data) => {
// после обработчика маршрута
});
Аналогично хукам маршрута, если глобальный хук возвращает значение
отличное от undefined и null, то такое
значение будет использовано как ответ сервера.
Установка переменной DEBUG включает вывод логов.
DEBUG=jsTrieRouter* npm run test
npm run test
MIT