Skip to main content

kpublic

한국 공공데이터포털(data.go.kr) API를 함정 없이 쓰는 파이썬 SDK.

포털에서 키를 받고 처음 API를 붙이면 거의 모두가 같은 곳에서 넘어진다. 인코딩 키를 넣어서 SERVICE_KEY_IS_NOT_REGISTERED_ERROR, JSON을 요청했는데 XML 에러가 와서 json.loads 크래시, HTTP 200인데 본문 resultCode는 실패, 데이터 없음이 items: ""로 오는 것, 기상청 격자 좌표… kpublic은 그 함정들을 코어에서 전부 처리하고, 자주 쓰는 API는 어댑터로 감싼다.

pip install kpublic
import kpublic

c = kpublic.Client("포털에서 복사한 키")   # 인코딩 키든 디코딩 키든 그대로 붙여넣으면 된다

# 어댑터 — 서울시청 지금 날씨
kma = kpublic.kma.Forecast(c)
now = kma.ultra_now(lat=37.5665, lon=126.9780)   # 격자 변환·발표시각 계산 자동
now.values            # {'T1H': 23.1, 'RN1': 0.0, 'REH': 78.0, 'PTY': 0.0, ...}
now.label("T1H")      # '기온(℃)'

# 어댑터 — 미세먼지 / 공휴일
kpublic.airkorea.AirKorea(c).by_sido("서울")[0].pm25      # 18.0  (결측 '-'는 None)
kpublic.holidays.Holidays(c).get(2026, 9)                 # [Holiday(date=2026-09-24, name='추석', ...), ...]

# 범용 — 어떤 data.go.kr API든 경로만 알면 된다
r = c.get("1360000/AsosDalyInfoService/getWthrDataList",
          dataCd="ASOS", dateCd="DAY", startDt="20260901", endDt="20260907", stnIds=108, dataType="JSON")
r.items, r.total_count

# 자동 페이징 — totalCount 보고 끝까지
for row in c.iter_items("B552584/ArpltnInfrqncyInqireSvc/getCtprvnRltmMesureDnsty",
                        sidoName="전국", returnType="json", ver="1.3", page_size=100):
    ...

코어가 대신 처리하는 것

함정 kpublic
인코딩 키(%2B…)를 넣으면 두 번 인코딩돼 30번 에러 어느 형태든 원본 키로 정규화 → 전송선엔 정확히 한 번 인코딩
실패해도 HTTP 200, 사유는 본문 resultCode 코드별 예외: ServiceKeyError(21/30/31) RateLimitError(22) UnregisteredIPError(32) InvalidParameterError(10/11) AccessDeniedError(12/20/33) ServerError(01/02/04/05/99)
JSON 요청해도 게이트웨이 에러는 XML 첫 글자 보고 자동 판별, OpenAPI_ServiceResponse/cmmMsgHeader 봉투 해석
items"" / null / 누락 / dict 하나 / list 전부 list[dict]
데이터 없음(03)이 예외인가 기본은 빈 Response(총건수 0). raise_on_nodata=TrueNoDataError
페이징 수동 iter_items()totalCount가 없어도 짧은 페이지에서 멈춤
서버 일시 장애 5xx·타임아웃·01/02/04/05/99만 지수 백오프 재시도. 22(일일 초과)·키 오류는 재시도하지 않는다 — 해봐야 소용없고 트래픽만 태운다

어댑터

모듈 API 제공
kpublic.kma 기상청 단기예보 2.0 Forecast.ultra_now / ultra_forecast / village, latlon_to_grid, grid_to_latlon, latest_base_time(발표시각 규칙)
kpublic.airkorea 에어코리아 대기오염정보 AirKorea.by_sido / by_stationAirQuality(결측 None, 등급 라벨)
kpublic.holidays 천문연 특일정보 Holidays.get(year, month=None), is_holiday(date)

어댑터가 없는 API는 Client.get(path, **params)로 그대로 부른다. 코어의 함정 처리는 똑같이 적용된다.

활용신청은 API마다 따로

키는 계정당 하나지만 API마다 활용신청을 해야 한다(대부분 자동승인). 안 하면 ServiceKeyError(30).

