AI 테스트 프레임워크 기획서
안드로이드 배포 전 AI 모델 실시간 검증 도구
1. 개요
목적
안드로이드에 AI 모델을 적용하기 전, PC 환경에서 카메라 입력을 기반으로 모델의 동작을 실시간으로 검증한다.
배경
- 안드로이드 배포 전 빠른 프로토타이핑 및 모델 검증 필요
- 다양한 모델 종류(분류기, 객체 탐지기 등)를 일관된 방식으로 테스트할 환경 부재
- 커스텀 학습 모델(. onnx, .tflite, .pth 등)을 직접 로드하여 검증하는 워크플로우 필요
2. 기술 스택
| 역할 | 선택 | 비고 |
|---|---|---|
| 언어 | Python | 빠른 프로토타이핑, AI 생태계 풍부 |
| 카메라 / 렌더링 | OpenCV | 실시간 프레임 캡처 및 결과 시각화 |
| 모델 추론 | ONNX Runtime | 포맷 통일, 안드로이드 포팅 용이 |
| 설정 관리 | PyYAML | 모델 경로 및 파라미터 외부화 |
| CLI | argparse / typer | 실행 시 모델 선택 |
| 성능 측정 | time, psutil | FPS, 지연시간 측정 |
Python 채택 근거
- 테스트 목적에 충분한 성능
- PyTorch / TensorFlow / ONNX 등 AI 라이브러리 즉시 활용 가능
- C++ 대비 개발 속도 및 유지보수성 우위
- C++은 ms 단위 최적화가 필요하거나 안드로이드와 추론 엔진을 공유해야 할 때 고려
3. 아키텍처
처리 흐름
카메라 입력 → 전처리 → [파이프라인] → 후처리 → 렌더링 / 출력
↑
모델을 플러그인처럼 등록 / 교체
디렉터리 구조
project/
├── main.py # 진입점
├── config/
│ └── models.yaml # 모델 설정 (경로, 파라미터, 활성화 여부)
├── core/
│ ├── camera.py # 카메라 입력 추상화
│ ├── pipeline.py # 파이프라인 오케스트레이터
│ └── renderer.py # 화면 출력
├── models/
│ ├── base_model.py # 추상 베이스 클래스
│ ├── classifier.py # 분류기 구현
│ ├── detector.py # 객체 탐지 구현
│ └── segmentor.py # 세그멘테이션 구현
└── utils/
├── preprocessor.py # 전처리 유틸
└── metrics.py # FPS, 지연시간 측정
4. 핵심 설계
4-1. 베이스 모델 인터페이스
모든 모델은 BaseModel 을 상속하여 구현한다. 파이프라인은 run() 하나만 호출하며, 내부 구현 방식에 의존하지 않는다.
# models/base_model.py
from abc import ABC, abstractmethod
import numpy as np
class BaseModel(ABC):
def __init__(self, config: dict):
self.config = config
self.load(config["model_path"])
@abstractmethod
def load(self, path: str): ...
@abstractmethod
def preprocess(self, frame: np.ndarray) -> any: ...
@abstractmethod
def infer(self, input) -> any: ...
@abstractmethod
def postprocess(self, output) -> dict: ...
def run(self, frame: np.ndarray) -> dict:
x = self.preprocess(frame)
y = self.infer(x)
return self.postprocess(y)
4-2. 파이프라인 오케스트레이터
# core/pipeline.py
class Pipeline:
def __init__(self):
self._models: dict[str, BaseModel] = {}
self._active: list[str] = []
def register(self, name: str, model: BaseModel):
self._models[name] = model
def activate(self, names: list[str]):
self._active = names
def run(self, frame) -> dict:
results = {}
for name in self._active:
results[name] = self._models[name].run(frame)
return results
4-3. 설정 파일 (models. yaml)
models:
mobilenet_classifier:
type: classifier
model_path: weights/mobilenet.onnx
input_size: [224, 224]
active: true
yolo_detector:
type: detector
model_path: weights/yolo.onnx
conf_threshold: 0.5
active: false
5. 모델 파일 로드 방식
패키지(pip) 설치 방식이 아닌 로컬 파일 직접 로드 방식을 채택한다.
포맷별 로드 방법
# .onnx
import onnxruntime as ort
self.session = ort.InferenceSession("model.onnx")
# .tflite
import tensorflow as tf
interpreter = tf.lite.Interpreter(model_path="model.tflite")
interpreter.allocate_tensors()
# .pth (PyTorch)
import torch
self.model = torch.load("model.pth")
self.model.eval()
# .pt (TorchScript)
self.model = torch.jit.load("model.pt")
방식 비교
| 항목 | 파일 직접 로드 (채택) | pip install |
|---|---|---|
| 커스텀 학습 모델 사용 | ✅ 가능 | ❌ 공개 모델만 |
| 안드로이드 포팅 검증 | ✅ 적합 | ❌ 내부 구조 미노출 |
| 모델 버전 관리 | weight 파일로 직접 관리 | pip 버전으로 관리 |
권장 포맷:
.onnxONNX Runtime은 PyTorch / TensorFlow 모델을 변환하여 일관되게 관리할 수 있으며, 안드로이드에서도 ONNX Runtime Mobile로 동일 포맷을 재사용할 수 있어 포팅 비용이 최소화된다.
6. 확장 계획
| 상황 | 대응 방법 |
|---|---|
| 새 모델 종류 추가 | BaseModel 상속 후 파일 1개 추가 |
| 모델 가중치 교체 | config/models.yaml 경로만 수정 |
| 복수 모델 동시 테스트 | --models A B C CLI 옵션으로 멀티 활성화 |
| 성능 측정 추가 | pipeline.run() 앞뒤에 metrics 삽입 |
| 안드로이드 포팅 | infer() 내부만 TFLite / ONNX Mobile API로 교체 |
7. 실행 방법 (예정)
# 단일 모델 실행
python main.py --models mobilenet_classifier
# 복수 모델 동시 실행
python main.py --models mobilenet_classifier yolo_detector
# 설정 파일 지정
python main.py --config config/models.yaml --models yolo_detector
8. 향후 검토 사항
- 멀티스레드 추론 (카메라 입력 / 추론 분리)
- 결과 로깅 및 저장 기능
- 모델별 정확도 / 속도 벤치마크 리포트 출력
- GUI 기반 모델 선택 인터페이스 (tkinter 등)
- 안드로이드 포팅 후 PC 결과와의 출력 비교 검증
C
Contents
