๐Swagger UI ๋ผ์ด๋ธ๋ฌ๋ฆฌ ์ถ๊ฐ
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-boot-starter</artifactId>
<version>3.0.0</version>
</dependency>
๐application.yml์ ์ค์ ์ถ๊ฐ
spring:
mvc:
pathmatch:
matching-strategy: ant_path_matcher
์ ๋ ์ค์ ์ ํ๊ณ ๋๋ฉด Swagger UI๋ฅผ ์ฌ์ฉํ ์ ์๋ค.
++) application.yml์ ์ค์ ์ถ๊ฐํด์ฃผ์ง ์์ผ๋ฉด ๋ค์ ์๋ฌ๊ฐ ๋ฐ์ํ๋ค.
Failed to start bean 'documentationPluginsBootstrapper'; nested exception is java.lang.NullPointerException
๐ํ๋ก์ ํธ ๊ตฌ์กฐ
โ Swagger ์ค์ ํ์ผ - Swagger.config
package com.example.demo.config;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import springfox.documentation.builders.PathSelectors;
import springfox.documentation.builders.RequestHandlerSelectors;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.service.Contact;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spring.web.plugins.Docket;
import java.util.ArrayList;
@Configuration
public class SwaggerConfig {
// Swagger Docket ๋น์ ์์ฑํ์ฌ API ๋ฌธ์ํ ์ค์ ์ ๋ฐํ
@Bean
public Docket api() {
return new Docket(DocumentationType.SWAGGER_2)
.select()
// ๋ฌธ์ํํ ๋์ ์ปจํธ๋กค๋ฌ ํจํค์ง๋ฅผ ์ง์
.apis(
RequestHandlerSelectors.basePackage("com.example.demo.member")
.or(RequestHandlerSelectors.basePackage("com.example.demo.product"))
)
// ๋ชจ๋ ๊ฒฝ๋ก๋ฅผ ๋ฌธ์ํ ๋์์ผ๋ก ์ง์
.paths(PathSelectors.any())
.build()
// API ์ ๋ณด๋ฅผ ์ค์
.apiInfo(apiInfo("์คํ๋ง ์์
", "v1.0"));
}
// API์ ๋ํ ์ ๋ณด๋ฅผ ์ค์ ํ์ฌ ๋ฐํ
private ApiInfo apiInfo(String title, String version) {
return new ApiInfo(
title, // API์ ์ ๋ชฉ
"์คํ๋ง ๋ฌธ์ํ Swagger ์ค์ต", // API์ ์ค๋ช
version, // API์ ๋ฒ์
"http://www.a.com", // API์ ๋ํ ์ถ๊ฐ ์ ๋ณด ๋งํฌ
// API์ ๋ํ ์ฐ๋ฝ์ฒ ์ ๋ณด (์ด๋ฆ, ๋ธ๋ก๊ทธ ์ฃผ์, ์ด๋ฉ์ผ)
new Contact("๋ธ๋ก๊ทธ ์ฃผ์", "https://xoxoxoxox.tistory.com", "songyeon0607@naver.com"),
"Licenses", // API ๋ผ์ด์ ์ค
"http://b.com", // ๋ผ์ด์ ์ค์ ๋ํ ๋งํฌ
new ArrayList<>() // Vendor Extensions (๋ฒค๋ ํ์ฅ)
);
}
}
ApiInfo apiInfo() {}; API์ ๋ํ ์ ๋ณด ์ค์
- title : API ์ด๋ฆ
- version : API ๋ฒ์
RequestHandlerSelectors.basePackage(String packageName)
Swagger๋ฅผ ์ ์ฉํ ํด๋์ค์ package๋ช ์ ๋ช ์
PathSelectors.any()
ํด๋น package ํ์์ ์๋ ๋ชจ๋ url์ swagger ์ ์ฉ
๊ทธ ์ธ ํ์ผ๋ค(์ปจํธ๋กค๋ฌ์ ๋ฉ์๋์ ๋ํ ์ด๋ฆ ํธ์ง ์์ )
MemberController
package com.example.demo.member.controller;
import com.example.demo.member.model.LoginMemberReq;
import com.example.demo.member.model.SignupMemberReq;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
import javax.validation.Valid;
@RestController
@Api(value = "ํ์ ์ปจํธ๋กค๋ฌ v1", tags = "ํ์ API")
@RequestMapping("/member")
public class MemberController {
@ApiOperation(value = "๋ก๊ทธ์ธ")
@RequestMapping(method = RequestMethod.POST, value = "/login")
public ResponseEntity login(@Valid LoginMemberReq loginMemberReq) {
return ResponseEntity.ok().body("login process");
}
@ApiOperation(value = "ํ์ ๊ฐ์
")
@RequestMapping(method = RequestMethod.POST, value = "/signup")
public ResponseEntity signup(SignupMemberReq signupMemberReq) {
return ResponseEntity.ok().body("signup process");
}
}
ProductController
package com.example.demo.product.controller;
import com.example.demo.member.model.SignupMemberReq;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
@RestController
@Api(value = "์ํ ์ปจํธ๋กค๋ฌ v1", tags = "์ํ API")
@RequestMapping("/product")
public class ProductController {
@RequestMapping(method = RequestMethod.GET, value = "/list")
@ApiOperation(value = "์ํ ๋ชฉ๋ก")
public ResponseEntity list() {
return ResponseEntity.ok().body("product list");
}
}
LoginMemberReq
package com.example.demo.member.model;
import io.swagger.annotations.ApiParam;
import lombok.*;
import javax.validation.constraints.*;
@Builder
@Getter
@Setter
@NoArgsConstructor
@AllArgsConstructor
public class LoginMemberReq {
@ApiParam(value = "ํ์์ ์ด๋ฉ์ผ์ ์
๋ ฅ", required = true, example = "test01@test.com")
private String email;
@ApiParam(value = "ํ์์ ํจ์ค์๋๋ฅผ ์
๋ ฅ", required = true, example = "qwer1234")
private String password;
}
๐์คํ๊ฒฐ๊ณผ
์์ฒ๋ผ ํ๋ก์ ํธ๋ฅผ ์คํ์ํค๊ณ ์๋ url๋ก ์ ์ํ๋ฉด swagger-ui๊ฐ ๋จ๊ฒ ๋๋ค.
API ์ด๋ฆ๋ค์ ์ค์ ํด์ค ๋๋ก ์ ๋จ๋ ๊ฒ์ ํ์ธํ ์ ์๋ค.
'โก๐ฉโ๐ป โก > ยบSpring' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
[Spring] AOP(Aspect Oriented Programming) ๊ด์ ์งํฅ ํ๋ก๊ทธ๋๋ฐ (0) | 2023.12.27 |
---|---|
[Spring] JPA(Hibernate)์ ์ด์ฉํ ์ ๋ ฅ๊ฐ ๊ฒ์ฆ (0) | 2023.12.26 |
[Spring JPA] JpaRepository ์ธํฐํ์ด์ค findById() ๋ฉ์๋ ์ฌ์ฌ์ฉ (0) | 2023.12.21 |
[Spring Security] Spring Security ์ด๊ธฐ ์ค์ (0) | 2023.12.21 |
[Spring] ORM, JPA, Spring Data JPA (0) | 2023.12.21 |