Swagger-core: ์ธ๋ผ์ธ ์‘๋‹ต์— ์ฃผ์„์„ ์ถ”๊ฐ€ํ•˜๋Š” ๋ฐฉ๋ฒ•์€ ๋ฌด์—‡์ž…๋‹ˆ๊นŒ?

์— ๋งŒ๋“  2019๋…„ 11์›” 25์ผ  ยท  4์ฝ”๋ฉ˜ํŠธ  ยท  ์ถœ์ฒ˜: swagger-api/swagger-core

springdoc-openapi๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋‚ด ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์€ ์ปจํŠธ๋กค๋Ÿฌ ๋ฐ ๋ชจ๋ธ์˜ Swagger 3 ์ฃผ์„์„ ๊ธฐ๋ฐ˜์œผ๋กœ OAS3 yaml ์‚ฌ์–‘์„ ์ƒ์„ฑํ•ฉ๋‹ˆ๋‹ค.

๋‚ด๊ฐ€ ๋‹ฌ์„ฑํ•˜๊ณ  ์‹ถ์€ ๊ฒƒ์€ ์ธ๋ผ์ธ ์ž‘์—… ์‘๋‹ต์„ ๊ฐ–๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ด ๊ฐ™์€:

paths:
  /myoperation:
    get:
      ...
      responses:
        '200':
          content:
            application/json:
              schema:
                required:
                  - count
                  - results
                type: object
                properties:
                  count:
                    type: integer
                  results:
                    type: array
            ...

์ปจํŠธ๋กค๋Ÿฌ ํด๋ž˜์Šค์˜ ์ž‘์—… ๋ฉ”์„œ๋“œ ์ฃผ์„์€ ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค.

