@bool-ts/core 2.2.4 → 2.3.1

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.
Files changed (70) hide show
  1. package/dist/constants/index.d.ts +3 -0
  2. package/dist/constants/keys.d.ts +34 -0
  3. package/dist/constants/objects.d.ts +505 -0
  4. package/dist/decorators/arguments.d.ts +2 -3
  5. package/dist/decorators/container.d.ts +5 -1
  6. package/dist/decorators/controller.d.ts +1 -1
  7. package/dist/decorators/guard.d.ts +1 -1
  8. package/dist/decorators/inject.d.ts +1 -1
  9. package/dist/decorators/injectable.d.ts +1 -1
  10. package/dist/decorators/interceptor.d.ts +1 -1
  11. package/dist/decorators/middleware.d.ts +1 -1
  12. package/dist/decorators/module.d.ts +1 -1
  13. package/dist/decorators/webSocket.d.ts +1 -1
  14. package/dist/decorators/webSocketArguments.d.ts +1 -1
  15. package/dist/entities/application.d.ts +13 -83
  16. package/dist/entities/httpRoute.d.ts +0 -2
  17. package/dist/entities/httpRouter.d.ts +29 -3
  18. package/dist/entities/httpRouterGroup.d.ts +5 -1
  19. package/dist/entities/injector.d.ts +2 -2
  20. package/dist/http/clientError.d.ts +5 -35
  21. package/dist/http/serverError.d.ts +7 -19
  22. package/dist/index.d.ts +2 -2
  23. package/dist/index.js +6 -6
  24. package/dist/index.js.map +31 -29
  25. package/dist/interfaces/@types.d.ts +114 -0
  26. package/dist/interfaces/guard.d.ts +2 -1
  27. package/dist/interfaces/index.d.ts +2 -1
  28. package/dist/producers/factory.d.ts +1 -1
  29. package/dist/utils/asyncFunction.d.ts +1 -0
  30. package/dist/utils/colors.d.ts +30 -0
  31. package/dist/utils/functions.d.ts +1 -0
  32. package/dist/utils/index.d.ts +5 -0
  33. package/dist/utils/socket.d.ts +1 -0
  34. package/package.json +5 -4
  35. package/src/constants/index.ts +10 -0
  36. package/src/constants/objects.ts +291 -0
  37. package/src/decorators/arguments.ts +3 -5
  38. package/src/decorators/container.ts +40 -20
  39. package/src/decorators/controller.ts +2 -2
  40. package/src/decorators/guard.ts +2 -2
  41. package/src/decorators/http.ts +1 -1
  42. package/src/decorators/inject.ts +2 -2
  43. package/src/decorators/injectable.ts +2 -2
  44. package/src/decorators/interceptor.ts +2 -2
  45. package/src/decorators/middleware.ts +2 -2
  46. package/src/decorators/module.ts +2 -2
  47. package/src/decorators/webSocket.ts +2 -2
  48. package/src/decorators/webSocketArguments.ts +1 -1
  49. package/src/decorators/webSocketEvent.ts +1 -1
  50. package/src/entities/application.ts +1603 -1559
  51. package/src/entities/httpRoute.ts +1 -4
  52. package/src/entities/httpRouter.ts +36 -6
  53. package/src/entities/httpRouterGroup.ts +16 -5
  54. package/src/entities/injector.ts +3 -3
  55. package/src/http/clientError.ts +16 -39
  56. package/src/http/serverError.ts +17 -22
  57. package/src/index.ts +12 -2
  58. package/src/interfaces/@types.ts +171 -0
  59. package/src/interfaces/guard.ts +7 -1
  60. package/src/interfaces/index.ts +24 -1
  61. package/src/producers/factory.ts +1 -1
  62. package/src/utils/colors.ts +50 -0
  63. package/src/utils/constructor.ts +1 -0
  64. package/src/utils/functions.ts +13 -0
  65. package/src/{ultils → utils}/index.ts +1 -0
  66. package/src/ultils/colors.ts +0 -56
  67. /package/{src/ultils/constructor.ts → dist/utils/constructor.d.ts} +0 -0
  68. /package/src/{keys/index.ts → constants/keys.ts} +0 -0
  69. /package/src/{ultils → utils}/asyncFunction.ts +0 -0
  70. /package/src/{ultils → utils}/socket.ts +0 -0
