26J09c

Young-Kyoo Kim·약 19시간 전

지금 환경에서는 “버킷별 3분류”보다 한 단계 더 세밀하게 워크로드·prefix·데이터 수명 단계별 정책으로 나누는 게 맞습니다. 특히 StarRocks, Spark, ETL, Airflow, observability log가 섞이면 같은 bucket 안에서도 tmp/, metadata/, data/current/, data/archive/, logs/, checkpoints/를 다르게 취급해야 합니다. 가이드에서도 Replication은 보호 목적, ILM Tiering은 비용·용량 최적화 목적이며, 두 기능은 독립적이지만 함께 쓸 때 stub-only replication 동작을 반드시 이해해야 한다고 정리하고 있습니다.


1. 먼저 결론

현재 조건, 즉 WORM 미사용, DR 미구성, Hot NVMe 공간 부족, Warm SATA/SSD 재활용, StarRocks/Spark/ETL/Log 혼재라면 기본 정책은 이렇게 잡는 것이 좋습니다.

1. tmp / staging / checkpoint / commit 임시 경로
   → Hot only + 짧은 expiration
   → versioning OFF
   → replication OFF
   → tiering OFF

2. append-only 로그 / 과거 raw / 오래된 partition / 재생성 가능한 ETL 산출물
   → Tiering only
   → versioning OFF
   → 필요 시 expire

3. 중요 원천 데이터 / catalog / metadata / table manifest / 업무상 복구 필요한 산출물
   → Replication only
   → versioning ON
   → delete replication OFF 기본
   → noncurrent cleanup 필수

4. 중요하면서 오래 보관해야 하는 데이터
   → 같은 object에 tiering+replication을 단순 동시 적용하지 말고
   → active bucket은 replication only
   → archive bucket 또는 archive prefix는 tiering only

5. Warm tier target bucket
   → AIStor ILM 전용
   → 애플리케이션 직접 접근 금지
   → 별도 lifecycle/expiration 금지
   → versioning도 기본적으로 불필요

핵심은 StarRocks/Spark 같은 애플리케이션이 직접 읽고 쓰는 active 경로에는 함부로 tiering을 걸지 않는 것입니다. Tiering은 객체 단위로는 투명하게 동작하더라도, 대량 query·compaction·commit·checkpoint·snapshot restore 같은 작업에서는 지연과 부하가 확 튈 수 있습니다.


2. 추천 bucket/prefix 구조

가능하면 bucket을 용도별로 나누는 게 가장 좋습니다. 이미 bucket을 나누기 어렵다면 최소한 prefix를 강하게 표준화해야 합니다.

hot-aistor
├─ lakehouse-prod
│  ├─ metadata/              # replication only
│  ├─ manifests/             # replication only
│  ├─ data/current/          # hot only or replication only
│  ├─ data/archive/          # tiering only
│  ├─ tmp/                   # expire only
│  ├─ _temporary/            # expire only
│  ├─ _spark_metadata/       # hot only, careful
│  └─ checkpoints/           # hot only, usually no versioning
│
├─ etl-landing
│  ├─ raw/incoming/           # hot short-term
│  ├─ raw/validated/          # tiering or replication by importance
│  ├─ staging/                # expire only
│  └─ rejected/               # short retention, optional tier
│
├─ starrocks-load
│  ├─ incoming/               # hot while load pending
│  ├─ loaded/                 # tiering or expire
│  └─ failed/                 # short retention
│
├─ airflow-logs
│  └─ dag_id=.../             # tiering only after recent UI window
│
├─ observability-logs
│  ├─ app/                    # tiering only
│  ├─ audit/                  # replication only or tiering+separate replica
│  └─ security/               # replication only preferred
│
└─ backups
   ├─ starrocks/              # warm direct or replication only
   └─ opensearch/             # warm direct preferred

Warm 쪽은 역할별 bucket을 분리합니다.

warm-aistor
├─ tier-hot-prod              # ILM tier target 전용, 직접 접근 금지
├─ repl-lakehouse-critical    # replication target, readable copy
├─ repl-etl-critical          # replication target
├─ repl-observability-audit   # replication target
├─ archive-native             # 애초에 Warm에 직접 쓰는 장기보관 데이터
└─ backup-repository          # StarRocks/OpenSearch 등 backup repository

