tspace-spear 1.0.3 → 1.0.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "tspace-spear",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.5",
|
|
4
4
|
"description": "tspace-spear is a lightweight API framework for Node.js that is fast and highly focused on providing the best developer experience. It utilizes the native HTTP server",
|
|
5
5
|
"main": "./build/lib/index.js",
|
|
6
6
|
"types": "./build/lib/index.d.ts",
|
|
@@ -27,6 +27,7 @@
|
|
|
27
27
|
"scripts": {
|
|
28
28
|
"build": "tsc",
|
|
29
29
|
"prepare": "npm run build",
|
|
30
|
+
"release": "npm run build && npm publish",
|
|
30
31
|
"test": "ts-node src/tests/benchmark.test.ts",
|
|
31
32
|
"test:build": "node build/tests/benchmark.test.js",
|
|
32
33
|
"test:load": "autocannon -c 100 -d 40 -p 10 localhost:3000"
|
|
File without changes
|
|
@@ -1,965 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
// import cluster from 'cluster'
|
|
3
|
-
// import os from 'os'
|
|
4
|
-
// import fs from 'fs';
|
|
5
|
-
// import path from 'path';
|
|
6
|
-
// import findMyWayRouter, { Instance } from 'find-my-way';
|
|
7
|
-
// import { parse } from 'url';
|
|
8
|
-
// import onFinished from "on-finished";
|
|
9
|
-
// import http, {
|
|
10
|
-
// IncomingMessage,
|
|
11
|
-
// Server,
|
|
12
|
-
// ServerResponse
|
|
13
|
-
// } from 'http';
|
|
14
|
-
// import {
|
|
15
|
-
// Router,
|
|
16
|
-
// TContext ,
|
|
17
|
-
// TNextFunction,
|
|
18
|
-
// TResponse ,
|
|
19
|
-
// TRouter,
|
|
20
|
-
// TApplication,
|
|
21
|
-
// TRequestFunction,
|
|
22
|
-
// TErrorFunction,
|
|
23
|
-
// TRequest,
|
|
24
|
-
// TBody,
|
|
25
|
-
// TFiles,
|
|
26
|
-
// TQuery,
|
|
27
|
-
// TCookies,
|
|
28
|
-
// THeaders,
|
|
29
|
-
// TSwagger
|
|
30
|
-
// } from '../..'
|
|
31
|
-
// import { ParserFactory } from './parser-factory';
|
|
32
|
-
// /**
|
|
33
|
-
// *
|
|
34
|
-
// * The 'Spear' class is used to create a server and handle HTTP requests.
|
|
35
|
-
// *
|
|
36
|
-
// * @returns {Spear} application
|
|
37
|
-
// * @example
|
|
38
|
-
// * new Spear()
|
|
39
|
-
// * .get('/' , () => 'Hello world!')
|
|
40
|
-
// * .get('/json' , () => {
|
|
41
|
-
// * return {
|
|
42
|
-
// * message : 'Hello world!'
|
|
43
|
-
// * }
|
|
44
|
-
// * })
|
|
45
|
-
// * .listen(3000 , () => console.log('server listening on port : 3000'))
|
|
46
|
-
// *
|
|
47
|
-
// */
|
|
48
|
-
// class Spear {
|
|
49
|
-
// private readonly _controllers ?: (new () => any)[] | { folder : string , name ?: RegExp}
|
|
50
|
-
// private readonly _middlewares ?: TRequestFunction[] | { folder : string , name ?: RegExp}
|
|
51
|
-
// private readonly _globalPrefix : string
|
|
52
|
-
// private readonly _cluster ?: { use : boolean, maxWorkers ?: number } = { use : false }
|
|
53
|
-
// private readonly _router : Instance<findMyWayRouter.HTTPVersion.V1> = findMyWayRouter()
|
|
54
|
-
// private readonly _parser = new ParserFactory()
|
|
55
|
-
// private _swagger : {
|
|
56
|
-
// use : boolean
|
|
57
|
-
// path ?: `/${string}`
|
|
58
|
-
// servers ?: { url : string }[]
|
|
59
|
-
// tags ?: string[]
|
|
60
|
-
// info ?: {
|
|
61
|
-
// title ?: string,
|
|
62
|
-
// description ?: string,
|
|
63
|
-
// version ?: string
|
|
64
|
-
// }
|
|
65
|
-
// } = {
|
|
66
|
-
// use : false,
|
|
67
|
-
// path : '/api/docs',
|
|
68
|
-
// servers : [
|
|
69
|
-
// {
|
|
70
|
-
// url : 'http://localhost:3000'
|
|
71
|
-
// }
|
|
72
|
-
// ],
|
|
73
|
-
// tags : [],
|
|
74
|
-
// info : {
|
|
75
|
-
// title : "API Documentation",
|
|
76
|
-
// description : "This is a sample documentation",
|
|
77
|
-
// version : "1.0.0"
|
|
78
|
-
// }
|
|
79
|
-
// }
|
|
80
|
-
// private _swaggerAdditional : (TSwagger & { path : string , method : string })[] = []
|
|
81
|
-
// private _errorHandler : TErrorFunction | null = null
|
|
82
|
-
// private _globalMiddlewares : TRequestFunction[] = []
|
|
83
|
-
// private _formatResponse : Function | null = null
|
|
84
|
-
// private _onListeners : Function[] = []
|
|
85
|
-
// private _fileUploadOptions : { limit : number; tempFileDir : string , removeTempFile : { remove : boolean; ms : number }} = {
|
|
86
|
-
// limit : Infinity,
|
|
87
|
-
// tempFileDir : 'tmp',
|
|
88
|
-
// removeTempFile : {
|
|
89
|
-
// remove : false,
|
|
90
|
-
// ms : 1000 * 60 * 10
|
|
91
|
-
// }
|
|
92
|
-
// }
|
|
93
|
-
// constructor({
|
|
94
|
-
// controllers,
|
|
95
|
-
// middlewares,
|
|
96
|
-
// globalPrefix,
|
|
97
|
-
// logger,
|
|
98
|
-
// cluster
|
|
99
|
-
// } : TApplication = {}) {
|
|
100
|
-
// if(logger) this._onListeners.push(() => this.use(this._logger))
|
|
101
|
-
// this._cluster = cluster;
|
|
102
|
-
// this._controllers = controllers;
|
|
103
|
-
// this._middlewares = middlewares;
|
|
104
|
-
// this._globalPrefix = globalPrefix == null ? '' : globalPrefix;
|
|
105
|
-
// }
|
|
106
|
-
// get instance () {
|
|
107
|
-
// return this
|
|
108
|
-
// }
|
|
109
|
-
// get routers () {
|
|
110
|
-
// return this._router;
|
|
111
|
-
// }
|
|
112
|
-
// /**
|
|
113
|
-
// * The 'enableCors' is used to enable the cors origins on the server.
|
|
114
|
-
// *
|
|
115
|
-
// * @params {Object}
|
|
116
|
-
// * @property {(string | RegExp)[]} origins
|
|
117
|
-
// * @property {boolean} credentials
|
|
118
|
-
// * @returns
|
|
119
|
-
// */
|
|
120
|
-
// enableCors({ origins , credentials } : {
|
|
121
|
-
// origins ?: (string | RegExp)[] ,
|
|
122
|
-
// credentials ?: boolean
|
|
123
|
-
// } = {}) {
|
|
124
|
-
// this._globalMiddlewares.push(({ req , res } : TContext , next : TNextFunction) => {
|
|
125
|
-
// const origin = req.headers?.origin
|
|
126
|
-
// if(origin == null) return next()
|
|
127
|
-
// res.setHeader('Access-Control-Allow-Methods', 'GET, POST, PUT, PATCH, DELETE, OPTIONS')
|
|
128
|
-
// res.setHeader('Access-Control-Allow-Headers', 'Content-Type, Authorization')
|
|
129
|
-
// if(origins == null) {
|
|
130
|
-
// res.setHeader('Access-Control-Allow-Origin', '*')
|
|
131
|
-
// }
|
|
132
|
-
// if(Array.isArray(origins) && origins.length) {
|
|
133
|
-
// if(origins.includes(origin)) {
|
|
134
|
-
// res.setHeader('Access-Control-Allow-Origin', origin);
|
|
135
|
-
// }
|
|
136
|
-
// }
|
|
137
|
-
// if(credentials) {
|
|
138
|
-
// res.setHeader('Access-Control-Allow-Credentials', 'true');
|
|
139
|
-
// }
|
|
140
|
-
// return next()
|
|
141
|
-
// })
|
|
142
|
-
// return this
|
|
143
|
-
// }
|
|
144
|
-
// /**
|
|
145
|
-
// * The 'use' method is used to add the middleware into the request pipeline.
|
|
146
|
-
// *
|
|
147
|
-
// * @callback {Function} middleware
|
|
148
|
-
// * @property {Object} ctx - context { req , res , query , params , cookies , files , body}
|
|
149
|
-
// * @property {Function} next - go to next function
|
|
150
|
-
// * @returns {this}
|
|
151
|
-
// */
|
|
152
|
-
// use (middleware : (ctx : TContext , next : TNextFunction) => void): this {
|
|
153
|
-
// this._globalMiddlewares.push(middleware)
|
|
154
|
-
// return this
|
|
155
|
-
// }
|
|
156
|
-
// /**
|
|
157
|
-
// * The 'useBodyParser' method is a middleware used to parse the request body of incoming HTTP requests.
|
|
158
|
-
// *
|
|
159
|
-
// * @returns {this}
|
|
160
|
-
// */
|
|
161
|
-
// useBodyParser (): this {
|
|
162
|
-
// this._globalMiddlewares.push(async ({ req , res } : TContext , next : TNextFunction) => {
|
|
163
|
-
// const contentType = req?.headers['content-type'];
|
|
164
|
-
// const isFileUpload = contentType && contentType.startsWith('multipart/form-data');
|
|
165
|
-
// if(isFileUpload) return next()
|
|
166
|
-
// if(req?._bodyParser != null) return next()
|
|
167
|
-
// req._bodyParser = await this._parser.body(req)
|
|
168
|
-
// return next()
|
|
169
|
-
// })
|
|
170
|
-
// return this
|
|
171
|
-
// }
|
|
172
|
-
// /**
|
|
173
|
-
// * The 'useCookiesParser' method is a middleware used to parses cookies attached to the client request object.
|
|
174
|
-
// *
|
|
175
|
-
// * @returns {this}
|
|
176
|
-
// */
|
|
177
|
-
// useCookiesParser (): this {
|
|
178
|
-
// this._globalMiddlewares.push(({ req } : TContext , next : TNextFunction) => {
|
|
179
|
-
// if(req?._cookiesParser != null) return next()
|
|
180
|
-
// req._cookiesParser = this._parser.cookies(req)
|
|
181
|
-
// return next()
|
|
182
|
-
// })
|
|
183
|
-
// return this
|
|
184
|
-
// }
|
|
185
|
-
// /**
|
|
186
|
-
// * The 'useRouter' method is used to add the router in the request context.
|
|
187
|
-
// *
|
|
188
|
-
// * @parms {Function} router
|
|
189
|
-
// * @property {Function} router - get() , post() , put() , patch() , delete()
|
|
190
|
-
// * @returns {this}
|
|
191
|
-
// */
|
|
192
|
-
// useRouter (router : Router): this {
|
|
193
|
-
// const routes = router.routes
|
|
194
|
-
// for(const {path , method , handlers} of routes) {
|
|
195
|
-
// this[method](this._normalizePath(this._globalPrefix , path) , ...handlers)
|
|
196
|
-
// }
|
|
197
|
-
// return this
|
|
198
|
-
// }
|
|
199
|
-
// /**
|
|
200
|
-
// * The 'useFileUpload' method is a middleware used to handler file uploads. It adds a file upload of incoming HTTP requests.
|
|
201
|
-
// *
|
|
202
|
-
// * @param {?Object}
|
|
203
|
-
// * @property {?number} limits
|
|
204
|
-
// * @property {?string} tempFileDir
|
|
205
|
-
// * @property {?Object} removeTempFile
|
|
206
|
-
// * @property {boolean} removeTempFile.remove
|
|
207
|
-
// * @property {number} removeTempFile.ms
|
|
208
|
-
// * @returns
|
|
209
|
-
// */
|
|
210
|
-
// useFileUpload ({ limit, tempFileDir , removeTempFile } : {
|
|
211
|
-
// limit ?: number
|
|
212
|
-
// tempFileDir ?: string
|
|
213
|
-
// removeTempFile ?: {
|
|
214
|
-
// remove : boolean
|
|
215
|
-
// ms : number
|
|
216
|
-
// }
|
|
217
|
-
// } = {}) {
|
|
218
|
-
// if(limit != null) {
|
|
219
|
-
// this._fileUploadOptions.limit = limit
|
|
220
|
-
// }
|
|
221
|
-
// if(tempFileDir != null) {
|
|
222
|
-
// this._fileUploadOptions.tempFileDir = tempFileDir
|
|
223
|
-
// }
|
|
224
|
-
// if(removeTempFile != null) {
|
|
225
|
-
// this._fileUploadOptions.removeTempFile = removeTempFile
|
|
226
|
-
// }
|
|
227
|
-
// this._globalMiddlewares.push(async ({ req } : TContext , next : TNextFunction) => {
|
|
228
|
-
// const contentType = req?.headers['content-type'];
|
|
229
|
-
// const isFileUpload = contentType && contentType.startsWith('multipart/form-data');
|
|
230
|
-
// const isListMethods = ['POST','PATCH','PUT','DELETE'].includes(String(req.method))
|
|
231
|
-
// if(!isListMethods || !isFileUpload) return next()
|
|
232
|
-
// if(req?._filesParser != null) return next()
|
|
233
|
-
// const { body , files } = await this._parser.files({ req , options : this._fileUploadOptions})
|
|
234
|
-
// req._filesParser = files
|
|
235
|
-
// req._bodyParser = body
|
|
236
|
-
// return next()
|
|
237
|
-
// })
|
|
238
|
-
// return this
|
|
239
|
-
// }
|
|
240
|
-
// /**
|
|
241
|
-
// * The 'useSwagger' method is a middleware used to create swagger api.
|
|
242
|
-
// *
|
|
243
|
-
// * @param {?Object}
|
|
244
|
-
// * @property {?string} path
|
|
245
|
-
// * @property {?array} servers
|
|
246
|
-
// * @property {?object} info
|
|
247
|
-
// * @property {?array} tags
|
|
248
|
-
// * @returns
|
|
249
|
-
// */
|
|
250
|
-
// useSwagger({
|
|
251
|
-
// path,
|
|
252
|
-
// servers,
|
|
253
|
-
// info,
|
|
254
|
-
// tags
|
|
255
|
-
// } : {
|
|
256
|
-
// path ?: `/${string}`
|
|
257
|
-
// servers ?: { url : string , description ?: string }[]
|
|
258
|
-
// tags ?: string[]
|
|
259
|
-
// info ?: {
|
|
260
|
-
// title ?: string,
|
|
261
|
-
// description ?: string,
|
|
262
|
-
// version ?: string
|
|
263
|
-
// }
|
|
264
|
-
// } = {}) {
|
|
265
|
-
// this._swagger = {
|
|
266
|
-
// use : true,
|
|
267
|
-
// path : path ?? this._swagger.path,
|
|
268
|
-
// servers : servers ?? this._swagger.servers,
|
|
269
|
-
// tags : tags ?? this._swagger.tags,
|
|
270
|
-
// info : info ?? this._swagger.info
|
|
271
|
-
// }
|
|
272
|
-
// return this
|
|
273
|
-
// }
|
|
274
|
-
// /**
|
|
275
|
-
// * The 'formatResponse' method is used to format the response
|
|
276
|
-
// *
|
|
277
|
-
// * @param {function} format
|
|
278
|
-
// * @returns
|
|
279
|
-
// */
|
|
280
|
-
// formatResponse (format : (r : unknown , statusCode : number) => any) {
|
|
281
|
-
// this._formatResponse = format
|
|
282
|
-
// return this
|
|
283
|
-
// }
|
|
284
|
-
// /**
|
|
285
|
-
// * The 'errorHandler' method is middleware that is specifically designed to handle errors that occur during the processing of requests
|
|
286
|
-
// *
|
|
287
|
-
// * @param {function} error
|
|
288
|
-
// * @returns
|
|
289
|
-
// */
|
|
290
|
-
// errorHandler (error : (err : Error , ctx : TContext) => any) {
|
|
291
|
-
// this._errorHandler = error
|
|
292
|
-
// return this
|
|
293
|
-
// }
|
|
294
|
-
// /**
|
|
295
|
-
// * The 'notFoundHandler' method is middleware that is specifically designed to handle errors notfound that occur during the processing of requests
|
|
296
|
-
// *
|
|
297
|
-
// * @param {function} notfound
|
|
298
|
-
// * @returns
|
|
299
|
-
// */
|
|
300
|
-
// notFoundHandler (notfound : (ctx : TContext) => any) {
|
|
301
|
-
// const handler = ({ req , res } : TContext) =>{
|
|
302
|
-
// return notfound({
|
|
303
|
-
// req,
|
|
304
|
-
// res : this._customizeResponse(req,res),
|
|
305
|
-
// headers : {},
|
|
306
|
-
// query : {},
|
|
307
|
-
// files : {},
|
|
308
|
-
// body : {},
|
|
309
|
-
// params : {},
|
|
310
|
-
// cookies : {}
|
|
311
|
-
// })
|
|
312
|
-
// }
|
|
313
|
-
// this._onListeners.push(() => {
|
|
314
|
-
// return this._router.all('*', this._wrapHandlers(...this._globalMiddlewares,handler))
|
|
315
|
-
// })
|
|
316
|
-
// return this
|
|
317
|
-
// }
|
|
318
|
-
// /**
|
|
319
|
-
// * The 'get' method is used to add the request handler to the router for the 'GET' method.
|
|
320
|
-
// *
|
|
321
|
-
// * @param {string} path
|
|
322
|
-
// * @callback {...Function[]} handlers of the middlewares
|
|
323
|
-
// * @property {Object} ctx - context { req , res , query , params , cookies , files , body}
|
|
324
|
-
// * @property {Function} next - go to next function
|
|
325
|
-
// * @returns {this}
|
|
326
|
-
// */
|
|
327
|
-
// get (path : string , ...handlers : ((ctx : TContext , next : TNextFunction) => any)[]): this {
|
|
328
|
-
// this._onListeners.push(() => {
|
|
329
|
-
// return this._router.get(
|
|
330
|
-
// this._normalizePath(this._globalPrefix, path),
|
|
331
|
-
// this._wrapHandlers(...this._globalMiddlewares,...handlers)
|
|
332
|
-
// );
|
|
333
|
-
// })
|
|
334
|
-
// return this
|
|
335
|
-
// }
|
|
336
|
-
// /**
|
|
337
|
-
// * The 'post' method is used to add the request handler to the router for the 'POST' method.
|
|
338
|
-
// *
|
|
339
|
-
// * @param {string} path
|
|
340
|
-
// * @callback {...Function[]} handlers of the middlewares
|
|
341
|
-
// * @property {Object} ctx - context { req , res , query , params , cookies , files , body}
|
|
342
|
-
// * @property {Function} next - go to next function
|
|
343
|
-
// * @returns {this}
|
|
344
|
-
// */
|
|
345
|
-
// post (path : string , ...handlers : ((ctx : TContext , next : TNextFunction) => any)[]): this {
|
|
346
|
-
// this._onListeners.push(() => {
|
|
347
|
-
// return this._router.post(
|
|
348
|
-
// this._normalizePath(this._globalPrefix, path),
|
|
349
|
-
// this._wrapHandlers(...this._globalMiddlewares,...handlers)
|
|
350
|
-
// );
|
|
351
|
-
// })
|
|
352
|
-
// return this
|
|
353
|
-
// }
|
|
354
|
-
// /**
|
|
355
|
-
// * The 'put' method is used to add the request handler to the router for the 'PUT' method.
|
|
356
|
-
// *
|
|
357
|
-
// * @param {string} path
|
|
358
|
-
// * @callback {...Function[]} handlers of the middlewares
|
|
359
|
-
// * @property {Object} ctx - context { req , res , query , params , cookies , files , body}
|
|
360
|
-
// * @property {Function} next - go to next function
|
|
361
|
-
// * @returns {this}
|
|
362
|
-
// */
|
|
363
|
-
// put (path : string , ...handlers : ((ctx : TContext , next : TNextFunction) => any)[]): this {
|
|
364
|
-
// this._onListeners.push(() => {
|
|
365
|
-
// return this._router.put(
|
|
366
|
-
// this._normalizePath(this._globalPrefix, path),
|
|
367
|
-
// this._wrapHandlers(...this._globalMiddlewares,...handlers)
|
|
368
|
-
// );
|
|
369
|
-
// })
|
|
370
|
-
// return this
|
|
371
|
-
// }
|
|
372
|
-
// /**
|
|
373
|
-
// * The 'patch' method is used to add the request handler to the router for the 'PATCH' method.
|
|
374
|
-
// *
|
|
375
|
-
// * @param {string} path
|
|
376
|
-
// * @callback {...Function[]} handlers of the middlewares
|
|
377
|
-
// * @property {Object} ctx - context { req , res , query , params , cookies , files , body}
|
|
378
|
-
// * @property {Function} next - go to next function
|
|
379
|
-
// * @returns {this}
|
|
380
|
-
// */
|
|
381
|
-
// patch (path : string , ...handlers : ((ctx : TContext , next : TNextFunction) => any)[]): this {
|
|
382
|
-
// this._onListeners.push(() => {
|
|
383
|
-
// return this._router.patch(
|
|
384
|
-
// this._normalizePath(this._globalPrefix, path),
|
|
385
|
-
// this._wrapHandlers(...this._globalMiddlewares,...handlers)
|
|
386
|
-
// );
|
|
387
|
-
// })
|
|
388
|
-
// return this
|
|
389
|
-
// }
|
|
390
|
-
// /**
|
|
391
|
-
// * The 'delete' method is used to add the request handler to the router for the 'DELETE' method.
|
|
392
|
-
// *
|
|
393
|
-
// * @param {string} path
|
|
394
|
-
// * @callback {...Function[]} handlers of the middlewares
|
|
395
|
-
// * @property {Object} ctx - context { req , res , query , params , cookies , files , body}
|
|
396
|
-
// * @property {Function} next - go to next function
|
|
397
|
-
// * @returns {this}
|
|
398
|
-
// */
|
|
399
|
-
// delete (path : string , ...handlers : ((ctx : TContext , next : TNextFunction) => any)[]): this {
|
|
400
|
-
// this._onListeners.push(() => {
|
|
401
|
-
// return this._router.delete(
|
|
402
|
-
// this._normalizePath(this._globalPrefix, path),
|
|
403
|
-
// this._wrapHandlers(...this._globalMiddlewares,...handlers)
|
|
404
|
-
// );
|
|
405
|
-
// })
|
|
406
|
-
// return this
|
|
407
|
-
// }
|
|
408
|
-
// /**
|
|
409
|
-
// * The 'all' method is used to add the request handler to the router for the 'all' method.
|
|
410
|
-
// *
|
|
411
|
-
// * @param {string} path
|
|
412
|
-
// * @callback {...Function[]} handlers of the middlewares
|
|
413
|
-
// * @property {object} ctx - context { req , res , query , params , cookies , files , body}
|
|
414
|
-
// * @property {function} next - go to next function
|
|
415
|
-
// * @returns {this}
|
|
416
|
-
// */
|
|
417
|
-
// all (path : string , ...handlers : ((ctx : TContext , next : TNextFunction) => any)[]): this {
|
|
418
|
-
// this._onListeners.push(() => {
|
|
419
|
-
// return this._router.all(
|
|
420
|
-
// this._normalizePath(this._globalPrefix, path),
|
|
421
|
-
// this._wrapHandlers(...this._globalMiddlewares,...handlers)
|
|
422
|
-
// );
|
|
423
|
-
// })
|
|
424
|
-
// return this
|
|
425
|
-
// }
|
|
426
|
-
// /**
|
|
427
|
-
// * The 'listen' method is used to bind and start a server to a particular port and optionally a hostname.
|
|
428
|
-
// *
|
|
429
|
-
// * @param {number} port
|
|
430
|
-
// * @param {function} cb
|
|
431
|
-
// * @returns
|
|
432
|
-
// */
|
|
433
|
-
// async listen(port : number | (() => ServerResponse) = 3000, cb : (callback : { server : Server , port : number }) => void) {
|
|
434
|
-
// if(arguments.length === 1 && typeof port === 'function') {
|
|
435
|
-
// cb = port
|
|
436
|
-
// port = 3000
|
|
437
|
-
// }
|
|
438
|
-
// const server = await this._createServer()
|
|
439
|
-
// if(this._cluster?.use) {
|
|
440
|
-
// this._clusterMode(server , Number(port) , cb)
|
|
441
|
-
// return
|
|
442
|
-
// }
|
|
443
|
-
// server.listen(port == null ? 3000 : port , () => {
|
|
444
|
-
// if(cb) cb({ server , port} as { server : Server , port : number })
|
|
445
|
-
// })
|
|
446
|
-
// server.on('listening', () => {
|
|
447
|
-
// this._onListeners.forEach(listener => listener())
|
|
448
|
-
// if(this._swagger.use) {
|
|
449
|
-
// const routes = (this.routers as unknown as { routes : any[]})
|
|
450
|
-
// .routes.filter(r => ["GET","POST","PUT","PATCH","DELETE"].includes(r.method))
|
|
451
|
-
// const {
|
|
452
|
-
// path ,
|
|
453
|
-
// html ,
|
|
454
|
-
// staticSwaggerHandler,
|
|
455
|
-
// staticUrl
|
|
456
|
-
// } = this._parser.swagger({
|
|
457
|
-
// ...this._swagger,
|
|
458
|
-
// options : this._swaggerAdditional,
|
|
459
|
-
// routes
|
|
460
|
-
// })
|
|
461
|
-
// this.routers.get(staticUrl, staticSwaggerHandler)
|
|
462
|
-
// this.routers.get(String(path) , (req, res) => {
|
|
463
|
-
// res.writeHead(200, {'Content-Type': 'text/html'})
|
|
464
|
-
// res.write(html)
|
|
465
|
-
// return res.end()
|
|
466
|
-
// })
|
|
467
|
-
// }
|
|
468
|
-
// })
|
|
469
|
-
// server.on('error', (_: NodeJS.ErrnoException) => {
|
|
470
|
-
// port = Math.floor(Math.random() * 8999) + 1000
|
|
471
|
-
// server.listen(port)
|
|
472
|
-
// })
|
|
473
|
-
// return
|
|
474
|
-
// }
|
|
475
|
-
// private _clusterMode (server : Server , port : number , cb : (callback : { server : Server , port : number }) => void ) {
|
|
476
|
-
// if (cluster.isPrimary) {
|
|
477
|
-
// const numCPUs = os.cpus().length
|
|
478
|
-
// const maxWorkers = this._cluster?.maxWorkers == null
|
|
479
|
-
// ? numCPUs
|
|
480
|
-
// : this._cluster.maxWorkers > numCPUs
|
|
481
|
-
// ? numCPUs
|
|
482
|
-
// : this._cluster.maxWorkers
|
|
483
|
-
// for (let i = 0; i < maxWorkers; i++) {
|
|
484
|
-
// cluster.fork()
|
|
485
|
-
// }
|
|
486
|
-
// cluster.on('exit', () => {
|
|
487
|
-
// cluster.fork()
|
|
488
|
-
// })
|
|
489
|
-
// }
|
|
490
|
-
// if(cluster.isWorker) {
|
|
491
|
-
// server.listen(port == null ? 3000 : port , () => {
|
|
492
|
-
// if(cb) {
|
|
493
|
-
// cb({ server , port} as { server : Server , port : number })
|
|
494
|
-
// }
|
|
495
|
-
// })
|
|
496
|
-
// server.on('listening', () => {
|
|
497
|
-
// this._onListeners.forEach(listener => listener())
|
|
498
|
-
// if(this._swagger.use) {
|
|
499
|
-
// const routes = (this.routers as unknown as { routes : any[]})
|
|
500
|
-
// .routes.filter(r => ["GET","POST","PUT","PATCH","DELETE"].includes(r.method))
|
|
501
|
-
// const {
|
|
502
|
-
// path ,
|
|
503
|
-
// html ,
|
|
504
|
-
// staticSwaggerHandler,
|
|
505
|
-
// staticUrl
|
|
506
|
-
// } = this._parser.swagger({
|
|
507
|
-
// ...this._swagger,
|
|
508
|
-
// options : this._swaggerAdditional,
|
|
509
|
-
// routes
|
|
510
|
-
// })
|
|
511
|
-
// this.routers.get(staticUrl, staticSwaggerHandler)
|
|
512
|
-
// this.routers.get(String(path) , (req, res) => {
|
|
513
|
-
// res.writeHead(200, {'Content-Type': 'text/html'})
|
|
514
|
-
// res.write(html)
|
|
515
|
-
// return res.end()
|
|
516
|
-
// })
|
|
517
|
-
// }
|
|
518
|
-
// })
|
|
519
|
-
// server.on('error', (_: NodeJS.ErrnoException) => {
|
|
520
|
-
// port = Math.floor(Math.random() * 8999) + 1000
|
|
521
|
-
// server.listen(port)
|
|
522
|
-
// })
|
|
523
|
-
// }
|
|
524
|
-
// return
|
|
525
|
-
// }
|
|
526
|
-
// private _logger ({ req , res } : TContext, next: TNextFunction) {
|
|
527
|
-
// const diffTime = (hrtime?: [number, number]) => {
|
|
528
|
-
// const MS = 1000
|
|
529
|
-
// if (hrtime == null) return 0
|
|
530
|
-
// const [start, end] = process.hrtime(hrtime)
|
|
531
|
-
// const time = +(((start * MS ) + (end / 1e6)).toFixed(2))
|
|
532
|
-
// return `${time > MS ? `${time / MS} s` : `${time} ms`}`
|
|
533
|
-
// };
|
|
534
|
-
// const statusCode = (res: TResponse) => {
|
|
535
|
-
// const statusCode = res.statusCode == null ? 500 : Number(res.statusCode);
|
|
536
|
-
// return statusCode < 400
|
|
537
|
-
// ? `\x1b[32m${statusCode}\x1b[0m`
|
|
538
|
-
// : `\x1b[31m${statusCode}\x1b[0m`;
|
|
539
|
-
// };
|
|
540
|
-
// const startTime = process.hrtime();
|
|
541
|
-
// onFinished(res, (): void => {
|
|
542
|
-
// console.log(
|
|
543
|
-
// [
|
|
544
|
-
// `[\x1b[1m\x1b[34mINFO\x1b[0m]`,
|
|
545
|
-
// `\x1b[34m${new Date().toJSON()}\x1b[0m`,
|
|
546
|
-
// `\x1b[33m${req.method}\x1b[0m`,
|
|
547
|
-
// `${decodeURIComponent(String(req.url))}`,
|
|
548
|
-
// `${statusCode(res)}`,
|
|
549
|
-
// `${diffTime(startTime)}`,
|
|
550
|
-
// ].join(" ")
|
|
551
|
-
// );
|
|
552
|
-
// });
|
|
553
|
-
// return next();
|
|
554
|
-
// }
|
|
555
|
-
// private async _import (dir: string , pattern ?: RegExp): Promise<string[]> {
|
|
556
|
-
// const directories = fs.readdirSync(dir, { withFileTypes: true });
|
|
557
|
-
// const files: any[] = (await Promise.all(
|
|
558
|
-
// directories.map((directory) => {
|
|
559
|
-
// const newDir = path.resolve(String(dir), directory.name);
|
|
560
|
-
// if(pattern == null) {
|
|
561
|
-
// return directory.isDirectory() ? this._import(newDir) : newDir;
|
|
562
|
-
// }
|
|
563
|
-
// return directory.isDirectory()
|
|
564
|
-
// ? this._import(newDir)
|
|
565
|
-
// : pattern.test(directory.name)
|
|
566
|
-
// ? newDir
|
|
567
|
-
// : null
|
|
568
|
-
// })
|
|
569
|
-
// )).filter(d => d != null)
|
|
570
|
-
// return [].concat(...files);
|
|
571
|
-
// }
|
|
572
|
-
// private async _registerControllers(): Promise<void> {
|
|
573
|
-
// if(this._controllers == null) return
|
|
574
|
-
// if(!Array.isArray(this._controllers)) {
|
|
575
|
-
// const controllers = await this._import(this._controllers.folder , this._controllers.name)
|
|
576
|
-
// for(const file of controllers) {
|
|
577
|
-
// const response = await import(file)
|
|
578
|
-
// const controller = response?.default
|
|
579
|
-
// const controllerInstance = new controller();
|
|
580
|
-
// const prefixPath: string = Reflect.getMetadata("controllers", controller) ?? ''
|
|
581
|
-
// const routers: TRouter[] = Reflect.getMetadata("routers", controller) ?? []
|
|
582
|
-
// const swaggers: any[] = Reflect.getMetadata("swaggers", controller) ?? []
|
|
583
|
-
// if(prefixPath == null) continue
|
|
584
|
-
// for(const { method, path, handler} of Array.from(routers)) {
|
|
585
|
-
// const find = Array.from(swaggers).find(s => s.handler === handler)
|
|
586
|
-
// if(find != null) {
|
|
587
|
-
// this._swaggerAdditional = [
|
|
588
|
-
// ...this._swaggerAdditional ,
|
|
589
|
-
// {
|
|
590
|
-
// ...find,
|
|
591
|
-
// path : this._normalizePath(this._globalPrefix , prefixPath, path),
|
|
592
|
-
// method
|
|
593
|
-
// }
|
|
594
|
-
// ]
|
|
595
|
-
// }
|
|
596
|
-
// this[method](
|
|
597
|
-
// this._normalizePath(this._globalPrefix ,prefixPath ,path),
|
|
598
|
-
// this._wrapResponse(
|
|
599
|
-
// controllerInstance[String(handler)].bind(controllerInstance)
|
|
600
|
-
// )
|
|
601
|
-
// )
|
|
602
|
-
// }
|
|
603
|
-
// }
|
|
604
|
-
// return
|
|
605
|
-
// }
|
|
606
|
-
// for(const controller of this._controllers) {
|
|
607
|
-
// const controllerInstance = new controller();
|
|
608
|
-
// const prefixPath: string = Reflect.getMetadata("controllers", controller) ?? ''
|
|
609
|
-
// const routers: TRouter[] = Reflect.getMetadata("routers", controller) ?? []
|
|
610
|
-
// const swaggers: any[] = Reflect.getMetadata("swaggers", controller) ?? []
|
|
611
|
-
// if(prefixPath == null) continue
|
|
612
|
-
// for(const { method, path, handler} of Array.from(routers)) {
|
|
613
|
-
// const find = Array.from(swaggers).find(s => s.handler === handler)
|
|
614
|
-
// if(find != null) {
|
|
615
|
-
// this._swaggerAdditional = [
|
|
616
|
-
// ...this._swaggerAdditional ,
|
|
617
|
-
// {
|
|
618
|
-
// ...find,
|
|
619
|
-
// path : this._normalizePath(this._globalPrefix , prefixPath, path),
|
|
620
|
-
// method
|
|
621
|
-
// }
|
|
622
|
-
// ]
|
|
623
|
-
// }
|
|
624
|
-
// this[method](
|
|
625
|
-
// this._normalizePath(this._globalPrefix , prefixPath, path),
|
|
626
|
-
// this._wrapResponse(controllerInstance[String(handler)].bind(controllerInstance))
|
|
627
|
-
// )
|
|
628
|
-
// }
|
|
629
|
-
// }
|
|
630
|
-
// }
|
|
631
|
-
// private async _registerMiddlewares(): Promise<void> {
|
|
632
|
-
// if(this._middlewares == null) return
|
|
633
|
-
// if(!Array.isArray(this._middlewares)) {
|
|
634
|
-
// const middlewares = await this._import(this._middlewares.folder , this._middlewares.name)
|
|
635
|
-
// for(const file of middlewares) {
|
|
636
|
-
// const response = await import(file)
|
|
637
|
-
// const middleware = response?.default
|
|
638
|
-
// this.use(middleware)
|
|
639
|
-
// }
|
|
640
|
-
// return
|
|
641
|
-
// }
|
|
642
|
-
// const middlewares : any[] = this._middlewares
|
|
643
|
-
// for(const middleware of middlewares) {
|
|
644
|
-
// this.use(middleware);
|
|
645
|
-
// }
|
|
646
|
-
// return
|
|
647
|
-
// }
|
|
648
|
-
// private _customizeResponse (req : IncomingMessage, res : ServerResponse) : TResponse {
|
|
649
|
-
// const response = res as unknown as TResponse
|
|
650
|
-
// response.json = (results ?: Record<string,any>) => {
|
|
651
|
-
// if(typeof results === 'string') {
|
|
652
|
-
// if(!res.headersSent) {
|
|
653
|
-
// res.writeHead(200, { 'Content-Type': 'text/plain' })
|
|
654
|
-
// }
|
|
655
|
-
// return res.end(results)
|
|
656
|
-
// }
|
|
657
|
-
// if(!res.headersSent) {
|
|
658
|
-
// res.writeHead(200, { 'Content-Type': 'application/json' })
|
|
659
|
-
// }
|
|
660
|
-
// if(results == null) {
|
|
661
|
-
// if(this._formatResponse != null) {
|
|
662
|
-
// return res.end(JSON.stringify(this._formatResponse(null, res.statusCode),null,2))
|
|
663
|
-
// }
|
|
664
|
-
// return res.end()
|
|
665
|
-
// }
|
|
666
|
-
// if(this._formatResponse != null) {
|
|
667
|
-
// return res.end(JSON.stringify(
|
|
668
|
-
// this._formatResponse({
|
|
669
|
-
// ...results
|
|
670
|
-
// }, res.statusCode) ,null, 2)
|
|
671
|
-
// )
|
|
672
|
-
// }
|
|
673
|
-
// return res.end(JSON.stringify({
|
|
674
|
-
// ...results,
|
|
675
|
-
// },null,2))
|
|
676
|
-
// }
|
|
677
|
-
// response.send = (results : string) => {
|
|
678
|
-
// res.writeHead(res.statusCode, { 'Content-Type': 'text/plain' })
|
|
679
|
-
// return res.end(results)
|
|
680
|
-
// }
|
|
681
|
-
// response.error = (err ) => {
|
|
682
|
-
// let code =
|
|
683
|
-
// +err.response?.data?.code ||
|
|
684
|
-
// +err.code ||
|
|
685
|
-
// +err.status ||
|
|
686
|
-
// +err.statusCode ||
|
|
687
|
-
// +err.response?.data?.statusCode ||
|
|
688
|
-
// 500;
|
|
689
|
-
// code = (code == null || typeof code !== 'number') ? 500 : Number.isNaN(code) ? 500 : code < 400 ? 500 : code
|
|
690
|
-
// const message =
|
|
691
|
-
// err.response?.data?.errorMessage ||
|
|
692
|
-
// err.response?.data?.message ||
|
|
693
|
-
// err.message ||
|
|
694
|
-
// `The url '${req.url}' resulted in a server error. Please investigate.`
|
|
695
|
-
// ;
|
|
696
|
-
// response.status(code as any)
|
|
697
|
-
// if(this._formatResponse != null) {
|
|
698
|
-
// return res.end(JSON.stringify(this._formatResponse({ message }, code) ,null,2))
|
|
699
|
-
// }
|
|
700
|
-
// return res.end(JSON.stringify({
|
|
701
|
-
// message : message
|
|
702
|
-
// },null,2))
|
|
703
|
-
// }
|
|
704
|
-
// response.ok = (results ?: Record<string,any> ) => {
|
|
705
|
-
// return response.json(results == null ? {} : results)
|
|
706
|
-
// }
|
|
707
|
-
// response.created = (results ?: Record<string,any>) => {
|
|
708
|
-
// response.status(201)
|
|
709
|
-
// return response.json(results == null ? {} : results)
|
|
710
|
-
// }
|
|
711
|
-
// response.accepted = (results ?: Record<string,any>) => {
|
|
712
|
-
// response.status(202)
|
|
713
|
-
// return response.json(results == null ? {} : results)
|
|
714
|
-
// }
|
|
715
|
-
// response.noContent = () => {
|
|
716
|
-
// response.status(202)
|
|
717
|
-
// return res.end()
|
|
718
|
-
// }
|
|
719
|
-
// response.badRequest = (message ?: string) => {
|
|
720
|
-
// response.status(400)
|
|
721
|
-
// message = message ?? `The url '${req.url}' resulted in a bad request. Please review the data and try again.`
|
|
722
|
-
// if(this._formatResponse != null) {
|
|
723
|
-
// return res.end(JSON.stringify(this._formatResponse({ message }, 400) ,null,2))
|
|
724
|
-
// }
|
|
725
|
-
// return res.end(JSON.stringify({
|
|
726
|
-
// message : message
|
|
727
|
-
// },null,2))
|
|
728
|
-
// }
|
|
729
|
-
// response.unauthorized = (message ?: string) => {
|
|
730
|
-
// response.status(401)
|
|
731
|
-
// message = message ?? `The url '${req.url}' is unauthorized. Please verify.`
|
|
732
|
-
// if(this._formatResponse != null) {
|
|
733
|
-
// return res.end(JSON.stringify(this._formatResponse({ message }, 401) ,null,2))
|
|
734
|
-
// }
|
|
735
|
-
// return res.end(JSON.stringify({
|
|
736
|
-
// message
|
|
737
|
-
// },null,2))
|
|
738
|
-
// }
|
|
739
|
-
// response.paymentRequired = (message ?: string) => {
|
|
740
|
-
// response.status(402)
|
|
741
|
-
// message = message ?? `The url '${req.url}' requires payment. Please proceed with payment.`
|
|
742
|
-
// if(this._formatResponse != null) {
|
|
743
|
-
// return res.end(JSON.stringify(this._formatResponse({ message }, 402) ,null,2))
|
|
744
|
-
// }
|
|
745
|
-
// return res.end(JSON.stringify({
|
|
746
|
-
// message
|
|
747
|
-
// },null,2))
|
|
748
|
-
// }
|
|
749
|
-
// response.forbidden = (message ?: string) => {
|
|
750
|
-
// response.status(403)
|
|
751
|
-
// message = message ?? `The url '${req.url}' is forbidden. Please check the permissions or access rights.`
|
|
752
|
-
// if(this._formatResponse != null) {
|
|
753
|
-
// return res.end(JSON.stringify(this._formatResponse({ message }, 403) ,null,2))
|
|
754
|
-
// }
|
|
755
|
-
// return res.end(JSON.stringify({
|
|
756
|
-
// message
|
|
757
|
-
// },null,2))
|
|
758
|
-
// }
|
|
759
|
-
// response.notFound = (message ?: string) => {
|
|
760
|
-
// response.status(404)
|
|
761
|
-
// message = message ?? `The url '${req.url}' was not found. Please re-check the your url again`
|
|
762
|
-
// if(this._formatResponse != null) {
|
|
763
|
-
// return res.end(JSON.stringify(this._formatResponse({ message }, 404) ,null,2))
|
|
764
|
-
// }
|
|
765
|
-
// return res.end(JSON.stringify({
|
|
766
|
-
// message
|
|
767
|
-
// },null,2))
|
|
768
|
-
// }
|
|
769
|
-
// response.serverError = (message ?: string) => {
|
|
770
|
-
// response.status(500)
|
|
771
|
-
// message = message ?? `The url '${req.url}' resulted in a server error. Please investigate.`
|
|
772
|
-
// if(this._formatResponse != null) {
|
|
773
|
-
// return res.end(JSON.stringify(this._formatResponse({ message }, 500) ,null,2))
|
|
774
|
-
// }
|
|
775
|
-
// return res.end(JSON.stringify({
|
|
776
|
-
// message
|
|
777
|
-
// },null,2))
|
|
778
|
-
// }
|
|
779
|
-
// response.status = (code : number) => {
|
|
780
|
-
// res.writeHead(code, { 'Content-Type': 'application/json' })
|
|
781
|
-
// return res as unknown as {
|
|
782
|
-
// json : (data?: { [key: string]: any }) => void;
|
|
783
|
-
// send : (message : string) => void;
|
|
784
|
-
// }
|
|
785
|
-
// }
|
|
786
|
-
// response.setCookies = (cookies : Record<string,string | {
|
|
787
|
-
// value : string
|
|
788
|
-
// sameSite ?: 'Strict' | 'Lax' | 'None'
|
|
789
|
-
// domain ?: string
|
|
790
|
-
// secure ?: boolean
|
|
791
|
-
// httpOnly ?: boolean
|
|
792
|
-
// expires ?: Date
|
|
793
|
-
// }> ) => {
|
|
794
|
-
// for(const [key,v] of Object.entries(cookies)) {
|
|
795
|
-
// if(typeof v === 'string') {
|
|
796
|
-
// res.setHeader('Set-Cookie', `${key}=${v}`);
|
|
797
|
-
// continue
|
|
798
|
-
// }
|
|
799
|
-
// if(v.value === '' || v.value == null) continue
|
|
800
|
-
// let str = `${key}=${v.value}`
|
|
801
|
-
// if(v.sameSite != null) {
|
|
802
|
-
// str += ` ;SameSite=${v.sameSite}`
|
|
803
|
-
// }
|
|
804
|
-
// if(v.domain != null) {
|
|
805
|
-
// str += ` ;Domain=${v.domain}`
|
|
806
|
-
// }
|
|
807
|
-
// if(v.httpOnly != null) {
|
|
808
|
-
// str += ` ;HttpOnly`
|
|
809
|
-
// }
|
|
810
|
-
// if(v.secure != null) {
|
|
811
|
-
// str += ` ;Secure`
|
|
812
|
-
// }
|
|
813
|
-
// if(v.expires != null) {
|
|
814
|
-
// str += ` ;Expires=${v.expires.toUTCString()}`
|
|
815
|
-
// }
|
|
816
|
-
// res.setHeader('Set-Cookie', str);
|
|
817
|
-
// }
|
|
818
|
-
// }
|
|
819
|
-
// return response
|
|
820
|
-
// }
|
|
821
|
-
// private _nextFunction (ctx : TContext) {
|
|
822
|
-
// return async (err ?: any) => {
|
|
823
|
-
// if(err != null) {
|
|
824
|
-
// if(this._errorHandler != null) {
|
|
825
|
-
// return this._errorHandler(err,ctx)
|
|
826
|
-
// }
|
|
827
|
-
// ctx.res.writeHead(500, { 'Content-Type': 'application/json' })
|
|
828
|
-
// if(this._formatResponse != null) {
|
|
829
|
-
// return ctx.res.end(JSON.stringify(
|
|
830
|
-
// this._formatResponse({
|
|
831
|
-
// message : err?.message,
|
|
832
|
-
// }, ctx.res.statusCode) ,null, 2)
|
|
833
|
-
// )
|
|
834
|
-
// }
|
|
835
|
-
// return ctx.res.end(JSON.stringify({
|
|
836
|
-
// message : err?.message,
|
|
837
|
-
// },null,2));
|
|
838
|
-
// }
|
|
839
|
-
// if(this._errorHandler != null) {
|
|
840
|
-
// return this._errorHandler(new Error(`The 'next' function does not have any subsequent function.`), ctx)
|
|
841
|
-
// }
|
|
842
|
-
// ctx.res.writeHead(500, { 'Content-Type': 'application/json' })
|
|
843
|
-
// if(this._formatResponse != null) {
|
|
844
|
-
// return ctx.res.end(JSON.stringify(
|
|
845
|
-
// this._formatResponse({
|
|
846
|
-
// message : `The 'next' function does not have any subsequent function.`
|
|
847
|
-
// }, ctx.res.statusCode) ,null, 2)
|
|
848
|
-
// )
|
|
849
|
-
// }
|
|
850
|
-
// return ctx.res.end(JSON.stringify({
|
|
851
|
-
// message : `The 'next' function does not have any subsequent function.`
|
|
852
|
-
// },null,2));
|
|
853
|
-
// }
|
|
854
|
-
// }
|
|
855
|
-
// private _wrapHandlers = (...handlers : ((ctx : TContext , next : TNextFunction) => any)[]) : any => {
|
|
856
|
-
// return async (req : IncomingMessage, res : ServerResponse , params : Record<string,any>) => {
|
|
857
|
-
// const runHandler = async (index : number = 0) : Promise<any> => {
|
|
858
|
-
// const response = this._customizeResponse(req,res) as TResponse
|
|
859
|
-
// const request = req as TRequest
|
|
860
|
-
// const body = request._bodyParser as TBody
|
|
861
|
-
// const files = request._filesParser as TFiles
|
|
862
|
-
// const cookies = request._cookiesParser as TCookies
|
|
863
|
-
// const headers = request.headers as THeaders
|
|
864
|
-
// const query = {...parse(String(req.url), true).query } as TQuery
|
|
865
|
-
// const RecordOrEmptyRecord = (data : any) => {
|
|
866
|
-
// if(data == null) return {}
|
|
867
|
-
// return Object.keys(data).length ? data : {}
|
|
868
|
-
// }
|
|
869
|
-
// const ctx = {
|
|
870
|
-
// req : request,
|
|
871
|
-
// res : response,
|
|
872
|
-
// headers : RecordOrEmptyRecord(headers),
|
|
873
|
-
// params : RecordOrEmptyRecord(params),
|
|
874
|
-
// query : RecordOrEmptyRecord(query),
|
|
875
|
-
// body : RecordOrEmptyRecord(body),
|
|
876
|
-
// files : RecordOrEmptyRecord(files),
|
|
877
|
-
// cookies : RecordOrEmptyRecord(cookies),
|
|
878
|
-
// }
|
|
879
|
-
// if(index === handlers.length - 1) {
|
|
880
|
-
// return this._wrapResponse(handlers[index].bind(handlers[index]))(ctx, this._nextFunction(ctx))
|
|
881
|
-
// }
|
|
882
|
-
// return handlers[index](ctx , () => {
|
|
883
|
-
// return runHandler(index + 1)
|
|
884
|
-
// })
|
|
885
|
-
// }
|
|
886
|
-
// await runHandler()
|
|
887
|
-
// .catch(err => {
|
|
888
|
-
// const ctx = {
|
|
889
|
-
// req,
|
|
890
|
-
// res : this._customizeResponse(req,res),
|
|
891
|
-
// params : Object.keys(params).length ? params : {},
|
|
892
|
-
// headers : {},
|
|
893
|
-
// query : {},
|
|
894
|
-
// body: {},
|
|
895
|
-
// files: {},
|
|
896
|
-
// cookies: {}
|
|
897
|
-
// }
|
|
898
|
-
// return this._nextFunction(ctx)(err)
|
|
899
|
-
// })
|
|
900
|
-
// };
|
|
901
|
-
// }
|
|
902
|
-
// private _wrapResponse(handler : (ctx : TContext , next : TNextFunction) => any) {
|
|
903
|
-
// return async (ctx : TContext , next : TNextFunction) => {
|
|
904
|
-
// const result = await handler(ctx , next);
|
|
905
|
-
// if(result instanceof ServerResponse) return
|
|
906
|
-
// if(typeof result === 'string') {
|
|
907
|
-
// if(!ctx.res.headersSent) {
|
|
908
|
-
// ctx.res.writeHead(200, { 'Content-Type': 'text/plain' })
|
|
909
|
-
// }
|
|
910
|
-
// return ctx.res.end(result)
|
|
911
|
-
// }
|
|
912
|
-
// if(this._formatResponse != null) {
|
|
913
|
-
// const formatResponse = this._formatResponse({ ...result }, ctx.res.statusCode)
|
|
914
|
-
// if(typeof formatResponse === 'string') {
|
|
915
|
-
// if(!ctx.res.headersSent) {
|
|
916
|
-
// ctx.res.writeHead(200, { 'Content-Type': 'text/plain' })
|
|
917
|
-
// }
|
|
918
|
-
// return ctx.res.end(formatResponse)
|
|
919
|
-
// }
|
|
920
|
-
// if(!ctx.res.headersSent) {
|
|
921
|
-
// ctx.res.writeHead(200, { 'Content-Type': 'application/json' })
|
|
922
|
-
// }
|
|
923
|
-
// if(Array.isArray(result)) {
|
|
924
|
-
// return ctx.res.end(JSON.stringify(this._formatResponse(result)))
|
|
925
|
-
// }
|
|
926
|
-
// return ctx.res.end(JSON.stringify(
|
|
927
|
-
// this._formatResponse({
|
|
928
|
-
// ...result
|
|
929
|
-
// }, ctx.res.statusCode) ,null, 2)
|
|
930
|
-
// )
|
|
931
|
-
// }
|
|
932
|
-
// if(!ctx.res.headersSent) {
|
|
933
|
-
// ctx.res.writeHead(200, { 'Content-Type': 'application/json' })
|
|
934
|
-
// }
|
|
935
|
-
// if(Array.isArray(result)) {
|
|
936
|
-
// return ctx.res.end(JSON.stringify(result))
|
|
937
|
-
// }
|
|
938
|
-
// return ctx.res.end(JSON.stringify({
|
|
939
|
-
// ...result,
|
|
940
|
-
// },null,2))
|
|
941
|
-
// };
|
|
942
|
-
// }
|
|
943
|
-
// private async _createServer () : Promise<Server> {
|
|
944
|
-
// await this._registerMiddlewares()
|
|
945
|
-
// await this._registerControllers()
|
|
946
|
-
// const server = http.createServer((req : IncomingMessage, res : ServerResponse) => {
|
|
947
|
-
// return this._router.lookup(req, res)
|
|
948
|
-
// })
|
|
949
|
-
// server.keepAliveTimeout = 1000 * 120
|
|
950
|
-
// server.requestTimeout = 1000 * 120
|
|
951
|
-
// return server
|
|
952
|
-
// }
|
|
953
|
-
// private _normalizePath (...paths: string[]) : string {
|
|
954
|
-
// const path = paths
|
|
955
|
-
// .join('/')
|
|
956
|
-
// .replace(/\/+/g, '/')
|
|
957
|
-
// .replace(/\/+$/, '')
|
|
958
|
-
// const normalizedPath = path.startsWith('/') ? path : `/${path}`
|
|
959
|
-
// return /\/api\/api/.test(normalizedPath) ? normalizedPath.replace(/\/api\/api\//, "/api/") : normalizedPath
|
|
960
|
-
// }
|
|
961
|
-
// }
|
|
962
|
-
// export { Spear }
|
|
963
|
-
// export class Application extends Spear {}
|
|
964
|
-
// export default Spear
|
|
965
|
-
//# sourceMappingURL=q.bak.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"q.bak.js","sourceRoot":"","sources":["../../../../src/lib/core/server/q.bak.ts"],"names":[],"mappings":"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"}
|