@@ -0,0 +1,114 @@
1
+ import type { BunFile } from "bun";
2
+ import type { TArgumentsMetadataCollection, TWebSocketEventHandlerMetadata } from "../decorators";
3
+ import type { HttpRouterGroup, THttpRouteModel, WebSocketRouterGroup } from "../entities";
4
+ import type { THttpMethods } from "../http";
5
+ import type { ICustomValidator } from "./customValidator";
6
+ import type { IGuard } from "./guard";
7
+ import type { IInterceptor } from "./interceptor";
8
+ import type { IMiddleware } from "./middleware";
9
+ import { parse as QsParse } from "qs";
10
+ export type THandlerMetadata<TClass extends Object = Object, TFuncName extends keyof TClass = keyof TClass, TFunc = TClass[TFuncName]> = Readonly<{
11
+ class: TClass;
12
+ func: TFunc;
13
+ funcName: TFuncName;
14
+ argumentsMetadata: TArgumentsMetadataCollection;
15
+ }>;
16
+ export type TStartMiddlewareHandlers = THandlerMetadata<IMiddleware, "start", NonNullable<IMiddleware["start"]>>[];
17
+ export type TEndMiddlewareHandlers = THandlerMetadata<IMiddleware, "end", NonNullable<IMiddleware["end"]>>[];
18
+ export type TGuardHandlers = THandlerMetadata<IGuard, "enforce", NonNullable<IGuard["enforce"]>>[];
19
+ export type TOpenInterceptorHandlers = THandlerMetadata<IInterceptor, "open", NonNullable<IInterceptor["open"]>>[];
20
+ export type TCloseInterceptorHandlers = THandlerMetadata<IInterceptor, "close", NonNullable<IInterceptor["close"]>>[];
21
+ export type TControllerHandlers = THttpRouteModel[];
22
+ export type TStartMiddlewaresPipe = {
23
+ type: "START_MIDDLEWARES";
24
+ handlers: TStartMiddlewareHandlers;
25
+ };
26
+ export type TEndMiddlewaresPipe = {
27
+ type: "END_MIDDLEWARES";
28
+ handlers: TEndMiddlewareHandlers;
29
+ };
30
+ export type TGuardsPipe = {
31
+ type: "GUARDS";
32
+ handlers: TGuardHandlers;
33
+ };
34
+ export type TOpenInterceptorsPipe = {
35
+ type: "OPEN_INTERCEPTORS";
36
+ handlers: TOpenInterceptorHandlers;
37
+ };
38
+ export type TCloseInterceptorsPipe = {
39
+ type: "CLOSE_INTERCEPTORS";
40
+ handlers: TCloseInterceptorHandlers;
41
+ };
42
+ export type TControllerPipe = {
43
+ type: "CONTROLLER";
44
+ handlers?: undefined;
45
+ };
46
+ export type TPipesEnforcerUnion = TStartMiddlewaresPipe | TEndMiddlewaresPipe | TGuardsPipe | TOpenInterceptorsPipe | TCloseInterceptorsPipe | TControllerPipe;
47
+ export type TParamsType = Record<string, string>;
48
+ export type TApplicationOptions<AllowedMethods extends Array<THttpMethods> = Array<THttpMethods>> = Required<{
49
+ port: number;
50
+ }> & Partial<{
51
+ config: Record<string | symbol, any> | (() => Record<string | symbol, any>);
52
+ prefix: string;
53
+ debug: boolean;
54
+ log: Partial<{
55
+ methods: AllowedMethods;
56
+ }>;
57
+ queryParser: Parameters<typeof QsParse>[1];
58
+ static: Required<{
59
+ path: string;
60
+ }> & Partial<{
61
+ headers: TParamsType;
62
+ cacheTimeInSeconds: number;
63
+ }>;
64
+ cors: Partial<{
65
+ credentials: boolean;
66
+ origins: string | Array<string>;
67
+ methods: Array<THttpMethods>;
68
+ headers: Array<string>;
69
+ }>;
70
+ pipelineStrategy: {
71
+ type: "SIMPLE";
72
+ targets: Partial<{
73
+ middlewares: "FIFO" | "FILO";
74
+ interceptors: "FIFO" | "FILO";
75
+ }>;
76
+ };
77
+ }>;
78
+ export type TStaticMap = Map<string, Readonly<{
79
+ expiredAt: Date;
80
+ file: BunFile;
81
+ }>>;
82
+ export type TResolutedOptions = Readonly<{
83
+ allowLogsMethods: Array<THttpMethods>;
84
+ allowOrigins: Array<string>;
85
+ allowMethods: Array<THttpMethods>;
86
+ allowHeaders: Array<string>;
87
+ allowCredentials: boolean;
88
+ staticOption?: Required<{
89
+ path: string;
90
+ }> & Partial<{
91
+ headers: TParamsType;
92
+ cacheTimeInSeconds: number;
93
+ }>;
94
+ pipelineStrategy: Required<{
95
+ startMiddlewares: "FIFO" | "FILO";
96
+ endMiddlewares: "FIFO" | "FILO";
97
+ openInterceptors: "FIFO" | "FILO";
98
+ closeInterceptors: "FIFO" | "FILO";
99
+ }>;
100
+ }>;
101
+ export type TWebSocketUpgradeData = {
102
+ pathname: string;
103
+ method: string;
104
+ query: Record<string, unknown>;
105
+ };
106
+ export type TPreLaunch = undefined | Readonly<{
107
+ startMiddlewareHandlers: TStartMiddlewareHandlers;
108
+ endMiddlewareHandlers: TEndMiddlewareHandlers;
109
+ controllerRouterGroup: HttpRouterGroup;
110
+ webSocketHttpRouterGroup: HttpRouterGroup;
111
+ webSocketRouterGroup: WebSocketRouterGroup;
112
+ webSocketsMap: Map<string, TWebSocketEventHandlerMetadata>;
113
+ }>;
114
+ export type TValidator = undefined | ICustomValidator;
@@ -1,3 +1,4 @@
1
+ export type TGuardReturn = boolean | "UNAUTHORIZATION" | "FORBIDDEN" | Promise<boolean | "UNAUTHORIZATION" | "FORBIDDEN">;
1
2
  export interface IGuard {
2
- enforce(...args: any[]): boolean | Promise<boolean>;
3
+ enforce(...args: any[]): TGuardReturn;
3
4
  }
