Lädt...


🔧 How to convert class to Swagger Schema in NodeJS application - Documentation with Swagger in NodeJS become easier than ever


Nachrichtenbereich: 🔧 Programmierung
🔗 Quelle: dev.to

Example that I have a DTO class that describe request body
for resgiter new user, I want to inject this class to the swagger schema

class RegisterUserRequestDto {
username!: string;

password!: string;
}

Here I will use the npm package: class-to-swagger-schema

npm i class-to-swagger-schema

The full gihub repo of this post is here: https://github.com/chabuuuu/class-to-swagger-schema/tree/main/example

First, I need to create a base schema for all request body to reuse it

//request-body-schema.ts

export const requestBodySchema = {
  type: "object",
  properties: {
    /**
     ** Add this if you want to inject your class here
     */
    injectClassHere: true,
  },
};

The base schema will have the same format of general Swagger schema in Json type.

In the example above, we add to anywhere we want to inject the Typescript class to it

In this example, the package will inject the RegisterUserRequestDto to it, the result when convert to Swagger Schema will look like this:

    components:
      schemas:
        type: "object",
            properties:
                username:
                    type: "string"
                    description: "Username of user"
                    example: "my_username_is_cool_123"
                password:
                    type: "string"
                    description: "Password of user"
                    example: "my_password_is_cool_123"

But you dont need to worry about the swagger yaml format anymore, let check below

import {
  SwaggerExample,
  SwaggerProperty,
  swaggerSchemaGenerator,
} from "class-to-swagger-schema";

const testRequestBody = swaggerSchemaGenerator.generateRequestBody(RegisterUserRequestDto);

The above will auto generate the swagger schema for you

Then you just need to map it to your swagger schema define as below

export const swaggerSchemaMapping = {

RegisterRequestBodyDto: testRequestBody,

};

//Finally, you can use the swaggerSchemaMapping to inject to the swagger schema in swagger option:

const options = {
  definition: {
    openapi: "3.1.0",
    info: {
      title: "ExpressJS Super Clean Base Source API Documentation",
      version: "0.1.0",
      description:
        "This is API application made with Express and documented with Swagger",
      license: {
        name: "MIT",
        url: "https://spdx.org/licenses/MIT.html",
      },
      contact: {
        name: "Thinh Ha",
        email: "[email protected]",
      },
    },
    servers: [],
    components: {
      schemas: swaggerSchemaMapping, //Inject the schema mapping here
    },
  },
  apis: ["./controllers/*.ts"],
};

Then, you just need to use the mapped schema normally using normal package swagger-ui-express:

export class UserController {
  /**
   * @openapi
   * /user/register:
   *   post:
   *     tags:
   *       - user
   *     summary: Register new user account
   *     description: Register new user account
   *     requestBody:
   *       required: true
   *       content:
   *         application/json:
   *           schema:
   *             $ref: '#/components/schemas/RegisterRequestBodyDto'
   */
  async registerUser(req: any, res: any, next: any) {}
}

The result will as below:

image

Class property decorator

@SwaggerProperty

This will define that the folow property in class that have this decorator will be show in Swagger schema

Usage:

class TestDto {

    @SwaggerProperty("The id of user") //This will add the description for the property when convert to swagger schema
    id!: string

    @SwaggerProperty()
    password!: string
}

@SwaggerExample

This will generate example for the folow property in swagger schema

class TestDto {

    @SwaggerProperty()
    @SwaggerExample("my_password") //This will show example as "my_password" in Swagger schema
    password!: string
}

Schema configure

Style A

swaggerSchemaGenerator.configure({
  createSuccessResponseSchema: createSuccessResponseSchema,
  deleteSuccessResponseSchema: deleteSuccessResponseSchema,
  errorResponseSchema: errorResponseSchema,
  findManyPagingResponseSchema: findManyPagingResponseSchema,
  findManyResponseSchema: findManyResponseSchema,
  findOneResponseSchema: findOneResponseSchema,
  requestBodySchema: requestBodySchema,
  updateSuccessResponseSchema: updateSuccessResponseSchema,
});

