반응형
아래는 **GPU-Hour + 평균 GPU 사용률 보정까지 포함한 “월별 GPU 리포트 Lambda 고급 버전”**입니다.
👉 실제 차지백(Chargeback) 분쟁이 거의 없는 방식
👉 대기업·연구기관에서 가장 많이 쓰는 정산 로직입니다.
1️⃣ 정산 로직 요약 (핵심)
✅ 최종 비용 계산식
최종 비용 = GPU-Hour × GPU 단가 × 사용률 보정 계수
✅ 사용률 보정 계수 표 (권장)
평균 GPU 사용률보정 계수
| 70% 이상 | 1.0 |
| 40 ~ 69% | 0.8 |
| 20 ~ 39% | 0.6 |
| 20% 미만 | 0.4 |
2️⃣ Prometheus 쿼리 (2개 사용)
① 월별 GPU 사용 시간 (GPU-Hour)
sum by (namespace, modelName) ( count_over_time( DCGM_FI_DEV_GPU_UTIL > 0 [30d]) )
② 월 평균 GPU 사용률
avg by (namespace, modelName) ( DCGM_FI_DEV_GPU_UTIL )
3️⃣ Lambda 환경 변수 (추가 포함)
변수명설명
| PROMETHEUS_URL | Prometheus URL |
| S3_BUCKET | 리포트 저장 버킷 |
| S3_PREFIX | reports/gpu |
| GPU_PRICE_A100 | A100 단가 |
| GPU_PRICE_T4 | T4 단가 |
| GPU_PRICE_A10G | A10G 단가 |
4️⃣ Lambda Python 코드 (고급 버전)
import os import csv import requests import boto3 from datetime import datetime, timedelta PROM_URL = os.environ['PROMETHEUS_URL'] S3_BUCKET = os.environ['S3_BUCKET'] S3_PREFIX = os.environ.get('S3_PREFIX', 'reports/gpu') GPU_PRICE = { "A100": float(os.environ.get("GPU_PRICE_A100", 4000)), "T4": float(os.environ.get("GPU_PRICE_T4", 900)), "A10G": float(os.environ.get("GPU_PRICE_A10G", 1500)), } s3 = boto3.client('s3') def query_prometheus(query): r = requests.get( f"{PROM_URL}/api/v1/query", params={"query": query}, timeout=15 ) r.raise_for_status() return r.json()['data']['result'] def utilization_factor(util): if util >= 70: return 1.0 elif util >= 40: return 0.8 elif util >= 20: return 0.6 else: return 0.4 def lambda_handler(event, context): # 전월 계산 today = datetime.utcnow() first_day = today.replace(day=1) last_month = first_day - timedelta(days=1) report_month = last_month.strftime("%Y-%m") # PromQL gpu_hour_q = """ sum by (namespace, modelName) ( count_over_time( DCGM_FI_DEV_GPU_UTIL > 0 [30d]) ) """ avg_util_q = """ avg by (namespace, modelName) ( DCGM_FI_DEV_GPU_UTIL ) """ gpu_hours = query_prometheus(gpu_hour_q) avg_utils = query_prometheus(avg_util_q) # 평균 사용률 매핑 util_map = {} for u in avg_utils: key = ( u['metric'].get('namespace', 'unknown'), u['metric'].get('modelName', 'unknown') ) util_map[key] = float(u['value'][1]) rows = [] for g in gpu_hours: namespace = g['metric'].get('namespace', 'unknown') model = g['metric'].get('modelName', 'unknown') hours = float(g['value'][1]) avg_util = util_map.get((namespace, model), 0.0) factor = utilization_factor(avg_util) price = GPU_PRICE.get(model, 0) raw_cost = hours * price final_cost = raw_cost * factor rows.append([ report_month, namespace, model, round(hours, 2), round(avg_util, 2), factor, price, round(final_cost, 2) ]) filename = f"gpu-usage-advanced-{report_month}.csv" path = f"/tmp/{filename}" with open(path, "w", newline="") as f: writer = csv.writer(f) writer.writerow([ "Month", "Namespace", "GPU_Model", "GPU_Hours", "Avg_GPU_Util(%)", "Util_Factor", "Price_per_Hour", "Final_Cost" ]) writer.writerows(rows) s3_key = f"{S3_PREFIX}/{filename}" s3.upload_file(path, S3_BUCKET, s3_key) return { "status": "success", "report": f"s3://{S3_BUCKET}/{s3_key}", "rows": len(rows) }
5️⃣ 생성되는 CSV 리포트 예시
MonthNamespaceGPUGPU-HoursAvg UtilFactorCost
| 2025-12 | team-ai | A100 | 320 | 78% | 1.0 | 1,280,000 |
| 2025-12 | team-data | T4 | 210 | 35% | 0.6 | 113,400 |
👉 “GPU는 썼지만 효율이 낮으면 비용도 줄어드는 구조”
6️⃣ 실무 운영 팁 (중요)
✔ 왜 이 방식이 좋은가?
- GPU 점유만 하고 놀리는 문제 방지
- 팀 간 비용 분쟁 최소화
- 사용자 스스로 GPU 효율 개선 유도
✔ 감사/재무 대응에 강함
- “사용 시간 + 사용률” 근거 명확
- 수작업 계산 불필요
- 월별 이력 추적 가능
반응형
'[GPUaaS]' 카테고리의 다른 글
| [네이버 MLXP] 사용 예시 총정리 (0) | 2026.01.08 |
|---|---|
| 📌 MLXP란 무엇인가? (1) | 2026.01.08 |
| [MLXP] GPU 효율화를 선도하는 대규모 MLOps 플랫폼 (0) | 2026.01.08 |
| [경영진 보고용] 월별 GPU 사용 PDF 리포트 자동 생성 (Lambda) (0) | 2026.01.07 |
| 월별 GPU 리포트 Lambda 코드 (Prometheus 기반) (0) | 2026.01.07 |
| [Prometheus] GPU 정산용 쿼리 모음 (실무 표준) (0) | 2026.01.07 |
| [GPU] 사용량 대시보드 제공 & 월별 리포트 자동 생성 방법 (0) | 2026.01.07 |
| [사내 GPUaaS] 표준 아키텍처 문서 (0) | 2026.01.07 |
댓글