@@ -1,8 +1,9 @@
1
+ export type { TApplicationOptions, TCloseInterceptorHandlers, TCloseInterceptorsPipe, TControllerHandlers, TControllerPipe, TEndMiddlewareHandlers, TEndMiddlewaresPipe, TGuardHandlers, TGuardsPipe, THandlerMetadata, TOpenInterceptorHandlers, TOpenInterceptorsPipe, TParamsType, TPipesEnforcerUnion, TPreLaunch, TResolutedOptions, TStartMiddlewareHandlers, TStartMiddlewaresPipe, TStaticMap, TValidator, TWebSocketUpgradeData } from "./@types";
1
2
  export type { IContainer } from "./container";
2
3
  export type { IContext, TContextOptions } from "./context";
3
4
  export type { IController } from "./controller";
4
5
  export type { ICustomValidator } from "./customValidator";
5
- export type { IGuard } from "./guard";
6
+ export type { IGuard, TGuardReturn } from "./guard";
6
7
  export type { IInterceptor } from "./interceptor";
7
8
  export type { IMiddleware } from "./middleware";
8
9
  export type { IModule } from "./module";
@@ -1,5 +1,5 @@
1
1
  import type { TArgumentsMetadataCollection } from "../decorators/arguments";
2
- import type { TConstructor } from "../ultils";
2
+ import type { TConstructor } from "../utils";
3
3
  import "reflect-metadata";
4
4
  import Qs from "qs";
5
5
  import { Application } from "../entities";
