Back-end/Spring
[JAVA/Springboot] open API 사용법(공공데이터)
Nellie Kim
2024. 4. 3. 15:09
728x90
1. OPEN API 신청
사용하고 싶은 오픈 API를 골라서 활용신청을 해준다. 나는 아래 사이트에서 영양정보를 제공하는 공공API를 사용하였다.
https://www.data.go.kr/iim/api
활용신청 클릭
활용내용은 대충 '웹사이트 개발용' 이라고 적었다.
그러면 기다릴 필요도 없이 자동 승인이 되고, 인증키를 사용할 수 있게 된다.
참고문서의 .doc 파일을 보니 아주 자세히 요청을 어떻게 하는지 나와있다.
이렇게 해도 되지만, URL마지막 부분을 type=json으로 해주면 JSON으로 반환되어 편리하다. 아래처럼 호출해주었다.
http://apis.data.go.kr/1470000/FoodNtrIrdntInfoService/getFoodNtrItdntList?ServiceKey=서비스키(URL Encode)&numOfRows=3&pageNo=1&type=json
받은 일반인증키(인코딩된것)만 넣고 그대로 주소창에 넣어보았다.
아래와 같이 잘 출력이 된다.
이제 진짜로 백엔드에 넣고 요청을 해보자.
2. 백엔드에서 사용하기
2-1. 컨트롤러
@RestController
@RequestMapping("/diet")
public class DietCtrl {
@Autowired
public DietSvc dietSvc;
// 음식 목록을 오픈 API로 조회
@GetMapping("/getFoodList")
public FoodInfoResponseDto getFoodList(@ModelAttribute FoodInfoRequestDto request) {
return dietSvc.getFoodList(request);
}
}
2-2. 서비스
@Service
public class DietSvcImpl implements DietSvc {
@Autowired
private CallApi callApi;
@Override
public FoodInfoResponseDto getFoodList(FoodInfoRequestDto request) {
return callApi.getRequest(FOOD_NUTRIENT_URL, request, FoodInfoResponseDto.class);
}
}
2-3. 호출 클래스
오픈API를 호출하는 클래스이다.
@Component
public class CallApi {
// API 호출에 필요한 인증 키
public static final String AUTH_ENCODING_KEY = "6pHHT~~~~~2FEjrQ%3D%3D";
// 식품의약품안전처_식품 영양성분 정보 API 엔드포인트 URL
public static final String FOOD_NUTRIENT_URL = "https://apis.data.go.kr/1470000/FoodNtrIrdntInfoService/getFoodNtrItdntList";
private final ObjectMapper objectMapper = new ObjectMapper();
// 호스트 이름 확인을 수행하는 OkHttpClient 생성
OkHttpClient.Builder client = new OkHttpClient.Builder().hostnameVerifier(new HostnameVerifier() {
@Override
public boolean verify(String hostname, SSLSession session) {
return true;
}
});
// GET 요청을 수행하고 결과를 객체로 반환하는 메서드
public <T, C> C getRequest(String url, T requestMap, Class<C> clazz) {
try {
// ObjectMapper 설정
ObjectMapper objectMapper = new ObjectMapper();
objectMapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
Map<String, Object> queryParams;
// 요청 맵이 맵인지 확인하여 변환
if (requestMap instanceof Map) {
queryParams = (Map<String, Object>) requestMap;
} else {
queryParams = objectMapper.convertValue(requestMap, Map.class);
}
// 쿼리 매개변수를 사용하여 URL 생성
StringBuilder urlString = new StringBuilder(url);
if (queryParams != null && !queryParams.isEmpty()) {
urlString.append("?");
for (Map.Entry<String, Object> entry : queryParams.entrySet()) {
urlString.append(entry.getKey())
.append("=")
.append(entry.getValue())
.append("&");
}
urlString.deleteCharAt(urlString.length() - 1); // 마지막 '&' 제거
}
// GET 요청 객체 생성
Request request = new Request.Builder()
.url(urlString.toString()) // 생성된 URL 문자열 사용
.get()
.addHeader("Connection", "keep-alive")
.build();
// 요청을 수행하고 응답을 받음
Response response = client.build().newCall(request).execute();
// 응답 내용을 객체로 변환하여 반환
return objectMapper.readValue(response.body().string(), clazz);
} catch (JsonProcessingException e) {
log.error("실패 - JsonProcessingException {}", e.getMessage());
return null;
} catch (IOException e) {
log.error("실패 - IOException {}", e.getMessage());
return null;
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}
백엔드 포스트맨 호출도 성공적으로 되었고,
프론트에서도 아래와 같이 요청을 했다.
성공적으로 호출이 완료되었다.
프론트에서 오픈API를 사용하여 음식 검색하는 화면을 완성했다.