HBase 버전 번호와 호환성

HBase 버전 번호와 호환성

HBase는 1.0.0 릴리스부터 시맨틱 버저닝을 지향해요. 이 문서는 HBase의 버저닝 방식과 다양한 호환성 차원(와이어 프로토콜, 파일 형식, 클라이언트 API, 바이너리 등)이 어떻게 보장되는지 설명해요. 업그레이드나 버전 선택 전에 이 정책을 이해하면 훨씬 안전해요.

출처: 문서

본문

지향하는 시맨틱 버저닝

1.0.0 릴리스부터 HBase는 릴리스 버저닝에 시맨틱 버저닝을 적용하기 위해 노력하고 있어요. 요약하면:

버전 번호 MAJOR.MINOR.PATCH가 주어졌을 때, 다음을 올려:

  • 호환되지 않는 API 변경을 만들 때는 MAJOR 버전,
  • 하위 호환되는 방식으로 기능을 추가할 때는 MINOR 버전,
  • 하위 호환되는 버그 수정을 할 때는 PATCH 버전.
  • 사전 릴리스(pre-release)와 빌드 메타데이터를 위한 추가 레이블은 MAJOR.MINOR.PATCH 형식의 확장으로 사용할 수 있어요.

호환성 차원

일반적인 API 버저닝 고려사항 외에도 HBase는 고려해야 할 다른 호환성 차원들이 있어요.

클라이언트-서버 와이어 프로토콜 호환성

  • 클라이언트와 서버를 비동기적으로 업데이트할 수 있게 해 줘요.
  • 서버를 먼저 업그레이드하는 것만 허용할 수도 있어요. 즉 서버가 이전 클라이언트에 대해 하위 호환되도록 해서 새 API가 문제없도록 하는 방식이에요.
  • 예시: 사용자가 업그레이드된 클러스터에 이전 클라이언트로 연결할 수 있어야 해요.

서버-서버 프로토콜 호환성

  • 다른 버전의 서버가 같은 클러스터에 공존할 수 있어요.
  • 서버 간 와이어 프로토콜이 호환돼요.
  • 복제(replication)와 로그 분할(log splitting) 같은 분산 작업의 워커가 같은 클러스터에 공존할 수 있어요.
  • (ZK를 사용한 조정 같은) 의존 프로토콜도 변경되지 않아요.
  • 예시: 사용자가 롤링 업그레이드를 수행할 수 있어요.

파일 형식 호환성

  • 하위·상위 호환되는 파일 형식을 지원해요.
  • 예시: 파일, ZK 인코딩, 디렉터리 레이아웃이 HBase 업그레이드의 일부로 자동 업그레이드돼요. 사용자는 이전 버전으로 다운그레이드할 수 있고 모든 것이 계속 동작해요.

클라이언트 API 호환성

  • 기존 클라이언트 API를 변경하거나 제거하는 것을 허용해요.
  • API는 변경/제거 전에 한 메이저 버전 전체에 걸쳐 deprecated 되어야 해요.
    • 예시: 2.0.1에서 deprecated된 API는 4.0.0에서 삭제 표시될 거예요. 반면 2.0.0에서 deprecated된 API는 3.0.0에서 제거될 수 있어요.
    • 가끔 실수가 있어서 내부 클래스가 필요한 것보다 높은 접근 수준으로 표시되기도 해요. 이런 드문 경우에는 deprecation 일정을 다음 메이저 버전으로 앞당길 거예요(즉 2.2.x에서 deprecated하고 3.0.0에서 IA.Private로 표시). 이러한 변경은 Jira의 릴리스 노트를 통해 전달되고 설명돼요.
  • 패치 버전에서 사용할 수 있는 API는 이후의 모든 패치 버전에서도 사용할 수 있어요. 단, 더 이른 패치 버전에서 사용할 수 없는 새 API가 추가될 수는 있어요.
  • 패치 버전에서 도입된 새 API는 소스 호환 방식으로만 추가돼요. 즉 공용 API를 구현하는 코드는 계속 컴파일돼요. 1
    • 예시: 새로 deprecated된 API를 사용하는 사용자는 다음 메이저 버전까지 HBase API 호출이 있는 애플리케이션 코드를 수정할 필요가 없어요. *