AIStor 공식 문서도 remote tier bucket은 AIStor가 독점적으로 접근해야 하며, 외부 애플리케이션이 remote tier의 object data나 Hot tier의 metadata를 직접 수정하면 데이터 손실이 날 수 있다고 설명합니다. 따라서 ILM target bucket과 replication target bucket은 절대 섞지 않는 것이 좋습니다. (MinIO AIStor Documentation)


3. 워크로드별 정책

3.1 Spark batch ETL 임시 경로

Spark/Hadoop 계열은 _temporary 같은 commit 임시 경로를 많이 씁니다. Hadoop S3A 문서도 task output을 _temporary 아래에 쓴 뒤 commit 시 rename하는 동작을 설명하고, object store에서 rename 기반 commit이 성능·안정성 문제를 만들 수 있음을 지적합니다. (하둡)

이 경로에는 versioning, replication, tiering을 모두 걸지 않는 것이 좋습니다.

대상:
- _temporary/
- .spark-staging/
- staging/
- tmp/
- scratch/
- work/
- failed-attempt/
- _committed_*
- _started_*

권장 정책:

versioning: OFF
replication: OFF
tiering: OFF
expiration: 1~7일

예시:

mc ilm rule add hot/lakehouse-prod \
  --prefix "_temporary/" \
  --expire-days 3

mc ilm rule add hot/lakehouse-prod \
  --prefix "tmp/" \
  --expire-days 3

mc ilm rule add hot/lakehouse-prod \
  --prefix ".spark-staging/" \
  --expire-days 7

버킷 전체에 versioning이 필요한 경우에는 Spark 임시 경로를 versioning 제외 prefix에 넣어야 합니다. 업로드 가이드도 tmp/, logs/, cache/ 같은 변경 빈도 높은 prefix를 versioning에서 제외하고, Spark/Hadoop처럼 directory marker가 많은 워크로드에는 --exclude-folders를 함께 쓰는 방식을 권장합니다. 다만 제외 prefix는 최대 10개 제한이 있으므로, 가능하면 임시 경로는 별도 bucket으로 분리하는 게 더 안전합니다.


3.2 Spark / Iceberg / Parquet data file

Spark가 만드는 Parquet/ORC data file, 특히 Iceberg/Hive partition data file은 보통 한 번 commit된 뒤 immutable에 가까운 성격입니다. 이런 파일은 Warm tiering에 가장 잘 맞습니다.

다만 metadata와 data file은 분리해야 합니다.

metadata/
manifests/
snapshots/
_catalog/
→ replication only
→ tiering 금지 또는 매우 보수적

data/current/
→ 최근 partition은 Hot 유지

data/archive/
→ tiering only

권장 예시:

# 오래된 data partition만 Warm으로 이동
mc ilm rule add hot/lakehouse-prod \
  --prefix "data/archive/" \
  --transition-days 30 \
  --transition-tier WARM_TIER

# 최근 partition은 90~180일 후 이동
mc ilm rule add hot/lakehouse-prod \
  --prefix "data/current/" \
  --transition-days 180 \
  --transition-tier WARM_TIER

Iceberg 계열에서는 object versioning으로 table rollback을 하려고 하기보다 Iceberg snapshot/metadata 기반 rollback을 기준으로 잡는 게 맞습니다. S3 object versioning은 객체 단위 이력일 뿐, 여러 data file과 manifest가 묶인 table-level transaction을 자동으로 일관성 있게 되돌려주지는 않습니다.


3.3 Spark Structured Streaming checkpoint

checkpoint는 작은 파일이 많고, 자주 갱신되며, streaming job 복구에 직접 영향을 줍니다. 여기에 versioning이나 replication을 걸면 version 폭증·LIST 지연·replication backlog가 발생하기 쉽습니다.

대상:
- checkpoints/
- _spark_metadata/
- offsets/
- commits/
- state/

권장 정책:

versioning: OFF 권장
tiering: OFF
replication: 보통 OFF
expiration: job 종료 후 별도 정리

