LLM WikiAccess-protected knowledge portal

WIKI

Apache Arrow 25.0.0: 인메모리 컬럼형 표준이 Flight SQL과 ADBC로 엔진 간 직렬화 비용을 없애는 방법

왜 지금 봐야 하나 2026년 7월 10일 공개된 Apache Arrow 25.0.0은 222개 이슈를 처리한 누적 릴리스다. 단일 기능이 폭발적인 릴리스는 아니지만, Arrow가 데이터 플랫폼 스택에서 차지하는 위치를 이해하지 못하면 숫자만 보고 넘어가기 쉽다. Arrow가 "보이지 않는 표준"인 이유가 있다. Spark, Flink, DuckDB, Trino, ClickHouse, Polars, Pandas 2.x, dbt

경로human/study/content/database-frontier/58-apache-arrow-25-flight-sql-adbc-zero-copy.md
카테고리Study
태그#adbc #copy #flight #mysql #sql #study #zero

왜 지금 봐야 하나

2026년 7월 10일 공개된 Apache Arrow 25.0.0은 222개 이슈를 처리한 누적 릴리스다. 단일 기능이 폭발적인 릴리스는 아니지만, Arrow가 데이터 플랫폼 스택에서 차지하는 위치를 이해하지 못하면 숫자만 보고 넘어가기 쉽다.

Arrow가 "보이지 않는 표준"인 이유가 있다. Spark, Flink, DuckDB, Trino, ClickHouse, Polars, Pandas 2.x, dbt, PyTorch DataLoader — 이 스택 어딘가에 Arrow가 없는 경우를 찾기 어렵다. 엔진 간 데이터를 넘길 때 Arrow IPC를 쓰면 직렬화/역직렬화 변환 없이 메모리 버퍼를 포인터로 전달할 수 있다. 변환 비용이 없다는 것이 데이터 파이프라인에서 무엇을 의미하는지가 이 챕터의 핵심 주제다.

25.0.0에서 주목할 변경은 두 방향이다:

  1. C++ 레이어: ARM64 SVE SIMD 지원, Parquet ListView 읽기·쓰기, Bloom filter 벡터화
  2. 프로토콜 레이어: Flight SQL 준비 구문 메타데이터 개선, C Data Interface 변형 버퍼 처리 명세

Apache Arrow 생태계 구조

Arrow는 단일 라이브러리가 아니다. 네 가지 구성 요소가 함께 동작한다.

형식 레이어 (Format)
Arrow Columnar Format
인메모리 컬럼형 레이아웃
버퍼 기반 · 제로 복사 가능
Arrow IPC
프로세스 간 전송
스트림 / 파일 형식
C Data Interface
FFI 경계 없는 버퍼 공유
Python↔C++↔Rust↔Java
프로토콜 레이어 (Wire Protocol)
Arrow Flight RPC
gRPC + Arrow IPC · 고속 대용량 전송
서버 → 클라이언트 스트리밍
Arrow Flight SQL
Flight 위에 SQL 시맨틱 추가
Catalog · PreparedStatement · Transaction
클라이언트 연결 레이어 (ADBC)
Snowflake 드라이버
BigQuery 드라이버
DuckDB 드라이버
PostgreSQL 드라이버
Flight SQL 드라이버
Databricks (Go) 드라이버
PyArrow (Python)
Arrow Java
Arrow Rust
Arrow Go
Arrow C++
Arrow R (arrow pkg)
Apache Arrow 생태계: 형식, 프로토콜, 드라이버, 언어 바인딩

각 레이어의 역할:


Arrow 25.0.0 주요 변경

C++: ARM64 SVE SIMD 동적 디스패치

25.0.0 이전까지 Arrow C++의 SIMD 동적 디스패치(CPU 기능에 따라 최적화 경로 선택)는 x86 플랫폼에서만 작동했다. 이제 ARM64(AArch64)에서도 SVE(Scalable Vector Extension) 최적화 루틴으로 동적 디스패치가 가능하다.

런타임 CPU 탐지 로직도 자체 구현에서 xsimd 라이브러리로 교체했다. xsimd는 SIMD 추상화 레이어로, AVX2/AVX-512(x86)와 SVE/NEON(ARM64)을 통일된 인터페이스로 다룬다. 유지 관리 부담을 줄이고 향후 새로운 SIMD 확장 지원을 추가할 때 기반이 된다.

데이터베이스 운영자에게 이 변화가 중요한 이유: ARM64 기반 클라우드 인스턴스(AWS Graviton, Ampere Altra 등)에서 Arrow를 사용하는 엔진의 필터링·집계 연산 처리량이 향상될 수 있다. Spark, Trino, DuckDB처럼 Arrow C++ 위에서 동작하는 엔진이 혜택을 본다.

C++: Parquet ListView 읽기·쓰기

Arrow의 ListView 타입(각 리스트 요소가 오프셋+길이로 정의되는 가변 길이 배열)을 Parquet 파일로 읽고 쓸 수 있게 됐다. 기존에는 ListView를 일반 List로 변환한 뒤 저장해야 했다.

실용적 의미: JSON 배열 컬럼, 이벤트 로그의 가변 길이 태그 배열 등을 Parquet에 저장하고 재로드할 때 Arrow 타입 정보가 손실 없이 보존된다.

