Repository: nestjs/swagger
Pull request #3362 (2025-03-25 10:04:17)

feat: make generated require() ESM compatible
## PR Checklist
Please check if your PR fulfills the following requirements:

- [x] The commit message follows our guidelines: https://github.com/nestjs/nest/blob/master/CONTRIBUTING.md
- [x] Tests for the changes have been added (for bug fixes / features)
- [x] Docs have been added / updated (for bug fixes / features)


## PR Type
What kind of change does this PR introduce?

<!-- Please check the one that applies to this PR using "x". -->
- [ ] Bugfix
- [x] Feature
- [ ] Code style update (formatting, local variables)
- [ ] Refactoring (no functional changes, no api changes)
- [x] Build related changes
- [ ] CI related changes
- [ ] Other... Please describe:

## What is the current behavior?
<!-- Please describe the current behavior that you are modifying, or link to a relevant issue. -->

Issue Number
- https://github.com/nestjs/swagger/pull/3235
- https://github.com/nestjs/swagger/pull/3253
This is a PR that improves the work that was reverted in the above issue.

I think NestJS is now generally usable in ESM projects.
- https://github.com/CatsMiaow/nestjs-project-performance/pull/3

However, when using dynamic `require(import)` like `@nestjs/swagger` module, if the extension is not present, build errors or runtime errors will occur.
This cannot be solved externally and the module needs to be modified.

## What is the new behavior?

I added the `esmCompatible` option to make it work in a custom way, as it shouldn't affect non-ESM projects or other projects.

## Does this PR introduce a breaking change?
- [ ] Yes
- [x] No

<!-- If this PR contains a breaking change, please describe the impact and migration path for existing applications below. -->


## Other information

050ff341f7da7fc982e95e93e679f5cef91fb221
- This is a commit that fixed an issue where the package was not recognized when installing from the github repo after forking for testing.
  - e.g. `npm install github:CatsMiaow/swagger#fix/esm-compatible`
- If there is an issue with this part, I will revert the commit.

