Tantangan Validasi Model Vision pada Pipeline CI
Penerapan continuous integration (CI) untuk model computer vision sering kali terhambat oleh durasi pengujian yang panjang dan ketiadaan verifikasi performa runtime sebelum artefak model masuk ke production registry. Pada arsitektur deteksi objek modern seperti YOLO26, verifikasi bobot (weights) tidak cukup hanya mengandalkan kelulusan syntax test script training. Diperlukan validasi komputasi nyata: verifikasi struktur graf export ONNX, evaluasi drop metrik mAP, serta uji regresi latensi inferensi.
Panduan ini menguraikan arsitektur CI berbasis GitHub Actions untuk mengeksekusi pipeline validasi model YOLO26. Alur kerja mencakup export ONNX terintegrasi, benchmark latensi inference engine, dan penerapan quality gate berbasis ambang batas (thresholds).
Arsitektur Validasi Otomatis
Pipeline validasi bekerja secara deterministik pada setiap pull request yang menyentuh berkas bobot model (.pt) atau konfigurasi inferensi. Alur eksekusi dirancang sebagai berikut:
- Restorasi Cache Lingkungan: Menggunakan layer cache untuk Python wheel dan ONNX Runtime backend guna menghemat waktu build runner.
- Validasi Graf & Export ONNX: Konversi bobot native PyTorch ke format ONNX opset 17+ dengan post-processing terintegrasi. Hal ini mengeliminasi kebutuhan Non-Maximum Suppression (NMS) manual di layer CPU klien.
- Evaluasi Metrik (mAP 50-95): Eksekusi validasi pada subset data test untuk memastikan kuantisasi atau export tidak mendegradasi akurasi deteksi melebihi batas toleransi.
- Quality Gate Latensi: Benchmark latensi end-to-end pada inference engine target (ONNX Runtime). Jika latensi P95 melewati threshold yang ditentukan, build ditandai gagal (exit status non-zero).
Script Benchmarking Latensi dan Verifikasi Threshold
Skrip berikut mengevaluasi waktu eksekusi model ONNX secara end-to-end. Benchmark mengisolasi overhead I/O, menerapkan fase warm-up untuk menstabilkan alokasi memori runtime, dan menghitung persentil latensi.
import time
import sys
import numpy as np
import onnxruntime as ort
def benchmark_model(onnx_path, iterations=200, warmup=20, max_latency_p95_ms=15.0):
session_options = ort.SessionOptions()
session_options.graph_optimization_level = ort.GraphOptimizationLevel.ORT_ENABLE_ALL
session = ort.InferenceSession(onnx_path, session_options, providers=["CPUExecutionProvider"])
input_meta = session.get_inputs()[0]
shape = [dim if isinstance(dim, int) else 1 for dim in input_meta.shape]
dummy_input = np.random.randn(*shape).astype(np.float32)
# Fase warm-up
for _ in range(warmup):
session.run(None, {input_meta.name: dummy_input})
# Pengukuran latensi
latencies = []
for _ in range(iterations):
t0 = time.perf_counter()
session.run(None, {input_meta.name: dummy_input})
latencies.append((time.perf_counter() - t0) * 1000.0)
p95_latency = np.percentile(latencies, 95)
mean_latency = np.mean(latencies)
print(f"[INFO] Benchmark Selesai: Rata-rata = {mean_latency:.2f} ms | P95 = {p95_latency:.2f} ms")
if p95_latency > max_latency_p95_ms:
print(f"[ERROR] Latensi P95 ({p95_latency:.2f} ms) melampaui batas ambang ({max_latency_p95_ms} ms)!")
sys.exit(1)
print("[SUCCESS] Kriteria performa terpenuhi.")
sys.exit(0)
if __name__ == "__main__":
benchmark_model(sys.argv[1])
Konfigurasi GitHub Actions & Strategi Caching
Dependencies deep learning seperti PyTorch dan ONNX Runtime berukuran besar (ratusan megabyte). Menyimpannya pada cache GitHub Actions menghemat waktu deployment runner hingga 60-70%. Konfigurasi di bawah menjalankan tahapan export, validasi mAP minimal, dan eksekusi quality gate latensi.
name: Model Validation & ONNX Latency Gate
on:
pull_request:
paths:
- 'models/**'
- '.github/workflows/model-ci.yml'
jobs:
validate-and-gate:
runs-on: ubuntu-latest
steps:
- name: Checkout Repository
uses: actions/checkout@v4
- name: Setup Python
uses: actions/setup-python@v5
with:
python-version: '3.10'
- name: Cache Pip Packages
uses: actions/cache@v4
with:
path: ~/.cache/pip
key: ${{ runner.os }}-pip-${{ hashFiles('requirements-ci.txt') }}
restore-keys: |
${{ runner.os }}-pip-
- name: Install Runtime Dependencies
run: |
pip install -r requirements-ci.txt
- name: Export Model to ONNX
run: |
# Export dengan end-to-end decoders terintegrasi
python -m yolo_framework.export --weights models/yolo26-custom.pt --format onnx --opset 17 --simplify
- name: Evaluate Accuracy Gate (mAP)
run: |
# Evaluasi pada validation subset
python -m yolo_framework.val --weights models/yolo26-custom.onnx --data data/ci-val-split.yaml --min-map50-95 0.45
- name: Evaluate Latency Gate
run: |
python scripts/ci_benchmark.py models/yolo26-custom.onnx
Trade-offs dan Pertimbangan Produksi
- Hardware Environment Parity: Runner GitHub Actions standar menggunakan CPU virtual (vCPU shared). Nilai latensi absolut tidak dapat disamakan secara langsung dengan edge device atau GPU target produksi. Gunakan CI self-hosted runner jika memerlukan profiling berbasis hardware khusus seperti TensorRT pada GPU NVIDIA atau NPU embedded.
- Model Graph Optimization: Export model langsung tanpa
--simplifysering kali menyisakan node redundan di graf ONNX yang memicu degradasi latensi sekunder. Selalu validasi struktur graf menggunakan tool seperti ONNX Simplifier sebelum evaluasi latensi. - Threshold Degradasi Dinamis: Alih-alih nilai latensi absolut statis, alternatif arsitektur yang lebih toleran terhadap fluktuasi runner vCPU adalah membandingkan latensi PR cabang terhadap latensi baseline branch
main(regresi persentase maksimal, misal +5%).
Komentar
0 komentar
Masuk ke akun kamu untuk ikut berkomentar.
Belum ada komentar
Jadilah yang pertama ikut berdiskusi!