정말 중요한 streaming job이라면 checkpoint를 replication으로 보호하고 싶을 수 있지만, 저는 우선 권하지 않습니다. checkpoint는 “업무 데이터”라기보다 “처리 상태”이고, 잘못 복구하면 중복 처리·누락 처리 이슈가 생길 수 있습니다. 보호가 필요하면 checkpoint 자체보다 source offset, sink table snapshot, ETL run metadata, Airflow run state를 별도로 보존하는 쪽이 더 낫습니다.


3.4 ETL landing / raw / validated 데이터

ETL 데이터는 단계별로 다르게 봐야 합니다.

incoming / landing

성격:
- 방금 들어온 원천
- 아직 검증 전
- 여러 downstream이 읽을 수 있음

권장:

최근 7~30일: Hot 유지
versioning: 보통 OFF
replication: 원천 재수집 불가 데이터만 ON
tiering: load/validation 완료 후

예시:

# 검증 완료 후 validated/로 이동된 데이터만 90일 후 tiering
mc ilm rule add hot/etl-landing \
  --prefix "raw/validated/" \
  --transition-days 90 \
  --transition-tier WARM_TIER

staging / transform intermediate

성격:
- 재생성 가능
- ETL 실패 시 잠깐 필요

권장:

versioning OFF
replication OFF
tiering OFF
expiration 3~14일
mc ilm rule add hot/etl-landing \
  --prefix "staging/" \
  --expire-days 7

rejected / quarantine

성격:
- 품질 오류, 파싱 실패, 재처리 가능성 있음

권장:

Hot 30일
이후 Warm tiering
180~365일 후 expire
versioning OFF
replication은 업무 중요도에 따라 선택
mc ilm rule add hot/etl-landing \
  --prefix "rejected/" \
  --transition-days 30 \
  --transition-tier WARM_TIER

3.5 중요 원천 데이터

재수집이 어렵거나 원천 자체가 업무상 보존 대상이면 tiering only보다 replication only가 우선입니다.

대상:
- 외부 기관으로부터 받은 원천
- 재생성 불가 데이터
- 수작업 업로드 데이터
- 계약/감사상 보존해야 하는 데이터

권장:

versioning ON
replication ON
delete replication OFF
tiering은 active bucket에서 직접 하지 않음
noncurrent cleanup 필수

예시:

mc version enable hot/critical-raw \
  --excluded-prefixes "tmp/,staging/,failed/" \
  --exclude-folders

mc version enable warm/repl-critical-raw

mc replicate add hot/critical-raw \
  --remote-bucket https://REPL_USER:REPL_SECRET@s3-warm.company.internal/repl-critical-raw \
  --replicate "existing-objects"

mc ilm rule add hot/critical-raw \
  --noncurrent-expire-days 90 \
  --noncurrent-expire-newer 5 \
  --expire-delete-marker

여기서 delete replication은 기본적으로 빼는 것이 좋습니다. 그래야 Hot에서 실수로 삭제해도 Warm replica에 사본이 남습니다. AIStor replication은 delete marker와 versioned delete replication을 명시적으로 켜야 동작하므로, 보호 사본 목적이면 delete,delete-marker를 기본으로 넣지 않는 것이 안전합니다. (MinIO AIStor Documentation)


3.6 중요하지만 장기 보관도 필요한 데이터

이게 가장 헷갈리는 영역입니다. “중요하니 replication도 해야 하고, 오래되니 tiering도 해야 한다”는 데이터입니다.

이 경우 같은 object에 replication과 tiering을 동시에 거는 방식은 기본 전략으로 두면 안 됩니다. 업로드 가이드에 따르면 tiering이 완료된 object는 Hot에 실제 bytes가 없고 metadata stub만 남으며, 이후 replication target에는 stub만 복제될 수 있고 target에서 직접 읽으면 오류가 날 수 있습니다.

권장 패턴은 다음입니다.

active bucket:
  hot/critical-active
  → replication only
  → Warm에 full readable copy

archive bucket:
  hot/critical-archive
  → tiering only
  → Hot 용량 절감