@@ -0,0 +1 @@
1
+ export declare const AsyncFunction: Function;
@@ -0,0 +1,30 @@
1
+ type AnsiOptions = {
2
+ color?: keyof typeof ansiColors;
3
+ backgroundColor?: keyof typeof backgroundColors;
4
+ bold?: boolean;
5
+ underline?: boolean;
6
+ };
7
+ declare const ansiColors: Readonly<{
8
+ black: "38;5;16";
9
+ red: "38;5;196";
10
+ green: "38;5;46";
11
+ yellow: "38;5;226";
12
+ blue: "38;5;21";
13
+ magenta: "38;5;201";
14
+ cyan: "38;5;51";
15
+ white: "38;5;231";
16
+ gray: "38;5;244";
17
+ }>;
18
+ declare const backgroundColors: Readonly<{
19
+ black: "48;5;16";
20
+ red: "48;5;196";
21
+ green: "48;5;46";
22
+ yellow: "48;5;226";
23
+ blue: "48;5;21";
24
+ magenta: "48;5;201";
25
+ cyan: "48;5;51";
26
+ white: "48;5;231";
27
+ gray: "48;5;244";
28
+ }>;
29
+ export declare const ansiText: (text: string, options?: AnsiOptions) => string;
30
+ export {};
@@ -0,0 +1 @@
1
+ export declare const inferStatusText: (httpCode: number) => string;
@@ -0,0 +1,5 @@
1
+ export * from "./asyncFunction";
2
+ export * from "./colors";
3
+ export * from "./constructor";
4
+ export * from "./functions";
5
+ export * from "./socket";
@@ -0,0 +1 @@
1
+ export declare const isWebSocketUpgrade: (request: Request) => boolean;
package/package.json CHANGED
@@ -5,9 +5,9 @@
5
5
  },
6
6
  "dependencies": {
7
7
  "@bool-ts/date-time": "^1.0.0",
8
- "qs": "^6.14.0",
8
+ "qs": "^6.14.1",
9
9
  "reflect-metadata": "^0.2.2",
10
- "zod": "^4.2.1"
10
+ "zod": "^4.3.4"
11
11
  },
12
12
  "description": "Core package for BoolTS framework",
13
13
  "devDependencies": {
@@ -40,8 +40,9 @@
40
40
  },
41
41
  "scripts": {
42
42
  "build": "tsc --emitDeclarationOnly && bun run app.build.ts",
43
- "test": "bun --hot run __test/index.ts"
43
+ "test:server": "bun --hot run __test/server/index.ts",
44
+ "test:socket": "bun --hot run __test/client/socket.ts"
44
45
  },
45
46
  "types": "./dist/index.d.ts",
46
- "version": "2.2.4"
47
+ "version": "2.3.1"
47
48
  }