Style B

swaggerSchemaGenerator.setCreateSuccessResponseSchema(
  createSuccessResponseSchema
);
swaggerSchemaGenerator.setDeleteSuccessResponseSchema(
  deleteSuccessResponseSchema
);
swaggerSchemaGenerator.setErrorResponseSchema(errorResponseSchema);
swaggerSchemaGenerator.setFindManyPagingResponseSchema(
  findManyPagingResponseSchema
);
swaggerSchemaGenerator.setFindManyResponseSchema(findManyResponseSchema);
swaggerSchemaGenerator.setFindOneResponseSchema(findOneResponseSchema);
swaggerSchemaGenerator.setRequestBodySchema(requestBodySchema);
swaggerSchemaGenerator.setUpdateSuccessResponseSchema(
  updateSuccessResponseSchema
);

Inject property

injectClassHere

This mark that the object that this will be replace with the class you inject:

export const requestBodySchema = {
  type: "object",
  properties: {
    /**
     ** Add this if you want to inject your class here
     */
    injectClassHere: true,
  },
};

Then do this:

swaggerSchemaGenerator.setRequestBodySchema(requestBodySchema);

const testRequestBody = swaggerSchemaGenerator.generateRequestBody(
  RegisterUserRequestDto
);

/*
 value of testRequestBody =
    components:
      schemas:
        type: "object",
            properties:
                username:
                    type: "string"
                    description: "Username of user"
                    example: "my_username_is_cool_123"
                password:
                    type: "string"
                    description: "Password of user"
                    example: "my_password_is_cool_123"
*/

injectHttpStatusExample

This mark that the object that this will be replace with the class you inject:

export const errorSchema = {
  type: "object",
    httpStatus: {
      type: "integer",
      description: "HTTP status code",
      example: {
        /**
         ** Add this if you want to inject http status example here
         */
        injectHttpStatusExample: true,
      },
    },
};

Then do this:

swaggerSchemaGenerator.setErrorResponseSchema(errorSchema);


const testError = swaggerSchemaGenerator.generateErrorResponse(
  "",
  null,
  400, //The status code you want to inject
  null,
);

As a result, this will inject the status code: 400 to the

/*
 value of testError =
    components:
      schemas:
        type: "object",
            properties:
                httpStatus:
                    type: "integer"
                    description: "HTTP status code"
                    example: "400"
*/

injectHttpMessageExample

This mark that the object that this will be replace with the class you inject:

export const errorSchema = {
  type: "object",
    httpMessage: {
      type: "string",
      description: "HTTP status message",
      example: {
        /**
         ** Add this if you want to inject http message example here
         */
        injectHttpMessageExample: true,
      },
    },
};

Then do this:

swaggerSchemaGenerator.setErrorResponseSchema(errorSchema);


const testError = swaggerSchemaGenerator.generateErrorResponse(
  "",
  null,
  null,
  "Bad request", //The status message you want to inject (optional)
);

As a result, this will inject the http message: "Bad request" to the

/*
 value of testError =
    components:
      schemas:
        type: "object",
            properties:
                httpMessage:
                    type: "string"
                    description: "HTTP status message"
                    example: ""Bad request""
*/

Other schema type (totally 8 schema type)

Create success response schema

First init create success response schema:

export const createSuccessResponseSchema = {
  type: "object",
  properties: {
    httpStatus: {
      type: "integer",
      description: "HTTP status code",
      example: "201",
    },
    httpMessage: {
      type: "string",
      description: "HTTP status message",
      example: "Created",
    },
    error: {
      type: "object",
      description: "Error response",
      example: null,
    },
    data: {
      type: "object",
      description: "Data response",
      properties: {
        /**
         ** Add this if you want to inject your class here
         */
        injectClassHere: true,
      },
    },
  },
};