운영 흐름:

1. ETL이 hot/critical-active 에 write
2. Hot → Warm replication으로 full copy 보호
3. 90~180일 뒤 archive job이 hot/critical-archive 로 이동 또는 복사
4. hot/critical-archive 는 ILM으로 Warm tiering
5. active 쪽 오래된 데이터는 업무 확인 후 expire 또는 delete

예시:

# active: 중요 보호
mc version enable hot/critical-active
mc version enable warm/repl-critical-active

mc replicate add hot/critical-active \
  --remote-bucket https://REPL_USER:REPL_SECRET@s3-warm.company.internal/repl-critical-active \
  --replicate "existing-objects"

# archive: 용량 절감
mc ilm rule add hot/critical-archive \
  --transition-days 30 \
  --transition-tier WARM_TIER

이 방식이 Hot 용량 절감과 보호 사본 유지 목적을 가장 명확히 분리합니다.


4. StarRocks 관련 정책

StarRocks는 S3/MinIO를 여러 방식으로 쓸 수 있습니다. StarRocks 문서는 MinIO에서 데이터를 load하는 방법으로 Broker Load, INSERT+FILES, Spark Load 등을 설명하고 있고, StarRocks 자체도 object storage에서 데이터를 read/load하는 패턴을 지원합니다. (StarRocks Docs)

4.1 StarRocks load source bucket

예를 들어 외부 데이터가 MinIO에 들어오고 StarRocks가 Broker Load, Pipe, INSERT+FILES로 읽는 구조라면 다음처럼 나눕니다.

starrocks-load/incoming/
→ Hot only
→ load 완료 전 tiering 금지

starrocks-load/loaded/
→ source-of-truth 아니면 expire 또는 tiering only

starrocks-load/failed/
→ 7~30일 보관 후 expire

starrocks-load/audit/
→ replication only

예시:

mc ilm rule add hot/starrocks-load \
  --prefix "loaded/" \
  --transition-days 30 \
  --transition-tier WARM_TIER

mc ilm rule add hot/starrocks-load \
  --prefix "failed/" \
  --expire-days 30

StarRocks Pipe는 대량 파일을 작은 순차 task로 나눠 load하는 방식이므로, load pending 상태의 파일은 Hot에 남겨두는 게 좋습니다. StarRocks 문서도 100GB~1TB 이상 대량 파일 load에는 Pipe를 권장한다고 설명합니다. (StarRocks Docs)


4.2 StarRocks shared-data / storage volume bucket

StarRocks가 S3 bucket을 storage volume으로 직접 쓰는 경우, 이 bucket은 StarRocks 내부 table storage에 가깝습니다. StarRocks 문서에는 S3 storage volume 생성과 S3 endpoint/access key 설정이 포함되어 있습니다. (StarRocks Docs)

이 bucket에는 AIStor ILM tiering을 직접 걸지 않는 쪽을 권합니다.

versioning: OFF 권장
tiering: OFF 권장
replication: StarRocks 레벨 backup/restore 또는 별도 snapshot 우선
expiration: StarRocks가 관리하지 않는 prefix에만 제한적으로

이유는 StarRocks가 compaction, delete, update, metadata 관리, segment lifecycle을 자체적으로 갖고 있기 때문입니다. Object storage 입장에서 “오래된 object”처럼 보여도 StarRocks query나 compaction에 필요할 수 있습니다. 여기서 AIStor ILM이 개입하면 성능 예측성이 떨어지고, versioning은 삭제된 segment를 계속 보존해 capacity가 급격히 늘 수 있습니다.


4.3 StarRocks backup repository

StarRocks는 snapshot을 remote storage system에 backup하고 다른 StarRocks cluster에 restore하는 기능을 지원합니다. (StarRocks Docs)

Backup repository는 애초에 Warm에 직접 쓰는 것을 우선 고려할 수 있습니다.

bucket: warm/backup-repository/starrocks/
policy: Warm only
versioning: OFF 또는 매우 짧게
replication: 현재 DR 없으면 OFF
expiration: StarRocks snapshot retention 정책과 맞춤

