13년차의 서버실

서버, 인프라, 홈랩 기술 블로그

[태그:] 인프라 성능 테스트

  • [Cloud] 객체 스토리지 성능 측정: S3/R2/GCS 벤치마크 방법론

    [Cloud] 객체 스토리지 성능 측정: S3/R2/GCS 벤치마크 방법론

    객체 스토리지 성능 측정 방법론: S3/R2/GCS 벤치마크

    객체 스토리지 성능 측정은 숫자 하나 뽑는 일보다 비교 조건을 설계하는 일에 더 가깝습니다. 업로드 한 번 돌려서 나온 시간에는 그 순간의 네트워크 상태, TLS 세션 재사용 여부, 클라이언트 CPU 상태, 리전 거리까지 한꺼번에 섞이거든요. 저도 처음엔 단일 파일 복사 시간만 보고 판단했다가, 운영에 올린 뒤 작은 파일 다건 업로드와 메타데이터 조회가 병목이 되면서 완전히 다른 그림을 봤습니다. 그래서 이 글은 “누가 더 빠르다”를 단정하려는 글이 아니라, 객체 스토리지 성능 측정을 실무에서 재현 가능하게 만드는 방법론을 정리한 글입니다.

    특히 S3, R2, GCS는 API 표면은 비슷해 보여도 측정 도구, 병렬화 방식, 재시도 전략, 멀티파트 또는 분할 업로드 동작이 꽤 다릅니다. 이 차이를 통제하지 않으면 저장소를 비교하는 게 아니라 각 벤치마크 도구의 기본값을 비교하게 됩니다. 현업에서는 이 실수가 진짜 치명적이더라고요. 비슷한 인프라 비교 글을 함께 정리해 두면, 나중에 CDN 캐시나 전송 비용 이슈까지 한 번에 판단하기도 훨씬 편합니다.

    객체 스토리지 성능 측정 아키텍처 다이어그램

    단일 벤치마크 클라이언트에서 S3, R2, GCS로 동일한 워크로드를 보내고 지표를 수집하는 구성 예시입니다.

    왜 단순 업로드 시간만 보면 자꾸 판단이 틀어질까

    객체 스토리지는 로컬 디스크 벤치마크처럼 순차 읽기·쓰기 하나로 설명되지 않습니다. 요청 하나마다 DNS, TCP, TLS, HTTP 연결 재사용, 인증, 서버 측 큐잉이 섞입니다. 같은 100GB 업로드라도 1GB 파일 100개와 256KB 파일 수십만 개는 완전히 다른 테스트예요. 전자는 스트림 처리량 문제고, 후자는 요청 수와 꼬리 지연 문제입니다.

    • 대용량 백업이면 단일 스트림 처리량, 멀티파트 분할 기준, 재시도 시 복구 비용이 핵심입니다.
    • 썸네일, 로그 조각, 문서 스니펫처럼 작은 객체가 많으면 평균 속도보다 요청당 지연 시간과 실패율이 더 중요합니다.
    • 애플리케이션이 HEAD, LIST, GET 또는 메타데이터 조회를 자주 쓰면 PUT 성능보다 p95·p99 응답 시간이 체감에 더 크게 작용합니다.

    제가 실무에서 제일 많이 보는 오판은 이것입니다. 큰 파일 하나는 빨랐는데 서비스는 느린 경우요. 이유는 단순합니다. 서비스는 큰 파일 한 번보다 작은 객체 수천 번을 더 자주 만지기 때문입니다. 그래서 벤치마크는 항상 워크로드를 먼저 정의해야 합니다. 저장소 이름보다 접근 패턴이 먼저예요.

    객체 스토리지 성능 측정에서 꼭 봐야 하는 지표

    표를 화려하게 만들 필요는 없습니다. 대신 운영 판단에 실제로 쓰이는 지표만 남겨야 합니다. 저는 아래 여섯 개를 기본 세트로 잡습니다.

    1. Throughput: 초당 전송 바이트 수입니다. 큰 파일 백업, 미디어 아카이브, 데이터 레이크 적재처럼 스트리밍 성격이 강한 워크로드에서 중요합니다.
    2. Latency: 요청 하나가 끝나는 시간입니다. 작은 객체 서비스는 이 값이 곧 체감 성능입니다.
    3. p95/p99 Tail Latency: 평균값이 멀쩡해도 느린 구간이 튀면 운영 품질은 나빠집니다. 사용자 불만은 거의 여기서 나옵니다.
    4. Error Rate / Retry Count: 4xx, 5xx, 타임아웃, 재시도 횟수입니다. 처리량이 조금 높아도 재시도가 많으면 운영 점수는 낮게 봐야 합니다.
    5. Concurrency Scaling: 동시성을 올렸을 때 얼마나 비례해서 늘어나는지 봅니다. 이 곡선이 평평해지는 지점이 병목 후보입니다.
    6. Client Resource Usage: CPU, NIC, 로컬 디스크 사용률입니다. 저장소를 재는 줄 알았는데 테스트 클라이언트의 암호화 비용이나 디스크 읽기 속도를 재는 경우가 생각보다 흔합니다.

    여기서 하나 더 붙이자면 변동성입니다. 같은 조건에서 5번 돌렸을 때 편차가 큰 서비스는 평균값이 좋아도 운영 예측 가능성이 낮습니다. 백업 창이 촘촘하거나 배치 종료 시간이 중요한 팀이라면 최고 속도보다 흔들림이 작은 쪽이 더 낫습니다. 이거, 막상 운영 붙이면 차이가 꽤 크게 느껴집니다.

    S3/R2/GCS 객체 스토리지 성능 측정을 공정하게 만드는 설계

    툴보다 중요한 건 통제 변수입니다. S3 성능 벤치마크, R2 속도 측정, GCS 처리량 비교를 따로따로 보면 쉬워 보여도 실제로는 한 줄만 달라도 해석이 깨집니다. 아래 항목은 최소한 맞춰두셔야 합니다.

    항목 왜 맞춰야 하나 권장 방식
    클라이언트 위치 리전 거리와 네트워크 경로가 바뀌면 저장소 자체 차이가 가려집니다 같은 VM 또는 같은 베어메탈 호스트에서 모든 테스트 수행
    파일 크기 분포 작은 파일과 큰 파일은 병목이 다릅니다 작은 파일, 중간 파일, 큰 파일, 혼합 패턴을 분리 측정
    동시성 단일 연결 수치만으로는 확장 특성을 보기 어렵습니다 1, 4, 8, 16처럼 단계적으로 올리고 증가 곡선을 기록
    재시도/타임아웃 도구 기본값이 다르면 실패율과 시간 값이 왜곡됩니다 가능하면 동일한 재시도 횟수와 타임아웃 정책을 명시
    멀티파트/병렬 업로드 기준 큰 파일 성능에 직접 영향을 줍니다 threshold, chunk size, 병렬 프로세스 수를 문서화해서 고정
    워밍업 첫 실행은 DNS, TLS, 캐시 영향으로 튀는 경우가 많습니다 워밍업 1회 후 본 측정 5회 이상

    제 기준으로는 한 서비스가 더 빨라 보일 때 바로 결론을 내리지 않습니다. 먼저 묻는 건 세 가지입니다. 같은 크기 분포였는지, 같은 동시성이었는지, 같은 재시도 정책이었는지. 이 셋이 다르면 사실상 다른 시험입니다.

    객체 스토리지 성능 측정용 워크로드 매트릭스 이미지

    큰 파일, 작은 파일, 혼합 워크로드와 동시성 단계별 측정 매트릭스를 한눈에 정리한 구성입니다.

    S3 성능 벤치마크를 위한 실전 준비

    1. 테스트 파일 세트 만들기

    데이터 세트는 재현 가능해야 합니다. 운영 덤프를 그대로 쓰면 현실성은 좋지만, 개인정보 처리와 반복성 문제가 생깁니다. 그래서 저는 보통 크기 분포만 닮은 합성 데이터 세트를 따로 만듭니다. 빈 파일이나 <code>truncate로 만든 희소 파일은 피하시는 편이 낫습니다. 압축, 중복 제거, 페이지 캐시 영향 때문에 실제 업로드 비용과 동떨어질 수 있어서요.

    mkdir -p ~/objbench/data/{small,medium,large}
    cd ~/objbench/data
    
    # 작은 파일 1000개: 요청 수와 지연 시간 측정용
    for i in $(seq -w 1 1000); do
      dd if=/dev/urandom of=small/small-${i}.bin bs=256K count=1 status=none
     done
    
    # 중간 파일 100개: 일반적인 애플리케이션 업로드 패턴 근사
    for i in $(seq -w 1 100); do
      dd if=/dev/urandom of=medium/medium-${i}.bin bs=8M count=8 status=none
     done
    
    # 큰 파일 4개: 멀티파트 처리량과 재시도 비용 확인용
    for i in $(seq -w 1 4); do
      dd if=/dev/urandom of=large/large-${i}.bin bs=64M count=16 status=progress
     done
    
    # 디렉터리별 총 용량 확인
    find ~/objbench/data -type f -printf '%h\n' | sort | uniq -c
    find ~/objbench/data -type f -exec du -ch {} + | tail -n 1

    이렇게 나누는 이유는 단순합니다. 큰 파일은 스트리밍 경로를 재고, 작은 파일은 요청 처리 경로를 잽니다. 같은 저장소라도 두 결과가 정반대로 나올 수 있습니다.

    2. AWS CLI로 S3와 R2 조건 맞추기

    S3와 R2는 같은 S3 호환 API 축에 있으니, 비교용 도구는 하나로 맞추는 편이 낫습니다. 여기서 핵심은 기본값을 믿지 않는 겁니다. AWS CLI는 max_concurrent_requests, multipart_threshold, multipart_chunksize, addressing_style 같은 값이 결과에 직접 영향을 줍니다. 큰 파일 테스트에서는 이 네 개를 반드시 기록해 두세요.

    # 기본 프로파일에 S3 전송 관련 설정 고정
    aws configure set default.s3.max_concurrent_requests 16
    aws configure set default.s3.multipart_threshold 64MB
    aws configure set default.s3.multipart_chunksize 16MB
    aws configure set default.s3.addressing_style path
    
    # 선택: 대역폭 제한이 필요한 경우만 사용
    # aws configure set default.s3.max_bandwidth 200MB/s
    
    # 설정 확인
    aws configure get default.s3.max_concurrent_requests
    aws configure get default.s3.multipart_threshold
    aws configure get default.s3.multipart_chunksize
    aws configure get default.s3.addressing_style
    
    # S3 업로드 측정
    /usr/bin/time -f 'elapsed=%E cpu=%P mem=%MKB' \
      aws s3 cp ~/objbench/data/large/large-01.bin s3://my-s3-bucket/bench/large-01.bin \
      --only-show-errors
    
    # R2 업로드 측정
    /usr/bin/time -f 'elapsed=%E cpu=%P mem=%MKB' \
      aws --endpoint-url https://ACCOUNT_ID.r2.cloudflarestorage.com \
      s3 cp ~/objbench/data/large/large-01.bin s3://my-r2-bucket/bench/large-01.bin \
      --only-show-errors

    여기서 자주 놓치는 부분이 두 가지입니다. 하나는 경로 방식(path style)과 가상 호스트 방식 차이, 다른 하나는 도구 내부 기본 동작 차이입니다. R2는 현재 path style과 virtual-hosted style을 모두 지원하지만, 비교 목적이라면 주소 지정 방식까지 한 번 정해 고정하는 편이 해석이 깔끔합니다. 조건이 자꾸 바뀌면 저장소 비교가 흐려지거든요.

    그리고 멀티파트를 너무 공격적으로 키우는 것도 능사는 아닙니다. 파트 수를 늘리면 처리량은 올라갈 수 있지만, 요청 수와 클라이언트 메모리 사용량도 같이 늘어납니다. 백업 창을 줄이는 게 목표라면 유효할 수 있지만, 공유 VM이나 제한된 NAT 환경에서는 오히려 타임아웃과 재시도가 늘 수 있습니다.

    3. GCS 처리량 측정은 gsutil 병렬 옵션을 분리해서 보기

    GCS 쪽은 여기서 많이 헷갈립니다. gsutil -m은 단순한 장식 옵션이 아니라 결과 해석을 바꾸는 변수입니다. 공식 문서 기준으로도 -m은 병렬 작업을 켜며, 여러 객체 작업에서 동작 특성이 달라집니다. 그래서 단일 실행 결과와 병렬 실행 결과를 같은 줄에 섞으면 안 됩니다.

    또 한 가지는 최신 상태입니다. 2026년 8월 30일 기준으로 Google Cloud는 새 자동화에는 gcloud storage 사용을 권장하고 있고, gsutil은 권장 CLI가 아닙니다. 게다가 공식 문서에는 2027년 3월 이후 gsutil이 Google Cloud CLI 설치 패키지에 더 이상 포함되지 않고 독립 도구로 배포된다고 안내돼 있습니다. 기존 스크립트 검증이라면 gsutil로 재도 되지만, 새 벤치마크 체계를 만든다면 gsutil 결과와 gcloud storage 결과를 혼용하지 않는 것이 좋습니다. 도구가 다르면 기본 병렬화와 출력 형식이 다르기 때문입니다.

    # gsutil 단일 실행
    /usr/bin/time -f 'elapsed=%E cpu=%P mem=%MKB' \
      gsutil cp ~/objbench/data/large/large-01.bin gs://my-gcs-bucket/bench/
    
    # gsutil 병렬 실행: 작은/중간 파일 다건 처리 패턴 확인용
    /usr/bin/time -f 'elapsed=%E cpu=%P mem=%MKB' \
      gsutil -m cp ~/objbench/data/medium/*.bin gs://my-gcs-bucket/bench/
    
    # 병렬 관련 boto 설정 예시
    cat > ~/.boto <<'EOF'
    [GSUtil]
    parallel_process_count = 4
    parallel_thread_count = 8
    resumable_threshold = 64M
    EOF
    
    # 객체 메타데이터 확인
    gsutil stat gs://my-gcs-bucket/bench/large-01.bin
    
    # 새 자동화 체계 예시: gcloud storage 기준으로 별도 측정
    /usr/bin/time -f 'elapsed=%E cpu=%P mem=%MKB' \
      gcloud storage cp ~/objbench/data/large/large-01.bin gs://my-gcs-bucket/bench/

    제가 권하는 방식은 간단합니다. GCS는 최소 두 시나리오로 나누세요. 1) 단일 객체 업로드 성능 2) 다건 병렬 처리 성능. 이 둘을 분리해야 S3/R2와 비교할 때 어디서 차이가 나는지 보입니다.

    클라이언트 병목을 같이 보지 않으면 숫자가 자꾸 거짓말합니다

    저장소 성능 테스트에서 가장 억울한 순간은, 나중에 보니 저장소가 아니라 내 테스트 머신이 병목이었던 경우입니다. 특히 암호화 오프로딩이 약한 VM, 공유 네트워크 인터페이스, 느린 로컬 디스크 위에서는 이런 일이 자주 납니다. 그래서 벤치마크 로그에는 저장소 지표와 함께 클라이언트 지표를 남겨야 합니다.

    sar, mpstat, iostat는 보통 Linux의 sysstat 패키지에 포함되니, 없는 환경이라면 먼저 설치 여부부터 확인해 두세요. 이런 사전 점검이 생각보다 시간을 많이 아껴줍니다.

    # 1초 간격으로 네트워크, CPU, 디스크 상태 확인
    sar -n DEV 1
    mpstat -P ALL 1
    iostat -x 1
    
    # DNS와 TCP/TLS가 병목인지 분리해서 보기 위한 curl 예시
    curl -s -o /dev/null \
      -w 'dns=%{time_namelookup} connect=%{time_connect} tls=%{time_appconnect} starttransfer=%{time_starttransfer} total=%{time_total} code=%{http_code}\n' \
      https://storage.googleapis.com/

    저는 해석을 이렇게 합니다.

    • 동시성을 1, 4, 8, 16으로 올렸는데 처리량이 거의 그대로면 저장소보다 클라이언트 NIC, CPU, TCP 윈도우, NAT 세션 한도를 먼저 의심합니다.
    • CPU 한 코어만 유독 높으면 CLI의 단일 스레드 구간이나 TLS 처리 비용이 병목일 수 있습니다.
    • await나 %util이 높은 디스크에서 업로드 테스트를 하면, 사실은 원본 파일 읽기 성능을 재고 있을 가능성이 큽니다.
    • 평균은 괜찮은데 체감이 느리면 p95/p99를 따로 적어야 합니다. 서비스 품질은 평균보다 꼬리 지연에 훨씬 민감합니다.

    여기서 하나 더. 공인 인터넷을 거치는 테스트라면 시간대 편차도 로그에 남기세요. 같은 조건인데 낮과 밤이 다르면 저장소보다 네트워크 경로 혼잡도가 결과를 더 크게 흔들고 있다는 뜻일 수 있습니다.

    객체 스토리지 성능 측정 중 병목 분석 화면

    저장소 자체 성능과 클라이언트 CPU·디스크·네트워크 병목을 함께 확인하는 실전 점검 화면 예시입니다.

    실제 트러블슈팅: 멀티파트 조건이 달라서 비교가 깨졌던 사례

    실무에서 가장 자주 보는 실패 모드는 화려하지 않습니다. 대개는 비교 조건이 숨은 곳에서 달라져 있는 문제입니다. 제가 크게 데인 사례도 그랬습니다. S3와 R2는 AWS CLI로, GCS는 별도 CLI로 측정했는데, 한쪽은 큰 파일을 여러 파트로 나눠 병렬 전송하고 있었고 다른 쪽은 사실상 단일 흐름에 가까웠습니다. 표만 보면 특정 서비스가 느려 보이는데, 저장소가 느린 게 아니라 전송 방식이 달랐던 거죠.

    증상은 이랬습니다.

    1. 큰 파일 업로드에서 한 서비스만 유독 시간이 길었습니다.
    2. 작은 파일 묶음 테스트에서는 차이가 크지 않았습니다.
    3. 클라이언트 CPU와 NIC는 한계에 닿지 않았고, 재시도 로그도 많지 않았습니다.

    이럴 때는 저장소를 탓하기 전에 먼저 전송 단위를 확인하셔야 합니다. 멀티파트 threshold, part size, 병렬 프로세스 수, 재시도 정책이 같지 않으면 결과 해석이 불가능합니다. 저는 그 뒤로 아예 아래 체크리스트를 벤치마크 시트 첫 줄에 적어둡니다.

    • 도구와 버전이 동일한가
    • 멀티파트 또는 병렬 업로드 기준이 동일한가
    • 동시성과 재시도 정책이 동일한가
    • 첫 실행을 버리고 워밍업 뒤 본 측정을 했는가
    • 클라이언트 CPU, NIC, 디스크 병목 여부를 함께 기록했는가

    이 체크리스트를 통과하면 그제야 숫자가 설명되기 시작합니다. 벤치마크는 예쁜 수치보다 왜 그런 결과가 나왔는지 설명 가능한 상태가 먼저입니다.

    결과는 어떻게 읽어야 하나: 숫자보다 패턴을 봅니다

    같은 결과표라도 읽는 기준이 없으면 결론이 흔들립니다. 저는 아래처럼 해석합니다.

    시나리오 기록할 값 읽는 방법
    큰 파일 업로드 경과 시간, 평균 처리량, 재시도 횟수, 멀티파트 설정 동시성 증가에 따라 처리량이 오르는지, 특정 지점에서 평평해지는지 봅니다
    작은 파일 다건 업로드 총 소요 시간, 파일당 평균 시간, 오류 수, p95/p99 평균보다 편차와 실패율을 더 무겁게 봅니다
    메타데이터 요청 HEAD/LIST 응답 시간 또는 메타데이터 조회 시간, 타임아웃 여부 애플리케이션 체감과 직접 연결되므로 꼬리 지연을 우선 봅니다
    반복 실행 안정성 실행별 분포, 중앙값, 최댓값/최솟값 차이 가장 빠른 값보다 흔들림이 작은 쪽이 운영 예측 가능성이 높습니다

    운영 관점에서 읽으면 기준이 더 선명해집니다.

    • 동시성을 올려도 처리량이 안 늘면 그 지점이 현재 병목입니다. 저장소가 아니라 클라이언트나 네트워크일 가능성도 큽니다.
    • 큰 파일은 빠른데 작은 파일이 느리면, 그 저장소가 나쁜 게 아니라 현재 워크로드와 안 맞는 겁니다.
    • 반복 5회 중 1회만 튄다면 최고 기록보다 안정성 리스크를 먼저 봐야 합니다.
    • 오류나 재시도가 보이면 평균 처리량이 좋아도 운영 점수는 낮게 잡는 편이 안전합니다.
    S3 R2 GCS 처리량과 지연 시간 비교 대시보드

    처리량, p95 지연 시간, 재시도 횟수를 한 화면에서 비교해 패턴을 읽는 결과 대시보드 예시입니다.

    자주 받는 질문 정리

    벤치마크는 몇 번 반복하면 좋을까요?

    워밍업 1회 후 본 측정 5회 이상은 잡으시는 게 좋습니다. 그보다 적으면 편차를 해석하기 어렵습니다. 가능하면 시간대도 나눠 보세요. 저장소보다 네트워크가 흔들리는지 구분하는 데 도움이 됩니다.

    다운로드 테스트도 꼭 해야 하나요?

    네. 업로드와 다운로드는 병목이 다를 수 있습니다. 서비스 제공용이면 GET 패턴이 더 중요할 때도 많고, 다운로드 경로에서 CDN이나 캐시 전략을 같이 볼 수도 있습니다.

    한 도구로 통일해야 하나요?

    가능하면 좋습니다. 다만 서비스별 공식 도구 차이가 있으니 현실적으로 완전 통일이 어려울 수는 있습니다. 그럴수록 비교 문서에 도구, 버전, 병렬화 옵션, 재시도 설정을 더 자세히 남겨야 합니다.

    벤치마크 비용은 어떻게 줄이나요?

    저는 먼저 작은 파일 세트와 중간 파일 세트로 병목 구간을 찾고, 마지막에만 큰 파일 반복 측정을 합니다. 큰 파일 다회 측정은 전송 비용과 시간 비용이 커서, 초반 탐색 단계에서는 효율이 좋지 않습니다.

    현업 기준으로 이렇게 추천드립니다

    판단 기준은 생각보다 명확합니다. 백업, 로그 아카이브, 대용량 적재처럼 큰 파일 중심이면 S3/R2/GCS 중 무엇이든 먼저 볼 것은 단일 업로드 성공률, 멀티파트 설정, 동시성 증가 시 처리량 곡선입니다. 여기서는 최고 속도 한 줄보다 재시도와 안정성이 더 중요합니다. 처리량이 조금 낮아도 흔들림이 작고 재시도가 적은 쪽이 운영에선 더 낫습니다.

    반대로 이미지, 썸네일, 문서 조각, 메타데이터 조회가 많은 서비스라면 p95 지연 시간, LIST/HEAD 응답, 반복 간 편차를 우선 보셔야 합니다. 이 경우 대역폭보다 요청당 지연이 더 아프게 들어옵니다. 큰 파일 업로드 수치가 좋아도 작은 객체에서 꼬리 지연이 크면 실제 서비스 만족도는 떨어집니다.

    도구 선택도 이렇게 가져가시면 됩니다. S3와 R2를 비교할 때는 AWS CLI로 최대한 조건을 맞추세요. GCS는 기존 스크립트 검증이면 gsutil을 쓰되, 새 자동화 체계라면 gcloud storage로 넘어갈 계획까지 같이 잡는 편이 낫습니다. 다만 한 번의 비교 세트에서는 두 도구를 섞지 않는 게 안전합니다.

    제가 현업에서 내리는 결론은 늘 비슷했습니다. “어느 서비스가 더 빠른가”보다 내 워크로드가 큰 파일 중심인지, 작은 객체 중심인지, 메타데이터 요청 중심인지부터 자르는 것. 그다음 같은 조건으로 재고, 평균보다 꼬리 지연과 변동성을 보고, 마지막에 비용과 운영 복잡도를 얹어 판단합니다. 벤치마크에서 진짜 가치가 있는 숫자는 가장 높은 숫자가 아니라, 운영에서 다시 재현되는 숫자입니다.

    워크로드별로 어떤 지표를 우선 봐야 하는지 정리한 요약 인포그래픽입니다.

  • [OpenStack] OpenStack Placement 벤치마크: 대규모 자원 할당 성능 분석

    [OpenStack] OpenStack Placement 벤치마크: 대규모 자원 할당 성능 분석

    [OpenStack] OpenStack Placement 벤치마크: 대규모 자원 할당 성능 분석

    OpenStack Placement 벤치마크를 처음 제대로 돌려본 건, 스케줄러가 이상하게 느려지는 순간 때문이었습니다. VM 몇 대 수준에서는 티가 안 나는데, 컴퓨트 노드 수가 늘고 자원 요청(Resource Request)이 복잡해지면 갑자기 API 응답이 늘어지고, 결국 사용자는 “왜 인스턴스 생성이 이렇게 오래 걸리죠?”라고 묻게 되거든요. 저도 처음엔 Nova Scheduler(노바 스케줄러) 쪽만 의심했었는데, 실제로 뜯어보니 Placement 서비스가 병목으로 보이는 구간이 있더라고요. 그래서 이번 글에서는 OpenStack Placement 벤치마크를 어떤 식으로 설계하고, 무엇을 봐야 하며, 결과를 어떻게 해석해야 하는지 제 경험 기준으로 정리해보겠습니다.

    특히 자원 할당 성능, OpenStack 인프라, Placement 서비스를 운영 관점에서 보고 싶은 분들께 도움이 될 겁니다. 숫자를 지어내는 식의 벤치마크는 의미가 없어서, 이번 글은 재현 가능한 테스트 절차와 해석 포인트 위주로 풀어보겠습니다. 혹시 운영 환경에서 “CPU는 남는데 스케줄링이 느리다” 같은 경험 있으신가요? 여기서 중요한 포인트가 바로 Placement입니다.

    Placement 서비스, Nova Scheduler, 데이터베이스, 컴퓨트 노드가 연결된 전체 벤치마크 아키텍처 개요입니다.

    1. 왜 OpenStack Placement 벤치마크가 중요한가

    쉽게 말해 Placement는 “이 요청을 만족할 수 있는 자원이 어디에 있나”를 빠르게 찾는 역할을 합니다. 예전에는 자원 조회 로직이 여러 군데 흩어져 있어서 복잡했는데, Placement가 그 책임을 상당 부분 분리해줬죠. 문제는 조회 대상이 커지면, 즉 Resource Provider(리소스 프로바이더, 자원 제공 주체) 수가 많아지고 Traits(트레이트, 자원 특성)나 Aggregate(애그리게이트, 그룹화 정보) 조건이 겹치면 성능 특성이 확 달라진다는 게 핵심이더라고요.

    제가 직접 해보니 단순 조회는 꽤 잘 버티는데, 아래 조건이 섞이면 체감 성능이 달라졌습니다.

    • 컴퓨트 노드가 많아져 Resource Provider 수가 크게 증가한 경우
    • NUMA, PCI passthrough, SR-IOV 같은 추가 조건이 붙는 경우
    • 동시 API 요청이 몰리는 경우
    • Inventory(인벤토리, 제공 가능한 자원량)와 Allocation(할당 상태) 갱신이 계속되는 경우

    운영에서는 이게 곧 사용자 경험으로 이어집니다. 인스턴스 생성 지연, 오토스케일 지연, 배치 작업 실패로 연결될 수 있거든요. 그래서 OpenStack Placement 벤치마크는 단순한 성능 놀이가 아니라, 실제 운영 여유치(headroom)를 확인하는 절차라고 보는 게 맞습니다.

    2. Placement 서비스 핵심 개념 정리

    저도 처음엔 용어 때문에 좀 헷갈렸는데, 이 부분만 정리되면 뒤가 훨씬 쉬워집니다.

    2-1. Resource Provider와 Inventory

    Resource Provider는 CPU, RAM, DISK 같은 자원을 제공하는 대상입니다. 보통 컴퓨트 노드가 대표적이지만, 구조상 더 세분화된 단위도 가능합니다. Inventory는 “이 노드가 얼마나 제공 가능한가”에 대한 정보고, Allocation은 “그 중 얼마가 이미 사용 중인가”에 가깝습니다.

    2-2. Trait와 Aggregate

    Trait는 특성 태그라고 생각하면 편합니다. 예를 들어 SSD, 특정 CPU 기능, 가상화 확장 여부 같은 성격을 표현할 때 씁니다. Aggregate는 여러 Resource Provider를 묶는 논리 그룹입니다. Availability Zone과 비슷하게 느껴질 수 있는데 쓰임은 조금 다르죠.

    2-3. Allocation Candidate

    벤치마크에서 자주 보게 되는 개념입니다. Allocation Candidate(할당 후보)는 요청 조건을 만족하는 자원 조합 후보인데, 결국 스케줄링 전에 “가능한 곳 리스트”를 만든다고 보면 됩니다. 이 후보 계산이 커질수록 Placement 서비스의 응답 시간도 영향을 받습니다.

    개념 쉽게 말한 의미 성능에 미치는 영향
    Resource Provider 자원을 제공하는 대상 대상이 많아질수록 조회 범위 증가
    Inventory 제공 가능한 총 자원 갱신 빈도와 조회 비용에 영향
    Allocation 이미 할당된 자원 상태 동시성 충돌과 상태 일관성에 영향
    Trait 자원 특성 태그 필터 조건 증가로 쿼리 복잡도 상승 가능
    Aggregate 리소스 그룹 묶음 후보군 축소 또는 조인 비용 증가 가능
    Allocation Candidate 요청 만족 후보 세트 대규모 환경에서 핵심 병목 포인트

    3. 벤치마크 설계: 뭘 측정해야 의미가 있나

    여기서 제일 많이 하는 실수가, 단순히 초당 요청 수만 보는 겁니다. 물론 Requests Per Second(RPS, 초당 요청 수)도 중요하지만, 운영 관점에서는 그것만 보면 안 되더라고요. 저는 보통 아래 항목을 함께 봅니다.

    1. 응답 시간 분포: 평균보다 P95, P99 같은 꼬리 지연(tail latency)이 더 중요합니다.
    2. 동시 요청 처리량: 단일 요청보다 burst 상황을 봐야 합니다.
    3. 오류율: 5xx 응답, 타임아웃, 충돌 응답 여부를 확인합니다.
    4. DB 부하: Placement 자체보다 백엔드 DB가 먼저 한계에 닿는 경우가 많습니다.
    5. 스케줄링 체감: Placement API만 빠르고 실제 인스턴스 생성은 느릴 수도 있습니다.

    벤치마크 시나리오도 분리하는 게 좋습니다. 제가 추천하는 기준은 이렇습니다.

    • 단순 조회 시나리오: traits 없이 기본 자원만 요청
    • 조건부 조회 시나리오: trait, aggregate, resource class 조건 추가
    • 대규모 후보 시나리오: 후보군이 매우 많도록 구성
    • 갱신 혼합 시나리오: allocation/inventory 업데이트와 조회를 동시에 수행

    사실 운영 장애는 마지막 시나리오에서 많이 튀어나옵니다. 읽기만 있는 테스트는 예쁘게 나오는데, 쓰기와 섞는 순간 이야기가 달라지거든요.

    OpenStack Placement 벤치마크의 리소스 프로바이더 토폴로지 이미지

    리소스 프로바이더 토폴로지와 요청 흐름, 후보 계산 경로를 보여주는 구성 다이어그램입니다.

    4. 홈랩 기준 실전 벤치마크 환경 구성

    제 홈랩에서도 완전히 똑같은 운영 환경을 만들 수는 없었지만, 패턴을 확인하는 데는 충분했습니다. 중요한 건 절대적인 숫자보다 병목이 어디서 시작되는지를 보는 겁니다.

    4-1. 테스트 전 체크리스트

    • Placement API 엔드포인트 접근 가능 여부 확인
    • 테스트용 프로젝트와 인증 토큰 준비
    • 백엔드 DB 상태 확인
    • 벤치마크 중 로그 레벨을 너무 과하게 올리지 않기
    • 테스트 시간대 분리: 운영 트래픽과 겹치지 않게

    4-2. 기본 확인 명령

    source admin-openrc.sh
    openstack endpoint list --service placement
    openstack resource provider list
    openstack --os-placement-api-version 1.0 resource provider list
    

    CLI가 환경마다 조금 다를 수 있어서, 저는 먼저 엔드포인트와 인증이 정상인지부터 확인합니다. 여기서 막히면 뒤 테스트는 전부 헛수고가 되더라고요. 삽질 좀 했습니다 ㅎㅎ

    4-3. API 직접 조회 예시

    export TOKEN=$(openstack token issue -f value -c id)
    export PLACEMENT_URL=$(openstack endpoint list --service placement -f value -c URL | head -n 1)
    
    curl -s -H "X-Auth-Token: ${TOKEN}" \
         -H "OpenStack-API-Version: placement 1.0" \
         "${PLACEMENT_URL}/resource_providers" | jq .
    

    이렇게 직접 보면 중간 계층 없이 Placement 서비스의 응답만 확인하기 좋습니다. 벤치마크는 가능하면 레이어를 나눠서 보세요. Nova까지 한 번에 보면 편하긴 한데, 원인 분리가 어려워집니다.

    4-4. 간단한 부하 스크립트 예시

    제가 자주 쓰는 방식은 Python(파이썬)으로 요청 수, 동시성, 헤더를 명시하는 간단한 스크립트를 먼저 만드는 겁니다. 전문 부하도구를 써도 되지만, 초기에 API 동작 확인은 직접 짠 스크립트가 오히려 빠를 때가 많습니다.

    import os
    import time
    import statistics
    import concurrent.futures
    import requests
    
    TOKEN = os.environ["TOKEN"]
    PLACEMENT_URL = os.environ["PLACEMENT_URL"].rstrip("/")
    HEADERS = {
        "X-Auth-Token": TOKEN,
        "OpenStack-API-Version": "placement 1.0",
    }
    URL = f"{PLACEMENT_URL}/allocation_candidates?resources=VCPU:2,MEMORY_MB:4096,DISK_GB:20"
    
    
    def fetch():
        start = time.perf_counter()
        r = requests.get(URL, headers=HEADERS, timeout=10)
        elapsed = time.perf_counter() - start
        return r.status_code, elapsed
    
    
    def run(total=100, workers=10):
        results = []
        with concurrent.futures.ThreadPoolExecutor(max_workers=workers) as ex:
            futures = [ex.submit(fetch) for _ in range(total)]
            for f in concurrent.futures.as_completed(futures):
                results.append(f.result())
    
        latencies = [elapsed for status, elapsed in results if status == 200]
        errors = [status for status, _ in results if status != 200]
    
        print("total=", len(results))
        print("success=", len(latencies))
        print("errors=", len(errors))
        if latencies:
            print("avg=", round(statistics.mean(latencies), 4))
            print("max=", round(max(latencies), 4))
    
    
    if __name__ == "__main__":
        run(total=300, workers=30)
    

    이 스크립트는 아주 기본형입니다. 운영에서 쓰려면 요청 경로를 더 나누고, P95/P99 계산도 붙이고, 결과를 파일로 남기면 좋습니다.

    5. 단계별 OpenStack Placement 벤치마크 진행 방법

    이제 실제 진행 순서입니다. 여기서는 벤치마크 결과를 왜곡하지 않도록, 시나리오를 점진적으로 키우는 방식이 좋습니다.

    1. 기준선(Baseline) 측정
      아무 조건 없는 조회부터 시작합니다. Resource Provider 수가 적은 상태에서 먼저 응답 시간을 봅니다.
    2. 조건 추가
      Trait와 Aggregate 조건을 하나씩 늘려봅니다. 어떤 조건이 급격한 지연을 만드는지 확인합니다.
    3. 동시성 증가
      workers 값을 점진적으로 올립니다. 갑자기 10배로 올리면 원인 파악이 힘듭니다.
    4. 데이터 규모 증가
      리소스 프로바이더와 할당 데이터를 늘린 상태에서 다시 측정합니다.
    5. 읽기/쓰기 혼합
      조회만이 아니라 할당 갱신 요청과 함께 테스트합니다.

    여기서 중요한 포인트! 한 번에 하나씩만 바꾸세요. 저도 예전에 노드 수, 동시성, 조건을 한꺼번에 바꿨다가 뭐가 원인인지 한참 못 찾았거든요.

    5-1. allocation_candidates 요청 예시

    curl -s -H "X-Auth-Token: ${TOKEN}" \
         -H "OpenStack-API-Version: placement 1.0" \
         "${PLACEMENT_URL}/allocation_candidates?resources=VCPU:4,MEMORY_MB:8192,DISK_GB:40" | jq .
    

    5-2. trait 조건 포함 예시

    curl -s -H "X-Auth-Token: ${TOKEN}" \
         -H "OpenStack-API-Version: placement 1.0" \
         "${PLACEMENT_URL}/allocation_candidates?resources=VCPU:4,MEMORY_MB:8192&required=CUSTOM_SSD" | jq .
    

    5-3. 결과 저장 예시

    for w in 1 5 10 20 30; do
      echo "workers=${w}" >> placement-bench.txt
      python3 placement_bench.py --workers ${w} --total 200 >> placement-bench.txt
      sleep 2
    done
    

    실제로 써보니까 중간중간 쿨다운을 조금 넣는 게 결과 해석에 편했습니다. 연속 폭격만 하면 캐시, DB 커넥션, 시스템 부하가 뒤섞여서 패턴이 흐려질 수 있거든요.

    OpenStack Placement 벤치마크 실행 과정 이미지

    터미널에서 Placement API 벤치마크를 실행하는 장면과 요청 흐름을 시각화한 이미지입니다.

    6. ⚠️ 실제로 겪은 문제와 트러블슈팅

    이 섹션은 진짜 중요합니다. 벤치마크는 돌렸는데 결과를 믿을 수 없는 경우가 생각보다 많거든요.

    6-1. 인증 토큰 만료

    장시간 테스트에서 은근 자주 나옵니다. 처음엔 성능 저하인 줄 알았는데, 알고 보니 중간부터 401이 섞이더라고요. 그래서 저는 토큰 재발급 루틴을 넣거나, 테스트 시간을 짧게 끊어서 돌립니다.

    6-2. DB가 먼저 병목이 되는 경우

    Placement 서비스만 보고 있으면 놓치기 쉽습니다. API 프로세스 CPU는 여유 있는데 응답 시간이 늘어난다면, DB 슬로우 쿼리(slow query)를 꼭 보셔야 합니다. 특히 후보 계산 관련 조회가 커지는 구간에서 차이가 보일 수 있습니다.

    6-3. 로그 레벨 때문에 성능이 왜곡되는 경우

    디버그 로그를 켜고 벤치마크 돌리면, 그 자체가 부하가 됩니다. 저도 “왜 오늘따라 이렇게 느리지?” 했다가 로그 설정부터 다시 봤던 적이 있습니다. 디버깅과 성능 측정은 분리하는 게 맞습니다.

    6-4. 캐시 효과로 첫 번째와 두 번째 결과가 다른 경우

    이건 꽤 흔합니다. 첫 실행과 반복 실행 결과를 구분해서 기록해두세요. 워밍업(warm-up) 구간을 따로 두는 이유가 있습니다.

    증상 의심 포인트 확인 방법
    응답 시간 급증 DB 병목 DB 모니터링, 슬로우 쿼리 로그 확인
    간헐적 실패 토큰 만료 또는 타임아웃 HTTP 상태 코드 분리 기록
    반복할수록 빨라짐 캐시 또는 워밍업 효과 초기 구간과 본 측정 구간 분리
    노드 수 증가 후 급격히 느려짐 후보 계산 복잡도 증가 조건별 시나리오 재실행

    7. 검증과 결과 해석: 숫자보다 패턴을 보세요

    벤치마크 결과를 볼 때 저는 보통 세 가지 질문을 던집니다.

    1. 동시성이 올라갈 때 지연 시간이 선형적으로 늘어나는가?
    2. 특정 조건(trait, aggregate)에서만 갑자기 악화되는가?
    3. Placement API 응답 시간과 실제 인스턴스 생성 지연이 같이 움직이는가?

    예를 들어 평균 응답 시간은 괜찮아 보여도, P99가 튄다면 운영 체감은 이미 나빠졌을 수 있습니다. 반대로 수치가 조금 높아도 일관되게 유지되면 운영상 더 다루기 쉽습니다. 결국 중요한 건 안정성 있는 자원 할당 성능입니다.

    제가 직접 해보니 결과 해석은 아래 순서가 제일 실용적이었습니다.

    • API 응답 시간 분포 확인
    • 오류율 확인
    • DB와 서비스 프로세스 리소스 사용량 확인
    • 실제 스케줄링 체감과 비교
    grep -E "avg|max|errors|workers" placement-bench.txt
    

    가능하다면 결과는 시각화해두세요. 작은 차이도 그래프로 보면 패턴이 보입니다. 특히 worker 수 증가에 따른 지연 변화는 선 그래프로 보면 바로 감이 오더라고요.

    OpenStack Placement 벤치마크 결과 대시보드 이미지

    응답 시간, 오류율, 동시성 변화가 한눈에 보이는 벤치마크 결과 대시보드 이미지입니다.

    8. 정리와 다음 단계

    OpenStack Placement 벤치마크는 단순히 API를 두드려보는 테스트가 아닙니다. 대규모 OpenStack 인프라에서 실제 스케줄링 여유치를 확인하고, 병목이 Placement 서비스 자체인지, DB인지, 아니면 상위 스케줄링 로직인지 구분하는 과정에 가깝습니다. 처음엔 좀 복잡해 보여도, 시나리오를 잘게 나누고 한 번에 하나씩 바꾸면 훨씬 명확해집니다.

    이번 글의 핵심만 다시 묶어보면 이렇습니다.

    • 평균값보다 분포를 보세요. 특히 꼬리 지연이 중요합니다.
    • 조회와 갱신을 분리해서도 보고, 섞어서도 보세요.
    • Placement만 보지 말고 DB와 실제 스케줄링 체감도 함께 보세요.
    • 결과 숫자보다 병목이 시작되는 패턴을 찾으세요.

    다음 글에서는 Nova Scheduler(노바 스케줄러)와 Placement 서비스의 상호작용을 조금 더 깊게 다뤄볼 예정입니다. 이전 글에서 다뤘던 API 응답 시간 분석 방법이 있다면 같이 보셔도 흐름이 잘 연결될 겁니다. 혹시 지금 운영 중인 환경에서 Placement 성능이 의심된다면, 오늘 소개한 최소 구성 벤치마크부터 먼저 돌려보세요. 생각보다 빨리 단서가 나옵니다. 드디어 됐다! 하는 순간이 오더라고요 🎉

    벤치마크 시나리오별 관찰 포인트와 튜닝 우선순위를 요약한 인포그래픽입니다.

    FAQ: 자주 묻는 질문

    Q1. Placement API만 빠르면 스케줄링도 무조건 빠른가요?

    그건 아닙니다. Placement는 중요한 구성요소지만 전부는 아니거든요. Nova Scheduler, MQ, DB, 하이퍼바이저 상태까지 같이 봐야 합니다.

    Q2. 작은 환경에서도 벤치마크가 의미가 있나요?

    네, 있습니다. 절대 수치보다 패턴을 보는 데 의미가 큽니다. 홈랩에서도 병목 시작 지점을 찾는 연습이 충분히 됩니다.

    Q3. 어느 수치가 정상인가요?

    환경마다 다르기 때문에 단일 기준을 말하기는 어렵습니다. 그래서 더더욱 동일 환경에서 조건별 상대 비교가 중요합니다.

    Q4. 튜닝은 어디부터 시작하면 될까요?

    제 경험상 무작정 서비스 파라미터부터 건드리기보다, 요청 패턴 분리, DB 관찰, 후보 계산이 무거운 조건 파악부터 하는 게 훨씬 효율적이었습니다.

  • [OpenStack] OpenStack Octavia 성능 벤치마크: 실제 환경 부하 테스트 분석

    [OpenStack] OpenStack Octavia 성능 벤치마크: 실제 환경 부하 테스트 분석

    OpenStack Octavia 성능 벤치마크: 실제 환경 부하 테스트 분석

    OpenStack Octavia 성능이 궁금할 때 제일 답답한 부분이 뭔지 아시나요? 문서는 분명 있는데, 막상 실제 환경에서 로드 밸런서 벤치마크를 해보면 숫자보다 병목 지점이 더 크게 보인다는 점입니다. 저도 홈랩과 사내 검증 환경에서 여러 번 테스트했었는데, 처음엔 단순히 가상머신 사양만 올리면 해결될 줄 알았습니다. 근데 실제로 써보니까 그게 다가 아니더라고요. 네트워크 경로, Amphora(앰포라, Octavia가 생성하는 로드 밸런서 인스턴스), 백엔드 응답 시간, health monitor(헬스 모니터) 간격까지 다 영향을 줍니다. 이번 글에서는 OpenStack Octavia 성능을 볼 때 어떤 항목을 기준으로 벤치마크를 잡아야 하는지, 그리고 제가 현장에서 자주 보는 병목 포인트를 기준으로 OpenStack 부하 테스트 방법을 정리해보겠습니다.

    1. 왜 OpenStack Octavia 성능 벤치마크가 중요한가

    로드 밸런서가 느리면 애플리케이션이 느린 것처럼 보입니다. 그래서 팀 내부에서 원인 분석을 시작하면 웹 서버를 의심하고, DB를 의심하고, 나중에 가서야 LB를 보는 경우가 많거든요. 사실 여기서 중요한 포인트는 Octavia는 단순 기능 확인만으로 끝내면 안 된다는 점입니다.

    • North-South traffic(외부에서 내부로 들어오는 트래픽) 집중 시 병목이 생길 수 있습니다.
    • Listener(리스너), Pool(풀), Member(멤버) 구성 방식에 따라 처리 경향이 달라집니다.
    • SSL termination(SSL 종료)를 LB에서 처리하면 CPU 사용량이 확 올라갑니다.
    • 백엔드가 느린 경우에도 LB 지표만 보면 정상처럼 보일 수 있습니다.

    쉽게 말해, Octavia 벤치마크는 단순히 "초당 몇 요청"만 보는 테스트가 아니라 어디서 밀리는지 찾는 과정이라고 보시면 됩니다.

    OpenStack Octavia 성능 테스트 전체 아키텍처 다이어그램

    OpenStack Octavia 성능 테스트에서 클라이언트, 로드 밸런서, 백엔드 서버, 모니터링 경로가 어떻게 연결되는지 보여주는 개요 이미지입니다.

    2. Octavia 구조를 먼저 이해해야 벤치마크가 보입니다

    저도 처음엔 헷갈렸는데, Octavia는 그냥 API만 있는 게 아니라 뒤에서 실제 트래픽을 받아주는 구성이 따로 있습니다. 많이 쓰는 방식은 Amphora provider(앰포라 프로바이더) 기반입니다. 이 방식은 로드 밸런서 생성 시 전용 인스턴스를 띄워서 트래픽을 처리하죠.

    2-1. 핵심 구성요소

    구성요소 역할 성능 관점 체크 포인트
    Listener 클라이언트 요청 수신 프로토콜, 포트, TLS 종료 여부
    Pool 백엔드 서버 그룹 알고리즘, 세션 분산 방식
    Member 실제 백엔드 인스턴스 응답 시간 편차, NIC 성능
    Health Monitor 상태 점검 체크 간격, timeout, 과민 탐지 여부
    Amphora 트래픽 처리 인스턴스 vCPU, 메모리, 네트워크 경로

    여기서 자주 하는 오해가 하나 있습니다. 백엔드 서버가 빠르면 LB도 빠를 거다라고 생각하는 건데요, 실제로는 LB가 먼저 CPU saturation(포화) 상태에 들어갈 수 있습니다. 특히 TLS를 넣는 순간 체감 차이가 꽤 큽니다.

    2-2. 벤치마크에서 꼭 나눠 봐야 하는 항목

    1. L4 성격의 단순 전달 테스트
    2. HTTP/HTTPS 요청 처리 테스트
    3. Keep-Alive(연결 재사용) 유무 비교
    4. 동시 접속 수 증가에 따른 지연 시간 변화
    5. 백엔드 응답 지연이 LB에 주는 영향

    이렇게 쪼개서 봐야 "Octavia가 느린지", 아니면 "뒤 서버가 느린지"가 구분됩니다.

    3. 테스트 전제 조건: 같은 조건으로 반복 가능하게 만들기

    로드 밸런서 벤치마크는 재현성이 생명입니다. 제가 직접 해보니 테스트할 때마다 부하 발생 위치가 조금씩 달라져서, 조건을 정리하지 않으면 결과 해석이 거의 불가능하더라고요.

    • 백엔드 서버 수는 고정합니다.
    • 응답하는 콘텐츠 크기를 일정하게 맞춥니다.
    • 클라이언트와 LB 사이 네트워크 구간을 동일하게 둡니다.
    • 테스트 도구와 동시성 수준을 기록합니다.
    • 모니터링 수집 주기를 맞춥니다.

    아래처럼 아주 단순한 HTTP 응답 서버를 두고 시작하면 비교가 편합니다.

    python3 -m http.server 8080

    물론 실서비스와 완전히 같지는 않지만, 1차로 LB 자체 오버헤드만 보기에 좋습니다. 그다음에 Nginx(엔진엑스, 웹 서버)나 실제 애플리케이션으로 넘어가면 되죠.

    4. OpenStack Octavia 성능 측정을 위한 실전 구성

    이제 실제로 구성해보겠습니다. 환경마다 네트워크 이름이나 서브넷 이름은 다르겠지만, 흐름은 거의 비슷합니다.

    4-1. 로드 밸런서 생성

    openstack loadbalancer create --name lb-octavia-bench --vip-subnet-id private-subnet
    openstack loadbalancer listener create --name listener-http --protocol HTTP --protocol-port 80 lb-octavia-bench
    openstack loadbalancer pool create --name pool-http --lb-algorithm ROUND_ROBIN --listener listener-http --protocol HTTP
    openstack loadbalancer member create --subnet-id private-subnet --address 10.0.0.21 --protocol-port 8080 pool-http
    openstack loadbalancer member create --subnet-id private-subnet --address 10.0.0.22 --protocol-port 8080 pool-http
    openstack loadbalancer healthmonitor create --delay 5 --timeout 3 --max-retries 3 --type HTTP pool-http

    여기서 ROUND_ROBIN(라운드 로빈)은 가장 무난한 시작점입니다. 처음엔 이게 뭔가 싶었는데, 비교 기준점으로 쓰기엔 제일 편하더라고요.

    4-2. Floating IP 연결 후 확인

    openstack loadbalancer show lb-octavia-bench
    curl -I http://<VIP_OR_FLOATING_IP>

    이 단계에서 응답 헤더가 안정적으로 오는지 먼저 확인합니다. 벤치마크 전에 기본 동작부터 체크해야 삽질을 줄일 수 있습니다.

    OpenStack Octavia 성능 벤치마크용 Listener Pool Member 구성 이미지

    Listener, Pool, Member, Health Monitor 구성이 어떻게 연결되는지 보여주는 중간 구성 이미지입니다.

    4-3. 부하 테스트 도구 실행

    도구는 여러 개가 있지만, 저는 보통 wrk나 ab(ApacheBench, 아파치벤치)처럼 간단한 것부터 봅니다. 처음부터 너무 복잡하게 들어가면 결과 해석이 어려워지거든요.

    wrk -t4 -c100 -d60s http://<VIP_OR_FLOATING_IP>/
    ab -n 10000 -c 100 http://<VIP_OR_FLOATING_IP>/

    중요한 건 숫자 자체보다 아래 항목입니다.

    • Latency(지연 시간) 분포가 급격히 튀는지
    • Requests/sec(초당 요청) 변화가 안정적인지
    • Socket errors(소켓 에러)나 timeout이 생기는지
    • 백엔드 서버 간 분산이 고르게 되는지

    5. 측정 중 같이 봐야 하는 모니터링 포인트

    OpenStack Octavia 성능을 제대로 보려면 LB만 보면 안 됩니다. 이건 정말 많이들 놓치시는데요, 최소한 아래 지표는 같이 봐야 합니다.

    1. Amphora 인스턴스 CPU 사용률
    2. Amphora 네트워크 송수신량
    3. 백엔드 인스턴스 CPU와 응답 시간
    4. Neutron(뉴트론, OpenStack 네트워크) 경로 이상 여부
    5. 에러 로그와 health monitor 상태 변화

    제가 실무에서 자주 보는 패턴은 이렇습니다. 클라이언트 측 처리량은 안 올라가는데, LB CPU가 먼저 꽉 찹니다. 또는 LB는 멀쩡한데 특정 백엔드 한 대만 응답이 늦어서 전체 지연이 길어집니다. 그래서 OpenStack 부하 테스트는 항상 다층으로 봐야 합니다.

    openstack loadbalancer amphora list
    openstack loadbalancer amphora show <AMPHORA_ID>
    openstack loadbalancer status show lb-octavia-bench

    상태 조회를 반복하면서 부하 순간에 멤버 변동이 있는지도 봐두면 좋습니다. health monitor가 너무 예민하면 정상 서버가 빠졌다가 다시 붙는 현상도 생기거든요.

    6. ⚠️ 실제로 많이 겪는 문제와 해결 포인트

    여기서는 제가 삽질 좀 했던 부분 위주로 적어보겠습니다. 문서만 보면 금방 될 것 같았는데, 실환경에서는 생각보다 변수 많습니다.

    6-1. TLS 종료를 넣자마자 처리량이 떨어지는 경우

    이건 꽤 흔합니다. HTTPS listener를 활성화하면 암복호화 비용이 생기니까요. 해결 방향은 단순합니다.

    • 우선 HTTP 기준 성능을 먼저 확인합니다.
    • TLS 적용 후 CPU 사용량 증가 패턴을 비교합니다.
    • 인증서 체인 구성과 cipher suite(암호군) 정책을 과도하게 잡지 않았는지 봅니다.

    6-2. 백엔드 분산이 고르지 않은 경우

    애플리케이션이 Keep-Alive 연결을 길게 유지하면 라운드 로빈 체감이 생각보다 덜 날 수 있습니다. 이런 경우는 짧은 테스트와 긴 테스트를 따로 보세요.

    6-3. health monitor가 정상 서버를 자꾸 제외하는 경우

    timeout과 delay가 너무 타이트하면 일시적인 지연만 있어도 멤버가 빠집니다. 특히 디스크 I/O가 순간적으로 튀는 백엔드에서 자주 보입니다.

    문제 증상 의심 포인트 우선 확인할 것
    응답 지연 급증 Amphora CPU 포화 LB 인스턴스 자원 사용률
    간헐적 5xx 백엔드 응답 불안정 멤버별 로그, health monitor
    분산 불균형 연결 재사용 영향 테스트 방식, 세션 유지 여부
    처리량 정체 네트워크 경로 병목 MTU, overlay 네트워크, 보안 정책

    ⚠️ 경고: LB 성능이 안 나온다고 바로 Octavia 설정부터 뒤집지 마세요. 실제로는 백엔드 애플리케이션 응답 패턴이 원인인 경우가 더 많았습니다.

    OpenStack Octavia 성능 부하 테스트 모니터링 대시보드 이미지

    부하 테스트 중 Amphora CPU, 네트워크 사용량, 응답 지연이 함께 보이는 모니터링 화면을 설명하는 이미지입니다.

    7. 결과는 어떻게 해석해야 하나

    이제 결과를 봐야 하는데, 여기서도 함정이 있습니다. 단일 숫자 하나로 결론 내리면 안 됩니다. 제 경험상 아래 순서로 보면 훨씬 덜 헷갈립니다.

    1. 에러 없이 테스트가 끝났는지 확인
    2. 지연 시간이 동시성 증가에 따라 선형적으로 늘어나는지 확인
    3. 특정 시점부터 급격히 꺾이는 구간이 있는지 확인
    4. 그 시점의 Amphora와 백엔드 상태를 대조

    예를 들어 이런 식으로 해석할 수 있습니다.

    • 초반부터 지연이 높다: 네트워크 경로나 백엔드 초기 응답 문제 가능성
    • 중간까지 안정적이다가 급락한다: LB 또는 백엔드 자원 포화 가능성
    • 에러 없이 처리량만 정체된다: 연결 수, 커널 튜닝, 테스트 클라이언트 한계도 의심

    제가 직접 해보니 결국 의미 있는 벤치마크는 비교 기준이 있는 테스트였습니다. HTTP 대 HTTPS, Keep-Alive on/off, 멤버 2대 대 4대, health monitor 완화 전후처럼요. 이런 비교가 있어야 Octavia 최적화 포인트가 보입니다.

    7-1. 검증 체크리스트

    • ✅ VIP 응답 정상
    • ✅ 백엔드 분산 정상
    • ✅ 부하 중 health monitor 오탐 없음
    • ✅ 테스트 반복 시 결과 경향 유사
    • ✅ LB와 백엔드 병목 구분 가능

    8. 정리: OpenStack Octavia 성능 최적화는 이렇게 접근하시면 됩니다

    OpenStack Octavia 성능을 높이려면 무조건 사양부터 올리는 접근보다, 어떤 레이어가 병목인지 먼저 나누는 게 훨씬 중요합니다. 저도 예전엔 수치만 보고 튜닝했었는데, 나중에 보니 health monitor 설정 하나가 더 큰 영향을 준 적도 있었습니다. 그래서 지금은 항상 기준선 측정 – 변경 – 재측정 순서로 갑니다.

    • 기준선 만들기: HTTP 단순 응답으로 시작
    • 변수 분리: TLS, 동시성, 멤버 수를 하나씩 변경
    • 모니터링 병행: Amphora와 백엔드 지표를 같이 확인
    • 해석 중심: 최대 처리량보다 지연과 에러 패턴을 우선 확인

    혹시 이런 경험 있으신가요? LB는 멀쩡해 보이는데 서비스는 느리고, 팀마다 서로 자기 쪽은 문제 없다고 하는 상황이요. 이럴 때 Octavia 벤치마크를 체계적으로 잡아두면 원인 분석 속도가 확실히 빨라집니다. 다음 글에서는 Octavia 최적화 관점에서 health monitor, TLS 종료, 백엔드 연결 유지 전략을 더 깊게 다뤄볼 예정입니다. 이전 글에서 다뤘던 Neutron 네트워크 점검 방법과 같이 보시면 더 도움이 될 겁니다.

    OpenStack Octavia 성능 최적화 전후 비교 요약 이미지

    벤치마크 결과를 해석하는 핵심 포인트와 튜닝 전후 비교 항목을 한눈에 보여주는 요약 이미지입니다.

    9. 자주 묻는 질문 FAQ

    Q1. Octavia 벤치마크는 어떤 도구로 시작하는 게 좋나요?

    A. 저는 wrk나 ab처럼 단순한 도구부터 시작하는 편입니다. 복잡한 시나리오는 나중에 넣어도 늦지 않습니다.

    Q2. 처리량보다 지연 시간을 더 봐야 하나요?

    A. 네, 특히 운영 환경에서는 평균 처리량보다 tail latency(상위 지연 구간)와 에러 발생 시점이 더 중요하더라고요.

    Q3. OpenStack 부하 테스트에서 가장 먼저 의심할 곳은 어디인가요?

    A. LB 단독보다는 네트워크 경로와 백엔드 응답 패턴을 먼저 함께 보시는 걸 권합니다.

    벤치마크 준비 항목, 모니터링 포인트, 자주 묻는 질문을 정리한 마무리 요약 이미지입니다.