C++: Bloom filter 벡터화

Parquet의 Bloom filter 연산을 SIMD로 벡터화했다. Bloom filter는 Parquet 파일 읽기 시 불필요한 Row Group을 스킵하는 데 쓰인다. 특히 IN 필터 프루닝에서 효과적이다. 필터 연산 자체가 빨라지면 파일 스캔 비용을 줄인다.

C++: API 추가

추가 메서드대상 클래스용도
ComputeLogicalNullCount()ChunkedArrayNull 카운트를 논리적으로 계산 (Array/ArrayData에 이미 있던 메서드의 ChunkedArray 버전)
ToTensor()Table컬럼형 Table을 2D 연속 텐서로 변환 (RecordBatch에 이미 있던 메서드의 Table 버전)

Table.ToTensor()는 Arrow 테이블을 PyTorch Tensor나 NumPy 배열로 변환할 때 직접 경로를 제공한다. ML 학습 파이프라인에서 피처 테이블을 Arrow로 로드한 뒤 텐서로 변환하는 코드가 단순해진다.

C Data Interface: 변형 버퍼 null 처리 명세

Arrow의 C Data Interface는 언어 경계를 넘어 Arrow 버퍼 포인터를 전달하는 ABI 명세다. 변형 버퍼(variadic buffers)가 null일 수 있다는 점을 25.0.0에서 명시적으로 명세에 포함했다.

변형 버퍼는 가변 길이 바이너리 데이터(문자열, 리스트 등)의 실제 데이터 버퍼다. 특정 조건에서 null 포인터가 전달될 수 있음에도 불구하고 기존 구현 일부가 이를 처리하지 않았다.

이 변경의 주의점: C Data Interface를 통해 Arrow 버퍼를 소비하는 코드(Python ↔ C++ 경계, Rust Arrow ↔ Python 경계 등)는 변형 버퍼 null 가능성을 처리하도록 코드를 확인해야 한다. null 포인터를 역참조하면 크래시가 발생한다.

Arrow Flight SQL: 준비 구문 결과셋 메타데이터

Flight SQL 프로토콜에 서버가 준비 구문(PreparedStatement)이 결과셋을 반환하는지 여부를 클라이언트에게 명시적으로 알릴 수 있는 메커니즘이 추가됐다(GH-49497).

기존에는 ExecuteQuery 유형(결과셋 있음)인지 ExecuteUpdate 유형(행 수 반환)인지 클라이언트가 추론하거나 첫 실행 후 결과를 확인해야 했다. 이제 Prepare 단계에서 서버가 이 정보를 전달한다.

# Flight SQL 준비 구문 실행 흐름 (변경 전)
Client: Prepare("INSERT INTO ...") → PreparedStatementHandle
Client: Execute(handle) → ???  # 결과셋이 있는지 없는지 불명확

# Flight SQL 준비 구문 실행 흐름 (변경 후)
Client: Prepare("INSERT INTO ...") → PreparedStatementHandle + has_result_set=false
Client: ExecuteUpdate(handle) → rows_affected  # 명확하게 DML 처리

Flight SQL을 구현하는 데이터베이스 엔진(DuckDB, ClickHouse, QuestDB 등)과 클라이언트 드라이버가 이 메타데이터를 활용하면 불필요한 왕복(roundtrip)을 줄인다.

PyArrow: ParquetDataset 단일 파일 경로 처리 복구

pyarrow.parquet.ParquetDataset에 단일 파일 경로를 전달했을 때 발생하는 병합 오류(merge error)를 수정했다. pyarrow.parquet.read_table()에서도 동일 문제가 수정됐다.

import pyarrow.parquet as pq

# 25.0.0에서 정상 작동 (이전 버전에서 오류 발생하던 케이스)
table = pq.read_table("/data/events_2026-07-10.parquet")
dataset = pq.ParquetDataset("/data/single_file.parquet")

ADBC 23: Arrow Database Connectivity 현황

Arrow 25.0.0과 함께 확인해야 할 맥락이 ADBC(Arrow Database Connectivity) 생태계다. 2026년 4월 릴리스된 ADBC 23은 API 명세 1.1.x와 함께 다음 데이터베이스 드라이버를 지원한다:

드라이버특이사항
Snowflake프로덕션 사용 지원
BigQuerymicrosecond 타임스탬프 처리 개선, 서비스 계정 impersonation 지원
DuckDBADBC를 통한 직접 쿼리 실행
PostgreSQL표준 연결
SQLite표준 연결
Flight SQLArrow Flight SQL 호환 서버 범용 연결
Databricks (Go)새로 기여된 Go 드라이버

ADBC와 JDBC의 근본적 차이:

JDBCADBC
결과 형식Row-oriented (행 단위)Arrow Columnar (컬럼 단위)
변환 비용읽을 때마다 Arrow 변환 필요변환 없음
대용량 결과셋 처리메모리 압력 큼스트리밍 Arrow RecordBatch
ML/분석 파이프라인추가 변환 필요직접 텐서·DataFrame 전환

ADBC가 COPY-level 성능을 단순한 코드로 달성한다는 벤치마크가 실제 운영에서 검증되고 있다.


데이터 플랫폼에서의 실용적 고려사항

Arrow를 사용해야 하는 경우

업그레이드 시 주의 사항


Open question


References