콘텐츠로 이동

ARK-1139: 데이터 플랫폼 리뉴얼

Jira: ARK-1139 | 상태: In Progress | 담당: 백재현 | 설계 보고서: data-platform-design.vercel.app


문제의식 — 왜 지금 바꿔야 하는가

현재 Data Platform의 설계는 "AI가 먼저 제안하고 사람이 고른다" 는 가정 위에 세워졌다. 하지만 실제 사용 패턴을 보면 이 가정이 틀렸음을 알 수 있다.

1. 자동 제안(Proposal)의 함정

데이터 소스를 연결하면 Agent가 자동으로 proposal을 생성한다. 얼핏 편리해 보이지만 사용자의 의도가 시스템 안으로 들어가는 입구 자체가 없다.

흐름 비교

사용자가 원하는 것: "이 DB의 거래 테이블로 월별 매출 추이 CM을 만들고 싶다"

현재 시스템: Agent가 자동으로 여러 proposal 생성 → 사용자가 그 중에서 선택 → 원하는 게 없으면 다시 요청

Agent가 먼저 추측하고, 사용자는 그 추측에 반응하는 수동적인 위치에 놓인다. 협업이 아니라 correction의 반복이 된다.

2. "Source가 주인공"인 구조의 경직성

현재 구조 Source → Proposals (1:N) 은 Source를 중심에 두지만, 실제 작업 단위와 맞지 않는다.

현재 구조는 "설계서(proposal)"를 "실행 단위(pipeline)"로 오용하고 있다.

  • 같은 Source에서 변환 로직이 다른 CM 2개를 만들고 싶다면? → 독립 Pipeline 2개가 있어야 한다
  • Pipeline을 일시정지하거나 재실행하고 싶다면? → Proposal에는 상태 개념이 없다
  • Pipeline 실행 이력을 추적하고 싶다면? → Proposal은 설계서지 실행 단위가 아니다

3. Schedule이 잘못된 곳에 묶여 있다

Schedule의 본질적인 의미는 "이 데이터 소스를 언제 갱신할 것인가" 다. Proposal을 선택했냐 안 했냐는 Schedule과 무관해야 한다.

올바른 모델: Dataset 단위로 schedule 설정 → 갱신 시 연결된 Pipeline 자동 트리거

4. 파일 업로드 부재 — 사용 케이스의 절반을 놓치고 있다

DB 커넥션만 지원하면 실제 사용자가 활용하는 데이터의 상당 부분을 커버할 수 없다.

  • 리서치 하우스의 리포트 데이터 (CSV)
  • 특수 데이터 벤더의 커스텀 포맷
  • 팀 내부에서 직접 가공한 데이터셋

파일만 있으면 CM을 만들 수 있어야 한다. 이 능력이 없으면 플랫폼의 접근성 자체가 제한된다.

5. 팀 사일로 — 좋은 데이터가 팀 안에 갇힌다

각 팀이 만든 Content Model이 팀 경계 안에 갇혀 있다. A팀이 공들여 만든 고품질 CM이 있어도 B팀은 그 존재조차 모른다.

데이터도 코드처럼 재사용될 수 있어야 한다. 검증된 CM은 팀 간에 공유·구독되어 중복 작업을 없애야 한다.


AS-IS vs TO-BE

관점 AS-IS TO-BE
워크플로우 Scan → Propose → Select → Extract User intent → Agent 협업 → Preview → Production
구조 1 Source → N Proposals 1 Pipeline = 1 Dataset (1:1)
실행 단위 Proposal (설계서) Pipeline (실행 단위)
Schedule 귀속 Proposal에 1:1 Dataset 단위 → Pipeline 자동 트리거
파일 지원 DB 커넥션만 DB + 파일 업로드 (CSV/Parquet/JSON/Excel)
Agent 역할 자동 제안 생성 사용자 피드백 기반 CM 초안 반복 생성
팀 간 공유 불가 Catalog Marketplace (구독 모델)

핵심 도메인 구조

flowchart TD
    direction TB
    subgraph Source["Source Layer"]
        direction TB
        S1[RDS Connection]
        S2[Cloud Warehouse]
        S3[File Upload]
    end
    subgraph Dataset["Dataset"]
        direction TB
        D1[spec 정의]
        D2[schedule/cron]
    end
    subgraph Pipeline["Pipeline Layer"]
        direction TB
        P1[1 Pipeline = 1 Dataset]
        P2[Agent 피드백 루프]
        P3[CM 생성]
    end
    subgraph Catalog["Catalog Layer"]
        direction TB
        C1[CatalogEntry]
        C2[Marketplace 구독]
    end
    Source --> Dataset --> Pipeline --> Catalog

도메인별 설계

Source

  • RDS Connection / Cloud Warehouse / File Upload 통합
  • vendor는 Source에 귀속 (RDS/Warehouse만 해당)
  • File Upload: S3 presigned URL, CSV/Parquet/JSON/Excel, 크기 제한 없음

Dataset

  • Source 하위 소속
  • vendor는 Source로부터 자동 상속
  • spec 메타정보 보유 (하단 ARK-1149 참조)
  • Dataset 단위로 schedule(cron) 설정
  • Dataset 갱신 시 연결된 Pipeline 자동 트리거

Pipeline

  • 1 Pipeline = 1 Dataset (엄격한 1:1)
  • vendor는 Dataset.vendor 자동 참조 (직접 설정 불필요)
  • 인터랙션: 채팅 아님 — Agent가 CM 초안 생성 → 사용자 피드백 → 반복
  • 1 Pipeline → N Content Model(CM) 생성 가능

