개발/Spring(Hodol)

Spring - 문서화 (Rest Docs 문서)

잇(IT) 2023. 9. 8. 00:17
728x90

- Rest Docs는 Spring MVC를 사용하는 REST API를 문서화하는데 도움을 주는 프로젝트이다.

- Restful 서비스를 문서화하는 것은 주로 해당 리소스를 설명하는 것이다. HTTP 요청과 생성되는 HTTP 응답의 세부정도이다.

 

- 빌드 구성
plugins {		// 1.
	id "org.asciidoctor.jvm.convert" version "3.3.2"
}

configurations {
	asciidoctorExt		// 2.
}

dependencies {
	asciidoctorExt 'org.springframework.restdocs:
    spring-restdocs-asciidoctor:{project-version}'		// 3. 
	testImplementation 'org.springframework.restdocs:
    spring-restdocs-mockmvc:{project-version}' 			// 4.
}

ext {		// 5.
	snippetsDir = file('build/generated-snippets')
}

test { 		// 6.
	outputs.dir snippetsDir
}

asciidoctor { 		// 7.
	inputs.dir snippetsDir 		// 8.
	configurations 'asciidoctorExt' 		// 9.
	dependsOn test 			// 10.
}

1. Asciidoctor 플러그인을 적용한다.

2. Asciidoctor를 확장하는 종속성에 대한 구성을 선언한다. asciidoctorExt

3. spring-restdocs-asciidoctor 구성에 asciidoctorExt. 종속성을 추가한다. 그러면 파일 snippets에서 사용할 속성이 .adoc을 가리키도록 자동으로 구성이 된다. / build/generated-snippets 또한 블록 매크로를 사용할 수도 있다.

4. spring-restdocs-mockmvc 구성에 종속성을 추가한다. testImplementation. MockMvc 대신 REST Assured를 사용하려면 대신에 또는 각각에 WebTestClient 대한 종속성을 추가해야 한다. spring-restdocs-webtestclient spring-restdocs-restassured

5. 생성된 조각의 출력 위치를 정의하는 속성을 구성한다.

6. test 코드 조각 디렉터리를 출력으로 추가하도록 작업을 구성한다.

7. 작업을 구성한다. asciidoctor

8. 코드 조각 디렉터리를 입력으로 구성한다.

9. 확장에 대한 구성 사용을 구성한다. asciidoctorExt

10. 문서가 생성되기 전에 테스트가 실행되도록 작업을 테스트 작업에 종속되게 만든다.

 

- 문서 패키징

- 생성된 문서를 프로젝트의 jar 파일에 패키징 할 수 있다. 

1. jar가 빌드되기 전에 문서가 생성된다.

2. 생성된 문서는 jar에 포함되어 있다.

bootJar {
	dependsOn asciidoctor 
	from ("${asciidoctor.outputDir}/html5") { 
		into 'static/docs'
	}
}

1. jar를 빌드하기 전에 문서가 생성되었는지 확인해야한다.

2. 생성된 문서를 jar static/docs 디렉터리에 복사한다.

 

- JUnit5 테스트 설정

- JUnit5를 사용할 때 문서 조각을 생성하는 첫 번째 단계는 RestDocumentationExtension 테스트 클래스에 적용하는 것이다.

@ExtendWith(RestDocumentationExtension.class)
public class JUnit5ExampleTests

 

- RestDocumentationExtension 프로젝트의 빌드 도구를 기반으로 하는 출력 디렉터리로 자동 구성된다.

빌드 도구 출력 디렉토리
Gradle build/generated-snippets

 

- RESTful 서비스 호출

- 테스트 프레임워크를 구성했으므로 이를 사용하여 RESTful 서비스를 호출하고 요청 및 응답을 문서화할 수 있다.

mockMvc.perform(get("/").accept(MediaType.APPLICATION_JSON))		// 1.
	.andExpect(status().isOk())			// 2.
    .andDo(document("index"));			// 3.

1. / 서비스의 루트()를 호출하고, application/json 응답이 필요함을 나타낸다.

2. 서비스가 예상한 응답을 생성했는지 확인한다.

3. 서비스 호출을 문서화하여 이름이 지정된 이렉터리 index(구성된 출력 디렉터리 아래에 있음)에 코드 조각을 작성한다. 스니펫은 RestDocumentationResultHandler.document의 정적 메서드에서 이 클래스의 인스턴스를 얻을 수 있다.

org.springframework.restdocs.mockMvc.MockMvcRestDocumentation

 

- 기본적으로 6개의 스니펫이 작성된다.

<output-directory>/index/curl-request.adoc

<output-directory>/index/http-request.adoc

<output-directory>/index/http-response.adoc

<output-directory>/index/httpie-request.adoc

<output-directory>/index/request-body.adoc

<output-directory>/index/response-body.adoc

 

- 스니펫 사용

- 생성된 스니펫을 사용하기 전에 소스 파일을 생성해야 한다. .adoc 접미사가 있으면 파일 이름을 원하는 대로 지정할 수 있다. .adoc 겨로가 HTML 파일은 이름은 동일하지만 접미사가 있다. .html 소스 파일과 결과 HTML 파일의 기본 위치는 