swaggerSchemaGenerator.setCreateSuccessResponseSchema(
  createSuccessResponseSchema
);

I have a DTO class that describe the response when register new user successfully:

class RegisterUserResponseDto {
@SwaggerProperty("Id of user")
@SwaggerExample("1562")
id!: number;

@SwaggerProperty("Username of user")
@SwaggerExample("my_user_name_is_cool_123")
username!: string;
}

Finally, convert the dto to schema:

const testCreate = swaggerSchemaGenerator.generateCreateSuccessResponse(
RegisterUserResponseDto
);

The result will as below:

image

Error schema

First, we need to create a base error schema

export const errorResponseSchema = {
  type: "object",
  properties: {
    httpStatus: {
      type: "integer",
      description: "HTTP status code",
      example: {
        /**
         ** Add this if you want to inject http status example here
         */
        injectHttpStatusExample: true,
      },
    },
    httpMessage: {
      type: "string",
      description: "HTTP status message",
      example: {
        /**
         ** Add this if you want to inject http message example here
         */
        injectHttpMessageExample: true,
      },
    },
    error: {
      type: "object",
      description: "Error response",
      properties: {
        /**
         ** Add this if you want to inject your class here
         */
        injectClassHere: true,
      },
    },
    data: {
      type: "object",
      description: "Data response",
      example: null,
    },
  },
};

Example that I want to generate schema for the error response when register new user:
User provide invalid password, http status code is 400,
custom error code is INVALID_PASSWORD_ERROR, I want to inject this error to the swagger schema

const testError = swaggerSchemaGenerator.generateErrorResponse({
  message: "Your password must be at least 10 charactors", //The error message you want to inject (required)
  code: "INVALID_PASSWORD_ERROR", //The error code you want to inject (optional)
  httpStatusCode: 400, //The status code you want to inject (optional)
  httpStatusMessage: "Bad request", //The status message you want to inject (optional)
});

Next, I need to mapping the schema above to the swagger schema

export const swaggerSchemaMapping = {
  /**
   ** POST /user/register
   */
  RegisterRequestBodyDto: testRequestBody,
  RegisterSuccessResponseDto: testCreate,
  Register_INVALID_PASSWORD_ERROR: testError,
};

The result will as below:
image

Update success response schema

Example that I want to generate schema for the update success response

Create base update success response:

export const updateSuccessResponseSchema = {
  type: "object",
  properties: {
    httpStatus: {
      type: "integer",
      description: "HTTP status code",
      example: "200",
    },
    httpMessage: {
      type: "string",
      description: "HTTP status message",
      example: "OK",
    },
    error: {
      type: "object",
      description: "Error response",
      example: null,
    },
    data: {
      type: "object",
      description: "Data response",
      properties: {
        message: {
          type: "string",
          description: "Message",
          example: "Updated successfully",
        },
      },
    },
  },
};


swaggerSchemaGenerator.setUpdateSuccessResponseSchema(
  updateSuccessResponseSchema
);

Next, convert and mapping

const testUpdate = swaggerSchemaGenerator.generateUpdateSuccessResponse();

Delete success response

Example that I want to generate schema for the delete success response

First, create delete success base schema:

export const deleteSuccessResponseSchema = {
  type: "object",
  properties: {
    httpStatus: {
      type: "integer",
      description: "HTTP status code",
      example: "200",
    },
    httpMessage: {
      type: "string",
      description: "HTTP status message",
      example: "OK",
    },
    error: {
      type: "object",
      description: "Error response",
      example: null,
    },
    data: {
      type: "object",
      description: "Data response",
      properties: {
        message: {
          type: "string",
          description: "Message",
          example: "Deleted successfully",
        },
      },
    },
  },
};

swaggerSchemaGenerator.setDeleteSuccessResponseSchema(
  deleteSuccessResponseSchema
);
const testDelete = swaggerSchemaGenerator.generateDeleteSuccessResponse();

Find one response schema

Example that I want to generate schema for the find one response

