@avleon/core 0.0.20 → 0.0.25

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 (75) hide show
  1. package/README.md +559 -2
  2. package/dist/application.d.ts +47 -0
  3. package/dist/application.js +50 -0
  4. package/dist/cache.d.ts +12 -0
  5. package/dist/cache.js +78 -0
  6. package/dist/collection.js +3 -2
  7. package/dist/container.d.ts +1 -0
  8. package/dist/container.js +2 -1
  9. package/dist/environment-variables.js +1 -1
  10. package/dist/file-storage.js +0 -128
  11. package/dist/helpers.d.ts +2 -0
  12. package/dist/helpers.js +41 -4
  13. package/dist/icore.d.ts +93 -42
  14. package/dist/icore.js +319 -251
  15. package/dist/index.d.ts +2 -2
  16. package/dist/index.js +4 -2
  17. package/dist/middleware.js +0 -8
  18. package/dist/multipart.js +4 -1
  19. package/dist/openapi.d.ts +37 -37
  20. package/dist/params.js +2 -2
  21. package/dist/response.js +6 -2
  22. package/dist/route-methods.js +1 -1
  23. package/dist/swagger-schema.js +4 -1
  24. package/dist/testing.js +6 -3
  25. package/dist/utils/index.d.ts +2 -0
  26. package/dist/utils/index.js +18 -0
  27. package/dist/utils/optional-require.d.ts +8 -0
  28. package/dist/utils/optional-require.js +70 -0
  29. package/dist/validation.d.ts +4 -1
  30. package/dist/validation.js +10 -5
  31. package/package.json +26 -9
  32. package/src/application.ts +125 -0
  33. package/src/authentication.ts +16 -0
  34. package/src/cache.ts +91 -0
  35. package/src/collection.ts +254 -0
  36. package/src/config.ts +42 -0
  37. package/src/constants.ts +1 -0
  38. package/src/container.ts +54 -0
  39. package/src/controller.ts +127 -0
  40. package/src/decorators.ts +27 -0
  41. package/src/environment-variables.ts +46 -0
  42. package/src/exceptions/http-exceptions.ts +86 -0
  43. package/src/exceptions/index.ts +1 -0
  44. package/src/exceptions/system-exception.ts +34 -0
  45. package/src/file-storage.ts +206 -0
  46. package/src/helpers.ts +328 -0
  47. package/src/icore.ts +1140 -0
  48. package/src/index.ts +30 -0
  49. package/src/logger.ts +72 -0
  50. package/src/map-types.ts +159 -0
  51. package/src/middleware.ts +98 -0
  52. package/src/multipart.ts +116 -0
  53. package/src/openapi.ts +372 -0
  54. package/src/params.ts +111 -0
  55. package/src/queue.ts +126 -0
  56. package/src/response.ts +117 -0
  57. package/src/results.ts +30 -0
  58. package/src/route-methods.ts +186 -0
  59. package/src/swagger-schema.ts +213 -0
  60. package/src/testing.ts +220 -0
  61. package/src/types/app-builder.interface.ts +19 -0
  62. package/src/types/application.interface.ts +9 -0
  63. package/src/utils/hash.ts +5 -0
  64. package/src/utils/index.ts +2 -0
  65. package/src/utils/optional-require.ts +50 -0
  66. package/src/validation.ts +156 -0
  67. package/src/validator-extend.ts +25 -0
  68. package/dist/classToOpenapi.d.ts +0 -0
  69. package/dist/classToOpenapi.js +0 -1
  70. package/dist/render.d.ts +0 -1
  71. package/dist/render.js +0 -8
  72. package/jest.config.ts +0 -9
  73. package/tsconfig.json +0 -25
  74. /package/dist/{security.d.ts → utils/hash.d.ts} +0 -0
  75. /package/dist/{security.js → utils/hash.js} +0 -0