빌드 도구 소스 파일 생성된 파일
Gradle src/docs/asciidoc/*.adoc build/asciidoc/html5/*.html

위와 같다.

- 그 다음 수동으로 생성된 Asciidoc 파일에 생성된 조각을 포함할 수 있다. 코드 조각 출력 디렉터리를 참조하기 위해 빌드 구성에서 snippets 자동으로 설정되는 속성을 사용할 수 있다. 

include::{snippets}/index/curl-request.adoc[]

 

- 요청 및 응답 페이로드

- 기본적으로 Spring REST Docs는 요청 본문과 응답 본문에 대한 스니펫을 자동으로 생성한다. 이러한 조각에는 각각 request-body.adoc 및 이름이 지정된다. response-body.adoc

 

- 요청 및 응답 필드

{
	"contact": {
		"name": "Jane Doe",
		"email": "jane.doe@example.com"
	}
}
this.mockMvc.perform(get("/user/5").accept(MediaType.APPLICATION_JSON)).andExpect(status().isOk())
		.andDo(document("index", responseFields(
        // 1.
				fieldWithPath("contact.email").description("The user's email address"),
                // 2.
				fieldWithPath("contact.name").description("The user's name"))));
                // 3.

1. 응답 페이로드의 필드를 설명하는 조각을 생성하도록 Spring REST 문서를 구성한다. 요청, 응답을 문서화하려면 requestFields, responseFields를 사용한다.

org.springframework.restdocs.payload.PayloadDocumentation

2. path가 있는 필드를 기대한다. contact.email -> fieldWithPath에서 정적 메서드를 사용한다.

 

- 결과는 필드를 설명하는 테이블이 포함된 조각이다. 요청과 응답의 스니펫의 이름은 각각 request-fields.adoc / response-fields.adoc이다.

- 필드를 문서화할 때 문서화되지 않은 필드가 페이로드에 있으면 테스트가 실패한다. 마찬가지로 문서화된 필드가 페이로드에서 발견되지 않고 해당 필드가 선택 사항으로 표시되지 않은 경우에도 테스트가 실패한다.

 

- 경로 매개변수

- 경로 매개변수를 사용하여 요청의 경로 매개변수를 문서화할 수 있다. pathParameters를 사용하면 된다.

this.mockMvc.perform(get("/locations/{latitude}/{longitude}", 51.5072, 0.1275)) 
//1.
		.andExpect(status().isOk()).andDo(document("locations", pathParameters(
        //2.
				parameterWithName("latitude").description("The location's latitude"), 
                //3.
				parameterWithName("longitude").description("The location's longitude") 
                //4.
		)));

1. GET 두 개의 경로 매개변수 latitude, longtitue를 사용하여 요청을 수행한다.

2. 요청의 경로 매개변수를 설명하는 조각을 생성하도록 Spring REST Docs를 구성한다. pathParameters에서 정적 메서드를 사용한다.

org.springframework.restdocs.request.RequestDocumentation

3. latitude라는 매개변수를 문서화한다. parameterWithName 메서드를 사용한다.

4. longitude라는 매개변수를 문서화한다. parameterWithName 메서드를 사용한다.

- 결과는 path-paramter.adoc 리소스에서 지원하는 경로 매개변수를 설명하는 테이블이 포함된 조각이다.

 

- 추가 정보 포함

- 생성된 코드 조각에 포함할 추가 정보를 제공하는 방법에는 두 가지가 있다.

1. 설명자에 메서드를 사용하여 attributes 하나 이상의 속성을 추가한다.

2. curlRequest, httpRequest, httpResponse 등을 호출할 때, 일부 속성을 전달한다. 이러한 속성은 전체적으로 스니펫과 연관되어 있다.

- 추가 속성은 템플릿 렌더링 프로세스 중에 사용할 수 있다. 사용자 정의 스니펫 템플릿과 결합하면 생성된 스니펫에 추가 정보를 포함할 수 있다.

- 요청 필드를 문서화할 때 제약 조건 열과 제목을 추가하는 것이다. 첫 번째 단계는 constranints 문서화하는 각 필드에 속성을 제공하고 title 속성을 제공하는 것이다.

.andDo(document("create-user", requestFields(attributes(key("title").
value("Fields for user creation")),
//1.
		fieldWithPath("name").description("The user's name")
				.attributes(key("constraints").value("Must not be null. Must not be empty")), 
                //2.
		fieldWithPath("email").description("The user's email address")
				.attributes(key("constraints").value("Must be a valid email address")))));
                //3.

1. title 요청 필드 조각에 대한 속성을 구성한다.

2. constraints 필드의 속성을 설정한다. -> name

3. constraints 필드의 속성을 설정한다. -> email

 

- request-fields.snippet 두 번째 단계는 생성된 코드 조각 테이블의 필드 제약 조건에 대한 정보를 포함하고 제목을 추가하는 사용자 정의 템플릿을 제공하는 것이다.

.{{title}}		//1.
|===
|Path|Type|Description|Constraints 		//2.

{{#fields}}
|{{path}}
|{{type}}
|{{description}}
|{{constraints}} 		//3.

{{/fields}}
|===

1. 테이블에 제목을 추가한다.

2. "Constraints"이라는 새 열을 추가한다.

3. contraints 테이블의 각 행에 설명자의 속성을 포함한다.

728x90