기상청 오픈 API 삽질기

Moon Works·2023년 1월 24일
7

달력에 날씨 정보 연동?

달력에 날씨 정보를 보여준다면 좀더 직관적으로 날짜 별 날씨 변화를 인지할 수 있겠다는 생각이 들었다.

이번 내용은 사이드 프로젝트공공데이터 포털 API 를 활용하여 달력에 단기 예보 보여주는 작업 진행 중 겪었던 이슈들과 해결 방안 그리고 기상청 데이터를 어떤 방식으로 데이터를 가공했는지 등의 정보를 담고 있다.

예보 API 연동 중 이슈 (or 알아야 할 점)

이슈1 - API 검색의 어려움 (검색 키워드를 잘못잡음)

공공데이터 포털에서 "날씨" 키워드 조회 시 나온 결과는 예상과 달랐다.

각 API 의 내용을 살펴 본 시간까지 합치면 적지 않은 시간을 허비했다.

휴게소별 날씨정보

원하는 검색 결과를 얻기 위해서는 "예보" 라는 키워드를 사용해야 했다. 그리고 정렬 순서를 "활용순"으로 바꾸면 실제로 많이 사용되는 순서로 예보 정보를 확인할 수 있다.

그 결과 "동네예보" 라고 알려진 기상청단기예보 ((구동네예보) 조회서비스가 가장 적합하게 여겨졌다. 실제로 많은 서비스에서 이 API 를 활용하고 있음을 확인했다.

이슈2 - 위도 경도의 x, y 좌표 변환 이슈

기상청단기예보 ((구동네예보) 조회서비스 API 는 날씨 정보를 받기 위해 x,y 좌표를 인자로 전달한다.

https://apis.data.go.kr/1360000/VilageFcstInfoService_2.0/getUltraSrtNcst?nx=x좌표&ny=y좌표&기타파라미터들추가

그런데 이 x,y 값은 위도, 경도 값이 아니다. API 페이지에서 다운로드 받을 수 있는 doc 문서를 확인해 보니 "Lambert Conformal Conic Projection" 라는 내용이 나온다. 중위도 지방의 한 대륙이나 대양 경도의 크기를 나타내는 일기도를 만드는 데 적당하고 여겨지는 좌표계라고 한다. (출처 : 월간산)

홈페이지에서 다운받을 수 있는 엑셀 문서는 주소별 x,y 좌표값 목록을 제공하고 있고 워드 문서에서는 좌표 변환 코드를 C 언어로만 제공하고 있다. 아쉽게도 JavaScript 코드는 제공하지 않았다. 아직도 많은 곳에서 C 언어가 사용되긴 하지만 좀 더 많은 언어를 제공해주었으면 좋겠다는 아쉬움이 들었다.

다행히 어떤 훌륭한 개발자 분이 변환 코드를 JavaScript 로 만들어 두셔서 바로 가져다 쓸 수 있었다. 그리고 그외 언어에 대한 변환 코드도 댓글로 추가되었다.

이슈 3 - 기상청 예보 데이터의 응답 포맷의 다름

이 기상청 단기예보 API 는 다음과 같은 정보를 제공하고 있다.

  1. 초단기실황정보: 예보 구역에 대한 대표 AWS 관측값
  2. 초단기예보: 예보시점부터 6시간 이내의 예보
  3. 단기예보: 예보기간과 구역을 시공간적으로 세분화한 예보

예보를 위한 두 API (2번, 3번)는 사용 방법이 동일하지만 응답 결과는 2가지 측면에서 다르다.

  1. 카테고리 코드 값
  2. 정렬 방식

다른 카테고리

전달되는 포맷은 동일하나 일부 카테고리의 종류가 다르다.

  • LGT(낙뢰) - 초단기 예보에만 제공
  • 같은 의미이지만 다른 카테고리 코드값
    • 1시간강수량(RN1 vs PCP)
    • 기온(TMP vs T1H)
  • PTY(강수형태) - 동일하지만 값 설명이 다소 달라보이는 경우

다른 정렬 방식

정렬방식이 다르다.

  • 초단기 예보는 카테고리 > 날짜 순 정렬
  • 단기 예보는 날짜별 > 카테고리 순 정렬

참고 내용

# getUltraSrtFcst (초단기예보)
- LGT: 낙뢰 kA(킬로암페어)
- T1H: 기온
- PTY: 강수형태 - (초단기) 없음(0), 비(1), 비/눈(2), 눈(3), 빗방울(5), 빗방울눈날림(6), 눈날림(7) 
- RN1: 1시간 강수량 mm
- SKY: 단기예보와 동일
- REH: 단기예보와 동일
- UUU: 단기예보와 동일
- VVV: 단기예보와 동일
- VEC: 단기예보와 동일
- WSD: 단기예보와 동일


# getVilageFcst (단기예보)
최대치(1000)로 요청 시 11개의 속성이 시간단위로 3일~4일간의 정보가 전달되기 때문에 600 ~ 900 개의 row 값을 갖는다.

- TMP : 1시간 기온
- UUU: 풍속(동서성분) m/s
- VVV: 풍속(남북성분) m/s
- VEC: 풍향 deg
- WSD: 풍속 m/s
- SKY: 맑음(1), 구름많음(3), 흐림(4)
- PTY: 강수형태 - (단기) 없음(0), 비(1), 비/눈(2), 눈(3), 소나기(4)
- POP: 강수확률 %
- WAV: 파고 M
- PCP: 1시간 강수량 (mm)
- REH: 습도 %
- SNO: 적설량 (cm)

나는 어떤 정보를 제공할 것인가?

드디어 기상청 날씨 정보를 제공받을 수 있는 방법과 제공되는 데이터 포맷을 이해할 수 있게 되었다.

기상청이나 네이버 날씨 처럼 정확한 세부 날씨 정보를 제공하는 것이 목적이 아니라 여러 날에 걸친 대략 적인 날씨 정보 노출을 목표로 했다. 그래서 내가 제공하는 제공하고자 하는 정보는 다음과 같았다.

  • 날짜별 최저/최고 기온
  • 눈/비가 얼마나 올지 (mm 가 높으면 확률도 높더라)
    - 이것도 최대/최소
  • 맑은지 흐린지 여부

그래서 다음 포맷으로 정리해보았다.

interface DayWeather {
  	date: string; // YYYYMMDD
	temperature: { min: number, max: number };
	rain: { min: number, max: number };
	snow: { min: number, max: number };
	sky: number; // 맑음(1), 구름많음(3), 흐림(4) 의 평균값
}

예보 데이터 중 어떤 데이터를 사용해야 할까?

  1. 초단기예보는 예보시점부터 6시간 이내의 예보를 알려주고, 여러 날에 걸친 날씨 정보는 단기예보 에서 제공하고 있다.

  2. 그리고 내가 제공하려는 정보는 다음과 같이 압축해볼 수 있었다.

  • TMP: 온도
  • SKY: 하늘
  • PTY: 강수형태
  • POP: 강수확률
  • PCP: 1시간 강수량
  • SNO: 적설량

문뜩 더 간단하게 사용할 수 있는 방법이 없는지 궁금했다. 하루에 24개로 나뉜 11개의 카테고리 정보를 3~4일 분량으로 전달해주는 정보는 700~900 (24 11 3~4) 개 수준으로 꽤 많았고 굳이 이걸 받아와서 조작하는 과정도 아끼고 싶었기 때문이다.

이런 API 가 있지 않을까?

여러 시간으로 분산된 정보를 어떻게 하나로 통합하지? 혹시 이걸 예보해주는 또 다른 API 가 있는건 아닐까?

  • 기상청 중기 예보 API
    - 예보구역코드, 발표시각의 조회 조건으로 예보일로부터 3일에서 10일까지 육상날씨정보를 조회하는 기능
    - 일 2회(06:00,18:00)회 생성 되며 발표시각을 입력. 최근 24시간 자료만 제공
    - 3일 ~ 10일 후의 정보를 제공

현재 날씨와 단기적인 조회를 하고 싶은 상황에서는 적합하지 않다.

결론적으로는 못찾았다.

시간 별 정보를 어떻게 하나로 보이지?

시간별(24시간)로 11개의 카테고리의 날씨 정보를 어떻게 하나로 압축해서 표현할 것인가?

먼저 날짜 단위로 나눈 후

  • 기온 (TMP) 은 동일 날짜에서 최저/최대
  • 강수량 (PCP), 적설량(SNO) 도 동일 날짜에서 최저/최대
  • 맑음 정도 (SKY)는 평균값을 사용하기로 했다.

이렇게 날짜 별로

[
	{
		"date":"20230124",
		"temperature":{"min":-16,"max":-13},
		"rain":{"min":0,"max":0},
		"snow":{"min":0,"max":0},
		"sky":2.2222222222222223}
	}
, ...]

날씨 아이콘 적용

위에서 결정된 날씨 변환 포맷 중 하늘(sky) 값의 평균 값에 따라 맑음, 부분흐림, 흐림의 아이콘을 결정했고, 강우(rain), 적설(snow) 의 최저 값이 1보다 크면 비, 눈 혹은 눈비 정보를 표현하고자 했다.

이를 적용할 수 있는 무료 날씨 아이콘도 매우 많았다.

난 마지막 것을 선택하여 적용하였다.

결론

결론적으로 다음과 같은 결과물을 얻었다.
오늘까지는 매우 추울 것이고 점차 온오가 올라갈 것임을 한눈에 파악할 수 있다.

그리고 날씨 정보를 이용하기 위해서는 위치 정보 API 특성상 동의가 필요한데... 이것을 항상 활성 시키면 귀찮아질 것 같아 기본적으로는 비활성화 했다.

사용하기 위해서는 필터 정보 중 날씨 필터를 추가하고 위치 정보를 동의한다.(개인정보를 수집하지 않으니 절대 안심)

이번 작업을 통해 공공데이터 포털에서 제공하는 날씨 API 를 사용해보고 날씨 아이콘으로 시각화 해볼 수 있었던 점이 재미있었다. 그리고 달력에서 날씨 정보를 제공함으로써 3~4일간의 예보를 좀더 직관적으로 인지할 수 있는 UI 를 만들어 볼 수 있어 의미있었던 경험이었다.

기타 의견

  • 초단기 예보와 단기예보의 예보 값이 다소 다르다.
    - NAVER 나 기상청에서 시간별로 보여주는 온도는 초단기 예보값과 일치한다.
  • 기상청 API 에서는 왜 굳이 변환을 하도록 해야했을까?
  • 데이터 포털에서 제공하는 API 는 문서화는 잘 되어 있는데 docs 로 제공한다. 이걸 해당 홈페이지에서 바로 확인해볼 수 있었다면 더 좋았을 것 같다는 생각이 든다.
  • 우리 나라 뿐만 아니라 세계 날씨까지 연동해 둔다면 다른 나라 사람들도 확인할 수 있어서 더 좋을 거 같다.
    - https://openweathermap.org/
    - openweathermap 이라는 api 가 있는 것 같다.
  • 지금은 초기 단계로 아직 변경될 여지가 매우 많기 때문에 혹시라도 이 API 를 이용하여 서비스에 활용하고자 한다면 말리고 싶다.
profile
계속 성장하고 싶은 개발자. 사이드프로젝트(https://www.month2k.com)

0개의 댓글