클라이언트 바이너리 호환성

  • 특정 패치 릴리스에서 사용 가능한 API에 대해 작성된 클라이언트 코드는 이후 패치 버전의 새 jar에 대해 (재컴파일 없이) 그대로 실행될 수 있어요.
  • 특정 패치 릴리스에서 사용 가능한 API에 대해 작성된 클라이언트 코드는 이전 패치 버전의 옛 jar에서는 실행되지 않을 수 있어요.
    • 예시: 옛 컴파일 클라이언트 코드는 새 jar로 그대로 동작할 거예요.
  • 클라이언트가 HBase 인터페이스를 구현한다면, 더 새로운 마이너 버전으로 업그레이드할 때 재컴파일이 필요할 수 있어요(호환되지 않는 변경에 대한 경고는 릴리스 노트를 참고). 기본 구현을 제공해서 이런 경우가 발생하지 않도록 최선을 다할 거예요.

서버 측 제한 API 호환성 (Hadoop에서 가져옴)

  • 내부 API는 Stable, Evolving, Unstable로 표시돼요.
  • 이는 coprocessor와 플러그인(복제를 포함한 플러그 가능한 클래스)이 표시된 인터페이스/클래스만 사용하는 한 바이너리 호환을 의미해요.
  • 예시: 옛 컴파일 Coprocessor, Filter, Plugin 코드는 새 jar로 그대로 동작할 거예요.

의존성 호환성

  • Apache Hadoop을 제외하고, HBase 업그레이드가 의존 프로젝트의 호환되지 않는 업그레이드를 요구하지 않아요.
  • HBase 업그레이드가 Java 런타임의 호환되지 않는 업그레이드를 요구하지 않아요.
  • 예시: Dependency Compatibility를 지원하는 버전으로 HBase를 업그레이드해도 Apache ZooKeeper 서비스를 업그레이드할 필요가 없어요.
  • 예시: 현재 HBase 버전이 JDK 8에서 실행을 지원했다면, Dependency Compatibility를 지원하는 버전으로 업그레이드해도 JDK 8에서 실행돼요.

이전에는 기본 Hadoop 서비스에 대한 의존성 호환성을 유지하려고 노력했지만, 지난 몇 년 동안 그것이 지속 불가능함이 드러났어요. HBase 프로젝트는 이전 버전의 Hadoop에 대한 지원을 유지하려 노력하지만, 더 이상 릴리스를 내지 않는 마이너 버전에 대해서는 "지원됨(supported)" 지정을 내려놓아요. 또한 Hadoop 프로젝트는 자체 호환성 지침이 있어서, 어떤 경우에는 더 새로운 지원 마이너 릴리스로 업데이트해야 할 수도 있고 이는 우리의 호환성 약속 중 일부를 깨뜨릴 수 있어요.

운영 호환성

  • 메트릭 변경
  • 서비스의 동작 변경
  • /jmx/ 엔드포인트를 통해 노출되는 JMX API

요약

  • 패치 업그레이드는 그냥 교체(drop-in replacement)예요. Java 바이너리 및 소스 호환이 아닌 변경은 허용되지 않아요. 2 패치 릴리스 내에서 버전을 다운그레이드하는 것은 호환되지 않을 수 있어요.
  • 마이너 업그레이드는 애플리케이션/클라이언트 코드 수정이 필요 없어요. 이상적으로는 그냥 교체 가능하지만, 새 jar를 사용하면 클라이언트 코드, coprocessor, filter 등은 재컴파일해야 할 수도 있어요.
  • 메이저 업그레이드는 HBase 커뮤니티가 파괴적인 변경을 할 수 있게 해 줘요.

호환성 매트릭스:

이 표는 무엇이 깨질 수 있는지를 나타내는 것이지, 반드시 깨진다는 뜻은 아니에요. 구체적인 내용은 릴리스 노트에 추가할 거예요.

Major Minor Patch
Client-Server wire Compatibility N Y Y
Server-Server Compatibility N Y Y
File Format Compatibility N 3 Y Y
Client API Compatibility N Y Y
Client Binary Compatibility N N Y
Server-Side Limited API Compatibility
→ Stable N Y Y
→ Evolving N N Y
→ Unstable N N N
Dependency Compatibility N Y Y
Operational Compatibility N N Y

HBase 1.7.0 릴리스는 클라이언트-서버 와이어 호환성 보장을 위반했고, 비호환성이 보고되고 1.7.1에서 수정된 후 철회됐어요. 1.7.x 라인으로의 업그레이드를 고려하고 있다면 Upgrading to 1.7.1+를 참고하세요.

HBase API 표면