신청 후 확인: KPUBLIC_SERVICE_KEY=발급키 python scripts/smoke.py

검증 상태 (0.1.0, 2026-09-09)

항목 방법 결과
코어 전 경로 · 어댑터 파싱 · 격자 기준값 단위 테스트 82개, httpx.MockTransport
기상청 ultra_now (서울시청) 실서버 T1H 24.0 · REH 59 · WSD 5.0 … 8개 카테고리
에어코리아 by_sido("서울") 실서버 ✅ 측정소 40곳, "-" 결측 → None 확인
천문연 Holidays.get(2026) 실서버 (두 번째 키) ✅ 공휴일 22일
인코딩 키(%2B…) 그대로 넣기 실서버 (두 번째 키는 인코딩 형태로 입력) ✅ 정규화 후 정상 인증
게이트웨이 오류가 HTTP 400/403 + JSON 봉투로 오는 경우 실서버에서 발견 → 테스트 5개 추가 ServiceKeyError(30) / AccessDeniedError(12) 매핑
미신청 API 호출 실서버 (각 키가 미신청인 API로) ServiceKeyError(30) + 활용신청 링크 안내

키 두 개(각각 다른 API에 신청됨)로 나눠 찍어 어댑터 3종 모두 happy path를 실서버에서 확인했다.

실서버 검증에서 잡힌 것 2건: 게이트웨이 오류의 4xx 처리 순서, 에어코리아 서비스 ID 오타(ArpltnInfrqncy…ArpltnInforInqireSvc). 둘 다 단위 테스트만으로는 못 잡는 종류다.

개발

uv sync --group dev
uv run pytest
uv run ruff check . && uv run mypy src
uv build

배포

토큰 없이 PyPI Trusted Publishing으로 배포한다. pyproject.toml·__init__.py 버전을 올리고 CHANGELOG에 항목을 추가한 뒤:

git tag v0.2.0 && git push origin v0.2.0

release.yml이 태그와 버전이 일치하는지 확인하고 테스트 → 빌드 → 업로드까지 한다.

로드맵

  • 0.2 — AsyncClient(같은 코어), 응답 캐시(sqlite), 기상청 ASOS·중기예보, 한강홍수통제소
  • 0.3 — pandas/polars 변환 헬퍼, CLI

라이선스

MIT

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

kpublic-0.1.1.tar.gz (16.9 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

kpublic-0.1.1-py3-none-any.whl (22.6 kB view details)

Uploaded Python 3

File details

Details for the file kpublic-0.1.1.tar.gz.

File metadata

  • Download URL: kpublic-0.1.1.tar.gz
  • Upload date:
  • Size: 16.9 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for kpublic-0.1.1.tar.gz
Algorithm Hash digest
SHA256 599f7586c78a4b98070f02b7a2465fc6ecfa09d2d1890494057fef9baf4e883c
MD5 0abcd8ba27bf3e6e23c2aab52c84dc61
BLAKE2b-256 8a33febe63070daff76ad437cda4aa11dcbee89d033f486454248e1ecb870e5c

See more details on using hashes here.

Provenance

The following attestation bundles were made for kpublic-0.1.1.tar.gz:

Publisher: release.yml on HyaC1107/kpublic

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file kpublic-0.1.1-py3-none-any.whl.

File metadata

  • Download URL: kpublic-0.1.1-py3-none-any.whl
  • Upload date:
  • Size: 22.6 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for kpublic-0.1.1-py3-none-any.whl
Algorithm Hash digest
SHA256 39d52180de3f5fcbd355bc47b88bed38e72e292d3ccda3dd6a198063885ce591
MD5 e96d169cf3c5b8f2f5a2141d09558510
BLAKE2b-256 636bd0b4df3c35ecd9c6d27425cee475f2dae8fe100391a196a5784521c449ae

See more details on using hashes here.

Provenance

The following attestation bundles were made for kpublic-0.1.1-py3-none-any.whl:

Publisher: release.yml on HyaC1107/kpublic

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

This release

0.1.1 This release

2 files

0.1.0

2 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page