`npm test` passed, and although it is not minimal, I tested that it works in two environments.
- `commonjs` + `tsc` [nestjs-project-structure#swagger](https://github.com/CatsMiaow/nestjs-project-structure/tree/swagger)
  - [package.json](https://github.com/CatsMiaow/nestjs-project-structure/blob/swagger/package.json#L39), [nest-cli.json](https://github.com/CatsMiaow/nestjs-project-structure/blob/swagger/nest-cli.json), [swagger.ts](https://github.com/CatsMiaow/nestjs-project-structure/blob/swagger/src/swagger.ts)
- `esm` + `swc` [nestjs-project-performance#swagger](https://github.com/CatsMiaow/nestjs-project-performance/tree/swagger)
  - [package.json](https://github.com/CatsMiaow/nestjs-project-performance/blob/swagger/package.json#L42), [nest-cli.json](https://github.com/CatsMiaow/nestjs-project-performance/blob/swagger/nest-cli.json), [swagger.ts](https://github.com/CatsMiaow/nestjs-project-performance/blob/swagger/src/swagger.ts), [generate-metadata.ts](https://github.com/CatsMiaow/nestjs-project-performance/blob/swagger/src/generate-metadata.ts)


Patch:
diff --git a/lib/document-builder.ts b/lib/document-builder.ts
index 738058aa..9f6c6373 100644
--- a/lib/document-builder.ts
+++ b/lib/document-builder.ts
@@ -1,6 +1,5 @@
 import { Logger } from '@nestjs/common';
-import { clone, isString, isUndefined, negate, omit, pickBy } from 'lodash';
-import { ApiResponseOptions } from './decorators/api-response.decorator';
+import { clone, isString, isUndefined, negate, pickBy } from 'lodash';
 import { buildDocumentBase } from './fixtures/document.base';
 import { OpenAPIObject } from './interfaces';
 import {
@@ -12,7 +11,6 @@ import {
   TagObject
 } from './interfaces/open-api-spec.interface';
 import { GlobalParametersStorage } from './storages/global-parameters.storage';
-import { GlobalResponsesStorage } from './storages/global-responses.storage';
 
 /**
  * @publicApi
@@ -121,20 +119,6 @@ export class DocumentBuilder {
     return this;
   }
 
-  public addGlobalResponse(...respones: ApiResponseOptions[]): this {
-    const groupedByStatus = respones.reduce(
-      (acc, response) => {
-        const { status = 'default' } = response;
-        acc[status] = omit(response, 'status');
-        return acc;
-      },
-      {} as Record<string, Omit<ApiResponseOptions, 'status'>>
-    );
-
-    GlobalResponsesStorage.add(groupedByStatus);
-    return this;
-  }
-
   public addGlobalParameters(
     // Examples should be specified under the "schema" object
     // Top level attributes are ignored
diff --git a/lib/explorers/api-response.explorer.ts b/lib/explorers/api-response.explorer.ts
index 1a029544..61f80558 100644
--- a/lib/explorers/api-response.explorer.ts
+++ b/lib/explorers/api-response.explorer.ts
@@ -10,7 +10,6 @@ import {
   FactoriesNeededByResponseFactory,
   ResponseObjectFactory
 } from '../services/response-object-factory';
-import { GlobalResponsesStorage } from '../storages/global-responses.storage';
 import { mergeAndUniq } from '../utils/merge-and-uniq.util';
 
 const responseObjectFactory = new ResponseObjectFactory();
@@ -24,34 +23,17 @@ export const exploreGlobalApiResponseMetadata = (
     DECORATORS.API_RESPONSE,
     metatype
   );
-  const globalResponses = GlobalResponsesStorage.getAll();
-  const mappedGlobalResponsesOrUndefined = globalResponses
-    ? mapResponsesToSwaggerResponses(
-        globalResponses,
-        schemas,
-        undefined,
-        factories
-      )
-    : undefined;
-
   const produces = Reflect.getMetadata(DECORATORS.API_PRODUCES, metatype);
   return responses
     ? {
-        responses: {
-          ...mappedGlobalResponsesOrUndefined,
-          ...mapResponsesToSwaggerResponses(
-            responses,
-            schemas,
-            produces,
-            factories
-          )
-        }
+        responses: mapResponsesToSwaggerResponses(
+          responses,
+          schemas,
+          produces,
+          factories
+        )
       }
-    : mappedGlobalResponsesOrUndefined
-      ? {
-          responses: mappedGlobalResponsesOrUndefined
-        }
-      : undefined;
+    : undefined;
 };
 
 export const exploreApiResponseMetadata = (
@@ -107,7 +89,7 @@ const getStatusCode = (method: Function) => {
 
 const omitParamType = (param: Record<string, any>) => omit(param, 'type');
 const mapResponsesToSwaggerResponses = (
-  responses: ApiResponseMetadata[] | Record<string, ApiResponseMetadata>,
+  responses: ApiResponseMetadata[],
   schemas: Record<string, SchemaObject>,
   produces: string[] = ['application/json'],
   factories: FactoriesNeededByResponseFactory
diff --git a/lib/plugin/merge-options.ts b/lib/plugin/merge-options.ts
index d3b6c5b6..7ee56906 100644
--- a/lib/plugin/merge-options.ts
+++ b/lib/plugin/merge-options.ts
@@ -9,6 +9,7 @@ export interface PluginOptions {
   dtoKeyOfComment?: string;
   controllerKeyOfComment?: string;
   introspectComments?: boolean;
+  esmCompatible?: boolean;
   readonly?: boolean;
   pathToSource?: string;
   debug?: boolean;
@@ -27,6 +28,7 @@ const defaultOptions: PluginOptions = {
   dtoKeyOfComment: 'description',
   controllerKeyOfComment: 'summary',
   introspectComments: false,
+  esmCompatible: false,
   readonly: false,
   debug: false
 };
diff --git a/lib/plugin/utils/plugin-utils.ts b/lib/plugin/utils/plugin-utils.ts
index 57c52318..3e74c667 100644
--- a/lib/plugin/utils/plugin-utils.ts
+++ b/lib/plugin/utils/plugin-utils.ts
@@ -140,6 +140,16 @@ export function hasPropertyKey(
     .some((item) => item.name.getText() === key);
 }
 
+export function getOutputExtension(fileName: string): string {
+  if (fileName.endsWith('.mts')) {
+    return '.mjs';
+  } else if (fileName.endsWith('.cts')) {
+    return '.cjs';
+  } else {
+    return '.js';
+  }
+}
+
 export function replaceImportPath(
   typeReference: string,
   fileName: string,
@@ -148,6 +158,14 @@ export function replaceImportPath(
   if (!typeReference.includes('import')) {
     return { typeReference, importPath: null };
   }
+
+  if (options.esmCompatible) {
+    typeReference = typeReference.replace(
+      ', { with: { "resolution-mode": "import" } }',
+      ''
+    );
+  }
+
   let importPath = /\(\"([^)]).+(\")/.exec(typeReference)[0];
   if (!importPath) {
     return { typeReference: undefined, importPath: null };
@@ -193,6 +211,10 @@ export function replaceImportPath(
       if (indexPos >= 0) {
         relativePath = relativePath.slice(0, indexPos);
       }
+    } else if (options.esmCompatible) {
+      // Add appropriate extension for non-node_modules imports
+      const extension = getOutputExtension(fileName);
+      relativePath += extension;
     }
 
     typeReference = typeReference.replace(importPath, relativePath);
@@ -206,6 +228,7 @@ export function replaceImportPath(
         importPath: relativePath
       };
     }
+
     return {
       typeReference: typeReference.replace('import', 'require'),
       importPath: relativePath
diff --git a/lib/plugin/visitors/controller-class.visitor.ts b/lib/plugin/visitors/controller-class.visitor.ts
index 91528bf3..97b739d7 100644
--- a/lib/plugin/visitors/controller-class.visitor.ts
+++ b/lib/plugin/visitors/controller-class.visitor.ts
@@ -15,6 +15,7 @@ import {
 import {
   convertPath,
   getDecoratorOrUndefinedByNames,
+  getOutputExtension,
   getTypeReferenceAsString,
   hasPropertyKey
 } from '../utils/plugin-utils';
@@ -34,13 +35,14 @@ export class ControllerClassVisitor extends AbstractFileVisitor {
     return this._typeImports;
   }
 
-  get collectedMetadata(): Array<
-    [ts.CallExpression, Record<string, ClassMetadata>]
-  > {
+  collectedMetadata(
+    options: PluginOptions
+  ): Array<[ts.CallExpression, Record<string, ClassMetadata>]> {
     const metadataWithImports = [];
     Object.keys(this._collectedMetadata).forEach((filePath) => {
       const metadata = this._collectedMetadata[filePath];
-      const path = filePath.replace(/\.[jt]s$/, '');
+      const fileExt = options.esmCompatible ? getOutputExtension(filePath) : '';
+      const path = filePath.replace(/\.[jt]s$/, fileExt);
       const importExpr = ts.factory.createCallExpression(
         ts.factory.createToken(ts.SyntaxKind.ImportKeyword) as ts.Expression,
         undefined,
diff --git a/lib/plugin/visitors/model-class.visitor.ts b/lib/plugin/visitors/model-class.visitor.ts
index 04c24813..6c5ad6ba 100644
--- a/lib/plugin/visitors/model-class.visitor.ts
+++ b/lib/plugin/visitors/model-class.visitor.ts
@@ -25,6 +25,7 @@ import {
   convertPath,
   extractTypeArgumentIfArray,
   getDecoratorOrUndefinedByNames,
+  getOutputExtension,
   getTypeReferenceAsString,
   hasPropertyKey,
   isAutoGeneratedEnumUnion,
@@ -43,13 +44,14 @@ export class ModelClassVisitor extends AbstractFileVisitor {
     return this._typeImports;
   }
 
-  get collectedMetadata(): Array<
-    [ts.CallExpression, Record<string, ClassMetadata>]
-  > {
+  collectedMetadata(
+    options: PluginOptions
+  ): Array<[ts.CallExpression, Record<string, ClassMetadata>]> {
     const metadataWithImports = [];
     Object.keys(this._collectedMetadata).forEach((filePath) => {
       const metadata = this._collectedMetadata[filePath];
-      const path = filePath.replace(/\.[jt]s$/, '');
+      const fileExt = options.esmCompatible ? getOutputExtension(filePath) : '';
+      const path = filePath.replace(/\.[jt]s$/, fileExt);
       const importExpr = ts.factory.createCallExpression(
         ts.factory.createToken(ts.SyntaxKind.ImportKeyword) as ts.Expression,
         undefined,
diff --git a/lib/plugin/visitors/readonly.visitor.ts b/lib/plugin/visitors/readonly.visitor.ts
index 867b0cab..e66a397d 100644
--- a/lib/plugin/visitors/readonly.visitor.ts
+++ b/lib/plugin/visitors/readonly.visitor.ts
@@ -50,8 +50,8 @@ export class ReadonlyVisitor {
 
   collect() {
     return {
-      models: this.modelClassVisitor.collectedMetadata,
-      controllers: this.controllerClassVisitor.collectedMetadata
+      models: this.modelClassVisitor.collectedMetadata(this.options),
+      controllers: this.controllerClassVisitor.collectedMetadata(this.options)
     };
   }
 }
diff --git a/lib/services/response-object-factory.ts b/lib/services/response-object-factory.ts
index 86edac5f..7f6d3b14 100644
--- a/lib/services/response-object-factory.ts
+++ b/lib/services/response-object-factory.ts
@@ -100,9 +100,6 @@ export class ResponseObjectFactory {
         parameter: string,
         field: string
       ) => {
-        if (!factories) {
-          return;
-        }
         const linkName = factories.linkName(
           controllerPrototype.constructor.name,
           method.name,
diff --git a/lib/services/schema-object-factory.ts b/lib/services/schema-object-factory.ts
index 076da32f..5efa2305 100644
--- a/lib/services/schema-object-factory.ts
+++ b/lib/services/schema-object-factory.ts
@@ -268,10 +268,10 @@ export class SchemaObjectFactory {
     };
 
     const typeDefinitionRequiredFields = propertiesWithType
-      .filter((property) =>
-        'selfRequired' in property
-          ? property.selfRequired != false
-          : property.required != false && !Array.isArray(property.required)
+      .filter(
+        (property) =>
+          (property.required != false && !Array.isArray(property.required)) ||
+          ('selfRequired' in property && property.selfRequired != false)
       )
       .map((property) => property.name);
 
diff --git a/lib/storages/global-responses.storage.ts b/lib/storages/global-responses.storage.ts
deleted file mode 100644
index 878b2c81..00000000
--- a/lib/storages/global-responses.storage.ts
+++ /dev/null
@@ -1,27 +0,0 @@
-import { ApiResponseOptions } from '../decorators';
-
-type GlobalResponesMap = Record<string, Omit<ApiResponseOptions, 'status'>>;
-
-export class GlobalResponsesStorageHost {
-  private responses: GlobalResponesMap = {};
-
-  add(responses: GlobalResponesMap) {
-    this.responses = {
-      ...this.responses,
-      ...responses
-    };
-  }
-
-  getAll() {
-    return this.responses;
-  }
-
-  clear() {
-    this.responses = {};
-  }
-}
-
-const globalRef = global as any;
-export const GlobalResponsesStorage: GlobalResponsesStorageHost =
-  globalRef.SwaggerGlobalResponsesStorage ||
-  (globalRef.SwaggerGlobalResponsesStorage = new GlobalResponsesStorageHost());
diff --git a/lib/swagger-explorer.ts b/lib/swagger-explorer.ts
index 81c261a2..eec12d6c 100644
--- a/lib/swagger-explorer.ts
+++ b/lib/swagger-explorer.ts
@@ -93,30 +93,21 @@ export class SwaggerExplorer {
       ? `${controllerKey}_${methodKey}_from_${fieldKey}`
       : `${methodKey}_from_${fieldKey}`;
 
-  constructor(
-    private readonly schemaObjectFactory: SchemaObjectFactory,
-    private readonly options: {
-      httpAdapterType?: string;
-    } = {}
-  ) {}
+  constructor(private readonly schemaObjectFactory: SchemaObjectFactory) {}
 
   public exploreController(
     wrapper: InstanceWrapper<Controller>,
     applicationConfig: ApplicationConfig,
-    options: {
-      modulePath?: string;
-      globalPrefix?: string;
-      operationIdFactory?: OperationIdFactory;
-      linkNameFactory?: (
-        controllerKey: string,
-        methodKey: string,
-        fieldKey: string
-      ) => string;
-      autoTagControllers?: boolean;
-    }
+    modulePath?: string,
+    globalPrefix?: string,
+    operationIdFactory?: OperationIdFactory,
+    linkNameFactory?: (
+      controllerKey: string,
+      methodKey: string,
+      fieldKey: string
+    ) => string,
+    autoTagControllers?: boolean
   ) {
-    const { operationIdFactory, linkNameFactory } = options;
-
     this.routePathFactory = new RoutePathFactory(applicationConfig);
     if (operationIdFactory) {
       this.operationIdFactory = operationIdFactory;
@@ -149,7 +140,11 @@ export class SwaggerExplorer {
       instance,
       documentResolvers,
       applicationConfig,
-      options
+      {
+        modulePath,
+        globalPrefix,
+        autoTagControllers
+      }
     );
   }
 
@@ -444,10 +439,7 @@ export class SwaggerExplorer {
     let pathWithParams = '';
 
     try {
-      let normalizedPath = LegacyRouteConverter.tryConvert(path, {
-        // Skip logs for Fastify as it has different rules for wildcard routes
-        logs: this.options.httpAdapterType !== 'fastify'
-      });
+      let normalizedPath = LegacyRouteConverter.tryConvert(path);
       // Optional segment groups are not supported by Fastify
       normalizedPath = normalizedPath.replace(/::/g, '\\:');
       normalizedPath = normalizedPath.replace(/\[:\]/g, '\\:');
diff --git a/lib/swagger-scanner.ts b/lib/swagger-scanner.ts
index 168204c9..04484f11 100644
--- a/lib/swagger-scanner.ts
+++ b/lib/swagger-scanner.ts
@@ -28,7 +28,7 @@ export class SwaggerScanner {
     new ModelPropertiesAccessor(),
     new SwaggerTypesMapper()
   );
-  private explorer: SwaggerExplorer | undefined;
+  private readonly explorer = new SwaggerExplorer(this.schemaObjectFactory);
 
   public scanApplication(
     app: INestApplication,
@@ -44,11 +44,8 @@ export class SwaggerScanner {
       autoTagControllers = true
     } = options;
 
-    const untypedApp = app as any;
-    const container = untypedApp.container as NestContainer;
-    const internalConfigRef = untypedApp.config as ApplicationConfig;
-    const httpAdapterType = app.getHttpAdapter().getType();
-    this.initializeSwaggerExplorer(httpAdapterType);
+    const container = (app as any).container as NestContainer;
+    const internalConfigRef = (app as any).config as ApplicationConfig;
 
     const modules: Module[] = this.getModules(
       container.getModules(),
@@ -75,25 +72,29 @@ export class SwaggerScanner {
                 metatype
               );
               result = result.concat(
-                this.scanModuleControllers(controllers, internalConfigRef, {
+                this.scanModuleControllers(
+                  controllers,
                   modulePath,
                   globalPrefix,
+                  internalConfigRef,
                   operationIdFactory,
                   linkNameFactory,
                   autoTagControllers
-                })
+                )
               );
             });
         }
         const modulePath = this.getModulePathMetadata(container, metatype);
         return result.concat(
-          this.scanModuleControllers(controllers, internalConfigRef, {
+          this.scanModuleControllers(
+            controllers,
             modulePath,
             globalPrefix,
+            internalConfigRef,
             operationIdFactory,
             linkNameFactory,
             autoTagControllers
-          })
+          )
         );
       }
     );
@@ -111,21 +112,27 @@ export class SwaggerScanner {
 
   public scanModuleControllers(
     controller: Map<InjectionToken, InstanceWrapper>,
+    modulePath: string | undefined,
+    globalPrefix: string | undefined,
     applicationConfig: ApplicationConfig,
-    options: {
-      modulePath: string | undefined;
-      globalPrefix: string | undefined;
-      operationIdFactory?: OperationIdFactory;
-      linkNameFactory?: (
-        controllerKey: string,
-        methodKey: string,
-        fieldKey: string
-      ) => string;
-      autoTagControllers?: boolean;
-    }
+    operationIdFactory?: OperationIdFactory,
+    linkNameFactory?: (
+      controllerKey: string,
+      methodKey: string,
+      fieldKey: string
+    ) => string,
+    autoTagControllers?: boolean
   ): ModuleRoute[] {
     const denormalizedArray = [...controller.values()].map((ctrl) =>
-      this.explorer.exploreController(ctrl, applicationConfig, options)
+      this.explorer.exploreController(
+        ctrl,
+        applicationConfig,
+        modulePath,
+        globalPrefix,
+        operationIdFactory,
+        linkNameFactory,
+        autoTagControllers
+      )
     );
     return flatten(denormalizedArray) as any;
   }
@@ -162,13 +169,4 @@ export class SwaggerScanner {
     );
     return modulePath ?? Reflect.getMetadata(MODULE_PATH, metatype);
   }
-
-  private initializeSwaggerExplorer(httpAdapterType: string) {
-    if (this.explorer) {
-      return;
-    }
-    this.explorer = new SwaggerExplorer(this.schemaObjectFactory, {
-      httpAdapterType
-    });
-  }
 }
diff --git a/package-lock.json b/package-lock.json
index 5b790153..8c17f541 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -1,12 +1,12 @@
 {
   "name": "@nestjs/swagger",
-  "version": "11.1.0",
+  "version": "11.0.6",
   "lockfileVersion": 3,
   "requires": true,
   "packages": {
     "": {
       "name": "@nestjs/swagger",
-      "version": "11.1.0",
+      "version": "11.0.6",
       "license": "MIT",
       "dependencies": {
         "@microsoft/tsdoc": "0.15.1",
@@ -14,27 +14,27 @@
         "js-yaml": "4.1.0",
         "lodash": "4.17.21",
         "path-to-regexp": "8.2.0",
-        "swagger-ui-dist": "5.20.1"
+        "swagger-ui-dist": "5.19.0"
       },
       "devDependencies": {
         "@commitlint/cli": "19.8.0",
         "@commitlint/config-angular": "19.8.0",
-        "@eslint/eslintrc": "3.3.1",
-        "@eslint/js": "9.23.0",
+        "@eslint/eslintrc": "3.3.0",
+        "@eslint/js": "9.22.0",
         "@fastify/static": "8.1.1",
-        "@nestjs/common": "11.0.12",
-        "@nestjs/core": "11.0.12",
-        "@nestjs/platform-express": "11.0.12",
-        "@nestjs/platform-fastify": "11.0.12",
+        "@nestjs/common": "^11.0.1",
+        "@nestjs/core": "^11.0.1",
+        "@nestjs/platform-express": "^11.0.1",
+        "@nestjs/platform-fastify": "^11.0.1",
         "@types/jest": "29.5.14",
         "@types/js-yaml": "4.0.9",
         "@types/lodash": "4.17.16",
-        "@types/node": "22.13.13",
+        "@types/node": "22.13.10",
         "class-transformer": "0.5.1",
         "class-validator": "0.14.1",
-        "eslint": "9.23.0",
+        "eslint": "9.22.0",
         "eslint-config-prettier": "10.1.1",
-        "eslint-plugin-prettier": "5.2.4",
+        "eslint-plugin-prettier": "5.2.3",
         "express": "5.0.1",
         "fastify": "5.2.1",
         "globals": "16.0.0",
@@ -47,11 +47,11 @@
         "prettier-v2": "npm:prettier@2.8.8",
         "reflect-metadata": "0.2.2",
         "release-it": "18.1.2",
-        "supertest": "7.1.0",
+        "supertest": "7.0.0",
         "swagger-parser": "10.0.3",
-        "ts-jest": "29.3.0",
+        "ts-jest": "29.2.6",
         "typescript": "5.8.2",
-        "typescript-eslint": "8.28.0"
+        "typescript-eslint": "8.26.1"
       },
       "peerDependencies": {
         "@fastify/static": "^8.0.0",
@@ -975,9 +975,9 @@
       }
     },
     "node_modules/@eslint/config-helpers": {
-      "version": "0.2.0",
-      "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.2.0.tgz",
-      "integrity": "sha512-yJLLmLexii32mGrhW29qvU3QBVTu0GUmEf/J4XsBtVhp4JkIUFN/BjWqTF63yRvGApIDpZm5fa97LtYtINmfeQ==",
+      "version": "0.1.0",
+      "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.1.0.tgz",
+      "integrity": "sha512-kLrdPDJE1ckPo94kmPPf9Hfd0DU0Jw6oKYrhe+pwSC0iTUInmTa+w6fw8sGgcfkFJGNdWOUeOaDM4quW4a7OkA==",
       "dev": true,
       "license": "Apache-2.0",
       "engines": {
@@ -998,9 +998,9 @@
       }
     },
     "node_modules/@eslint/eslintrc": {
-      "version": "3.3.1",
-      "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-3.3.1.tgz",
-      "integrity": "sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==",
+      "version": "3.3.0",
+      "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-3.3.0.tgz",
+      "integrity": "sha512-yaVPAiNAalnCZedKLdR21GOGILMLKPyqSLWaAjQFvYA2i/ciDi8ArYVr69Anohb6cH2Ukhqti4aFnYyPm8wdwQ==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
@@ -1059,9 +1059,9 @@
       "license": "MIT"
     },
     "node_modules/@eslint/js": {
-      "version": "9.23.0",
-      "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.23.0.tgz",
-      "integrity": "sha512-35MJ8vCPU0ZMxo7zfev2pypqTwWTofFZO6m4KAtdoFhRpLJUpHTZZ+KB3C7Hb1d7bULYwO4lJXGCi5Se+8OMbw==",
+      "version": "9.22.0",
+      "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.22.0.tgz",
+      "integrity": "sha512-vLFajx9o8d1/oL2ZkpMYbkLv8nDB6yaIwFNt7nI4+I80U/z03SxmfOMsLbvWr3p7C+Wnoh//aOu2pQW8cS0HCQ==",
       "dev": true,
       "license": "MIT",
       "engines": {
@@ -2480,9 +2480,9 @@
       "license": "MIT"
     },
     "node_modules/@nestjs/common": {
-      "version": "11.0.12",
-      "resolved": "https://registry.npmjs.org/@nestjs/common/-/common-11.0.12.tgz",
-      "integrity": "sha512-6PXxmDe2iYmb57xacnxzpW1NAxRZ7Gf+acMT7/hmRB/4KpZiFU/cNvLWwgbM2BL5QSzQulOwY6ny5bbKnPpB+A==",
+      "version": "11.0.11",
+      "resolved": "https://registry.npmjs.org/@nestjs/common/-/common-11.0.11.tgz",
+      "integrity": "sha512-b3zYiho5/XGCnLa7W2hHv5ecSBR1huQrXCHu6pxd+g2HY2B7sKP5CXHMv4gHYqpIqu4ClOb7Q4tLKXMp9LyLUg==",
       "license": "MIT",
       "dependencies": {
         "iterare": "1.2.1",
@@ -2509,9 +2509,9 @@
       }
     },
     "node_modules/@nestjs/core": {
-      "version": "11.0.12",
-      "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-11.0.12.tgz",
-      "integrity": "sha512-micQrbh9iL0PuYVx2vsUojuNmMUyqoMCuj7eGAUhvjiZUh4DBLPdxYmJEayCT/equHSiw9vNC95Vm0JigVZ44g==",
+      "version": "11.0.11",
+      "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-11.0.11.tgz",
+      "integrity": "sha512-jMH3jrjrPiaGrkQ5hANNcgDWN+j+hcM5GMQ3jSs4vOWNs3lmKHTVR11wJ9y5tTNnwKydzMogeju0VTUdfXDI5Q==",
       "dev": true,
       "hasInstallScript": true,
       "license": "MIT",
@@ -2571,9 +2571,9 @@
       }
     },
     "node_modules/@nestjs/platform-express": {
-      "version": "11.0.12",
-      "resolved": "https://registry.npmjs.org/@nestjs/platform-express/-/platform-express-11.0.12.tgz",
-      "integrity": "sha512-Jze6dY1q1BBAjFuPQT9CLjYFl5IxMSQQxD+xs6cV+4EIysHxgSFZMJqiTpknZTFgPneyp0zF1TtQAjxBshnwlg==",
+      "version": "11.0.11",
+      "resolved": "https://registry.npmjs.org/@nestjs/platform-express/-/platform-express-11.0.11.tgz",
+      "integrity": "sha512-iv6nH66i/RuRQufg5UUboQ4jQX4NuuePrYQpHB3ueiEIhJm2yLhhNYM6Y2l/76y9woW2eckbiqbzmW/JajAgeQ==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
@@ -2593,9 +2593,9 @@
       }
     },
     "node_modules/@nestjs/platform-fastify": {
-      "version": "11.0.12",
-      "resolved": "https://registry.npmjs.org/@nestjs/platform-fastify/-/platform-fastify-11.0.12.tgz",
-      "integrity": "sha512-wpUI+A5jlSTEUyc212kMG2pGVCS29A3xzn8Y73tgu+szX+womi6zXud//+GArrlUcOIaA8Z2sCJLiROkiH2D2A==",
+      "version": "11.0.11",
+      "resolved": "https://registry.npmjs.org/@nestjs/platform-fastify/-/platform-fastify-11.0.11.tgz",
+      "integrity": "sha512-Ts7jMc3GE35k8KMY8m7/qtc4/Zqo4BFSXsfUy646o+JeJSkUZOSofevxkkI2smhX6w9SKJzyfEpRHzMZNs/oRA==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
@@ -2614,7 +2614,7 @@
       },
       "peerDependencies": {
         "@fastify/static": "^8.0.0",
-        "@fastify/view": "^10.0.0 || ^11.0.0",
+        "@fastify/view": "^10.0.0",
         "@nestjs/common": "^11.0.0",
         "@nestjs/core": "^11.0.0"
       },
@@ -2875,9 +2875,9 @@
       }
     },
     "node_modules/@pkgr/core": {
-      "version": "0.2.0",
-      "resolved": "https://registry.npmjs.org/@pkgr/core/-/core-0.2.0.tgz",
-      "integrity": "sha512-vsJDAkYR6qCPu+ioGScGiMYR7LvZYIXh/dlQeviqoTWNCVfKTLYD/LkNWH4Mxsv2a5vpIRc77FN5DnmK1eBggQ==",
+      "version": "0.1.1",
+      "resolved": "https://registry.npmjs.org/@pkgr/core/-/core-0.1.1.tgz",
+      "integrity": "sha512-cq8o4cWH0ibXh9VGi5P20Tu9XF/0fFXl9EUinr9QfTM7a7p0oTA4iJRCQWppXR1Pg8dSM0UCItCkPwsk9qWWYA==",
       "dev": true,
       "license": "MIT",
       "engines": {
@@ -3135,9 +3135,9 @@
       "license": "MIT"
     },
     "node_modules/@types/node": {
-      "version": "22.13.13",
-      "resolved": "https://registry.npmjs.org/@types/node/-/node-22.13.13.tgz",
-      "integrity": "sha512-ClsL5nMwKaBRwPcCvH8E7+nU4GxHVx1axNvMZTFHMEfNI7oahimt26P5zjVCRrjiIWj6YFXfE1v3dEp94wLcGQ==",
+      "version": "22.13.10",
+      "resolved": "https://registry.npmjs.org/@types/node/-/node-22.13.10.tgz",
+      "integrity": "sha512-I6LPUvlRH+O6VRUqYOcMudhaIdUVWfsjnZavnsraHvpBwaEyMN29ry+0UVJhImYL16xsscu0aske3yA+uPOWfw==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
@@ -3183,17 +3183,17 @@
       "license": "MIT"
     },
     "node_modules/@typescript-eslint/eslint-plugin": {
-      "version": "8.28.0",
-      "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.28.0.tgz",
-      "integrity": "sha512-lvFK3TCGAHsItNdWZ/1FkvpzCxTHUVuFrdnOGLMa0GGCFIbCgQWVk3CzCGdA7kM3qGVc+dfW9tr0Z/sHnGDFyg==",
+      "version": "8.26.1",
+      "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.26.1.tgz",
+      "integrity": "sha512-2X3mwqsj9Bd3Ciz508ZUtoQQYpOhU/kWoUqIf49H8Z0+Vbh6UF/y0OEYp0Q0axOGzaBGs7QxRwq0knSQ8khQNA==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
         "@eslint-community/regexpp": "^4.10.0",
-        "@typescript-eslint/scope-manager": "8.28.0",
-        "@typescript-eslint/type-utils": "8.28.0",
-        "@typescript-eslint/utils": "8.28.0",
-        "@typescript-eslint/visitor-keys": "8.28.0",
+        "@typescript-eslint/scope-manager": "8.26.1",
+        "@typescript-eslint/type-utils": "8.26.1",
+        "@typescript-eslint/utils": "8.26.1",
+        "@typescript-eslint/visitor-keys": "8.26.1",
         "graphemer": "^1.4.0",
         "ignore": "^5.3.1",
         "natural-compare": "^1.4.0",
@@ -3213,16 +3213,16 @@
       }
     },
     "node_modules/@typescript-eslint/parser": {
-      "version": "8.28.0",
-      "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.28.0.tgz",
-      "integrity": "sha512-LPcw1yHD3ToaDEoljFEfQ9j2xShY367h7FZ1sq5NJT9I3yj4LHer1Xd1yRSOdYy9BpsrxU7R+eoDokChYM53lQ==",
+      "version": "8.26.1",
+      "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.26.1.tgz",
+      "integrity": "sha512-w6HZUV4NWxqd8BdeFf81t07d7/YV9s7TCWrQQbG5uhuvGUAW+fq1usZ1Hmz9UPNLniFnD8GLSsDpjP0hm1S4lQ==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
-        "@typescript-eslint/scope-manager": "8.28.0",
-        "@typescript-eslint/types": "8.28.0",
-        "@typescript-eslint/typescript-estree": "8.28.0",
-        "@typescript-eslint/visitor-keys": "8.28.0",
+        "@typescript-eslint/scope-manager": "8.26.1",
+        "@typescript-eslint/types": "8.26.1",
+        "@typescript-eslint/typescript-estree": "8.26.1",
+        "@typescript-eslint/visitor-keys": "8.26.1",
         "debug": "^4.3.4"
       },
       "engines": {
@@ -3238,14 +3238,14 @@
       }
     },
     "node_modules/@typescript-eslint/scope-manager": {
-      "version": "8.28.0",
-      "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.28.0.tgz",
-      "integrity": "sha512-u2oITX3BJwzWCapoZ/pXw6BCOl8rJP4Ij/3wPoGvY8XwvXflOzd1kLrDUUUAIEdJSFh+ASwdTHqtan9xSg8buw==",
+      "version": "8.26.1",
+      "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.26.1.tgz",
+      "integrity": "sha512-6EIvbE5cNER8sqBu6V7+KeMZIC1664d2Yjt+B9EWUXrsyWpxx4lEZrmvxgSKRC6gX+efDL/UY9OpPZ267io3mg==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
-        "@typescript-eslint/types": "8.28.0",
-        "@typescript-eslint/visitor-keys": "8.28.0"
+        "@typescript-eslint/types": "8.26.1",
+        "@typescript-eslint/visitor-keys": "8.26.1"
       },
       "engines": {
         "node": "^18.18.0 || ^20.9.0 || >=21.1.0"
@@ -3256,14 +3256,14 @@
       }
     },
     "node_modules/@typescript-eslint/type-utils": {
-      "version": "8.28.0",
-      "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.28.0.tgz",
-      "integrity": "sha512-oRoXu2v0Rsy/VoOGhtWrOKDiIehvI+YNrDk5Oqj40Mwm0Yt01FC/Q7nFqg088d3yAsR1ZcZFVfPCTTFCe/KPwg==",
+      "version": "8.26.1",
+      "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.26.1.tgz",
+      "integrity": "sha512-Kcj/TagJLwoY/5w9JGEFV0dclQdyqw9+VMndxOJKtoFSjfZhLXhYjzsQEeyza03rwHx2vFEGvrJWJBXKleRvZg==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
-        "@typescript-eslint/typescript-estree": "8.28.0",
-        "@typescript-eslint/utils": "8.28.0",
+        "@typescript-eslint/typescript-estree": "8.26.1",
+        "@typescript-eslint/utils": "8.26.1",
         "debug": "^4.3.4",
         "ts-api-utils": "^2.0.1"
       },
@@ -3280,9 +3280,9 @@
       }
     },
     "node_modules/@typescript-eslint/types": {
-      "version": "8.28.0",
-      "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.28.0.tgz",
-      "integrity": "sha512-bn4WS1bkKEjx7HqiwG2JNB3YJdC1q6Ue7GyGlwPHyt0TnVq6TtD/hiOdTZt71sq0s7UzqBFXD8t8o2e63tXgwA==",
+      "version": "8.26.1",
+      "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.26.1.tgz",
+      "integrity": "sha512-n4THUQW27VmQMx+3P+B0Yptl7ydfceUj4ON/AQILAASwgYdZ/2dhfymRMh5egRUrvK5lSmaOm77Ry+lmXPOgBQ==",
       "dev": true,
       "license": "MIT",
       "engines": {
@@ -3294,14 +3294,14 @@
       }
     },
     "node_modules/@typescript-eslint/typescript-estree": {
-      "version": "8.28.0",
-      "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.28.0.tgz",
-      "integrity": "sha512-H74nHEeBGeklctAVUvmDkxB1mk+PAZ9FiOMPFncdqeRBXxk1lWSYraHw8V12b7aa6Sg9HOBNbGdSHobBPuQSuA==",
+      "version": "8.26.1",
+      "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.26.1.tgz",
+      "integrity": "sha512-yUwPpUHDgdrv1QJ7YQal3cMVBGWfnuCdKbXw1yyjArax3353rEJP1ZA+4F8nOlQ3RfS2hUN/wze3nlY+ZOhvoA==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
-        "@typescript-eslint/types": "8.28.0",
-        "@typescript-eslint/visitor-keys": "8.28.0",
+        "@typescript-eslint/types": "8.26.1",
+        "@typescript-eslint/visitor-keys": "8.26.1",
         "debug": "^4.3.4",
         "fast-glob": "^3.3.2",
         "is-glob": "^4.0.3",
@@ -3347,16 +3347,16 @@
       }
     },
     "node_modules/@typescript-eslint/utils": {
-      "version": "8.28.0",
-      "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.28.0.tgz",
-      "integrity": "sha512-OELa9hbTYciYITqgurT1u/SzpQVtDLmQMFzy/N8pQE+tefOyCWT79jHsav294aTqV1q1u+VzqDGbuujvRYaeSQ==",
+      "version": "8.26.1",
+      "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.26.1.tgz",
+      "integrity": "sha512-V4Urxa/XtSUroUrnI7q6yUTD3hDtfJ2jzVfeT3VK0ciizfK2q/zGC0iDh1lFMUZR8cImRrep6/q0xd/1ZGPQpg==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
         "@eslint-community/eslint-utils": "^4.4.0",
-        "@typescript-eslint/scope-manager": "8.28.0",
-        "@typescript-eslint/types": "8.28.0",
-        "@typescript-eslint/typescript-estree": "8.28.0"
+        "@typescript-eslint/scope-manager": "8.26.1",
+        "@typescript-eslint/types": "8.26.1",
+        "@typescript-eslint/typescript-estree": "8.26.1"
       },
       "engines": {
         "node": "^18.18.0 || ^20.9.0 || >=21.1.0"
@@ -3371,13 +3371,13 @@
       }
     },
     "node_modules/@typescript-eslint/visitor-keys": {
-      "version": "8.28.0",
-      "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.28.0.tgz",
-      "integrity": "sha512-hbn8SZ8w4u2pRwgQ1GlUrPKE+t2XvcCW5tTRF7j6SMYIuYG37XuzIW44JCZPa36evi0Oy2SnM664BlIaAuQcvg==",
+      "version": "8.26.1",
+      "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.26.1.tgz",
+      "integrity": "sha512-AjOC3zfnxd6S4Eiy3jwktJPclqhFHNyd8L6Gycf9WUPoKZpgM5PjkxY1X7uSy61xVpiJDhhk7XT2NVsN3ALTWg==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
-        "@typescript-eslint/types": "8.28.0",
+        "@typescript-eslint/types": "8.26.1",
         "eslint-visitor-keys": "^4.2.0"
       },
       "engines": {
@@ -5770,19 +5770,19 @@
       }
     },
     "node_modules/eslint": {
-      "version": "9.23.0",
-      "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.23.0.tgz",
-      "integrity": "sha512-jV7AbNoFPAY1EkFYpLq5bslU9NLNO8xnEeQXwErNibVryjk67wHVmddTBilc5srIttJDBrB0eMHKZBFbSIABCw==",
+      "version": "9.22.0",
+      "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.22.0.tgz",
+      "integrity": "sha512-9V/QURhsRN40xuHXWjV64yvrzMjcz7ZyNoF2jJFmy9j/SLk0u1OLSZgXi28MrXjymnjEGSR80WCdab3RGMDveQ==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
         "@eslint-community/eslint-utils": "^4.2.0",
         "@eslint-community/regexpp": "^4.12.1",
         "@eslint/config-array": "^0.19.2",
-        "@eslint/config-helpers": "^0.2.0",
+        "@eslint/config-helpers": "^0.1.0",
         "@eslint/core": "^0.12.0",
-        "@eslint/eslintrc": "^3.3.1",
-        "@eslint/js": "9.23.0",
+        "@eslint/eslintrc": "^3.3.0",
+        "@eslint/js": "9.22.0",
         "@eslint/plugin-kit": "^0.2.7",
         "@humanfs/node": "^0.16.6",
         "@humanwhocodes/module-importer": "^1.0.1",
@@ -5844,14 +5844,14 @@
       }
     },
     "node_modules/eslint-plugin-prettier": {
-      "version": "5.2.4",
-      "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-5.2.4.tgz",
-      "integrity": "sha512-SFtuYmnhwYCtuCDTKPoK+CEzCnEgKTU2qTLwoCxvrC0MFBTIXo1i6hDYOI4cwHaE5GZtlWmTN3YfucYi7KJwPw==",
+      "version": "5.2.3",
+      "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-5.2.3.tgz",
+      "integrity": "sha512-qJ+y0FfCp/mQYQ/vWQ3s7eUlFEL4PyKfAJxsnYTJ4YT73nsJBWqmEpFryxV9OeUiqmsTsYJ5Y+KDNaeP31wrRw==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
         "prettier-linter-helpers": "^1.0.0",
-        "synckit": "^0.10.2"
+        "synckit": "^0.9.1"
       },
       "engines": {
         "node": "^14.18.0 || >=16.0.0"
@@ -13205,9 +13205,9 @@
       }
     },
     "node_modules/supertest": {
-      "version": "7.1.0",
-      "resolved": "https://registry.npmjs.org/supertest/-/supertest-7.1.0.tgz",
-      "integrity": "sha512-5QeSO8hSrKghtcWEoPiO036fxH0Ii2wVQfFZSP0oqQhmjk8bOLhDFXr4JrvaFmPuEWUoq4znY3uSi8UzLKxGqw==",
+      "version": "7.0.0",
+      "resolved": "https://registry.npmjs.org/supertest/-/supertest-7.0.0.tgz",
+      "integrity": "sha512-qlsr7fIC0lSddmA3tzojvzubYxvlGtzumcdHgPwbFWMISQwL22MhM2Y3LNt+6w9Yyx7559VW5ab70dgphm8qQA==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
@@ -13258,23 +13258,23 @@
       }
     },
     "node_modules/swagger-ui-dist": {
-      "version": "5.20.1",
-      "resolved": "https://registry.npmjs.org/swagger-ui-dist/-/swagger-ui-dist-5.20.1.tgz",
-      "integrity": "sha512-qBPCis2w8nP4US7SvUxdJD3OwKcqiWeZmjN2VWhq2v+ESZEXOP/7n4DeiOiiZcGYTKMHAHUUrroHaTsjUWTEGw==",
+      "version": "5.19.0",
+      "resolved": "https://registry.npmjs.org/swagger-ui-dist/-/swagger-ui-dist-5.19.0.tgz",
+      "integrity": "sha512-bSVZeYaqanMFeW5ZY3+EejFbsjkjazYxm1I7Lz3xayYz5XU3m2aUzvuPC0jI95WCQdduszHYV3ER4buQoy8DXA==",
       "license": "Apache-2.0",
       "dependencies": {
         "@scarf/scarf": "=1.4.0"
       }
     },
     "node_modules/synckit": {
-      "version": "0.10.2",
-      "resolved": "https://registry.npmjs.org/synckit/-/synckit-0.10.2.tgz",
-      "integrity": "sha512-cSGiaCPhFzeFIQY8KKEacv46LclENY4d60jgkwCrKomvRkIjtMyss1dPkHLp/62c1leuOjEedB1+lWcwqTJSvA==",
+      "version": "0.9.2",
+      "resolved": "https://registry.npmjs.org/synckit/-/synckit-0.9.2.tgz",
+      "integrity": "sha512-vrozgXDQwYO72vHjUb/HnFbQx1exDjoKzqx23aXEg2a9VIg2TSFZ8FmeZpTjUCFMYw7mpX4BE2SFu8wI7asYsw==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
-        "@pkgr/core": "^0.2.0",
-        "tslib": "^2.8.1"
+        "@pkgr/core": "^0.1.0",
+        "tslib": "^2.6.2"
       },
       "engines": {
         "node": "^14.18.0 || >=16.0.0"
@@ -13482,9 +13482,9 @@
       }
     },
     "node_modules/ts-jest": {
-      "version": "29.3.0",
-      "resolved": "https://registry.npmjs.org/ts-jest/-/ts-jest-29.3.0.tgz",
-      "integrity": "sha512-4bfGBX7Gd1Aqz3SyeDS9O276wEU/BInZxskPrbhZLyv+c1wskDCqDFMJQJLWrIr/fKoAH4GE5dKUlrdyvo+39A==",
+      "version": "29.2.6",
+      "resolved": "https://registry.npmjs.org/ts-jest/-/ts-jest-29.2.6.tgz",
+      "integrity": "sha512-yTNZVZqc8lSixm+QGVFcPe6+yj7+TWZwIesuOWvfcn4B9bz5x4NDzVCQQjOs7Hfouu36aEqfEbo9Qpo+gq8dDg==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
@@ -13496,7 +13496,6 @@
         "lodash.memoize": "^4.1.2",
         "make-error": "^1.3.6",
         "semver": "^7.7.1",
-        "type-fest": "^4.37.0",
         "yargs-parser": "^21.1.1"
       },
       "bin": {
@@ -13544,19 +13543,6 @@
         "node": ">=10"
       }
     },
-    "node_modules/ts-jest/node_modules/type-fest": {
-      "version": "4.38.0",
-      "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-4.38.0.tgz",
-      "integrity": "sha512-2dBz5D5ycHIoliLYLi0Q2V7KRaDlH0uWIvmk7TYlAg5slqwiPv1ezJdZm1QEM0xgk29oYWMCbIG7E6gHpvChlg==",
-      "dev": true,
-      "license": "(MIT OR CC0-1.0)",
-      "engines": {
-        "node": ">=16"
-      },
-      "funding": {
-        "url": "https://github.com/sponsors/sindresorhus"
-      }
-    },
     "node_modules/tslib": {
       "version": "2.8.1",
       "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz",
@@ -13636,15 +13622,15 @@
       }
     },
     "node_modules/typescript-eslint": {
-      "version": "8.28.0",
-      "resolved": "https://registry.npmjs.org/typescript-eslint/-/typescript-eslint-8.28.0.tgz",
-      "integrity": "sha512-jfZtxJoHm59bvoCMYCe2BM0/baMswRhMmYhy+w6VfcyHrjxZ0OJe0tGasydCpIpA+A/WIJhTyZfb3EtwNC/kHQ==",
+      "version": "8.26.1",
+      "resolved": "https://registry.npmjs.org/typescript-eslint/-/typescript-eslint-8.26.1.tgz",
+      "integrity": "sha512-t/oIs9mYyrwZGRpDv3g+3K6nZ5uhKEMt2oNmAPwaY4/ye0+EH4nXIPYNtkYFS6QHm+1DFg34DbglYBz5P9Xysg==",
       "dev": true,
       "license": "MIT",
       "dependencies": {
-        "@typescript-eslint/eslint-plugin": "8.28.0",
-        "@typescript-eslint/parser": "8.28.0",
-        "@typescript-eslint/utils": "8.28.0"
+        "@typescript-eslint/eslint-plugin": "8.26.1",
+        "@typescript-eslint/parser": "8.26.1",
+        "@typescript-eslint/utils": "8.26.1"
       },
       "engines": {
         "node": "^18.18.0 || ^20.9.0 || >=21.1.0"
diff --git a/package.json b/package.json
index 51bee11e..baed428a 100644
--- a/package.json
+++ b/package.json
@@ -1,10 +1,12 @@
 {
   "name": "@nestjs/swagger",
-  "version": "11.1.0",
+  "version": "11.0.6",
   "description": "Nest - modern, fast, powerful node.js web framework (@swagger)",
   "author": "Kamil Mysliwiec",
   "license": "MIT",
   "repository": "https://github.com/nestjs/swagger",
+  "main": "dist/index.js",
+  "types": "dist/index.d.ts",
   "scripts": {
     "build": "tsc -p tsconfig.build.json",
     "format": "prettier \"lib/**/*.ts\" --write",
@@ -13,6 +15,7 @@
     "publish:next": "npm publish --access public --tag next",
     "prepublish:npm": "npm run build",
     "publish:npm": "npm publish --access public",
+    "prepare": "npm run build",
     "test": "jest",
     "test:dev": "jest --watch",
     "test:e2e": "jest --config e2e/jest-e2e.json",
@@ -29,30 +32,30 @@
     "js-yaml": "4.1.0",
     "lodash": "4.17.21",
     "path-to-regexp": "8.2.0",
-    "swagger-ui-dist": "5.20.1"
+    "swagger-ui-dist": "5.19.0"
   },
   "devDependencies": {
     "@commitlint/cli": "19.8.0",
     "@commitlint/config-angular": "19.8.0",
-    "@eslint/eslintrc": "3.3.1",
-    "@eslint/js": "9.23.0",
+    "@eslint/eslintrc": "3.3.0",
+    "@eslint/js": "9.22.0",
     "@fastify/static": "8.1.1",
-    "@nestjs/common": "11.0.12",
-    "@nestjs/core": "11.0.12",
-    "@nestjs/platform-express": "11.0.12",
-    "@nestjs/platform-fastify": "11.0.12",
+    "@nestjs/common": "^11.0.1",
+    "@nestjs/core": "^11.0.1",
+    "@nestjs/platform-express": "^11.0.1",
+    "@nestjs/platform-fastify": "^11.0.1",
     "@types/jest": "29.5.14",
     "@types/js-yaml": "4.0.9",
     "@types/lodash": "4.17.16",
-    "@types/node": "22.13.13",
+    "@types/node": "22.13.10",
     "class-transformer": "0.5.1",
     "class-validator": "0.14.1",
-    "eslint": "9.23.0",
+    "eslint": "9.22.0",
     "eslint-config-prettier": "10.1.1",
-    "eslint-plugin-prettier": "5.2.4",
+    "eslint-plugin-prettier": "5.2.3",
+    "globals": "16.0.0",
     "express": "5.0.1",
     "fastify": "5.2.1",
-    "globals": "16.0.0",
     "husky": "9.1.7",
     "jest": "29.7.0",
     "lerna-changelog": "2.2.0",
@@ -62,11 +65,11 @@
     "prettier-v2": "npm:prettier@2.8.8",
     "reflect-metadata": "0.2.2",
     "release-it": "18.1.2",
-    "supertest": "7.1.0",
+    "supertest": "7.0.0",
     "swagger-parser": "10.0.3",
-    "ts-jest": "29.3.0",
+    "ts-jest": "29.2.6",
     "typescript": "5.8.2",
-    "typescript-eslint": "8.28.0"
+    "typescript-eslint": "8.26.1"
   },
   "peerDependencies": {
     "@fastify/static": "^8.0.0",


Test patch:
diff --git a/e2e/api-spec.json b/e2e/api-spec.json
index d770e783..cb89d3fa 100644
--- a/e2e/api-spec.json
+++ b/e2e/api-spec.json
@@ -16,19 +16,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "tags": [
@@ -51,19 +38,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "tags": [
@@ -86,19 +60,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "tags": [
@@ -121,19 +82,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "tags": [
@@ -156,19 +104,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "tags": [
@@ -191,19 +126,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "tags": [
@@ -226,19 +148,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "tags": [
@@ -261,19 +170,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "tags": [
@@ -368,21 +264,8 @@
               }
             }
           },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
           "403": {
             "description": "Forbidden."
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -562,19 +445,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -650,19 +520,6 @@
         "responses": {
           "201": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -730,19 +587,6 @@
                 }
               }
             }
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -907,19 +751,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -982,19 +813,6 @@
                 }
               }
             }
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -1051,19 +869,6 @@
         "responses": {
           "201": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -1134,21 +939,8 @@
               }
             }
           },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
           "403": {
             "description": "Forbidden."
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -1194,19 +986,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -1264,19 +1043,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -1331,19 +1097,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -1410,19 +1163,6 @@
         "responses": {
           "200": {
             "description": ""
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -1558,19 +1298,6 @@
                 }
               }
             }
-          },
-          "400": {
-            "description": "Bad request",
-            "content": {
-              "application/json": {
-                "schema": {
-                  "$ref": "#/components/schemas/ValidationErrorDto"
-                }
-              }
-            }
-          },
-          "500": {
-            "description": "Internal server error"
           }
         },
         "security": [
@@ -1641,23 +1368,6 @@
       }
     },
     "schemas": {
-      "ValidationErrorDto": {
-        "type": "object",
-        "properties": {
-          "status": {
-            "type": "number",
-            "description": "HTTP status code"
-          },
-          "description": {
-            "type": "string",
-            "description": "Error description"
-          }
-        },
-        "required": [
-          "status",
-          "description"
-        ]
-      },
       "ExtraModel": {
         "type": "object",
         "properties": {
@@ -1753,23 +1463,6 @@
               }
             }
           },
-          "rawDefinition": {
-            "type": "object",
-            "properties": {
-              "name": {
-                "type": "string",
-                "example": "ErrorName"
-              },
-              "status": {
-                "type": "number",
-                "example": 400
-              }
-            },
-            "required": [
-              "name",
-              "status"
-            ]
-          },
           "enumWithDescription": {
             "enum": [
               "A",
@@ -1832,7 +1525,6 @@
           "createdAt",
           "urls",
           "options",
-          "rawDefinition",
           "enumWithDescription",
           "enum",
           "enumArr",
@@ -1908,12 +1600,6 @@
               "status"
             ]
           },
-          "optionalRawDefinition": {
-            "type": "object",
-            "additionalProperties": {
-              "type": "boolean"
-            }
-          },
           "enum": {
             "type": "string",
             "enum": [
diff --git a/e2e/src/cats/classes/cat.class.ts b/e2e/src/cats/classes/cat.class.ts
index 793df6d1..0c47fffd 100644
--- a/e2e/src/cats/classes/cat.class.ts
+++ b/e2e/src/cats/classes/cat.class.ts
@@ -60,14 +60,7 @@ export class Cat {
     required: ['name', 'status'],
     selfRequired: true
   })
-  rawDefinition: Record<string, any>;
-
-  @ApiProperty({
-    type: 'object',
-    additionalProperties: { type: 'boolean' },
-    selfRequired: false
-  })
-  optionalRawDefinition?: Record<string, boolean>;
+  rawDefinition?: Record<string, any>;
 
   @ApiProperty({
     enum: LettersEnum
diff --git a/e2e/src/cats/dto/create-cat.dto.ts b/e2e/src/cats/dto/create-cat.dto.ts
index 99506026..c3bbc8fa 100644
--- a/e2e/src/cats/dto/create-cat.dto.ts
+++ b/e2e/src/cats/dto/create-cat.dto.ts
@@ -44,23 +44,6 @@ export class CreateCatDto {
   })
   readonly options?: Record<string, any>[];
 
-  @ApiProperty({
-    type: 'object',
-    properties: {
-      name: {
-        type: 'string',
-        example: 'ErrorName'
-      },
-      status: {
-        type: 'number',
-        example: 400
-      }
-    },
-    required: ['name', 'status'],
-    selfRequired: true
-  })
-  rawDefinition: Record<string, any>;
-
   @ApiProperty({
     description: 'Enum with description'
   })
diff --git a/e2e/src/common/dto/validation-error.dto.ts b/e2e/src/common/dto/validation-error.dto.ts
deleted file mode 100644
index d2cac2ce..00000000
--- a/e2e/src/common/dto/validation-error.dto.ts
+++ /dev/null
@@ -1,15 +0,0 @@
-import { ApiProperty } from '../../../../lib';
-
-export class ValidationErrorDto {
-  @ApiProperty({
-    type: 'number',
-    description: 'HTTP status code'
-  })
-  status: number;
-
-  @ApiProperty({
-    type: 'string',
-    description: 'Error description'
-  })
-  description: string;
-}
diff --git a/e2e/validate-schema.e2e-spec.ts b/e2e/validate-schema.e2e-spec.ts
index cc62930a..335d9fa8 100644
--- a/e2e/validate-schema.e2e-spec.ts
+++ b/e2e/validate-schema.e2e-spec.ts
@@ -10,11 +10,9 @@ import {
   OpenAPIObject,
   SwaggerModule
 } from '../lib';
-import { SchemaObject } from '../lib/interfaces/open-api-spec.interface';
 import { ApplicationModule } from './src/app.module';
 import { Cat } from './src/cats/classes/cat.class';
 import { TagDto } from './src/cats/dto/tag.dto';
-import { ValidationErrorDto } from './src/common/dto/validation-error.dto';
 import { ExpressController } from './src/express.controller';
 
 describe('Validate OpenAPI schema', () => {
@@ -50,15 +48,6 @@ describe('Validate OpenAPI schema', () => {
       .addCookieAuth()
       .addSecurityRequirements('bearer')
       .addSecurityRequirements({ basic: [], cookie: [] })
-      .addGlobalResponse({
-        status: 500,
-        description: 'Internal server error'
-      })
-      .addGlobalResponse({
-        status: 400,
-        description: 'Bad request',
-        type: ValidationErrorDto
-      })
       .addGlobalParameters({
         name: 'x-tenant-id',
         in: 'header',
@@ -211,7 +200,7 @@ describe('Validate OpenAPI schema', () => {
       }
     });
 
-    const api = (await SwaggerParser.validate(
+    let api = (await SwaggerParser.validate(
       document as any
     )) as OpenAPIV3.Document;
     console.log('API name: %s, Version: %s', api.info.title, api.info.version);
@@ -233,11 +222,4 @@ describe('Validate OpenAPI schema', () => {
       }
     });
   });
-
-  it('should not add optional properties to required list', async () => {
-    const document = SwaggerModule.createDocument(app, options);
-    const required = (document.components?.schemas?.Cat as SchemaObject)
-      ?.required;
-    expect(required).not.toContain('optionalRawDefinition');
-  });
 });
diff --git a/test/explorer/swagger-explorer.spec.ts b/test/explorer/swagger-explorer.spec.ts
index 3ff4d0bc..fa4087d0 100644
--- a/test/explorer/swagger-explorer.spec.ts
+++ b/test/explorer/swagger-explorer.spec.ts
@@ -31,7 +31,6 @@ import {
   ApiProperty,
   ApiPropertyOptional,
   ApiQuery,
-  ApiResponse,
   ApiSchema
 } from '../../lib/decorators';
 import { DenormalizedDoc } from '../../lib/interfaces/denormalized-doc.interface';
@@ -41,7 +40,6 @@ import { ModelPropertiesAccessor } from '../../lib/services/model-properties-acc
 import { SchemaObjectFactory } from '../../lib/services/schema-object-factory';
 import { SwaggerTypesMapper } from '../../lib/services/swagger-types-mapper';
 import { GlobalParametersStorage } from '../../lib/storages/global-parameters.storage';
-import { GlobalResponsesStorage } from '../../lib/storages/global-responses.storage';
 import { SwaggerExplorer } from '../../lib/swagger-explorer';
 
 describe('SwaggerExplorer', () => {
@@ -183,10 +181,8 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
 
       expect(
@@ -209,10 +205,8 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
       const operationPrefix = 'FooController_';
 
@@ -270,10 +264,8 @@ describe('SwaggerExplorer', () => {
           metatype: FooWithMetadataController
         } as unknown as InstanceWrapper<FooWithMetadataController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
       const operationPrefix = 'FooWithMetadataController_';
 
@@ -288,11 +280,9 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix',
-          operationIdFactory: methodKeyOperationIdFactory
-        }
+        'modulePath',
+        'globalPrefix',
+        methodKeyOperationIdFactory
       );
       const operationPrefix = '';
 
@@ -307,11 +297,9 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix',
-          operationIdFactory: controllerKeyMethodKeyOperationIdFactory
-        }
+        'modulePath',
+        'globalPrefix',
+        controllerKeyMethodKeyOperationIdFactory
       );
       const operationPrefix = 'FooController.';
 
@@ -325,12 +313,12 @@ describe('SwaggerExplorer', () => {
       expect(routes.length).toEqual(3);
 
       // POST
-      expect(routes[0].root.operationId).toEqual(operationPrefix + 'create');
-      expect(routes[0].root.method).toEqual('post');
-      expect(routes[0].root.path).toEqual('/globalPrefix/modulePath/foos');
-      expect(routes[0].root.summary).toEqual('Create foo');
-      expect(routes[0].root.parameters.length).toEqual(7);
-      expect(routes[0].root.parameters).toEqual([
+      expect(routes[0].root!.operationId).toEqual(operationPrefix + 'create');
+      expect(routes[0].root!.method).toEqual('post');
+      expect(routes[0].root!.path).toEqual('/globalPrefix/modulePath/foos');
+      expect(routes[0].root!.summary).toEqual('Create foo');
+      expect(routes[0].root!.parameters.length).toEqual(7);
+      expect(routes[0].root!.parameters).toEqual([
         {
           in: 'query',
           name: 'page',
@@ -404,7 +392,7 @@ describe('SwaggerExplorer', () => {
           }
         }
       ]);
-      expect(routes[0].root.requestBody).toEqual({
+      expect(routes[0].root!.requestBody).toEqual({
         required: true,
         content: {
           'application/json': {
@@ -427,14 +415,14 @@ describe('SwaggerExplorer', () => {
       expect(createdResponse).not.toHaveProperty('examples');
 
       // GET
-      expect(routes[1].root.operationId).toEqual(operationPrefix + 'find[0]');
-      expect(routes[1].root.method).toEqual('get');
-      expect(routes[1].root.path).toEqual(
+      expect(routes[1].root!.operationId).toEqual(operationPrefix + 'find[0]');
+      expect(routes[1].root!.method).toEqual('get');
+      expect(routes[1].root!.path).toEqual(
         '/globalPrefix/modulePath/foos/{objectId}'
       );
-      expect(routes[1].root.summary).toEqual('List all Foos');
-      expect(routes[1].root.parameters.length).toEqual(2);
-      expect(routes[1].root.parameters).toEqual([
+      expect(routes[1].root!.summary).toEqual('List all Foos');
+      expect(routes[1].root!.parameters.length).toEqual(2);
+      expect(routes[1].root!.parameters).toEqual([
         {
           in: 'path',
           name: 'objectId',
@@ -469,14 +457,14 @@ describe('SwaggerExplorer', () => {
       });
 
       // GET alias
-      expect(routes[2].root.operationId).toEqual(operationPrefix + 'find[1]');
-      expect(routes[2].root.method).toEqual('get');
-      expect(routes[2].root.path).toEqual(
+      expect(routes[2].root!.operationId).toEqual(operationPrefix + 'find[1]');
+      expect(routes[2].root!.method).toEqual('get');
+      expect(routes[2].root!.path).toEqual(
         '/globalPrefix/modulePath/foo/{objectId}'
       );
-      expect(routes[2].root.summary).toEqual('List all Foos');
-      expect(routes[2].root.parameters.length).toEqual(2);
-      expect(routes[2].root.parameters).toEqual([
+      expect(routes[2].root!.summary).toEqual('List all Foos');
+      expect(routes[2].root!.parameters.length).toEqual(2);
+      expect(routes[2].root!.parameters).toEqual([
         {
           in: 'path',
           name: 'objectId',
@@ -553,7 +541,8 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        { modulePath: undefined, globalPrefix: 'globalPrefix' }
+        undefined,
+        'globalPrefix'
       );
       const prefix = 'FooController_';
 
@@ -568,11 +557,9 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: undefined,
-          globalPrefix: 'globalPrefix',
-          operationIdFactory: methodKeyOperationIdFactory
-        }
+        undefined,
+        'globalPrefix',
+        methodKeyOperationIdFactory
       );
       const prefix = '';
 
@@ -587,11 +574,9 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: undefined,
-          globalPrefix: 'globalPrefix',
-          operationIdFactory: controllerKeyMethodKeyOperationIdFactory
-        }
+        undefined,
+        'globalPrefix',
+        controllerKeyMethodKeyOperationIdFactory
       );
       const prefix = 'FooController.';
 
@@ -605,12 +590,12 @@ describe('SwaggerExplorer', () => {
       expect(routes.length).toEqual(2);
 
       // POST
-      expect(routes[0].root.operationId).toEqual(operationPrefix + 'create');
-      expect(routes[0].root.method).toEqual('post');
-      expect(routes[0].root.path).toEqual('/globalPrefix/foos');
-      expect(routes[0].root.summary).toEqual('Create foo');
-      expect(routes[0].root.parameters.length).toEqual(0);
-      expect(routes[0].root.requestBody).toEqual({
+      expect(routes[0].root!.operationId).toEqual(operationPrefix + 'create');
+      expect(routes[0].root!.method).toEqual('post');
+      expect(routes[0].root!.path).toEqual('/globalPrefix/foos');
+      expect(routes[0].root!.summary).toEqual('Create foo');
+      expect(routes[0].root!.parameters.length).toEqual(0);
+      expect(routes[0].root!.requestBody).toEqual({
         required: true,
         content: {
           'application/json': {
@@ -638,12 +623,12 @@ describe('SwaggerExplorer', () => {
       });
 
       // GET
-      expect(routes[1].root.operationId).toEqual(operationPrefix + 'find');
-      expect(routes[1].root.method).toEqual('get');
-      expect(routes[1].root.path).toEqual('/globalPrefix/foos/{objectId}');
-      expect(routes[1].root.summary).toEqual('List all Foos');
-      expect(routes[1].root.parameters.length).toEqual(2);
-      expect(routes[1].root.parameters).toEqual([
+      expect(routes[1].root!.operationId).toEqual(operationPrefix + 'find');
+      expect(routes[1].root!.method).toEqual('get');
+      expect(routes[1].root!.path).toEqual('/globalPrefix/foos/{objectId}');
+      expect(routes[1].root!.summary).toEqual('List all Foos');
+      expect(routes[1].root!.parameters.length).toEqual(2);
+      expect(routes[1].root!.parameters).toEqual([
         {
           in: 'path',
           name: 'objectId',
@@ -757,9 +742,8 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath'
-        }
+        'modulePath',
+        undefined
       );
       const operationPrefix = 'FooController_';
 
@@ -774,10 +758,8 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
 
       const badRequestResponse = routes[0].responses['400'] as ResponseObject;
@@ -801,10 +783,9 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          operationIdFactory: methodKeyOperationIdFactory
-        }
+        'modulePath',
+        undefined,
+        methodKeyOperationIdFactory
       );
       const operationPrefix = '';
 
@@ -819,10 +800,9 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          operationIdFactory: controllerKeyMethodKeyOperationIdFactory
-        }
+        'modulePath',
+        undefined,
+        controllerKeyMethodKeyOperationIdFactory
       );
       const operationPrefix = 'FooController.';
 
@@ -836,12 +816,12 @@ describe('SwaggerExplorer', () => {
       expect(routes.length).toEqual(2);
 
       // POST
-      expect(routes[0].root.operationId).toEqual(operationPrefix + 'create');
-      expect(routes[0].root.method).toEqual('post');
-      expect(routes[0].root.path).toEqual('/modulePath/foos');
-      expect(routes[0].root.summary).toEqual('Create foo');
-      expect(routes[0].root.parameters.length).toEqual(0);
-      expect(routes[0].root.requestBody).toEqual({
+      expect(routes[0].root!.operationId).toEqual(operationPrefix + 'create');
+      expect(routes[0].root!.method).toEqual('post');
+      expect(routes[0].root!.path).toEqual('/modulePath/foos');
+      expect(routes[0].root!.summary).toEqual('Create foo');
+      expect(routes[0].root!.parameters.length).toEqual(0);
+      expect(routes[0].root!.requestBody).toEqual({
         required: true,
         content: {
           'application/xml': {
@@ -866,12 +846,12 @@ describe('SwaggerExplorer', () => {
       });
 
       // GET
-      expect(routes[1].root.operationId).toEqual(operationPrefix + 'find');
-      expect(routes[1].root.method).toEqual('get');
-      expect(routes[1].root.path).toEqual('/modulePath/foos/{objectId}');
-      expect(routes[1].root.summary).toEqual('List all Foos');
-      expect(routes[1].root.parameters.length).toEqual(2);
-      expect(routes[1].root.parameters).toEqual([
+      expect(routes[1].root!.operationId).toEqual(operationPrefix + 'find');
+      expect(routes[1].root!.method).toEqual('get');
+      expect(routes[1].root!.path).toEqual('/modulePath/foos/{objectId}');
+      expect(routes[1].root!.summary).toEqual('List all Foos');
+      expect(routes[1].root!.parameters.length).toEqual(2);
+      expect(routes[1].root!.parameters).toEqual([
         {
           in: 'query',
           name: 'page',
@@ -976,10 +956,8 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         config,
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
 
       validateRoutes(routes);
@@ -997,10 +975,8 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         config,
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
 
       validateRoutes(routes);
@@ -1010,11 +986,11 @@ describe('SwaggerExplorer', () => {
       expect(routes.length).toEqual(2);
 
       // POST
-      expect(routes[0].root.description).toEqual('Allows creating Foo item');
-      expect(routes[0].root.tags).toEqual(['foo']);
-      expect(routes[0].root.operationId).toEqual('FooController_create2');
-      expect(routes[0].root.parameters.length).toEqual(0);
-      expect(routes[0].root.requestBody).toEqual({
+      expect(routes[0].root!.description).toEqual('Allows creating Foo item');
+      expect(routes[0].root!.tags).toEqual(['foo']);
+      expect(routes[0].root!.operationId).toEqual('FooController_create2');
+      expect(routes[0].root!.parameters.length).toEqual(0);
+      expect(routes[0].root!.requestBody).toEqual({
         required: true,
         content: {
           'application/xml': {
@@ -1043,12 +1019,12 @@ describe('SwaggerExplorer', () => {
       });
 
       // GET
-      expect(routes[1].root.path).toEqual(
+      expect(routes[1].root!.path).toEqual(
         '/globalPrefix/v2/modulePath/foos/{objectId}'
       );
-      expect(routes[1].root.operationId).toEqual('FooController_find2');
-      expect(routes[1].root.parameters.length).toEqual(2);
-      expect(routes[1].root.parameters).toEqual([
+      expect(routes[1].root!.operationId).toEqual('FooController_find2');
+      expect(routes[1].root!.parameters.length).toEqual(2);
+      expect(routes[1].root!.parameters).toEqual([
         {
           in: 'query',
           name: 'page',
@@ -1069,7 +1045,7 @@ describe('SwaggerExplorer', () => {
           }
         }
       ]);
-      expect(routes[1].root.requestBody).toEqual({
+      expect(routes[1].root!.requestBody).toEqual({
         required: true,
         content: {
           'application/json': {
@@ -1197,16 +1173,14 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         config,
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
 
-      expect(routes[0].root.path).toEqual(
+      expect(routes[0].root!.path).toEqual(
         '/globalPrefix/v3/modulePath/foos/{objectId}'
       );
-      expect(routes[0].root.parameters).toEqual([
+      expect(routes[0].root!.parameters).toEqual([
         {
           in: 'path',
           name: 'objectId',
@@ -1248,10 +1222,10 @@ describe('SwaggerExplorer', () => {
           metatype: Foo2Controller
         } as InstanceWrapper<Foo2Controller>,
         new ApplicationConfig(),
-        { modulePath: 'path' }
+        'path'
       );
 
-      expect(routes[0].root.parameters).toEqual([
+      expect(routes[0].root!.parameters).toEqual([
         {
           in: 'path',
           name: 'objectId',
@@ -1290,13 +1264,11 @@ describe('SwaggerExplorer', () => {
           metatype: BarController
         } as InstanceWrapper<BarController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
 
-      expect(routes[0].root.parameters).toEqual([
+      expect(routes[0].root!.parameters).toEqual([
         {
           in: 'path',
           name: 'objectId',
@@ -1337,14 +1309,12 @@ describe('SwaggerExplorer', () => {
           metatype: Bar2Controller
         } as InstanceWrapper<Bar2Controller>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
 
       expect(schema.NumberEnum).toEqual({ type: 'number', enum: [1, 2, 3] });
-      expect(routes[0].root.parameters).toEqual([
+      expect(routes[0].root!.parameters).toEqual([
         {
           in: 'path',
           name: 'objectId',
@@ -1392,13 +1362,11 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
 
-      expect(routes[0].root.parameters).toEqual([
+      expect(routes[0].root!.parameters).toEqual([
         {
           description: 'auth token',
           name: 'Authorization',
@@ -1417,7 +1385,7 @@ describe('SwaggerExplorer', () => {
           }
         }
       ]);
-      expect(routes[1].root.parameters).toEqual([
+      expect(routes[1].root!.parameters).toEqual([
         {
           description: 'auth token',
           name: 'Authorization',
@@ -1460,7 +1428,7 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        { modulePath: 'path' }
+        'path'
       );
 
       const schemas = explorer.getSchemas();
@@ -1487,7 +1455,7 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        { modulePath: 'path' }
+        'path'
       );
 
       const schemas = explorer.getSchemas();
@@ -1521,7 +1489,7 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        { modulePath: 'path' }
+        'path'
       );
 
       expect(routes).toHaveLength(0);
@@ -1587,10 +1555,8 @@ describe('SwaggerExplorer', () => {
               metatype: WithVersionController
             } as InstanceWrapper<WithVersionController>,
             config,
-            {
-              modulePath: 'modulePath',
-              globalPrefix: 'globalPrefix'
-            }
+            'modulePath',
+            'globalPrefix'
           );
 
           expect(routes[0].root.path).toEqual(
@@ -1608,10 +1574,8 @@ describe('SwaggerExplorer', () => {
               metatype: WithVersionController
             } as InstanceWrapper<WithVersionController>,
             config,
-            {
-              modulePath: 'modulePath',
-              globalPrefix: 'globalPrefix'
-            }
+            'modulePath',
+            'globalPrefix'
           );
 
           expect(routes[1].root.path).toEqual(
@@ -1629,10 +1593,8 @@ describe('SwaggerExplorer', () => {
               metatype: WithMultipleVersionsController
             } as InstanceWrapper<WithMultipleVersionsController>,
             config,
-            {
-              modulePath: 'modulePath',
-              globalPrefix: 'globalPrefix'
-            }
+            'modulePath',
+            'globalPrefix'
           );
 
           expect(routes[0].root.path).toEqual(
@@ -1660,7 +1622,8 @@ describe('SwaggerExplorer', () => {
               metatype: WithMultipleVersionsNeutralController
             } as InstanceWrapper<WithMultipleVersionsNeutralController>,
             config,
-            { modulePath: 'modulePath', globalPrefix: 'globalPrefix' }
+            'modulePath',
+            'globalPrefix'
           );
 
           expect(routes[0].root.path).toEqual(
@@ -1689,12 +1652,9 @@ describe('SwaggerExplorer', () => {
               metatype: WithVersionController
             } as InstanceWrapper<WithVersionController>,
             config,
-            {
-              modulePath: 'modulePath',
-              globalPrefix: 'globalPrefix',
-              operationIdFactory:
-                controllerKeyMethodKeyVersionKeyOperationIdFactory
-            }
+            'modulePath',
+            'globalPrefix',
+            controllerKeyMethodKeyVersionKeyOperationIdFactory
           );
 
           expect(routes[0].root.path).toEqual(
@@ -1712,12 +1672,9 @@ describe('SwaggerExplorer', () => {
               metatype: WithVersionController
             } as InstanceWrapper<WithVersionController>,
             config,
-            {
-              modulePath: 'modulePath',
-              globalPrefix: 'globalPrefix',
-              operationIdFactory:
-                controllerKeyMethodKeyVersionKeyOperationIdFactory
-            }
+            'modulePath',
+            'globalPrefix',
+            controllerKeyMethodKeyVersionKeyOperationIdFactory
           );
 
           expect(routes[1].root.path).toEqual(
@@ -1735,12 +1692,9 @@ describe('SwaggerExplorer', () => {
               metatype: WithMultipleVersionsController
             } as InstanceWrapper<WithMultipleVersionsController>,
             config,
-            {
-              modulePath: 'modulePath',
-              globalPrefix: 'globalPrefix',
-              operationIdFactory:
-                controllerKeyMethodKeyVersionKeyOperationIdFactory
-            }
+            'modulePath',
+            'globalPrefix',
+            controllerKeyMethodKeyVersionKeyOperationIdFactory
           );
 
           expect(routes[0].root.path).toEqual(
@@ -1772,12 +1726,9 @@ describe('SwaggerExplorer', () => {
               metatype: WithMultipleVersionsNeutralController
             } as InstanceWrapper<WithMultipleVersionsNeutralController>,
             config,
-            {
-              modulePath: 'modulePath',
-              globalPrefix: 'globalPrefix',
-              operationIdFactory:
-                controllerKeyMethodKeyVersionKeyOperationIdFactory
-            }
+            'modulePath',
+            'globalPrefix',
+            controllerKeyMethodKeyVersionKeyOperationIdFactory
           );
 
           expect(routes[0].root.path).toEqual(
@@ -1806,10 +1757,11 @@ describe('SwaggerExplorer', () => {
             metatype: WithVersionController
           } as InstanceWrapper<WithVersionController>,
           config,
-          { modulePath: 'modulePath', globalPrefix: 'globalPrefix' }
+          'modulePath',
+          'globalPrefix'
         );
 
-        expect(routes[0].root.path).toEqual(
+        expect(routes[0].root!.path).toEqual(
           `/globalPrefix/v${CONTROLLER_VERSION}/modulePath/with-version`
         );
       });
@@ -1821,13 +1773,11 @@ describe('SwaggerExplorer', () => {
             metatype: WithVersionController
           } as InstanceWrapper<WithVersionController>,
           config,
-          {
-            modulePath: 'modulePath',
-            globalPrefix: 'globalPrefix'
-          }
+          'modulePath',
+          'globalPrefix'
         );
 
-        expect(routes[1].root.path).toEqual(
+        expect(routes[1].root!.path).toEqual(
           `/globalPrefix/v${METHOD_VERSION}/modulePath/with-version`
         );
       });
@@ -1839,15 +1789,16 @@ describe('SwaggerExplorer', () => {
             metatype: WithMultipleVersionsController
           } as InstanceWrapper<WithMultipleVersionsController>,
           config,
-          { modulePath: 'modulePath', globalPrefix: 'globalPrefix' }
+          'modulePath',
+          'globalPrefix'
         );
 
-        expect(routes[0].root.path).toEqual(
+        expect(routes[0].root!.path).toEqual(
           `/globalPrefix/v${
             CONTROLLER_MULTIPLE_VERSIONS[0] as string
           }/modulePath/with-multiple-version`
         );
-        expect(routes[1].root.path).toEqual(
+        expect(routes[1].root!.path).toEqual(
           `/globalPrefix/v${
             CONTROLLER_MULTIPLE_VERSIONS[1] as string
           }/modulePath/with-multiple-version`
@@ -1877,10 +1828,11 @@ describe('SwaggerExplorer', () => {
             metatype: WithoutVersionsController
           } as InstanceWrapper<WithoutVersionsController>,
           config,
-          { modulePath: 'modulePath', globalPrefix: 'globalPrefix' }
+          'modulePath',
+          'globalPrefix'
         );
 
-        expect(routes[0].root.path).toEqual(
+        expect(routes[0].root!.path).toEqual(
           `/globalPrefix/v${DEFAULT_VERSION}/modulePath/with-multiple-version`
         );
       });
@@ -1928,15 +1880,16 @@ describe('SwaggerExplorer', () => {
             metatype: WithMultipleVersionsController
           } as InstanceWrapper<WithMultipleVersionsController>,
           config,
-          { modulePath: 'modulePath', globalPrefix: 'globalPrefix' }
+          'modulePath',
+          'globalPrefix'
         );
 
-        expect(routes[0].root.path).toEqual(
+        expect(routes[0].root!.path).toEqual(
           `/globalPrefix/v${
             CONTROLLER_MULTIPLE_VERSIONS[0] as string
           }/modulePath/with-multiple-version`
         );
-        expect(routes[1].root.path).toEqual(
+        expect(routes[1].root!.path).toEqual(
           `/globalPrefix/modulePath/with-multiple-version`
         );
       });
@@ -1948,14 +1901,15 @@ describe('SwaggerExplorer', () => {
             metatype: WithMultipleVersionsController
           } as InstanceWrapper<WithMultipleVersionsController>,
           config,
-          { modulePath: 'modulePath', globalPrefix: 'globalPrefix' }
+          'modulePath',
+          'globalPrefix'
         );
         const postRoutes = routes.filter(
           (route) => route.root?.method === 'post'
         );
 
-        expect(postRoutes[0].root.requestBody).toBeDefined();
-        expect(postRoutes[1].root.requestBody).toBeDefined();
+        expect(postRoutes[0].root!.requestBody).toBeDefined();
+        expect(postRoutes[1].root!.requestBody).toBeDefined();
       });
     });
   });
@@ -1977,10 +1931,8 @@ describe('SwaggerExplorer', () => {
           metatype: AllController
         } as InstanceWrapper<AllController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
 
       expect(routes.length).toEqual(8);
@@ -1995,10 +1947,10 @@ describe('SwaggerExplorer', () => {
           'head',
           'search'
         ].every((method) =>
-          routes.find((route) => route.root.method === method)
+          routes.find((route) => route.root!.method === method)
         )
       ).toBe(true);
-      expect(routes.find((route) => route.root.method === 'all')).toBe(
+      expect(routes.find((route) => route.root!.method === 'all')).toBe(
         undefined
       );
       // check if all routes are equal except for method
@@ -2059,7 +2011,7 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        { modulePath: 'path' }
+        'path'
       );
 
       expect(routes.length).toEqual(2);
@@ -2179,13 +2131,11 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'modulePath',
-          globalPrefix: 'globalPrefix'
-        }
+        'modulePath',
+        'globalPrefix'
       );
 
-      expect(routes[0].root.parameters).toEqual([
+      expect(routes[0].root!.parameters).toEqual([
         {
           name: 'x-tenant-id',
           in: 'header',
@@ -2257,7 +2207,7 @@ describe('SwaggerExplorer', () => {
           metatype: HumanController
         } as InstanceWrapper<HumanController>,
         new ApplicationConfig(),
-        { modulePath: 'path' }
+        'path'
       );
 
       expect((routes[0].responses['200'] as ResponseObject).links).toEqual({
@@ -2295,13 +2245,13 @@ describe('SwaggerExplorer', () => {
           metatype: HumanController
         } as InstanceWrapper<HumanController>,
         new ApplicationConfig(),
-        {
-          modulePath: 'path',
-          linkNameFactory: (controllerKey, methodKey, paramKey) =>
-            paramKey === 'id'
-              ? methodKey.replace(/^get/, '')
-              : upperFirst(paramKey.replace(/Id(s)?$/, '$1'))
-        }
+        'path',
+        undefined,
+        undefined,
+        (controllerKey, methodKey, paramKey) =>
+          paramKey === 'id'
+            ? methodKey.replace(/^get/, '')
+            : upperFirst(paramKey.replace(/Id(s)?$/, '$1'))
       );
 
       expect((routes[0].responses['200'] as ResponseObject).links).toEqual({
@@ -2353,7 +2303,7 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        { modulePath: 'path' }
+        'path'
       );
 
       expect(routes[0].root.parameters).toEqual([
@@ -2413,7 +2363,7 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        { modulePath: 'path' }
+        'path'
       );
 
       expect(routes[0].root.parameters).toEqual([
@@ -2501,7 +2451,7 @@ describe('SwaggerExplorer', () => {
           metatype: FooController
         } as InstanceWrapper<FooController>,
         new ApplicationConfig(),
-        { modulePath: 'path' }
+        'path'
       );
 
       expect(routes[0].root.parameters).toEqual([
@@ -2559,60 +2509,4 @@ describe('SwaggerExplorer', () => {
       ]);
     });
   });
-
-  describe('when global responses defined', () => {
-    @Controller('')
-    @ApiResponse({
-      status: 502,
-      description: '502 - controller error response'
-    })
-    class FooController {
-      @Post('foos')
-      @ApiResponse({
-        status: 200,
-        description: '200 - method response'
-      })
-      get(): Promise<any> {
-        return Promise.resolve({});
-      }
-    }
-
-    it('should merge global responses with explicit ones', () => {
-      GlobalResponsesStorage.add({
-        401: { description: '401 - global error response' },
-        403: { description: '403 - global error response' },
-        500: { description: '500 - global internal server error' }
-      });
-
-      const explorer = new SwaggerExplorer(schemaObjectFactory);
-      const routes = explorer.exploreController(
-        {
-          instance: new FooController(),
-          metatype: FooController
-        } as InstanceWrapper<FooController>,
-        new ApplicationConfig(),
-        {
-          modulePath: 'modulePath'
-        }
-      );
-
-      expect(
-        (routes[0].responses['401'] as ResponseObject).description
-      ).toEqual('401 - global error response');
-      expect(
-        (routes[0].responses['500'] as ResponseObject).description
-      ).toEqual('500 - global internal server error');
-      expect(
-        (routes[0].responses['502'] as ResponseObject).description
-      ).toEqual('502 - controller error response');
-      expect(
-        (routes[0].responses['200'] as ResponseObject).description
-      ).toEqual('200 - method response');
-      expect(
-        (routes[0].responses['403'] as ResponseObject).description
-      ).toEqual('403 - global error response');
-
-      GlobalParametersStorage.clear();
-    });
-  });
 });
diff --git a/test/plugin/fixtures/create-option.ts b/test/plugin/fixtures/create-option.ts
index 9d3662c4..ea68157f 100644
--- a/test/plugin/fixtures/create-option.ts
+++ b/test/plugin/fixtures/create-option.ts
@@ -16,6 +16,7 @@ export const mergedCliPluginMultiOption = {
   dtoKeyOfComment: 'description',
   controllerKeyOfComment: 'summary',
   introspectComments: true,
+  esmCompatible: false,
   readonly: false,
   debug: false
 };
@@ -28,6 +29,7 @@ export const mergedCliPluginSingleOption = {
   dtoKeyOfComment: 'description',
   controllerKeyOfComment: 'summary',
   introspectComments: true,
+  esmCompatible: false,
   readonly: false,
   debug: false
 };
diff --git a/test/plugin/fixtures/parameter-property.dto.ts b/test/plugin/fixtures/parameter-property.dto.ts
index 3d8ef3f5..02d1b53a 100644
--- a/test/plugin/fixtures/parameter-property.dto.ts
+++ b/test/plugin/fixtures/parameter-property.dto.ts
@@ -1,11 +1,13 @@
+import { getOutputExtension } from '../../../lib/plugin/utils/plugin-utils';
+
 export const parameterPropertyDtoText = `
 export class ParameterPropertyDto {
   constructor(
-    readonly readonlyValue?: string, 
-    private privateValue: string | null, 
-    public publicValue: ItemDto[], 
+    readonly readonlyValue?: string,
+    private privateValue: string | null,
+    public publicValue: ItemDto[],
     regularParameter: string
-    protected protectedValue: string = '1234', 
+    protected protectedValue: string = '1234',
 ) {}
 }
 
@@ -20,7 +22,13 @@ export class ItemDto {
 }
 `;
 
-export const parameterPropertyDtoTextTranspiled = `import * as openapi from "@nestjs/swagger";
+export const parameterPropertyDtoTextTranspiled = (esmCompatible?: boolean) => {
+  let fileName = 'parameter-property.dto';
+  if (esmCompatible) {
+    fileName += getOutputExtension(fileName);
+  }
+
+  return `import * as openapi from "@nestjs/swagger";
 export class ParameterPropertyDto {
     constructor(readonlyValue, privateValue, publicValue, regularParameter, protectedValue = '1234') {
         this.readonlyValue = readonlyValue;
@@ -29,7 +37,7 @@ export class ParameterPropertyDto {
         this.protectedValue = protectedValue;
     }
     static _OPENAPI_METADATA_FACTORY() {
-        return { readonlyValue: { required: false, type: () => String }, privateValue: { required: true, type: () => String, nullable: true }, publicValue: { required: true, type: () => [require("./parameter-property.dto").ItemDto] }, protectedValue: { required: true, type: () => String, default: "1234" } };
+        return { readonlyValue: { required: false, type: () => String }, privateValue: { required: true, type: () => String, nullable: true }, publicValue: { required: true, type: () => [require("./${fileName}").ItemDto] }, protectedValue: { required: true, type: () => String, default: "1234" } };
     }
 }
 export var LettersEnum;
@@ -43,7 +51,8 @@ export class ItemDto {
         this.enumValue = enumValue;
     }
     static _OPENAPI_METADATA_FACTORY() {
-        return { enumValue: { required: true, enum: require("./parameter-property.dto").LettersEnum } };
+        return { enumValue: { required: true, enum: require("./${fileName}").LettersEnum } };
     }
 }
 `;
+};
diff --git a/test/plugin/fixtures/serialized-meta-esm.fixture.ts b/test/plugin/fixtures/serialized-meta-esm.fixture.ts
new file mode 100644
index 00000000..83e5260a
--- /dev/null
+++ b/test/plugin/fixtures/serialized-meta-esm.fixture.ts
@@ -0,0 +1,215 @@
+// @ts-nocheck
+export default async () => {
+  const t = {
+    ['./cats/dto/pagination-query.dto.js']: await import(
+      './cats/dto/pagination-query.dto.js'
+    ),
+    ['./cats/dto/create-cat.dto.js']: await import(
+      './cats/dto/create-cat.dto.js'
+    ),
+    ['./cats/dto/tag.dto.js']: await import('./cats/dto/tag.dto.js'),
+    ['./cats/classes/cat.class.js']: await import('./cats/classes/cat.class.js')
+  };
+  return {
+    '@nestjs/swagger': {
+      models: [
+        [
+          import('./cats/dto/pagination-query.dto.js'),
+          {
+            PaginationQuery: {
+              page: { required: true, type: () => Number },
+              sortBy: { required: true, type: () => [String] },
+              limit: { required: true, type: () => Number },
+              constrainedLimit: { required: false, type: () => Number },
+              enum: {
+                required: true,
+                enum: t['./cats/dto/pagination-query.dto.js'].LettersEnum
+              },
+              enumArr: {
+                required: true,
+                enum: t['./cats/dto/pagination-query.dto.js'].LettersEnum,
+                isArray: true
+              },
+              letters: {
+                required: true,
+                enum: t['./cats/dto/pagination-query.dto.js'].LettersEnum,
+                isArray: true
+              },
+              beforeDate: { required: true, type: () => Date },
+              filter: { required: true, type: () => Object }
+            }
+          }
+        ],
+        [
+          import('./cats/classes/cat.class.js'),
+          {
+            Cat: {
+              name: { required: true, type: () => String },
+              age: {
+                required: true,
+                type: () => Number,
+                description: 'The age of the Cat',
+                example: 4
+              },
+              breed: {
+                required: true,
+                type: () => String,
+                description: 'The breed of the Cat'
+              },
+              tags: { required: false, type: () => [String] },
+              createdAt: { required: true, type: () => Date },
+              urls: { required: false, type: () => [String] },
+              options: { required: false, type: () => [Object] },
+              enum: {
+                required: true,
+                enum: t['./cats/dto/pagination-query.dto.js'].LettersEnum
+              },
+              enumArr: {
+                required: true,
+                enum: t['./cats/dto/pagination-query.dto.js'].LettersEnum
+              },
+              uppercaseString: { required: true, type: () => String },
+              lowercaseString: { required: true, type: () => String },
+              capitalizeString: { required: true, type: () => String },
+              uncapitalizeString: { required: true, type: () => String }
+            }
+          }
+        ],
+        [
+          import('./cats/dto/extra-model.dto.js'),
+          {
+            ExtraModel: {
+              one: { required: true, type: () => String },
+              two: { required: true, type: () => Number }
+            }
+          }
+        ],
+        [
+          import('./cats/dto/tag.dto.js'),
+          { TagDto: { name: { required: true, type: () => String } } }
+        ],
+        [
+          import('./cats/dto/create-cat.dto.js'),
+          {
+            CreateCatDto: {
+              isIn: { required: true, type: () => String },
+              pattern: {
+                required: true,
+                type: () => String,
+                pattern: '/^[+]?abc$/'
+              },
+              positive: {
+                required: true,
+                type: () => Number,
+                default: 5,
+                minimum: 1
+              },
+              negative: {
+                required: true,
+                type: () => Number,
+                default: -1,
+                maximum: -1
+              },
+              lengthMin: {
+                required: true,
+                type: () => String,
+                nullable: true,
+                default: null,
+                minLength: 2
+              },
+              lengthMinMax: {
+                required: true,
+                type: () => String,
+                minLength: 3,
+                maxLength: 5
+              },
+              date: { required: true, type: () => Object, default: new Date() },
+              active: { required: true, type: () => Boolean, default: false },
+              name: { required: true, type: () => String },
+              age: {
+                required: true,
+                type: () => Number,
+                default: 14,
+                minimum: 1
+              },
+              breed: { required: true, type: () => String, default: 'Persian' },
+              tags: { required: false, type: () => [String] },
+              createdAt: { required: true, type: () => Date },
+              urls: { required: false, type: () => [String] },
+              options: { required: false, type: () => [Object] },
+              enum: {
+                required: true,
+                enum: t['./cats/dto/pagination-query.dto.js'].LettersEnum
+              },
+              state: {
+                required: false,
+                description: 'Available language in the application',
+                example: 'FR',
+                enum: t['./cats/dto/create-cat.dto.js'].CategoryState
+              },
+              enumArr: {
+                required: true,
+                enum: t['./cats/dto/pagination-query.dto.js'].LettersEnum
+              },
+              enumArr2: {
+                required: true,
+                enum: t['./cats/dto/pagination-query.dto.js'].LettersEnum,
+                isArray: true
+              },
+              tag: {
+                required: true,
+                type: () => t['./cats/dto/tag.dto.js'].TagDto
+              },
+              multipleTags: {
+                required: true,
+                type: () => [t['./cats/dto/tag.dto.js'].TagDto]
+              },
+              nested: {
+                required: true,
+                type: () => ({
+                  first: { required: true, type: () => String },
+                  second: { required: true, type: () => Number }
+                })
+              },
+              logger: { required: true, type: () => Object }
+            }
+          }
+        ]
+      ],
+      controllers: [
+        [
+          import('./app.controller.js'),
+          {
+            AppController: {
+              getHello: {
+                summary: 'Says hello',
+                deprecated: true,
+                type: String
+              },
+              withAliases: { type: String },
+              withColonExpress: { type: String },
+              withColonFastify: {
+                summary: 'Returns information about the application',
+                type: String
+              }
+            }
+          }
+        ],
+        [
+          import('./cats/cats.controller.js'),
+          {
+            CatsController: {
+              create: { type: t['./cats/classes/cat.class.js'].Cat },
+              findOne: { type: t['./cats/classes/cat.class.js'].Cat },
+              findAll: {},
+              createBulk: { type: t['./cats/classes/cat.class.js'].Cat },
+              createAsFormData: { type: t['./cats/classes/cat.class.js'].Cat },
+              getWithEnumParam: {},
+              getWithRandomQuery: {}
+            }
+          }
+        ]
+      ]
+    }
+  };
+};
diff --git a/test/plugin/model-class-visitor.spec.ts b/test/plugin/model-class-visitor.spec.ts
index 36dd2a71..6274333c 100644
--- a/test/plugin/model-class-visitor.spec.ts
+++ b/test/plugin/model-class-visitor.spec.ts
@@ -287,7 +287,26 @@ describe('API model properties', () => {
         ]
       }
     });
-    expect(result.outputText).toEqual(parameterPropertyDtoTextTranspiled);
+    expect(result.outputText).toEqual(parameterPropertyDtoTextTranspiled());
+
+    const esmResult = ts.transpileModule(parameterPropertyDtoText, {
+      compilerOptions: options,
+      fileName: filename,
+      transformers: {
+        before: [
+          before(
+            {
+              introspectComments: true,
+              esmCompatible: true,
+              classValidatorShim: true,
+              parameterProperties: true
+            },
+            fakeProgram
+          )
+        ]
+      }
+    });
+    expect(esmResult.outputText).toEqual(parameterPropertyDtoTextTranspiled(true));
   });
 
   it('should ignore Exclude decorator', () => {
diff --git a/test/plugin/readonly-visitor.spec.ts b/test/plugin/readonly-visitor.spec.ts
index 1331989c..f922ba38 100644
--- a/test/plugin/readonly-visitor.spec.ts
+++ b/test/plugin/readonly-visitor.spec.ts
@@ -23,6 +23,14 @@ describe('Readonly visitor', () => {
     classValidatorShim: true,
     debug: true
   });
+  const esmVisitor = new ReadonlyVisitor({
+    pathToSource: join(__dirname, 'fixtures', 'project'),
+    introspectComments: true,
+    esmCompatible: true,
+    dtoFileNameSuffix: ['.dto.ts', '.model.ts', '.class.ts'],
+    classValidatorShim: true,
+    debug: true
+  });
   const metadataPrinter = new PluginMetadataPrinter();
 
   it('should generate a serialized metadata', () => {
@@ -63,4 +71,36 @@ describe('Readonly visitor', () => {
 
     expect(result).toEqual(expectedOutput);
   });
+
+  it('should generate a serialized metadata esm', () => {
+    const tsconfigPath = join(
+      __dirname,
+      'fixtures',
+      'project',
+      'tsconfig.json'
+    );
+    const program = createTsProgram(tsconfigPath);
+
+    for (const sourceFile of program.getSourceFiles()) {
+      if (!sourceFile.isDeclarationFile) {
+        esmVisitor.visit(program, sourceFile);
+      }
+    }
+
+    const result = metadataPrinter.print(
+      {
+        [esmVisitor.key]: esmVisitor.collect()
+      },
+      esmVisitor.typeImports
+    );
+
+    const expectedOutput = readFileSync(
+      join(__dirname, 'fixtures', 'serialized-meta-esm.fixture.ts'),
+      'utf-8'
+    )
+      .replace(/\r\n/g, '\n')
+      .replace(/\r/g, '\n');
+
+    expect(result).toEqual(expectedOutput);
+  });
 });