First, create base find one success response schema:

export const findOneResponseSchema = {
  type: "object",
  properties: {
    httpStatus: {
      type: "integer",
      description: "HTTP status code",
      example: "200",
    },
    httpMessage: {
      type: "string",
      description: "HTTP status message",
      example: "OK",
    },
    error: {
      type: "object",
      description: "Error response",
      example: null,
    },
    data: {
      type: "object",
      description: "Data response",
      properties: {
        /**
         ** Add this if you want to inject your class here
         */
        injectClassHere: true,
      },
    },
  },
};

swaggerSchemaGenerator.setFindOneResponseSchema(findOneResponseSchema);

Convert as folow:

class ExampleDto {
@SwaggerProperty()
example!: string;
}

const testFindOne = swaggerSchemaGenerator.generateFindOneResponse(ExampleDto);

Find many response schema

Example that I want to generate schema for the find many response

Create base find many response schema:

export const findManyResponseSchema = {
  type: "object",
  properties: {
    httpStatus: {
      type: "integer",
      description: "HTTP status code",
      example: "200",
    },
    httpMessage: {
      type: "string",
      description: "HTTP status message",
      example: "OK",
    },
    error: {
      type: "object",
      description: "Error response",
      example: null,
    },
    data: {
      type: "array",
      description: "Data response",
      items: {
        type: "object",
        properties: {
          /**
           ** Add this if you want to inject your class here
           */
          injectClassHere: true,
        },
      },
    },
  },
};

swaggerSchemaGenerator.setFindManyResponseSchema(findManyResponseSchema);

Convert as below:

class ExampleDto {
@SwaggerProperty()
example!: string;
}

const testFindMany =
swaggerSchemaGenerator.generateFindManyResponse(ExampleDto);

Find many (with paging) response schema

Example that I want to generate schema for the find many paging response

First create find many (with paging) response schema:

export const findManyPagingResponseSchema = {
  type: "object",
  properties: {
    httpStatus: {
      type: "integer",
      description: "HTTP status code",
      example: "200",
    },
    httpMessage: {
      type: "string",
      description: "HTTP status message",
      example: "OK",
    },
    error: {
      type: "object",
      description: "Error response",
      example: null,
    },
    data: {
      type: "object",
      description: "Paging response",
      properties: {
        records: {
          type: "integer",
          description: "Total records",
          example: 20,
        },
        items: {
          type: "array",
          description: "Item response",
          items: {
            type: "object",
            properties: {
              /**
               ** Add this if you want to inject your class here
               */
              injectClassHere: true,
            },
          },
        },
        pages: {
          type: "integer",
          description: "Total pages",
          example: 2,
        },
        page: {
          type: "integer",
          description: "Current page",
          example: 1,
        },
        recordFrom: {
          type: "integer",
          description: "Record from",
          example: 1,
        },
        recordTo: {
          type: "integer",
          description: "Record to",
          example: 10,
        },
      },
    },
  },
};

swaggerSchemaGenerator.setFindManyPagingResponseSchema(
  findManyPagingResponseSchema
);

Convert as below:

class ExampleDto {
@SwaggerProperty()
example!: string;
}

const testFindManyPaging =
swaggerSchemaGenerator.generateFindManyPagingResponse(ExampleDto);
...

🔧 BigQuery Schema Generation Made Easier with PyPI’s bigquery-schema-generator


📈 42.59 Punkte
🔧 Programmierung

🍏 Convert PDFs easier than ever with this software loved by users, $24.97 for life


📈 39.37 Punkte
🍏 iOS / Mac OS

🐧 Finding Your Lost Laptop Will Soon Become Easier Than Ever


📈 37.45 Punkte
🐧 Linux Tipps

🪟 Logitech's new StreamCam makes it easier than ever to become a streamer


📈 37.45 Punkte
🪟 Windows Tipps

🪟 Windows 11's Microsoft Store update will make it easier than ever to find any app you've ever installed