@@ -0,0 +1,10 @@
1
+ export * as Keys from "./keys";
2
+ export * as Objects from "./objects";
3
+
4
+ export type {
5
+ TClientErrorStatuses,
6
+ TInformationalStatuses,
7
+ TRedirectionStatuses,
8
+ TServerErrorStatuses,
9
+ TSuccessfulStatuses
10
+ } from "./objects";
@@ -0,0 +1,291 @@
1
+ //#region [Informational]
2
+ export const informationalStatuses = Object.freeze({
3
+ CONTINUE: Object.freeze({
4
+ status: 100,
5
+ statusText: "Continue"
6
+ }),
7
+ SWITCHING_PROTOCOLS: Object.freeze({
8
+ status: 101,
9
+ statusText: "Switching Protocols"
10
+ }),
11
+ EARLY_HINTS: Object.freeze({
12
+ status: 103,
13
+ statusText: "Early Hints"
14
+ })
15
+ });
16
+
17
+ export type TInformationalStatuses =
18
+ (typeof informationalStatuses)[keyof typeof informationalStatuses]["status"];
19
+ //#endregion
20
+
21
+ //#region [Successful]
22
+ export const successfulStatuses = Object.freeze({
23
+ OK: Object.freeze({
24
+ status: 200,
25
+ statusText: "OK"
26
+ }),
27
+ CREATED: Object.freeze({
28
+ status: 201,
29
+ statusText: "Created"
30
+ }),
31
+ ACCEPTED: Object.freeze({
32
+ status: 202,
33
+ statusText: "Accepted"
34
+ }),
35
+ NON_AUTHORITATIVE_INFORMATION: Object.freeze({
36
+ status: 203,
37
+ statusText: "Non-Authoritative Information"
38
+ }),
39
+ NO_CONTENT: Object.freeze({
40
+ status: 204,
41
+ statusText: "No Content"
42
+ }),
43
+ RESET_CONTENT: Object.freeze({
44
+ status: 205,
45
+ statusText: "Reset Content"
46
+ }),
47
+ PARTIAL_CONTENT: Object.freeze({
48
+ status: 206,
49
+ statusText: "Partial Content"
50
+ }),
51
+ MULTI_STATUS: Object.freeze({
52
+ status: 207,
53
+ statusText: "Multi-Status"
54
+ }),
55
+ ALREADY_REPORTED: Object.freeze({
56
+ status: 208,
57
+ statusText: "Already Reported"
58
+ }),
59
+ IM_USED: Object.freeze({
60
+ status: 226,
61
+ statusText: "IM Used"
62
+ })
63
+ });
64
+
65
+ export type TSuccessfulStatuses =
66
+ (typeof successfulStatuses)[keyof typeof successfulStatuses]["status"];
67
+ //#endregion
68
+
69
+ //#region [Redirection]
70
+ export const redirectionStatuses = Object.freeze({
71
+ MULTIPLE_CHOICES: Object.freeze({
72
+ status: 300,
73
+ statusText: "Multiple Choices"
74
+ }),
75
+ MOVED_PERMANENTLY: Object.freeze({
76
+ status: 301,
77
+ statusText: "Moved Permanently"
78
+ }),
79
+ FOUND: Object.freeze({
80
+ status: 302,
81
+ statusText: "Found"
82
+ }),
83
+ SEE_OTHER: Object.freeze({
84
+ status: 303,
85
+ statusText: "See Other"
86
+ }),
87
+ NOT_MODIFIED: Object.freeze({
88
+ status: 304,
89
+ statusText: "Not Modified"
90
+ }),
91
+ UNUSED: Object.freeze({
92
+ status: 306,
93
+ statusText: "Unused"
94
+ }),
95
+ TEMPORARY_REDIRECT: Object.freeze({
96
+ status: 307,
97
+ statusText: "Temporary Redirect"
98
+ }),
99
+ PERMANENT_REDIRECT: Object.freeze({
100
+ status: 308,
101
+ statusText: "Permanent Redirect"
102
+ })
103
+ });
104
+
105
+ export type TRedirectionStatuses =
106
+ (typeof redirectionStatuses)[keyof typeof redirectionStatuses]["status"];
107
+ //#endregion
108
+
109
+ //#region [Client error]
110
+ export const clientErrorStatuses = Object.freeze({
111
+ BAD_REQUEST: Object.freeze({
112
+ status: 400,
113
+ statusText: "Bad Request"
114
+ }),
115
+ UNAUTHORIZED: Object.freeze({
116
+ status: 401,
117
+ statusText: "Unauthorized"
118
+ }),
119
+ PAYMENT_REQUIRED: Object.freeze({
120
+ status: 402,
121
+ statusText: "Payment Required"
122
+ }),
123
+ FORBIDDEN: Object.freeze({
124
+ status: 403,
125
+ statusText: "Forbidden"
126
+ }),
127
+ NOT_FOUND: Object.freeze({
128
+ status: 404,
129
+ statusText: "Not Found"
130
+ }),
131
+ METHOD_NOT_ALLOWED: Object.freeze({
132
+ status: 405,
133
+ statusText: "Method Not Allowed"
134
+ }),
135
+ NOT_ACCEPTABLE: Object.freeze({
136
+ status: 406,
137
+ statusText: "Not Acceptable"
138
+ }),
139
+ PROXY_AUTHENTICATION_REQUIRED: Object.freeze({
140
+ status: 407,
141
+ statusText: "Proxy Authentication Required"
142
+ }),
143
+ REQUEST_TIMEOUT: Object.freeze({
144
+ status: 408,
145
+ statusText: "Request Timeout"
146
+ }),
147
+ CONFLICT: Object.freeze({
148
+ status: 409,
149
+ statusText: "Conflict"
150
+ }),
151
+ GONE: Object.freeze({
152
+ status: 410,
153
+ statusText: "Gone"
154
+ }),
155
+ LENGTH_REQUIRED: Object.freeze({
156
+ status: 411,
157
+ statusText: "Length Required"
158
+ }),
159
+ PRECONDITION_FAILED: Object.freeze({
160
+ status: 412,
161
+ statusText: "Precondition Failed"
162
+ }),
163
+ CONTENT_TOO_LARGE: Object.freeze({
164
+ status: 413,
165
+ statusText: "Content Too Large"
166
+ }),
167
+ URI_TOO_LONG: Object.freeze({
168
+ status: 414,
169
+ statusText: "URI Too Long"
170
+ }),
171
+ UNSUPPORTED_MEDIA_TYPE: Object.freeze({
172
+ status: 415,
173
+ statusText: "Unsupported Media Type"
174
+ }),
175
+ RANGE_NOT_SATISFIABLE: Object.freeze({
176
+ status: 416,
177
+ statusText: "Range Not Satisfiable"
178
+ }),
179
+ EXPECTATION_FAILED: Object.freeze({
180
+ status: 417,
181
+ statusText: "Expectation Failed"
182
+ }),
183
+ I_AM_A_TEAPOT: Object.freeze({
184
+ status: 418,
185
+ statusText: "I'm a teapot"
186
+ }),
187
+ MISDIRECTED_REQUEST: Object.freeze({
188
+ status: 421,
189
+ statusText: "Misdirected Request"
190
+ }),
191
+ UNPROCESSABLE_CONTENT: Object.freeze({
192
+ status: 422,
193
+ statusText: "Unprocessable Content"
194
+ }),
195
+ LOCKED: Object.freeze({
196
+ status: 423,
197
+ statusText: "Locked"
198
+ }),
199
+ FAILED_DEPENDENCY: Object.freeze({
200
+ status: 424,
201
+ statusText: "Failed Dependency"
202
+ }),
203
+ TOO_EARLY: Object.freeze({
204
+ status: 425,
205
+ statusText: "Too Early"
206
+ }),
207
+ UPGRADE_REQUIRED: Object.freeze({
208
+ status: 426,
209
+ statusText: "Upgrade Required"
210
+ }),
211
+ PRECONDITION_REQUIRED: Object.freeze({
212
+ status: 428,
213
+ statusText: "Precondition Required"
214
+ }),
215
+ TOO_MANY_REQUESTS: Object.freeze({
216
+ status: 429,
217
+ statusText: "Too Many Requests"
218
+ }),
219
+ REQUEST_HEADER_FIELDS_TOO_LARGE: Object.freeze({
220
+ status: 431,
221
+ statusText: "Request Header Fields Too Large"
222
+ }),
223
+ UNAVAILABLE_FOR_LEGAL_REASONS: Object.freeze({
224
+ status: 451,
225
+ statusText: "Unavailable For Legal Reasons"
226
+ })
227
+ });
228
+
229
+ export type TClientErrorStatuses =
230
+ (typeof clientErrorStatuses)[keyof typeof clientErrorStatuses]["status"];
231
+ //#endregion
232
+
233
+ //#region [Server error]
234
+ export const serverErrorStatuses = Object.freeze({
235
+ INTERNAL_SERVER_ERROR: Object.freeze({
236
+ status: 500,
237
+ statusText: "Internal Server Error"
238
+ }),
239
+ NOT_IMPLEMENTED: Object.freeze({
240
+ status: 501,
241
+ statusText: "Not Implemented"
242
+ }),
243
+ BAD_GATEWAY: Object.freeze({
244
+ status: 502,
245
+ statusText: "Bad Gateway"
246
+ }),
247
+ SERVICE_UNAVAILABLE: Object.freeze({
248
+ status: 503,
249
+ statusText: "Service Unavailable"
250
+ }),
251
+ GATEWAY_TIMEOUT: Object.freeze({
252
+ status: 504,
253
+ statusText: "Gateway Timeout"
254
+ }),
255
+ HTTP_VERSION_NOT_SUPPORTED: Object.freeze({
256
+ status: 505,
257
+ statusText: "HTTP Version Not Supported"
258
+ }),
259
+ VARIANT_ALSO_NEGOTIATES: Object.freeze({
260
+ status: 506,
261
+ statusText: "Variant Also Negotiates"
262
+ }),
263
+ INSUFFICIENT_STORAGE: Object.freeze({
264
+ status: 507,
265
+ statusText: "Insufficient Storage"
266
+ }),
267
+ LOOP_DETECTED: Object.freeze({
268
+ status: 508,
269
+ statusText: "Loop Detected"
270
+ }),
271
+ NOT_EXTENDED: Object.freeze({
272
+ status: 510,
273
+ statusText: "Not Extended"
274
+ }),
275
+ NETWORK_AUTHENTICATION_REQUIRED: Object.freeze({
276
+ status: 511,
277
+ statusText: "Network Authentication Required"
278
+ })
279
+ });
280
+
281
+ export type TServerErrorStatuses =
282
+ (typeof serverErrorStatuses)[keyof typeof serverErrorStatuses]["status"];
283
+ //#endregion
284
+
285
+ export const httpStatuses = Object.freeze({
286
+ ...informationalStatuses,
287
+ ...successfulStatuses,
288
+ ...redirectionStatuses,
289
+ ...clientErrorStatuses,
290
+ ...serverErrorStatuses
291
+ });
@@ -11,7 +11,7 @@ import {
11
11
  requestHeadersArgsKey,
12
12
  responseHeadersArgsKey,
13
13
  routeModelArgsKey
14
- } from "../keys";
14
+ } from "../constants/keys";
15
15
 