Content Model (CM)

  • Pipeline에서 생산되는 개별 데이터 산출물
  • 상태: buildingpreviewscheduledrunningpaused
  • 결과는 CatalogEntry로 연결

Catalog

  • CM 생산 결과물 집합소
  • is_public 플래그로 Marketplace 공개 여부 결정
  • CatalogSubscription으로 팀 간 구독

핵심 설계 결정 (ADR)

ADR-1: Pipeline과 Dataset을 1:1로 제한

결정: 1 Pipeline = 1 Dataset (N:1 금지)

이유:

  • Pipeline은 Dataset의 schema와 긴밀하게 결합된다 (transform definition이 schema 기반)
  • Dataset schema가 바뀌면 Pipeline의 transform도 재검토가 필요
  • 1:1 제약이 있으면 Dataset 변경의 영향 범위가 명확해진다
  • 같은 Dataset으로 다른 변환이 필요하면 → Pipeline을 새로 만들면 된다 (명시적)

ADR-2: Schedule을 Dataset에 귀속

결정: Schedule은 Dataset 단위로 설정, Pipeline을 자동 트리거

이유:

  • Schedule의 의미론적 주체는 "데이터 소스의 갱신 주기"이지 "어떤 변환을 선택했나"가 아님
  • Dataset이 갱신되면 연결된 모든 Pipeline이 트리거되어야 함 (데이터 일관성)
  • Pipeline 레벨에서 수동 트리거도 가능 (유연성 확보)

ADR-3: Agent 인터랙션을 구조화된 피드백 루프로

결정: 채팅 UI 대신 "CM 초안 → 피드백 입력 → 재생성" 루프

이유:

  • 채팅은 이력 관리가 어렵고 "어느 버전의 CM인가"를 추적하기 어렵다
  • 구조화된 피드백은 각 수정 사항이 PipelineFeedback 레코드로 저장됨
  • 특정 시점으로 롤백하거나 다른 피드백으로 재시도 가능
  • Agent 입장에서도 명확한 diff 기반 수정이 더 정확하다

ADR-4: 파일 업로드는 S3 presigned URL

결정: 파일 업로드는 S3 presigned URL 방식, 크기 제한 없음

이유:

  • API 서버를 통한 파일 프록시는 대용량 파일에서 병목이 됨
  • Presigned URL은 클라이언트 → S3 직접 업로드로 서버 부하 없음
  • 금융 데이터의 특성상 대용량 파일이 많아 크기 제한을 두지 않음

Sub-tasks

이슈 제목 상태
ARK-1149 Dataset spec 정의 및 파일 업로드 검증 파이프라인 도입 Backlog

ARK-1149: Dataset spec 정의 및 검증 파이프라인

문제

현재 파일 업로드 시마다 LLM Full Pipeline이 실행된다:

업로드 → detect_normalize → cm_check → spec → transform → register

데이터 형상을 매번 추론해야 하므로 비효율적이고, 기존 Dataset과의 형상 일치 여부 검증이 없다.

설계 방향

Dataset = 데이터 파일들 + 그 파일들이 따라야 할 spec

Dataset spec 구조

{
  "columns": [{"name": "date", "type": "date"}, ...],
  "time_axis": {"column": "date", "format": "%Y-%m-%d", "frequency": "daily"},
  "entity_axis": {"column": "ticker"},
  "value_columns": ["close", "volume"],
  "cm_name": "kr_stock_price_daily",
  "delivery_lag": 1
}

spec 정의 시점

Dataset 생성 경로 spec 정의 시점 출처
Source(RDB) → Dataset Dataset 생성 시 trial 결과 spec.json 승계
첫 파일 업로드 첫 업로드 Full Pipeline 완료 후 생성된 spec.json 저장

업로드 파이프라인 분기 변경

flowchart TD
    direction TB
    A[파일 업로드 confirm]
    A --> B{Dataset에 spec 있음?}
    B -->|없음 - 첫 업로드| C[Full Pipeline<br>detect_normalize → spec 생성 → 저장]
    B -->|있음| D[검증 모드<br>spec 형상 검증]
    D -->|통과| E[transform + register]
    D -->|실패| F[에러 리포트 반환]

검증 스텝 (신규)

  • 컬럼명/타입 일치 여부
  • time_axis, entity_axis 존재 여부
  • 타입 호환성 (e.g., date 컬럼이 실제로 파싱 가능한지)

영향 범위

레포 변경 내용
arkraft-api Dataset 모델 spec 컬럼 추가, migration, upload 서비스 분기 변경
arkraft-agent-data 검증 스텝 구현
arkraft-web Dataset 상세 UI에 spec 메타 표시

마이그레이션 고려사항

AS-IS TO-BE 비고
data_sources sources vendor, type 재분류 필요
dataset_proposals datasets + pipelines 1 proposal → 1 dataset + 1 pipeline으로 분해
proposal.schedule dataset.cron_schedule schedule 귀속 이동
content_models 신규
catalog_entries 신규

마이그레이션 원칙

  • 기존 selected 상태의 proposal만 pipeline으로 이관 (unselected는 아카이브)
  • 이관 전 충분한 검증 기간 필요 (기존 API 병행 운영)

미결 사항

  • 파일 Dataset의 vendor 지정 방식
  • Agent tool use 접근 범위 (읽기 전용 vs 쓰기)
  • Catalog Marketplace 접근 제어 (추후)
  • 기존 데이터 마이그레이션 전략