
Materialized View(MView)는 Kafka 기반 스트림 데이터에서 집계·가공된 결과를 빠르게 조회하기 위한 구조다.
일반 View와 달리 실제 저장 공간(State Store = RocksDB)을 가지며 기반 Stream/Table의 변경 사항을 반영해 최신 상태를 유지한다.
CTAS는 집계를 수행해 Table 형태의 MView를 만드는 방식이다.
Create Table customer_activity_mv01
with (
KAFKA_TOPIC = 'customer_activity_mv01_topic',
KEY_FORMAT = 'KAFKA',
VALUE_FORMAT = 'JSON',
PARTITIONS = 3
)
As
Select
customer_id,
avg(activity_point) as avg_point
from customer_activity_stream
group by customer_id;
입력 Stream
customer_activity_stream에서 레코드가 지속적으로 들어옴
집계 처리(Aggregation)
customer_id 기준으로 avg(activity_point) 집계 수행
State Store(RocksDB)에 저장
각 customer_id의 최신 avg_point를 RocksDB에 저장
Changelog Internal Topic 기록
RocksDB 변경분을 changelog로 내부 토픽에 기록하여 복구 가능
결과 Topic(KAFKA_TOPIC)
customer_activity_mv01_topic에 집계 결과가 출력됨
CSAS는 MView를 Stream 형태로 생성하는 방식이다.
create stream customer_activity_strm_mv01
with (
KAFKA_TOPIC = 'customer_activity_strm_mv01_topic',
KEY_FORMAT = 'KAFKA',
VALUE_FORMAT = 'JSON',
PARTITIONS = 3
)
as
Select *
from customer_activity_stream
where activity_type in ('web_open', 'mobile_open');
SELECT ACT_TYPE, COUNT(*) AS CNT, SUM(POINT) AS SUM_P,
AVG(POINT) AS AVG_P, MAX(POINT) AS MAX_P
FROM CUSTOMER_ACTIVITY_STREAM
GROUP BY ACT_TYPE
EMIT CHANGES;
Repartition은 GROUP BY 기준 Key가 기존 Key와 다를 때 자동으로 발생한다.
하지만 Repartition에는 아래와 같은 단점과 비용이 존재한다.
개별 Stream Task가 모든 파티션을 조회해야 하는 상황이 발생한다.
→ 파티션 단위로 분산 처리하지 못하므로 처리 효율이 떨어진다.
분산 병렬 처리가 제대로 수행되지 못한다.
→ 특정 Task가 특정 Key만 처리하는 구조가 깨지고 병렬성이 낮아진다.
데이터가 여러 노드에 분산된 경우
→ 네트워크로 데이터를 지속적으로 전송해야 한다.
→ 이로 인해 네트워크 대역폭 소모, 지연 증가, 시스템 부하 증가가 발생한다.
RocksDB는 Local DB이기 때문에
→ 분산된 데이터를 기반으로 Stateful 연산을 수행할 수 없다.
→ 결국 Key가 동일 파티션으로 모여야만 RocksDB에서 상태를 유지할 수 있다.
위와 같은 단점이 있음에도 불구하고 GROUP BY를 수행하기 위해 Key를 맞추기 위해 Repartition이 실행된다.