단, StarRocks shared-data cluster는 data BACKUP/RESTORE를 지원하지 않는다는 제약이 있으므로, 여러분의 StarRocks 배포 모드가 shared-nothing인지 shared-data인지 먼저 확인해야 합니다. (StarRocks Docs)


5. Airflow log 정책

Airflow는 task log를 S3 remote logging으로 쓸 수 있고, Airflow UI에서 task별 log를 조회하는 구조입니다. Apache Airflow 문서도 S3 remote logging은 기존 Airflow connection을 사용해 log를 read/write한다고 설명합니다. (Apache Airflow)

Airflow log는 보통 append-like이고, 최근 며칠~몇 주만 UI에서 빠르게 보면 됩니다.

권장:

최근 14~30일: Hot
30일 이후: Warm tiering
180~365일 이후: expire
versioning: OFF
replication: 보통 OFF
중요 감사성 DAG만 replication

예시:

mc ilm rule add hot/airflow-logs \
  --transition-days 30 \
  --transition-tier WARM_TIER

mc ilm rule add hot/airflow-logs \
  --expire-days 365

중요 DAG나 감사 대상 DAG는 prefix를 분리합니다.

airflow-logs/audit/
→ replication only 또는 30일 후 tiering + 별도 audit replica

airflow-logs/normal/
→ tiering only
mc version enable hot/airflow-audit-logs \
  --exclude-folders

mc version enable warm/repl-airflow-audit-logs

mc replicate add hot/airflow-audit-logs \
  --remote-bucket https://REPL_USER:REPL_SECRET@s3-warm.company.internal/repl-airflow-audit-logs \
  --replicate "existing-objects"

mc ilm rule add hot/airflow-audit-logs \
  --noncurrent-expire-days 30 \
  --noncurrent-expire-newer 3 \
  --expire-delete-marker

일반 task log bucket 전체에 versioning을 켜는 것은 권하지 않습니다. retry, 재실행, log overwrite 또는 delete marker가 누적되면 LIST 성능과 scanner 부하가 불필요하게 커집니다.


6. Observability log 정책

Observability 쪽은 세 가지로 나눕니다.

6.1 Fluent Bit / app log S3 archive

Fluent Bit S3 output은 log record를 S3 object store로 업로드하며, multipart upload가 기본이고 권장되는 방식입니다. (Fluent Bit)

일반 app log archive는 tiering only가 잘 맞습니다.

versioning: OFF
replication: OFF
tiering: 7~30일
expiration: 90~365일, 업무 기준
mc ilm rule add hot/observability-logs \
  --prefix "app/" \
  --transition-days 7 \
  --transition-tier WARM_TIER

mc ilm rule add hot/observability-logs \
  --prefix "app/" \
  --expire-days 180

다만 작은 log object가 너무 많으면 ILM scanner와 transition queue에 부담이 됩니다. 가능하면 Fluent Bit buffer/chunk 정책을 조정해 너무 작은 object를 만들지 않는 것이 좋습니다.


6.2 audit / security log

보안 감사, 권한 변경, 접근 이력, 운영 명령 이력 같은 log는 단순 tiering only보다 replication only가 낫습니다.

versioning: ON
replication: ON
delete replication: OFF
tiering: active bucket에서는 가급적 OFF
noncurrent cleanup: 90~180일
mc version enable hot/security-audit-logs \
  --exclude-folders

mc version enable warm/repl-security-audit-logs

mc replicate add hot/security-audit-logs \
  --remote-bucket https://REPL_USER:REPL_SECRET@s3-warm.company.internal/repl-security-audit-logs \
  --replicate "existing-objects"

mc ilm rule add hot/security-audit-logs \
  --noncurrent-expire-days 180 \
  --noncurrent-expire-newer 5 \
  --expire-delete-marker

WORM을 아직 쓰지 않는다고 했으므로 법적 불변성까지 보장되지는 않습니다. 그래도 delete replication을 끄면 실수 삭제로부터는 어느 정도 보호됩니다.


6.3 OpenSearch snapshot repository