16
16
  export type TArgumentsMetadata<TValidationSchema = unknown> =
17
17
  | {
@@ -50,7 +50,6 @@ export type TArgumentsMetadata<TValidationSchema = unknown> =
50
50
  | {
51
51
  index: number;
52
52
  type: typeof requestArgsKey;
53
- validationSchema?: TValidationSchema;
54
53
  }
55
54
  | {
56
55
  index: number;
@@ -229,7 +228,7 @@ export const Query =
229
228
  };
230
229
 
231
230
  export const Request =
232
- <TTarget extends Object, TValidationSchema = unknown>(validationSchema?: TValidationSchema) =>
231
+ <TTarget extends Object, TValidationSchema = unknown>() =>
233
232
  (target: TTarget, methodName: string | symbol | undefined, parameterIndex: number) => {
234
233
  if (!methodName) {
235
234
  return;
@@ -240,8 +239,7 @@ export const Request =
240
239
 
241
240
  metadata[`argumentIndexes.${parameterIndex}`] = {
242
241
  index: parameterIndex,
243
- type: requestArgsKey,
244
- validationSchema: validationSchema
242
+ type: requestArgsKey
245
243
  } satisfies Extract<
246
244
  TArgumentsMetadata,
247
245
  {
@@ -1,6 +1,14 @@
1
- import type { TConstructor } from "../ultils";
1
+ import type { TConstructor } from "../utils";
2
+ import type { TModuleMetadata } from "./module";
2
3
 
3
- import { containerKey, guardKey, injectableKey, middlewareKey, moduleKey } from "../keys";
4
+ import {
5
+ containerKey,
6
+ guardKey,
7
+ injectableKey,
8
+ interceptorKey,
9
+ middlewareKey,
10
+ moduleKey
11
+ } from "../constants/keys";
4
12
 
5
13
  type TLoaders<TConfig extends {} = {}> = Record<
6
14
  string | symbol,
@@ -16,23 +24,27 @@ export type TContainerConfig<TConfig> =
16
24
 
17
25
  export type TContainerOptions<TConfig extends {} = {}> =
18
26
  | Partial<{
27
+ prefix: string;
19
28
  loaders: TLoaders<TConfig>;
20
29
  config: TContainerConfig<TConfig>;
21
30
  modules: Array<TConstructor<unknown>>;
22
31
  dependencies: Array<TConstructor<unknown>>;
23
32
  middlewares: Array<TConstructor<unknown>>;
24
33
  guards: Array<TConstructor<unknown>>;
34
+ interceptors: Array<TConstructor<unknown>>;
25
35
  }>
26
36
  | undefined;
27
37
 
28
38
  export type TContainerMetadata<TConfig extends {} = {}> =
29
39
  | Partial<{
40
+ prefix: string;
30
41
  loaders: TLoaders<TConfig>;
31
42
  config: TContainerConfig<TConfig>;
32
43
  modules: Array<TConstructor<unknown>>;
33
44
  dependencies: Array<TConstructor<unknown>>;
34
45
  middlewares: Array<TConstructor<unknown>>;
35
46
  guards: Array<TConstructor<unknown>>;
47
+ interceptors: Array<TConstructor<unknown>>;
36
48
  }>
37
49
  | undefined;
38
50
 
@@ -41,7 +53,7 @@ export const Container =
41
53
  args?: TContainerOptions<TConfig>
42
54
  ) =>
43
55
  (target: K) => {
44
- const { modules, middlewares, guards, dependencies } = args || {};
56
+ const { modules, middlewares, guards, interceptors, dependencies } = args || {};
45
57
 
46
58
  if (Reflect.hasOwnMetadata(moduleKey, target)) {
47
59
  throw new Error(
@@ -50,41 +62,49 @@ export const Container =
50
62
  }
51
63
 
52
64
  if (modules) {
53
- for (let i = 0; i < modules.length; i++) {
54
- if (!Reflect.getOwnMetadataKeys(modules[i]).includes(moduleKey)) {
55
- throw Error(`${modules[i].name} is not a module.`);
65
+ const modulePrefixes: string[] = [];
66
+
67
+ for (const module of modules) {
68
+ if (!Reflect.getOwnMetadataKeys(module).includes(moduleKey)) {
69
+ throw Error(`[${module.name}] is not a module.`);
70
+ }
71
+
72
+ const moduleMetadata: TModuleMetadata = Reflect.getOwnMetadata(moduleKey, module);
73
+
74
+ if (modulePrefixes.includes(moduleMetadata?.prefix || "")) {
75
+ throw new Error(`Duplicated prefix of module [${module.name}].`);
56
76
  }
57
77
  }
58
78
  }
59
79
 
60
80
  if (middlewares) {
61
- for (let i = 0; i < middlewares.length; i++) {
62
- if (!Reflect.getOwnMetadataKeys(middlewares[i]).includes(middlewareKey)) {
63
- throw Error(`${middlewares[i].name} is not a middleware.`);
81
+ for (const middleware of middlewares) {
82
+ if (!Reflect.getOwnMetadataKeys(middleware).includes(middlewareKey)) {
83
+ throw Error(`[${middleware.name}] is not a middleware.`);
64
84
  }
65
85
  }
66
86
  }
67
87
 
68
- if (middlewares) {
69
- for (let i = 0; i < middlewares.length; i++) {
70
- if (!Reflect.getOwnMetadataKeys(middlewares[i]).includes(middlewareKey)) {
71
- throw Error(`${middlewares[i].name} is not a middleware.`);
88
+ if (guards) {
89
+ for (const guard of guards) {
90
+ if (!Reflect.getOwnMetadataKeys(guard).includes(guardKey)) {
91
+ throw Error(`[${guard.name}] is not a guard.`);
72
92
  }
73
93
  }
74
94
  }
75
95
 
76
- if (guards) {
77
- for (let i = 0; i < guards.length; i++) {
78
- if (!Reflect.getOwnMetadataKeys(guards[i]).includes(guardKey)) {
79
- throw Error(`${guards[i].name} is not a guard.`);
96
+ if (interceptors) {
97
+ for (const interceptor of interceptors) {
98
+ if (!Reflect.getOwnMetadataKeys(interceptor).includes(interceptorKey)) {
99
+ throw Error(`${interceptor.name} is not a middleware.`);
80
100
  }
81
101
  }
82
102
  }
83
103
 
84
104
  if (dependencies) {
85
- for (let i = 0; i < dependencies.length; i++) {
86
- if (!Reflect.getOwnMetadataKeys(dependencies[i]).includes(injectableKey)) {
87
- throw Error(`${dependencies[i].name} is not an injectable.`);
105
+ for (const dependency of dependencies) {
106
+ if (!Reflect.getOwnMetadataKeys(dependency).includes(injectableKey)) {
107
+ throw Error(`${dependency.name} is not an injectable.`);
88
108
  }
89
109
  }
90
110
  }
@@ -1,7 +1,7 @@
1
- import type { TConstructor } from "../ultils";
1
+ import type { TConstructor } from "../utils";
2
2
  import type { THttpMetadata } from "./http";
3
3
 
4
- import { controllerHttpKey, controllerKey } from "../keys";
4
+ import { controllerHttpKey, controllerKey } from "../constants/keys";
5
5
 
6
6
  export type TControllerMetadata = Required<{
7
7
  prefix: string;