package/dist/cache.js ADDED
@@ -0,0 +1,78 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.CacheManager = void 0;
4
+ class CacheManager {
5
+ constructor(redisInstance) {
6
+ this.store = new Map();
7
+ this.tagsMap = new Map();
8
+ this.redis = null;
9
+ this.redis = redisInstance || null;
10
+ }
11
+ redisTagKey(tag) {
12
+ return `cache-tags:${tag}`;
13
+ }
14
+ async get(key) {
15
+ if (this.redis) {
16
+ const val = await this.redis.get(key);
17
+ return val ? JSON.parse(val) : null;
18
+ }
19
+ const cached = this.store.get(key);
20
+ return cached ? cached.data : null;
21
+ }
22
+ async set(key, value, tags = [], ttl = 3600) {
23
+ const entry = {
24
+ data: value,
25
+ timestamp: Date.now(),
26
+ };
27
+ if (this.redis) {
28
+ await this.redis.set(key, JSON.stringify(entry.data), 'EX', ttl);
29
+ for (const tag of tags) {
30
+ await this.redis.sadd(this.redisTagKey(tag), key);
31
+ }
32
+ }
33
+ else {
34
+ this.store.set(key, entry);
35
+ for (const tag of tags) {
36
+ if (!this.tagsMap.has(tag))
37
+ this.tagsMap.set(tag, new Set());
38
+ this.tagsMap.get(tag).add(key);
39
+ }
40
+ }
41
+ }
42
+ async delete(key) {
43
+ if (this.redis) {
44
+ await this.redis.del(key);
45
+ // Also clean up from any tag sets
46
+ const tagKeys = await this.redis.keys('cache-tags:*');
47
+ for (const tagKey of tagKeys) {
48
+ await this.redis.srem(tagKey, key);
49
+ }
50
+ }
51
+ else {
52
+ this.store.delete(key);
53
+ for (const keys of this.tagsMap.values()) {
54
+ keys.delete(key);
55
+ }
56
+ }
57
+ }
58
+ async invalidateTag(tag) {
59
+ if (this.redis) {
60
+ const tagKey = this.redisTagKey(tag);
61
+ const keys = await this.redis.smembers(tagKey);
62
+ if (keys.length) {
63
+ await this.redis.del(...keys); // delete all cached keys
64
+ await this.redis.del(tagKey); // delete the tag set
65
+ }
66
+ }
67
+ else {
68
+ const keys = this.tagsMap.get(tag);
69
+ if (keys) {
70
+ for (const key of keys) {
71
+ this.store.delete(key);
72
+ }
73
+ this.tagsMap.delete(tag);
74
+ }
75
+ }
76
+ }
77
+ }
78
+ exports.CacheManager = CacheManager;
@@ -45,7 +45,7 @@ class BasicCollection {
45
45
  const item = this.items.find(predicate);
46
46
  if (item) {
47
47
  const index = this.items.indexOf(item);
48
- this.items[index] = Object.assign(Object.assign({}, item), updater);
48
+ this.items[index] = { ...item, ...updater };
49
49
  }
50
50
  else {
51
51
  throw new exceptions_1.NotFoundException("Item not found");
@@ -108,8 +108,9 @@ class AsynchronousCollection {
108
108
  }
109
109
  getRepository() {
110
110
  if (!this.repo) {
111
- const dataSourceKey = process.env.NODE_ENV === "test" ? "itestdatasource" : "idatasource";
111
+ const dataSourceKey = "idatasource";
112
112
  const dataSource = typedi_1.default.get(dataSourceKey);
113
+ console.log('datasource', dataSource);
113
114
  const repository = dataSource.getRepository(this.model);
114
115
  this.repo = repository;
115
116
  return repository;
@@ -5,6 +5,7 @@
5
5
  * @url https://github.com/xtareq
6
6
  */
7
7
  import TypediContainer from "typedi";
8
+ export declare const FEATURE_KEY: unique symbol;
8
9
  export declare const ROUTE_META_KEY: unique symbol;
9
10
  export declare const CONTROLLER_META_KEY: unique symbol;
10
11
  export declare const PARAM_META_KEY: unique symbol;
package/dist/container.js CHANGED
@@ -3,7 +3,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
3
3
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.API_CONTROLLER_METADATA_KEY = exports.AUTHORIZATION_META_KEY = exports.DATASOURCE_META_KEY = exports.REQUEST_HEADER_META_KEY = exports.REQUEST_USER_META_KEY = exports.REQUEST_BODY_FILES_KEY = exports.REQUEST_BODY_FILE_KEY = exports.REQUEST_BODY_META_KEY = exports.QUERY_META_KEY = exports.PARAM_META_KEY = exports.CONTROLLER_META_KEY = exports.ROUTE_META_KEY = void 0;
6
+ exports.API_CONTROLLER_METADATA_KEY = exports.AUTHORIZATION_META_KEY = exports.DATASOURCE_META_KEY = exports.REQUEST_HEADER_META_KEY = exports.REQUEST_USER_META_KEY = exports.REQUEST_BODY_FILES_KEY = exports.REQUEST_BODY_FILE_KEY = exports.REQUEST_BODY_META_KEY = exports.QUERY_META_KEY = exports.PARAM_META_KEY = exports.CONTROLLER_META_KEY = exports.ROUTE_META_KEY = exports.FEATURE_KEY = void 0;
7
7
  exports.registerController = registerController;
8
8
  exports.registerService = registerService;
9
9
  exports.getRegisteredServices = getRegisteredServices;
@@ -17,6 +17,7 @@ exports.registerDataSource = registerDataSource;
17
17
  * @url https://github.com/xtareq
18
18
  */
19
19
  const typedi_1 = __importDefault(require("typedi"));
20
+ exports.FEATURE_KEY = Symbol.for("features");
20
21
  exports.ROUTE_META_KEY = Symbol("iroute:options");
21
22
  exports.CONTROLLER_META_KEY = Symbol("icontroller:options");
22
23
  exports.PARAM_META_KEY = Symbol("iparam:options");
@@ -27,7 +27,7 @@ let Environment = class Environment {
27
27
  try {
28
28
  const fileContent = fs_1.default.readFileSync(filePath, 'utf8');
29
29
  const parsedEnv = dotenv_1.default.parse(fileContent);
30
- return Object.assign(Object.assign({}, parsedEnv), process.env);
30
+ return { ...parsedEnv, ...process.env };
31
31
  }
32
32
  catch (error) {
33
33
  console.error(`Error parsing .env file: ${error}`);
@@ -112,134 +112,6 @@ let FileStorage = class FileStorage {
112
112
  throw new system_exception_1.SystemUseError("Can't upload file");
113
113
  }
114
114
  }
115
- /* private async saveSingleFile(
116
- f: MultipartFile,
117
- options: any
118
- ): Promise<MultipartFile | null> {
119
- if (f && f.type == "file") {
120
- let fname = f.filename;
121
- if (options) {
122
- if (options.dest) {
123
- fname = options.saveAs
124
- ? options.dest + "/" + options.saveAs
125
- : options.dest + "/" + f.filename;
126
- } else {
127
- fname = path.join(
128
- process.cwd(),
129
- `public/${options.saveAs ? options.saveAs : f.filename}`
130
- );
131
- }
132
- } else {
133
- fname = path.join(process.cwd(), `public/${f.filename}`);
134
- }
135
- await this.ensureDirectoryExists(fname); // Ensure directory exists
136
-
137
- if (fs.existsSync(fname) && !options.overwrite) {
138
- throw new InternalErrorException("File already exists.");
139
- }
140
-
141
- if (this.transformOptions) {
142
- if (f.type == "file") {
143
- const tempFilePath = path.join(
144
- os.tmpdir(),
145
- `temp-${Date.now()}-${f.filename}`
146
- );
147
- await pipeline(f.file!, fs.createWriteStream(tempFilePath));
148
- await this.processImage(fs.createReadStream(tempFilePath), fname);
149
- fs.unlinkSync(tempFilePath);
150
- } else if (f.type == "fil") {
151
- await this.processImage(fs.createReadStream(f.filepath), fname);
152
- }
153
- } else {
154
- if (f.file) {
155
- await pipeline(f.file!, fs.createWriteStream(fname));
156
- } else if (f.filepath) {
157
- fs.copyFileSync(f.filepath, fname);
158
- }
159
- }
160
- return {
161
- ...f,
162
- filename: options?.saveAs ? options.saveAs : f.filename,
163
- } as MultipartFile;
164
- }
165
- return null;
166
- }
167
-
168
- async saveAs(
169
- f: MultipartFile | MultipartFile[],
170
- filename: string | string[],
171
- options: any
172
- ) {
173
- if (
174
- Array.isArray(f) &&
175
- Array.isArray(filename) &&
176
- f.length === filename.length
177
- ) {
178
- const savedFiles: MultipartFile[] = [];
179
- for (let i = 0; i < f.length; i++) {
180
- const savedFile = await this.saveSingleFileAs(
181
- f[i],
182
- filename[i],
183
- options
184
- );
185
- if (savedFile) {
186
- savedFiles.push(savedFile);
187
- }
188
- }
189
- return savedFiles;
190
- } else if (!Array.isArray(f) && !Array.isArray(filename)) {
191
- return await this.saveSingleFileAs(f, filename as string, options);
192
- } else {
193
- throw new InternalErrorException(
194
- "File and filename array lengths do not match."
195
- );
196
- }
197
- }
198
-
199
- private async saveSingleFileAs(
200
- f: MultipartFile,
201
- filename: string,
202
- options: any
203
- ): Promise<MultipartFile | null> {
204
- if (f) {
205
- let fname = filename;
206
-
207
- if (options && options.dest) {
208
- fname = options.dest + "/" + filename;
209
- } else {
210
- fname = path.join(process.cwd(), `public/${filename}`);
211
- }
212
- await this.ensureDirectoryExists(fname);
213
-
214
- if (fs.existsSync(fname) && !options.overwrite) {
215
- throw new InternalErrorException("File already exists.");
216
- }
217
-
218
- if (this.transformOptions) {
219
- if (f.file) {
220
- const tempFilePath = path.join(
221
- os.tmpdir(),
222
- `temp-${Date.now()}-${f.filename}`
223
- );
224
- await pipeline(f.file!, fs.createWriteStream(tempFilePath));
225
- await this.processImage(fs.createReadStream(tempFilePath), fname);
226
- fs.unlinkSync(tempFilePath);
227
- } else if (f.filepath) {
228
- await this.processImage(fs.createReadStream(f.filepath), fname);
229
- }
230
- } else {
231
- if (f.file) {
232
- await pipeline(f.file!, fs.createWriteStream(fname));
233
- } else if (f.filepath) {
234
- fs.copyFileSync(f.filepath, fname);
235
- }
236
- }
237
-
238
- return { ...f, filename: filename } as MultipartFile;
239
- }
240
- return null;
241
- }
242
- */
243
115
  async processImage(fileStream, outputPath) {
244
116
  var _a, _b;
245
117
  try {
package/dist/helpers.d.ts CHANGED
@@ -29,4 +29,6 @@ type ValidationError = {
29
29
  errors: any;
30
30
  };
31
31
  export declare function validateRequestBody(target: Constructor, value: object, options?: "object" | "array"): ValidationError;
32
+ export declare function pick<T extends object>(obj: T, paths: string[]): Partial<T>;
33
+ export declare function exclude<T extends object>(obj: T | T[], paths: string[]): Partial<T> | Partial<T>[];
32
34
  export {};
package/dist/helpers.js CHANGED
@@ -19,6 +19,8 @@ exports.jsonToInstance = jsonToInstance;
19
19
  exports.transformObjectByInstanceToObject = transformObjectByInstanceToObject;
20
20
  exports.validateObjectByInstance = validateObjectByInstance;
21
21
  exports.validateRequestBody = validateRequestBody;
22
+ exports.pick = pick;
23
+ exports.exclude = exclude;
22
24
  /**
23
25
  * @copyright 2024
24
26
  * @author Tareq Hossain
@@ -42,19 +44,15 @@ function inject(cls) {
42
44
  }
43
45
  }
44
46
  function isConstructor(func) {
45
- // Check if the func is a function
46
47
  if (typeof func !== "function") {
47
48
  return false;
48
49
  }
49
- // Check if it's an arrow function or a built-in JavaScript function
50
50
  if (func === Function.prototype.bind || func instanceof RegExp) {
51
51
  return false;
52
52
  }
53
- // Check if it has a `prototype` property
54
53
  if (func.prototype && typeof func.prototype === "object") {
55
54
  return true;
56
55
  }
57
- // If it's not a constructor, check if it can be called with the new keyword
58
56
  try {
59
57
  const instance = new func();
60
58
  return typeof instance === "object";
@@ -253,3 +251,42 @@ function validateRequestBody(target, value, options = "array") {
253
251
  : error.map((x) => ({ path: x.property, constraints: x.constraints }));
254
252
  return { count: error.length, errors };
255
253
  }
254
+ function pick(obj, paths) {
255
+ const result = {};
256
+ for (const path of paths) {
257
+ const keys = path.split(".");
258
+ let source = obj;
259
+ let target = result;
260
+ for (let i = 0; i < keys.length; i++) {
261
+ const key = keys[i];
262
+ if (!(key in source))
263
+ break;
264
+ if (i === keys.length - 1) {
265
+ target[key] = source[key];
266
+ }
267
+ else {
268
+ source = source[key];
269
+ target[key] = target[key] || {};
270
+ target = target[key];
271
+ }
272
+ }
273
+ }
274
+ return result;
275
+ }
276
+ function exclude(obj, paths) {
277
+ if (Array.isArray(obj)) {
278
+ return obj.map((item) => exclude(item, paths));
279
+ }
280
+ const clone = structuredClone(obj); // Or use lodash.cloneDeep
281
+ for (const path of paths) {
282
+ const keys = path.split(".");
283
+ let target = clone;
284
+ for (let i = 0; i < keys.length - 1; i++) {
285
+ if (!(keys[i] in target))
286
+ break;
287
+ target = target[keys[i]];
288
+ }
289
+ target === null || target === void 0 ? true : delete target[keys[keys.length - 1]];
290
+ }
291
+ return clone;
292
+ }
package/dist/icore.d.ts CHANGED
@@ -8,7 +8,7 @@ import { FastifyReply, FastifyRequest, HookHandlerDoneFunction, InjectOptions, L
8
8
  import { Constructable } from "typedi";
9
9
  import { Constructor } from "./helpers";
10
10
  import { PathLike } from "fs";
11
- import { DataSourceOptions } from "typeorm";
11
+ import { DataSource, DataSourceOptions } from "typeorm";
12
12
  import { AppMiddleware } from "./middleware";
13
13
  import { OpenApiOptions, OpenApiUiOptions } from "./openapi";
14
14
  import { IConfig } from "./config";
@@ -78,18 +78,24 @@ type MultipartOptions = {
78
78
  } & FastifyMultipartOptions;
79
79
  export type TestAppOptions = {
80
80
  controllers: Constructor[];
81
+ dataSource?: DataSource;
81
82
  };
82
83
  export interface AvleonTestAppliction {
83
84
  addDataSource: (dataSourceOptions: DataSourceOptions) => void;
84
85
  getApp: (options?: TestAppOptions) => any;
85
- getController: <T>(controller: Constructor<T>) => T;
86
+ getController: <T>(controller: Constructor<T>, deps: any[]) => T;
86
87
  }
88
+ export type AutoControllerOptions = {
89
+ auto: true;
90
+ path?: string;
91
+ };
87
92
  export interface IAvleonApplication {
88
93
  isDevelopment(): boolean;
89
94
  useCors(corsOptions?: FastifyCorsOptions): void;
95
+ useDataSource<T extends IConfig<R>, R = ReturnType<InstanceType<Constructable<T>>["config"]>>(ConfigClass: Constructable<T>, modifyConfig?: (config: R) => R): void;
90
96
  useOpenApi<T extends IConfig<R>, R = ReturnType<InstanceType<Constructable<T>>["config"]>>(ConfigClass: Constructable<T>, modifyConfig?: (config: R) => R): void;
91
- useSwagger(options: OpenApiUiOptions): Promise<void>;
92
97
  useMultipart(options: MultipartOptions): void;
98
+ useCache(options: any): void;
93
99
  useMiddlewares<T extends AppMiddleware>(mclasses: Constructor<T>[]): void;
94
100
  useAuthoriztion<T extends any>(middleware: Constructor<T>): void;
95
101
  mapRoute<T extends (...args: any[]) => any>(method: "get" | "post" | "put" | "delete", path: string, fn: T): Promise<void>;
@@ -97,12 +103,16 @@ export interface IAvleonApplication {
97
103
  mapPost<T extends (...args: any[]) => any>(path: string, fn: T): any;
98
104
  mapPut<T extends (...args: any[]) => any>(path: string, fn: T): any;
99
105
  mapDelete<T extends (...args: any[]) => any>(path: string, fn: T): any;
100
- mapControllers(controllers: any[]): any;
106
+ useControllers(controllers: any[]): any;
107
+ useControllers(controllersOptions: AutoControllerOptions): any;
108
+ useControllers(controllersOrOptions: any[] | AutoControllerOptions): any;
101
109
  useStaticFiles(options?: StaticFileOptions): void;
102
110
  run(port?: number): Promise<void>;
103
111
  getTestApp(): TestApplication;
104
112
  }
105
- export declare class AvleonApplication implements IAvleonApplication {
113
+ type OpenApiConfigClass<T = any> = Constructable<IConfig<T>>;
114
+ type OpenApiConfigInput<T = any> = OpenApiConfigClass<T> | T;
115
+ export declare class AvleonApplication {
106
116
  private static instance;
107
117
  private static buildOptions;
108
118
  private app;
@@ -118,21 +128,78 @@ export declare class AvleonApplication implements IAvleonApplication {
118
128
  private authorizeMiddleware?;
119
129
  private appConfig;
120
130
  private dataSource?;
131
+ private isMapFeatures;
132
+ private registerControllerAuto;
133
+ private registerControllerPath;
121
134
  private metaCache;
122
135
  private multipartOptions;
123
136
  private constructor();
124
137
  private isTest;
138
+ static getApp(): AvleonApplication;
125
139
  static getInternalApp(buildOptions: any): AvleonApplication;
126
140
  isDevelopment(): boolean;
127
141
  private initSwagger;
128
142
  useCors(corsOptions?: FastifyCorsOptions): void;
129
- useOpenApi<T extends IConfig<R>, R = ReturnType<InstanceType<Constructable<T>>["config"]>>(ConfigClass: Constructable<T>, modifyConfig?: (config: R) => R): void;
143
+ useOpenApi<T = OpenApiUiOptions>(configOrClass: OpenApiConfigInput<T>, modifyConfig?: (config: T) => T): void;
130
144
  /**
131
- * @deprecated
132
- * Will remove in next major version
145
+ * Registers the fastify-multipart plugin with the Fastify instance.
146
+ * This enables handling of multipart/form-data requests, typically used for file uploads.
147
+ *
148
+ * @param {MultipartOptions} options - Options to configure the fastify-multipart plugin.
149
+ * @param {FastifyInstance} this.app - The Fastify instance to register the plugin with.
150
+ * @property {MultipartOptions} this.multipartOptions - Stores the provided multipart options.
151
+ * @see {@link https://github.com/fastify/fastify-multipart} for more details on available options.
133
152
  */
134
- useSwagger(options: OpenApiUiOptions): Promise<void>;
135
153
  useMultipart(options: MultipartOptions): void;
154
+ /**
155
+ * Configures and initializes a TypeORM DataSource based on the provided configuration class.
156
+ * It retrieves the configuration from the application's configuration service and allows for optional modification.
157
+ * The initialized DataSource is then stored and registered within a dependency injection container.
158
+ *
159
+ * @template T - A generic type extending the `IConfig` interface, representing the configuration class.
160
+ * @template R - A generic type representing the return type of the configuration method of the `ConfigClass`.
161
+ * @param {Constructable<T>} ConfigClass - The constructor of the configuration class to be used for creating the DataSource.
162
+ * @param {(config: R) => R} [modifyConfig] - An optional function that takes the initial configuration and returns a modified configuration.
163
+ * @returns {void}
164
+ * @property {DataSourceOptions} this.dataSourceOptions - Stores the final DataSource options after potential modification.
165
+ * @property {DataSource} this.dataSource - Stores the initialized TypeORM DataSource instance.
166
+ * @see {@link https://typeorm.io/} for more information about TypeORM.
167
+ */
168
+ useDataSource<T extends IConfig<R>, R = ReturnType<InstanceType<Constructable<T>>["config"]>>(ConfigClass: Constructable<T>, modifyConfig?: (config: R) => R): void;
169
+ useCache(options: any): void;
170
+ /**
171
+ * Registers an array of middleware classes to be executed before request handlers.
172
+ * It retrieves instances of the middleware classes from the dependency injection container
173
+ * and adds them as 'preHandler' hooks to the Fastify application.
174
+ *
175
+ * @template T - A generic type extending the `AppMiddleware` interface, representing the middleware class.
176
+ * @param {Constructor<T>[]} mclasses - An array of middleware class constructors to be registered.
177
+ * @returns {void}
178
+ * @property {Map<string, T>} this.middlewares - Stores the registered middleware instances, keyed by their class names.
179
+ * @see {@link https://www.fastify.io/docs/latest/Reference/Hooks/#prehandler} for more information about Fastify preHandler hooks.
180
+ */
181
+ useMiddlewares<T extends AppMiddleware>(mclasses: Constructor<T>[]): void;
182
+ /**
183
+ * Registers a middleware constructor to be used for authorization purposes.
184
+ * The specific implementation and usage of this middleware will depend on the application's authorization logic.
185
+ *
186
+ * @template T - A generic type representing the constructor of the authorization middleware.
187
+ * @param {Constructor<T>} middleware - The constructor of the middleware to be used for authorization.
188
+ * @returns {void}
189
+ * @property {any} this.authorizeMiddleware - Stores the constructor of the authorization middleware.
190
+ */
191
+ useAuthoriztion<T extends any>(middleware: Constructor<T>): void;
192
+ /**
193
+ * Registers the `@fastify/static` plugin to serve static files.
194
+ * It configures the root directory and URL prefix for serving static assets.
195
+ *
196
+ * @param {StaticFileOptions} [options={ path: undefined, prefix: undefined }] - Optional configuration for serving static files.
197
+ * @param {string} [options.path] - The absolute path to the static files directory. Defaults to 'process.cwd()/public'.
198
+ * @param {string} [options.prefix] - The URL prefix for serving static files. Defaults to '/static/'.
199
+ * @returns {void}
200
+ * @see {@link https://github.com/fastify/fastify-static} for more details on available options.
201
+ */
202
+ useStaticFiles(options?: StaticFileOptions): void;
136
203
  private handleMiddlewares;
137
204
  private executeMiddlewares;
138
205
  /**
@@ -155,36 +222,33 @@ export declare class AvleonApplication implements IAvleonApplication {
155
222
  * @returns
156
223
  */
157
224
  private _processMeta;
158
- autoControllers(): Promise<void>;
159
- mapControllers(controllers: Function[]): void;
225
+ private _resolveControllerDir;
226
+ private autoControllers;
227
+ useControllers(controllers: Constructor[] | AutoControllerOptions): void;
160
228
  private _mapControllers;
161
- mapControllersAuto(): void;
162
- handleRoute(args: any): Promise<void>;
163
229
  private mapFn;
164
- useMiddlewares<T extends AppMiddleware>(mclasses: Constructor<T>[]): void;
165
- useAuthoriztion<T extends any>(middleware: Constructor<T>): void;
166
230
  private _handleError;
167
231
  mapRoute<T extends (...args: any[]) => any>(method: "get" | "post" | "put" | "delete", path: string | undefined, fn: T): Promise<void>;
168
232
  private _routeHandler;
169
233
  mapGet<T extends (...args: any[]) => any>(path: string | undefined, fn: T): {
170
234
  useMiddleware: <M extends AppMiddleware>(middlewares: Constructor<AppMiddleware>[]) => /*elided*/ any;
171
- useSwagger: (options: OpenApiOptions) => /*elided*/ any;
235
+ useOpenApi: (options: OpenApiOptions) => /*elided*/ any;
172
236
  };
173
237
  mapPost<T extends (...args: any[]) => any>(path: string | undefined, fn: T): {
174
238
  useMiddleware: <M extends AppMiddleware>(middlewares: Constructor<AppMiddleware>[]) => /*elided*/ any;
175
- useSwagger: (options: OpenApiOptions) => /*elided*/ any;
239
+ useOpenApi: (options: OpenApiOptions) => /*elided*/ any;
176
240
  };
177
241
  mapPut<T extends (...args: any[]) => any>(path: string | undefined, fn: T): {
178
242
  useMiddleware: <M extends AppMiddleware>(middlewares: Constructor<AppMiddleware>[]) => /*elided*/ any;
179
- useSwagger: (options: OpenApiOptions) => /*elided*/ any;
243
+ useOpenApi: (options: OpenApiOptions) => /*elided*/ any;
180
244
  };
181
245
  mapDelete<T extends (...args: any[]) => any>(path: string | undefined, fn: T): {
182
246
  useMiddleware: <M extends AppMiddleware>(middlewares: Constructor<AppMiddleware>[]) => /*elided*/ any;
183
- useSwagger: (options: OpenApiOptions) => /*elided*/ any;
247
+ useOpenApi: (options: OpenApiOptions) => /*elided*/ any;
184
248
  };
185
- useStaticFiles(options?: StaticFileOptions): void;
249
+ private _mapFeatures;
186
250
  initializeDatabase(): Promise<void>;
187
- run(port?: number): Promise<void>;
251
+ run(port?: number, fn?: CallableFunction): Promise<void>;
188
252
  getTestApp(buildOptions?: any): TestApplication;
189
253
  }
190
254
  export type Application = typeof AvleonApplication;
@@ -197,32 +261,19 @@ export interface IAppBuilder {
197
261
  addDataSource<T extends IConfig<R>, R = ReturnType<InstanceType<Constructable<T>>["config"]>>(ConfigClass: Constructable<T>, modifyConfig?: (config: R) => R): void;
198
262
  build<T extends IAvleonApplication>(): T;
199
263
  }
200
- export declare class TestBuilder {
264
+ export declare class AvleonTest {
201
265
  private static instance;
202
266
  private app;
203
267
  private dataSourceOptions?;
204
268
  private constructor();
205
- static createBuilder(): TestBuilder;
206
- addDatasource(options: DataSourceOptions): void;
207
- private getController;
269
+ private addDatasource;
270
+ getController<T>(controller: Constructor<T>, deps?: any[]): T;
208
271
  private getService;
209
- getTestApplication(options: TestAppOptions): TestApplication;
210
- build(app: IAvleonApplication): TestApplication;
211
- fromApplication(app: IAvleonApplication): TestApplication;
272
+ static createTestApplication(options: TestAppOptions): TestApplication;
273
+ static from(app: AvleonApplication): TestApplication;
274
+ static clean(): void;
212
275
  }
213
- export declare class Builder implements IAppBuilder {
214
- private static instance;
215
- private alreadyBuilt;
216
- private database;
217
- private dataSource?;
218
- private multipartOptions;
219
- private dataSourceOptions?;
220
- private testBuilder;
221
- private appConfig;
222
- private constructor();
223
- static createAppBuilder(): Builder;
224
- registerPlugin<T extends Function, S extends {}>(plugin: T, options: S): Promise<void>;
225
- addDataSource<T extends IConfig<R>, R = ReturnType<InstanceType<Constructable<T>>["config"]>>(ConfigClass: Constructable<T>, modifyConfig?: (config: R) => R): void;
226
- build<T extends IAvleonApplication>(): T;
276
+ export declare class Avleon {
277
+ static createApplication(): AvleonApplication;
227
278
  }
228
279
  export {};