스프링 부트에서 파이썬 서버에 HTTP POST 요청을 하여 데이터를 받아와야한다.
방법을 찾아본 결과 스프링에서 지원하는 RestTemplate
이라는 내장 클래스를 알게되었다.
RestTemplate을 공부하고 나중에 알게되었는데, Spring Framework 5 이후부터 RestTemplate이 Deprecated 될 예정이다. 대신에 WebClient라는 새로운 방식을 지원한다.
RestTemplate
에는 다양한 지원 메서드가 있는데 그 중 postForEntity
에 대해서만 작성하겠다.
postForEntity
는 POST 방식 요청 결과를 ResponseEntity 타입으로 반환받는다.
코드는 다음과 같다.
// HTTP 요청을 보낼 URL을 설정한다.
String url = "http://localhost:8000/audios/sentence";
// RestTemplate 객체를 생성한다.
RestTemplate restTemplate = new RestTemplate();
// header 설정을 위해 HttpHeaders 객체를 생성하고, JSON 형태로 보낼 것이므로
// MediaType.APPLICATION_JSON으로 설정한다.
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_JSON);
// dependency에 JSONObject를 추가해주고 바디에 들어갈 정보들을 추가해준다.
JSONObject jsonObject = new JSONObject();
jsonObject.put("username", request.getUsername());
jsonObject.put("text", sentences);
jsonObject.put("narration", request.getNarration());
// URL과 header를 HttpEntity 객체에 추가해준다.
HttpEntity<String> requestMessage = new HttpEntity<>(jsonObject.toString(), headers);
// 요청을 보내고 응답을 받으면 ResponseEntity 타입으로 받게된다.
// 응답 데이터를 넣을 타입을 지정할 수 있다.
ResponseEntity<PythonServerDto.CreateAudioResponse> responseEntity
= restTemplate.postForEntity(url, requestMessage, PythonServerDto.CreateAudioResponse.class);
// getBody()로 바디에 있는 데이터를 가져올 수 있다.
PythonServerDto.CreateAudioResponse response = responseEntity.getBody();
위 코드와 같이 url과 헤더를 설정한 다음 HttpEntity
를 통해 요청 메시지를 만들고, 요청을 보내면 파이썬 서버에서 데이터를 받을 수 있다.
그리고 파이썬 서버에서 데이터를 JSON 형태로 보내준다하면 우리는 특정 DTO를 만들어서 필드에 주입받을 수 있다.
다음은 파이썬에서 받는 데이터 형식이다.
{
"status": "success",
"url": [
{
"sentence": "안녕하세요.",
"url": "jeongsu/e7b99419.wav"
},
{
"sentence": "이정수입니다.",
"url": "jeongsu/d6673881.wav"
},
{
"sentence": "잘부탁드립니다.",
"url": "jeongsu/d27644ad.wav"
}
]
}
위와 같은 형식으로 파이썬 서버에서 데이터를 보내주기 때문에 DTO를 변수명 하나하나 똑같이 해주었다.
@Getter
@NoArgsConstructor
@Builder
public static class CreateAudioResponse {
private String status;
private List<SentenceAndUrl> url;
}
@Getter
@NoArgsConstructor
@Builder
public static class SentenceAndUrl {
private String sentence;
private String url;
}
DTO를 만들어서 받을 때 주의할 점이 있다.
처음 DTO를 만들 때, @NoArgsConstructor
를 붙이지 않고 통신을 하였다.
파이썬 서버에서는 200이 떳는데 스프링 부트에서는 cannot deserialize from Object value
에러가 발생하였다.
그래서 이 에러의 원인을 찾아보니 jackson library
가 빈 생성자가 없는 모델을 생성하는 방법을 모른다고 스택오버플로우에 적혀있었다. 그래서 @NoArgsConstructor
를 붙여주니 바로 성공해버렸다!