OpenSearch snapshot repository를 S3로 둘 경우에는 아예 Warm에 직접 쓰는 구조가 좋습니다. OpenSearch 문서는 S3 repository plugin을 설치해 S3 bucket을 snapshot repository로 사용할 수 있다고 설명합니다. (OpenSearch Documentation)

bucket: warm/backup-repository/opensearch/
policy: Warm only
versioning: OFF 권장
tiering: 없음
replication: 현재 DR 없으면 OFF
expiration: snapshot retention 정책으로 관리

Snapshot repository bucket에 AIStor versioning을 켜면 snapshot 삭제가 실제 공간 회수로 이어지지 않고 delete marker/noncurrent version이 누적될 수 있습니다. Snapshot 도구가 자체적으로 metadata와 retention을 관리하므로, bucket-level versioning은 특별한 이유가 없으면 끄는 편이 낫습니다.


7. 정책 매트릭스

대상VersioningTieringReplicationExpiration권장 이유
Spark _temporary/, staging, tmpOFFOFFOFF1~7일재생성 가능, churn 큼
Spark checkpointOFFOFFOFFjob별 수동/정책복구 상태 파일, 작은 파일 많음
Iceberg metadata/manifest/catalogON 또는 짧게 ONOFFONnoncurrent 정리table consistency 핵심
Parquet/ORC 과거 partitionOFFON선택선택immutable, 용량 큼
ETL raw incomingOFFOFF중요도별짧게load 전 Hot 유지
ETL validated rawOFFON중요 원천만 ON선택장기 보관
ETL staging/intermediateOFFOFFOFF3~14일재생성 가능
StarRocks load source loadedOFFON 또는 expire중요도별선택load 후 cold 처리
StarRocks storage volumeOFFOFF별도 backup 우선StarRocks 관리앱 내부 storage
StarRocks backup repositoryOFFWarm directDR 없으면 OFFbackup retention앱 레벨 snapshot
Airflow normal logsOFFONOFF180~365일append-like log
Airflow audit logsON선택ONnoncurrent 정리감사/복구
Fluent Bit app logsOFFONOFF90~365일append archive
Security/audit logsON선택ONnoncurrent 정리실수 삭제 보호
OpenSearch snapshotsOFFWarm directDR 없으면 OFFsnapshot retentionrepository 관리

8. Versioning + ILM stub 상태에서 특정 version rollback 가능 여부

질문하신 핵심에 답하면 다음입니다.

Hot source bucket 기준으로는 가능합니다.
Versioning이 켜져 있고 특정 object version이 ILM으로 Warm tier에 transition되어 Hot에는 stub metadata만 남아 있어도, 그 version의 metadata가 Hot에 남아 있고 Warm tier의 실제 bytes가 보존되어 있다면 Hot endpoint를 통해 version ID로 읽거나 restore할 수 있습니다. MinIO AIStor 공식 문서도 version ID를 지정해 이전 version을 retrieve할 수 있다고 설명하고, mc get --version-id/--vid로 특정 version을 가져올 수 있다고 설명합니다. (MinIO AIStor Documentation)

또한 mc ilm restore는 remote tier로 archive된 특정 object version을 --vid로 restore하는 예시를 제공합니다. 즉 transitioned version을 Hot에 임시 복원한 뒤 조회·복구하는 흐름이 가능합니다. (MinIO AIStor Documentation) 업로드 가이드도 mc ilm restore HOT_ALIAS/BUCKET/path --days 7 형태로 Warm tier object를 Hot에 임시 복원하고, 기간 만료 후 다시 Warm으로 전환된다고 설명합니다.

다만 “문제 없다”는 말에는 조건이 붙습니다.

가능한 조건:
1. rollback하려는 version이 noncurrent expire로 삭제되지 않았어야 함
2. Warm tier target bucket의 실제 object data가 삭제/변경되지 않았어야 함
3. 반드시 Hot source endpoint를 통해 접근해야 함
4. replication target의 stub-only copy를 직접 읽으려 하면 안 됨
5. 단일 object rollback과 table/dataset rollback을 구분해야 함

