GIS

QGIS 파이썬 콘솔: 공적 마스크 데이터 API 활용 지도화

유병혁 2020. 3. 11. 02:44

안녕하세요? 2020년 3월 10일 오후 7시부터 공공데이터 포털을 통해 '공적 마스크 데이터 API'가 개방되었습니다.

이번 글은 QGIS 파이썬 콘솔에서 공적 마스크 데이터 API를 호출하고, 이 정보를 지도화하는 과정을 정리해 보겠습니다.

 

공적 마스크 판매 현황 조회 API
https://app.swaggerhub.com/apis-docs/Promptech/public-mask-info/20200307-oas3#/

 

Build, Collaborate & Integrate APIs | SwaggerHub

 

app.swaggerhub.com

일단 이 API는 4가지 GET 방식으로 요청할 수 있습니다.

제가 이 글에서 다룰 내용은 '/storesByAddr/json'입니다. 이것은 주소(address)를 기준으로 해당 구 또는 동내에 존재하는 판매처 및 재고 상태 등의 판매 정보 제공합니다(예: '서울특별시 강남구' or '서울특별시 강남구 논현동').
※ '서울특별시' 와 같이 '시'단위만 입력하는 것은 불가능합니다.

수량 상태정보는 색상으로 표시할 경우 녹색(100개 이상) / 노랑색(30~99개) / 빨강색(2~29개) / 회색(0~1개) 준수를 안내하고 있습니다. 결과값은 JSON(JavaScript Object Notation) 형식으로 반환됩니다. 아래 코드를 보시면, count는 조회결과 수, stores 내 name은 약국이름, addr은 약국주소, lat은 위도, lng은 경도, 그리고 remain_stat이 재고상태임을 알 수 있습니다.

{
  "count": 0,
  "stores": [
    {
      "code": "string",
      "name": "string",
      "addr": "string",
      "type": "string",
      "lat": 0,
      "lng": 0,
      "stock_at": "string",
      "remain_stat": "string",
      "created_at": "string"
    }
  ]
}

 

자, 그럼 파이썬으로 이 API를 다뤄볼까요?! 먼저 필요한 모듈을 추가합니다.

GET 방식의 URL 호출을 위한 requests과 데이터 조작을 위한 pandas를 추가했습니다.

# 모듈 추가
import requests
import pandas as pd

URL에 주소(address)를 담아 GET 방식으로 데이터를 호출한 후, 결과값을 JSON으로 받았습니다.

# 공적 마스크 데이터 API
url = "https://8oi9s0nnth.apigw.ntruss.com/corona19-masks/v1/storesByAddr/json?&address=강원도 원주시 명륜동"
json_obj = requests.get(url).json()
json_obj

결과값 예시는 다음과 같습니다. '강원도 원주시 명륜동'을 조회해 보니, 총8개 약국(count)이 확인됩니다.

첫번째 판매처는 김약국으로 재고 상태는 부족(few)으로 확인됩니다. 반복문을 통해 전체 결과를 정리해 보겠습니다.

{'address': '강원도 원주시 명륜동',
 'count': 8,
 'stores': [{'addr': '강원도 원주시 남원로 671 (명륜동)',
   'code': '32801289',
   'created_at': '2020/03/10 23:55:00',
   'lat': 37.3424591,
   'lng': 127.9544838,
   'name': '김약국',
   'remain_stat': 'few',
   'stock_at': '2020/03/10 10:23:00',
   'type': '01'},

이전 코드에서 주소를 '강원도 원주시'로 변경해서 재실행한 후, 약국이름, 재고상태, 위도, 경도 값을 판다스 데이터프레임으로 정리해 봤습니다. head()를 통해 5개 행까지 데이터를 확인해 보니, 아남약국을 방문하는 게 유리할 것 같습니다.

# 100개 이상: 충분 (plenty)          * 녹색
# 100개 미만(99개~30개): 보통 (some) * 노랑색
# 30개 미만(29개~2개): 부족 (few)    * 빨강색
# 1개~0개: 없음 또는 판매전 (empty): * 회색
list = []
for store in json_obj['stores']:
    if store.get('remain_stat'):
        list.append([store['name'],store['lat'],store['lng'],store['remain_stat']])
df = pd.DataFrame(list, columns = ['name', 'lat', 'lng', 'remain_stat'])
df.head()

그 결과값을 CSV 파일로 저장해 보겠습니다.

# CSV 파일로 저장
df.to_csv('D:/GEODATA/MASK_PHAR.csv', header=True, index=False)

자, 이제 CSV 파일을 벡터 레이어로 추가합니다.

# QGIS 파이썬 콘솔
from qgis.core import QgsProject
uri = "file:///D:/GEODATA/MASK_PHAR.csv?delimiter=%s,&crs=epsg:4326&xField=%s&yField=%s" % (",", "lng", "lat")
vlayer = QgsVectorLayer(uri,'공적 마스크','delimitedtext')
QgsProject.instance().addMapLayer(vlayer)

결과는 아래와 같습니다. 스타일링을 통해 보다 직관적인 지도를 만들어볼까요?!

배경지도는 VworldBase를, 공적 마스크는 4단계(empty, few, some, plenty)로 구분한 결과입니다.