📈 36.41 Punkte
🪟 Windows Tipps

🔧 I made "TypeScript Swagger Editor", new type of Swagger UI writing TypeScript code in the browser


📈 33.3 Punkte
🔧 Programmierung

🔧 How Incorporating NLP Capabilities Into an Existing Application Stack Is Easier Than Ever


📈 33.26 Punkte
🔧 Programmierung

🔧 New NestJS Swagger Generator evolved than ever


📈 32.61 Punkte
🔧 Programmierung

🔧 OpenAI (LLM) Function Call Schema Generator from Swagger (OpenAPI) Document


📈 32.28 Punkte
🔧 Programmierung

🕵️ Apache Solr bis 5.2 Schema Handler schema-browser.js Cross Site Scripting


📈 31.27 Punkte
🕵️ Sicherheitslücken

🕵️ Apache Solr bis 5.2 Schema Handler schema-browser.js Cross Site Scripting


📈 31.27 Punkte
🕵️ Sicherheitslücken

🔧 Snowflake Schema vs. Star Schema: Pros, Cons, and Use Cases


📈 31.27 Punkte
🔧 Programmierung

🔧 Handling Schema Versioning and Updates in Event Streaming Platforms Without Schema Registries


📈 31.27 Punkte
🔧 Programmierung

🔧 Snowflake Schema vs. Star Schema: Pros, Cons, and Use Cases


📈 31.27 Punkte
🔧 Programmierung

🔧 schema-org-java 0.4.0 released - Java library for working with Schema.org data in JSON-LD format


📈 31.27 Punkte
🔧 Programmierung

🕵️ Added URL schema validation to prevent URL schema hijacking


📈 31.27 Punkte
🕵️ Sicherheitslücken

🕵️ Medium CVE-2020-7742: Simpl-schema project Simpl-schema


📈 31.27 Punkte
🕵️ Sicherheitslücken

🎥 Ever Wonder Why Some Websites Convert Better Than Others?


📈 28.04 Punkte
🎥 Video | Youtube

🎥 Ever Wonder Why Some Websites Convert Better Than Others?


📈 28.04 Punkte
🎥 Video | Youtube

🔧 How make a Swagger UI using postman collections in nodejs


📈 27.91 Punkte
🔧 Programmierung

📰 Severe Swagger vulnerability compromises NodeJS, PHP, Java


📈 27.91 Punkte
📰 IT Security Nachrichten

📰 Severe Swagger vulnerability compromises NodeJS, PHP, Java


📈 27.91 Punkte
📰 IT Security Nachrichten

📰 Telling the Truth About Defects in Technology Should Never, Ever, Ever Be Illegal. EVER.


📈 27.35 Punkte
📰 IT Security Nachrichten

🍏 Moovit’s New Live Location Feature Makes Urban Mobility Easier Than Ever


📈 27.29 Punkte
🍏 iOS / Mac OS

📰 EasySploit - Metasploit Automation (EASIER And FASTER Than EVER)


📈 27.29 Punkte
📰 IT Security Nachrichten

🕵️ Discovering programs is easier than ever with the new and improved Program Directory


📈 27.29 Punkte
🕵️ Hacking

📰 New machine learning algorithm breaks text CAPTCHAs easier than ever


📈 27.29 Punkte
📰 IT Security Nachrichten

💾 TorBox v.0.4.1 released — easier than ever


📈 27.29 Punkte
💾 Downloads

🐧 Valve could be working on compatibility tools to make gaming on Linux easier than ever


📈 27.29 Punkte
🐧 Linux Tipps

🕵️ Now It's Easier than Ever to Steal Someone's Keys


📈 27.29 Punkte
🕵️ Reverse Engineering

🕵️ Discovering programs is easier than ever with the new and improved Program Directory


📈 27.29 Punkte
🕵️ Hacking

🔧 Screwing Up Is Easier Than Ever Before!


📈 27.29 Punkte
🔧 Programmierung

matomo