특히 remote tier bucket에 별도 lifecycle/expiration을 걸거나 사람이 직접 object를 지우면 안 됩니다. AIStor 공식 문서도 transitioned object는 Hot metadata와 Warm data가 연결되어 있고, remote data를 외부에서 수정·삭제하면 object data 손실이 발생할 수 있다고 경고합니다. (MinIO AIStor Documentation)


9. “회귀”의 두 가지 의미

9.1 특정 version을 읽는 것

이건 비교적 안전합니다.

# version 목록 확인
mc ls --versions hot/bucket/path/to/object

# 특정 version을 조회 또는 다운로드
mc get --vid VERSION_ID hot/bucket/path/to/object ./object.old

# 특정 transitioned version을 Hot에 임시 restore
mc ilm restore --vid VERSION_ID hot/bucket/path/to/object --days 7

9.2 특정 version을 current로 되돌리는 것

이건 더 조심해야 합니다. MinIO AIStor의 mc undo는 지정 경로의 최근 PUT/DELETE를 되돌릴 수 있고, 예를 들어 가장 최근 PUT을 되돌려 이전 version으로 회귀하는 예시가 공식 문서에 있습니다. (MinIO AIStor Documentation)

# 최근 PUT을 되돌려 이전 version을 current로 복구
mc undo hot/bucket/path/to/object --action "PUT"

# 최근 DELETE를 되돌림
mc undo hot/bucket/path/to/object --action "DELETE"

또는 현재 version을 version ID로 삭제하면 바로 이전 version이 current가 될 수 있습니다. 하지만 version ID를 지정한 delete는 irreversible hard delete이므로 운영 절차로는 매우 조심해야 합니다. AIStor 문서도 특정 version ID 삭제는 영구 삭제이며 되돌릴 수 없다고 설명합니다. (MinIO AIStor Documentation)

따라서 운영 절차는 보통 이렇게 잡는 게 안전합니다.

1. mc ls --versions 로 대상 version 확인
2. mc ilm restore --vid 로 해당 version을 임시 Hot 복원
3. mc get --vid 또는 검증 job으로 내용 확인
4. 단일 object면 mc undo 또는 copy-back
5. 다중 object/table이면 애플리케이션 레벨 rollback 사용

10. Spark/StarRocks에서는 object version rollback을 “테이블 복구”로 쓰면 안 됨

이 부분이 가장 중요합니다.

Spark/Iceberg/StarRocks/ETL 테이블은 하나의 object가 아니라 여러 data file, metadata file, manifest, transaction log, catalog 상태가 묶여 하나의 일관된 상태를 이룹니다. S3 versioning은 object 단위이므로, 특정 시점의 수천~수억 object version을 정확히 맞춰 current로 되돌리는 것은 운영상 거의 별도 복구 프로젝트가 됩니다.

따라서:

Iceberg table rollback
→ Iceberg snapshot rollback 사용

StarRocks internal table rollback
→ StarRocks BACKUP/RESTORE 또는 StarRocks 자체 recovery 사용

ETL 결과 dataset rollback
→ run_id/date partition 단위 재처리 또는 publish pointer 교체

Object versioning
→ 개별 object 복구, 실수 삭제 복구, 단기 PITR 보조 수단

즉, versioning은 휴지통과 개별 object 복구용으로 보고, table-level consistency는 application/table format이 책임지게 설계해야 합니다.


11. 실제 권장 조합 예시

11.1 Lakehouse bucket

# metadata 보호용: versioning + replication
mc version enable hot/lakehouse-meta \
  --exclude-folders

mc version enable warm/repl-lakehouse-meta

mc replicate add hot/lakehouse-meta \
  --remote-bucket https://REPL_USER:REPL_SECRET@s3-warm.company.internal/repl-lakehouse-meta \
  --replicate "existing-objects"

mc ilm rule add hot/lakehouse-meta \
  --noncurrent-expire-days 90 \
  --noncurrent-expire-newer 10 \
  --expire-delete-marker

# data archive: tiering only
mc ilm rule add hot/lakehouse-data \
  --prefix "archive/" \
  --transition-days 30 \
  --transition-tier WARM_TIER

11.2 Spark ETL bucket

# 임시 경로 정리
mc ilm rule add hot/spark-etl \
  --prefix "_temporary/" \
  --expire-days 3