@ApiResponse(responseCode = "200",
             description = "OK",
             content = @Content(mediaType = "application/json", schema = @Schema(implementation = MyResponseDTO.class, requiredProperties = { "count", "results"} ))

๋ฐ MyResponseDTO:

public class MyResponseDTO {

    @Schema(required = true, description = "")
    private long count;

    @ArraySchema(schema = @Schema(implementation = MyModel.class))
    private List<DTO> results;

    ... getters/setters

}

๊ทธ ๊ฒฐ๊ณผ ๋‹ค์Œ๊ณผ ๊ฐ™์€ ์Šคํ‚ค๋งˆ๊ฐ€ ์ƒ์„ฑ๋ฉ๋‹ˆ๋‹ค.

...
      responses:
        200:
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MyResponseDTO'

...
components:
    MyResponseDTO:
      required:
      - count
      type: object
      properties:
        count:
          type: integer
          format: int64
        results:
          type: array
          items:
            $ref: '#/components/schemas/MyModel'

์‘๋‹ต ๋‚ด์šฉ์€ ์ธ๋ผ์ธ ๊ฐœ์ฒด๊ฐ€ ์•„๋‹Œ ์ฐธ์กฐ์ž…๋‹ˆ๋‹ค. ๋ฌธ์„œ์— ์ธ๋ผ์ธ์œผ๋กœ ํ‘œ์‹œ๋˜๋„๋ก ์‘๋‹ต/์Šคํ‚ค๋งˆ์— ์ฃผ์„์„ ๋‹ฌ ์ˆ˜ ์žˆ๋Š” ๋ฐฉ๋ฒ•์ด ์žˆ์Šต๋‹ˆ๊นŒ?

๋‚˜๋Š” ์ด๋ฏธ ์ด ์งˆ๋ฌธ์„ springdoc-openapi์— ๋Œ€ํ•œ ๋ฌธ์ œ ๋กœ ๊ฒŒ์‹œํ–ˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋Ÿฌ๋‚˜ ๊ทธ๋“ค์€ ๋‚˜์—๊ฒŒ ์—ฌ๊ธฐ์— ์งˆ๋ฌธ์„ ํ•˜๋ผ๊ณ  ์กฐ์–ธํ–ˆ์Šต๋‹ˆ๋‹ค.

์—ฌ๊ธฐ ๋ˆ„๊ตฐ๊ฐ€๊ฐ€ ๋‚˜๋ฅผ ๋„์šธ ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ? ๊ฐ์‚ฌ ํ•ด์š”!

๋ผ๋ชฌ ๋ก์Šค

๊ฐ€์žฅ ์œ ์šฉํ•œ ๋Œ“๊ธ€

์•Œ๊ฒ ์Šต๋‹ˆ๋‹ค. ์ œ์•ˆํ•ด ์ฃผ์…”์„œ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค. ์ˆ˜๋™ ์„ค๋ช…์„ ์‹œ๋„ํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.
์•„๋งˆ๋„ ๋ฏธ๋ž˜์—๋Š” @Schema ์ฃผ์„์— ๋Œ€ํ•œ ์ถ”๊ฐ€ inline=true|false ์š”์†Œ๊ฐ€ ์ข‹์„ ๊ฒƒ์ž…๋‹ˆ๋‹ค.

๋ชจ๋“  4 ๋Œ“๊ธ€

๋‚˜๋Š” ์šฐ๋ฆฌ๊ฐ€ ๊ทธ๋ ‡๊ฒŒ ํ•  ๋ฐฉ๋ฒ•์ด ์—†๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค(๊ทธ๋Ÿฌ๋‚˜ @frantuma ๊ฐ€ ๋‚˜๋ฅผ

์ธ๋ผ์ธ ์ •์˜๋ฅผ ์ฐพ๋Š” ์ด์œ ๋Š” ๋ฌด์—‡์ž…๋‹ˆ๊นŒ? ์ผ๋ฐ˜์ ์œผ๋กœ ์ฐธ์กฐ๋œ ์ •์˜๋Š” ๊ด€๋ฆฌํ•˜๊ธฐ ์‰ฝ์ง€๋งŒ ์‚ฌ์šฉ ์‚ฌ๋ก€๋ฅผ ์ดํ•ดํ•˜๊ณ  ์‹ถ์Šต๋‹ˆ๋‹ค.

ํƒ€์‚ฌ์—์„œ ์šฐ๋ฆฌ ์ œํ’ˆ์ด ๊ตฌํ˜„ํ•ด์•ผ ํ•˜๋Š” OAS3 ์ธํ„ฐํŽ˜์ด์Šค๋ฅผ ์ง€์ •ํ–ˆ์Šต๋‹ˆ๋‹ค. ์ธํ„ฐํŽ˜์ด์Šค ๋ฌธ์„œ(yaml)์—๋Š” ์ธ๋ผ์ธ ์ž‘์—… ์‘๋‹ต์ด ํฌํ•จ๋˜์–ด ์žˆ์Šต๋‹ˆ๋‹ค.
์š”๊ตฌ ์‚ฌํ•ญ ์ค‘ ํ•˜๋‚˜๋Š” ๋™์ผํ•œ ๋ฌธ์„œ๋ฅผ ์ œ๊ณตํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ฆ‰, ์ œ 3์ž๊ฐ€ ์ œ๊ณตํ•œ ๊ฒƒ๊ณผ ๋˜‘๊ฐ™์€ ๋ฌธ์„œ๋ฅผ ์ƒ์„ฑํ•˜๊ธฐ ์œ„ํ•ด Spring ์ปจํŠธ๋กค๋Ÿฌ/๋ชจ๋ธ์— ์ฃผ์„์„ ๋‹ฌ๋ ค๊ณ  ํ•ฉ๋‹ˆ๋‹ค.
๋”ฐ๋ผ์„œ ์ธ๋ผ์ธ ์‘๋‹ต์„ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์€ ๊ฐœ์ธ์ ์ธ ์„ ํƒ์ด ์•„๋‹ˆ๋ผ ๊ทœ์ •๋œ ๊ฒƒ์ž…๋‹ˆ๋‹ค.

์•Œ์•˜์–ด์š”. ๊ทธ๋ž˜์„œ ์ง€๊ธˆ ๋‹น์žฅ์€ ์ด๊ฒƒ์„ ํ•˜๋Š” ๊ฐ„๋‹จํ•œ ๋ฐฉ๋ฒ•์ด ์—†์Šต๋‹ˆ๋‹ค. @Schema ์ฃผ์„ ๋‚ด๋ถ€์— ์Šคํ‚ค๋งˆ๋ฅผ ์ˆ˜๋™์œผ๋กœ _์ˆ˜_ํ•  ์ˆ˜ ์žˆ์ง€๋งŒ, ๊ทธ๊ฒƒ์ด ํฌ๊ณ  ๋ณต์žกํ•œ ํด๋ž˜์Šค๋ผ๋ฉด ๊ณ ํ†ต์Šค๋Ÿฌ์šธ ๊ฒƒ์ž…๋‹ˆ๋‹ค.

๋” ์ž๋™ํ™”ํ•˜๋ ค๋ฉด ์ธ๋ผ์ธ์ด์–ด์•ผ ํ•œ๋‹ค๋Š” ๋˜ ๋‹ค๋ฅธ ์ฃผ์„์„ ๋งŒ๋“ค๊ณ  Reader๋ฅผ ํ™•์žฅํ•˜์—ฌ ๊ทธ๋Ÿฐ ๋ฐฉ์‹์œผ๋กœ ์ฒ˜๋ฆฌํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์•Œ๊ฒ ์Šต๋‹ˆ๋‹ค. ์ œ์•ˆํ•ด ์ฃผ์…”์„œ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค. ์ˆ˜๋™ ์„ค๋ช…์„ ์‹œ๋„ํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.
์•„๋งˆ๋„ ๋ฏธ๋ž˜์—๋Š” @Schema ์ฃผ์„์— ๋Œ€ํ•œ ์ถ”๊ฐ€ inline=true|false ์š”์†Œ๊ฐ€ ์ข‹์„ ๊ฒƒ์ž…๋‹ˆ๋‹ค.

์ด ํŽ˜์ด์ง€๊ฐ€ ๋„์›€์ด ๋˜์—ˆ๋‚˜์š”?
0 / 5 - 0 ๋“ฑ๊ธ‰