HBase는 API 지점이 많지만, 위 호환성 매트릭스에서는 Client API, Limited Private API, Private API를 구분해요. HBase는 Apache Yetus Audience Annotations를 사용해 다운스트림의 안정성 기대치를 안내해요.

  • InterfaceAudience (javadocs): 의도된 대상을 나타내요. 가능한 값은:
    • Public: 최종 사용자와 외부 프로젝트에 안전
    • LimitedPrivate: coprocessor처럼 플러그 가능하길 기대하는 내부용
    • Private: 오직 HBase 자체 내부에서만 사용. IA.Private로 정의된 클래스는 IA.LimitedPrivate로 선언된 인터페이스의 파라미터나 반환 값으로 사용될 수 있어요. IA.Private 객체는 불투명하게 취급하세요. 그 메서드나 필드에 직접 접근하지 마세요.
  • InterfaceStability (javadocs): 어떤 유형의 인터페이스 변경이 허용되는지 설명해요. 가능한 값은:
    • Stable: 인터페이스가 고정되어 있고 변경될 것으로 예상되지 않음
    • Evolving: 향후 마이너 버전에서 인터페이스가 변경될 수 있음
    • Unstable: 인터페이스가 언제든 변경될 수 있음

HBase 프로젝트 내 InterfaceAudience와 InterfaceStability 주석 간의 다음 상호작용을 명심하세요:

  • IA.Public 클래스는 본질적으로 안정적이고 메이저·마이너·패치 업그레이드 유형과 관련된 안정성 보장을 준수해요.
  • IA.LimitedPrivate 클래스는 항상 주어진 InterfaceStability 값 중 하나로 주석 처리되어야 해요. 그렇지 않다면 IS.Unstable로 간주해야 해요.
  • IA.Private 클래스는 암묵적으로 불안정하고 릴리스 간 안정성 보장이 없어야 해요.

HBase Client API

HBase Client API는 InterfaceAudience.Public으로 표시된 모든 클래스나 메서드로 구성돼요. hbase-client와 의존 모듈의 모든 주요 클래스는 InterfaceAudience.Public, InterfaceAudience.LimitedPrivate, 또는 InterfaceAudience.Private 마커 중 하나를 가지고 있어요. 다른 모듈(hbase-server 등)의 모든 클래스가 마커를 가진 것은 아니에요. 이 중 하나로 주석 처리되지 않은 클래스는 InterfaceAudience.Private 클래스로 간주돼요.

HBase LimitedPrivate API

LimitedPrivate 주석에는 인터페이스의 대상 소비자 집합이 함께 온다. 그 소비자는 coprocessor, phoenix, replication endpoint 구현 등이에요. 현재 HBase는 이러한 인터페이스에 대해 패치 버전 간 소스 및 바이너리 호환성만 보장해요.

HBase Private API

InterfaceAudience.Private로 주석 처리된 모든 클래스 또는 주석이 없는 모든 클래스는 HBase 내부 전용이에요. 인터페이스와 메서드 시그니처는 언제든 변경될 수 있어요. Private으로 표시된 특정 인터페이스에 의존한다면, 그 인터페이스를 Public 또는 LimitedPrivate로 변경하거나 이 목적으로 노출된 인터페이스로 제안하기 위해 jira를 열어야 해요.

바이너리 호환성

두 HBase 버전이 호환된다고 말할 때는 와이어와 바이너리 모두 호환된다는 뜻이에요. 호환되는 HBase 버전은 클라이언트가 호환되지만 버전이 다른 서버와 대화할 수 있다는 뜻이에요. 또한 한 버전의 jar를 빼서 다른 호환 버전의 jar로 교체하면 모든 것이 그대로 동작한다는 뜻이기도 해요. 달리 명시되지 않는 한, HBase 포인트 버전은 (대부분) 바이너리 호환이에요. 바이너리 호환 버전 간, 즉 메인터넌스 릴리스 간(예: 1.4.4에서 1.4.6으로) 안전하게 롤링 업그레이드를 할 수 있어요. "Does compatibility between versions also mean binary compatibility?" 토론은 HBase dev 메일링 리스트에서 확인하세요.

각주

  1. 'Source Compatibility' https://wiki.openjdk.org/spaces/csr/pages/32342052/Kinds+of+Compatibility 참고
  2. http://docs.oracle.com/javase/specs/jls/se8/html/jls-13.html 참고.
  3. 다운그레이드 없는 오프라인 업그레이드 도구를 실행해야 할 수도 있어요. 일반적으로 메이저 버전 X에서 메이저 버전 X+1로 데이터를 마이그레이션하는 것만 지원할 거예요.

더 알아보기 (Learn more)