mc ilm rule add hot/spark-etl \
  --prefix "staging/" \
  --expire-days 7

# 검증 완료 데이터 tiering
mc ilm rule add hot/spark-etl \
  --prefix "validated/" \
  --transition-days 90 \
  --transition-tier WARM_TIER

11.3 StarRocks load bucket

# load 완료 후 30일 뒤 warm
mc ilm rule add hot/starrocks-load \
  --prefix "loaded/" \
  --transition-days 30 \
  --transition-tier WARM_TIER

# failed data는 30일만 보관
mc ilm rule add hot/starrocks-load \
  --prefix "failed/" \
  --expire-days 30

11.4 Airflow logs

mc ilm rule add hot/airflow-logs \
  --transition-days 30 \
  --transition-tier WARM_TIER

mc ilm rule add hot/airflow-logs \
  --expire-days 365

11.5 Observability app logs

mc ilm rule add hot/observability-logs \
  --prefix "app/" \
  --transition-days 7 \
  --transition-tier WARM_TIER

mc ilm rule add hot/observability-logs \
  --prefix "app/" \
  --expire-days 180

11.6 Security audit logs

mc version enable hot/security-audit-logs \
  --exclude-folders

mc version enable warm/repl-security-audit-logs

mc replicate add hot/security-audit-logs \
  --remote-bucket https://REPL_USER:REPL_SECRET@s3-warm.company.internal/repl-security-audit-logs \
  --replicate "existing-objects"

mc ilm rule add hot/security-audit-logs \
  --noncurrent-expire-days 180 \
  --noncurrent-expire-newer 5 \
  --expire-delete-marker

12. 운영상 반드시 볼 지표

업로드 가이드도 ILM transition queue, tier journal 실패, replication backlog, expiry pending을 핵심 지표로 제시합니다. 특히 대규모 Spark/ETL/log bucket에서는 transition 대상 object가 한 번에 몰리면서 queue가 포화될 수 있습니다.

최소 알람은 다음입니다.

ILM:
- minio_ilm_transition_pending_tasks
- minio_ilm_transition_missed_immediate_tasks
- minio_ilm_expiry_missed_tier_journal_tasks
- minio_ilm_expiry_pending_tasks

Replication:
- minio_replication_recent_backlog_count
- mc replicate status
- mc replicate backlog

Versioning:
- s3:ObjectManyVersions
- s3:ObjectLargeVersions
- mc admin scanner info

Versioning bucket에는 반드시 --noncurrent-expire-days, --noncurrent-expire-newer, --expire-delete-marker를 같이 둬야 합니다. 가이드도 delete marker를 명시적으로 정리하지 않으면 versioning bucket에서 DELETE 반복 시 LIST 성능 저하가 발생할 수 있다고 설명합니다.


최종 정리

현재 환경에서는 이렇게 가면 됩니다.

Spark/ETL 임시 경로:
→ expire only

Spark/Iceberg/Parquet 오래된 data file:
→ tiering only

Iceberg metadata / catalog / manifest:
→ replication only + versioning short retention

StarRocks load source:
→ load 전 Hot, load 후 tiering or expire

StarRocks storage volume:
→ AIStor ILM 직접 적용 금지에 가깝게 보수 운영

StarRocks/OpenSearch backup repository:
→ Warm direct, versioning OFF 권장

Airflow 일반 task log:
→ tiering only

Security/audit log:
→ replication only, delete replication OFF

중요하면서 오래 보관할 데이터:
→ active는 replication only
→ archive는 tiering only
→ 같은 object에 단순 tiering+replication 동시 적용은 예외로만

그리고 versioning + ILM stub 상태에서의 rollback은 Hot source endpoint 기준으로는 가능합니다. 다만 그건 개별 object version 복구이지, Spark/Iceberg/StarRocks table 전체를 일관된 시점으로 되돌리는 수단은 아닙니다. Table 복구는 Iceberg snapshot, StarRocks BACKUP/RESTORE, ETL run_id 재처리 같은 애플리케이션 레벨 절차로 설계하는 것이 안전합니다.

0개의 댓글