ADR 0007 — kpubdata 버전 호환성 정책 및 핀 강화¶
- 상태: 승인됨(Accepted)
- 관련 이슈: #213, kpubdata#233
- 관련 문서: CONTRIBUTING.md §3-1, pyproject.toml
결정 (승인됨)¶
권고안을 채택한다.
pyproject.toml의 kpubdata 종속성을>=0.1.0a0에서>=0.5.0,<0.6으로 명시적으로 핀한다.- CI에 하한(lower-bound) 테스트 잡을 추가하여, 선언된 최소 버전에서 테스트 스위트가 통과하는지 강제한다.
- 호환성 정책을 문서화하여, 상위 버전(kpubdata 0.6+)에 대한 업그레이드 경로와 검증 절차를 명확히 한다.
배경¶
kpubdata-builder는 kpubdata 라이브러리의 0.5.x 시리즈 API에 의존한다:
Client.dataset(...).list— 데이터셋 메타데이터 조회RecordBatch필드 구조 — 레코드 배치의 표준화된 스키마- 기타 0.5.x 도입된 계약 메서드
그러나 pyproject.toml의 종속성 선언이 kpubdata >=0.1.0a0으로 되어 있어, 사실상 모든 버전을 허용하고 있었다. 이는 clean install 시 0.1.x~0.4.x 버전이 설치되면 런타임 에러가 발생하는 상황을 초래했다.
문제¶
- 하한 미준수: 선언된 최소 버전(0.1.0a0)이 실제 요구되는 API(0.5.x)보다 낮아, 의존성 해석 시 호환되지 않는 버전이 설치될 수 있다.
- CI 검증 부재: 하한 버전에서 테스트가 수행되지 않아, 실제 호환성이 검증되지 않았다.
- 상한 미정의: 0.6+ 버전의 호환성 정책이 확정되지 않아, 의도치 않은 주요 버전이 설치되는 것을 막지 못했다.
- 문서 누락: 종속성 핀의 의미와 업그레이드 절차가 문서화되지 않아, 기여자가 의도를 파악하기 어려웠다.
결정 필요 사항¶
- 하한 버전을 실제 필요한 API 버전(0.5.0)으로 올릴 것인가?
- 상한 버전을 둘 것인가? 둔다면 어떤 형식(직역, compatible release)인가?
- CI에서 하한 버전을 테스트할 것인가?
- 호환성 정책을 어디에 어떻게 문서화할 것인가?
검토한 대안¶
대안 A — 하한만 설정 (>=0.5.0)¶
- 장점: 명시적 하한, 유연한 상한
- 단점: 0.6+ breaking change가 자동으로 설치되어 런타임 에러 위험
대안 B — Compatible Release (~=0.5.0)¶
- 장점: PEP 440 표준, 명시적 의미(0.5.x만 허용)
- 단점: 문법이 less explicit, CI에서 하한 추출이 어려울 수 있음
대안 C — 명시적 하한/상한 (>=0.5.0,<0.6)¶
- 장점: 의도가 가장 명확, CI 스크립트에서 파싱 용이
- 단점: 상한 변경 시 수동 갱신 필요 (하지만 이는 의도된 것: 의식적 업그레이드 강제)
대안 D — 하한 테스트 방식¶
D-1. 전체 lowest-direct resolution
uv pip install --resolution=lowest-direct
pyyaml>=6.0,<7)이 하한으로 해석되어 빌드 실패
D-2. kpubdata만 하한으로 고정
uv sync --no-sources && uv pip install "kpubdata==$floor" --no-deps
권고 (제안)¶
대안 C(명시적 핀 >=0.5.0,<0.6)와 대안 D-2(CI 하한 테스트)를 조합하여 채택한다.
1. pyproject.toml 수정¶
dependencies = [
# Builder depends on the 0.5.x kpubdata API (Client.dataset(...).list, etc.).
# The old >=0.1.0a0 floor accepted any release and broke on clean installs that
# resolved an older kpubdata; pin to the 0.5 line until a compat policy lands (#213).
"kpubdata>=0.5.0,<0.6",
...
]
2. CI 하한 테스트 잡 추가 (.github/workflows/ci.yml)¶
min-deps:
name: Minimum kpubdata floor
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@...
- name: Install uv
uses: astral-sh/setup-uv@...
- name: Install dependencies (normal resolution)
run: uv sync --extra dev --no-sources
- name: Pin kpubdata to its declared floor
run: |
floor=$(sed -n 's/.*kpubdata>=\([0-9][0-9.]*\).*/\1/p' pyproject.toml | head -1)
echo "Pinning kpubdata to declared floor: $floor"
test -n "$floor" || { echo "could not extract kpubdata floor from pyproject.toml"; exit 1; }
uv pip install "kpubdata==$floor" --no-deps
- name: Run tests at the floor
run: uv run --no-sync pytest
3. 문서화 (CONTRIBUTING.md §3-1 확장)¶
- 로컬 개발과 CI/배포 환경의 의존성 해석 차이를 명시
- 핀 범위(
>=0.5.0,<0.6)의 의미와 이슈 #213 링크를 추가 - 하한 테스트 잡의 목적과 절차를 설명
영향¶
- 빌드: clean install 시 최소 0.5.0이 보장되어 런타임 에러 방지
- CI: 매 PR/merge마다 하한 버전에서 테스트가 수행되어 실제 호환성 검증
- 문서: 기여자가 종속성 정책과 업그레이드 절차를 명확히 이해
- 관련 이슈: kpubdata#233(cross-repo compatibility matrix)와 연계하여, 상위 버전 업그레이드 시 ADR 갱신 절차 확립 필요
미해결 질문¶
- kpubdata 0.6+ 호환성: 0.6이 호환 가능한 breaking change 없는 minor 업그레이드인지, 신규 ADR/테스트로 검증 후 상한을
<0.7으로 올릴 것인가? - 자동 상한 관리: pyproject.toml에서 상한을 CI/CD가 자동 갱신할 것인가? (현재는 수동 갱신으로 의도적 업그레이드 강제)
- Cross-repo compatibility matrix: kpubdata#233의 compatibility matrix가 확정되면, 이 ADR을 어떻게 연동/갱신할 것인가?
갱신 — 릴리스 매트릭스 (#832, 2026-09-30)¶
호환성은 릴리스된 버전에 대한 주장이다 (Independence Rule 11·12). 하한 하나만 돌리던
Minimum kpubdata floor 잡을 매트릭스로 넓혔다.
List supported kpubdata releases잡이scripts/kpubdata_release_matrix.py로 pyproject 의kpubdata범위와 PyPI JSON 을 읽어, 범위 안의 릴리스(yanked·pre-release 제외)를 모두 나열한다. 하한이 릴리스 목록에 없거나 목록이 비면 실패한다 — 조용히 줄어든 매트릭스는 테스트하지 않은 버전을 숨긴다.kpubdata <version>매트릭스 잡이 각 버전을--no-deps로 설치하고 설치된 버전을 확인한 뒤 전체 스위트를 돈다. 하한은 이 목록의 첫 항목이다.- 필수 검사는 여전히
CI gate하나다. 매트릭스 이름은 필수 검사가 아니므로 범위에 릴리스가 더해지거나 빠져도 branch protection 은 바뀌지 않는다. kpubdata main ↔ Builder(cross-repo-contract.yml) 는 조기 경보다. kpubdatamain은 릴리스가 아니므로 그 잡의 통과·실패는 호환성 계약의 근거가 아니다 (Rule 12). 거기서 깨진 것은 다음 릴리스 전에 고칠 신호이고, 호환성은 이 매트릭스로만 말한다.