# S01: Core Pipeline — Preprocessing + Vectorization — UAT

**Milestone:** M001
**Written:** 2026-03-26

## UAT Type

- UAT mode: artifact-driven
- Why this mode is sufficient: All pipeline stages are pure functions with deterministic output from synthetic inputs. The 76 automated tests cover the full pipeline from raw bytes to SVG response. No live runtime or human-visual judgment is needed at this stage.

## Preconditions

- Python venv is set up: `engine/.venv/bin/python` exists
- All dependencies installed: `cd engine && .venv/bin/python -c "import cv2, potrace, vtracer, fastapi"` exits 0
- System C libraries present: `dpkg -l libpotrace-dev libagg-dev pkg-config` shows installed

## Smoke Test

```bash
cd engine && .venv/bin/python -m pytest tests/ -v --tb=short
```
**Expected:** 76 passed, 0 failed, 0 errors. Exit code 0.

## Test Cases

### 1. Full test suite passes

1. `cd engine && .venv/bin/python -m pytest tests/ -v`
2. **Expected:** 76 tests pass — 24 preprocessing, 38 vectorize, 14 API integration

### 2. Potrace mode produces valid SVG from PNG

1. `cd engine && .venv/bin/python -m pytest tests/test_api.py::TestTraceEndpointPotrace -v`
2. **Expected:** 4 tests pass — basic trace returns SVG, metadata has correct shape, SVG contains `<path>` elements, custom params are accepted

### 3. VTracer mode produces valid SVG from PNG

1. `cd engine && .venv/bin/python -m pytest tests/test_api.py::TestTraceEndpointVtracer -v`
2. **Expected:** 3 tests pass — basic trace returns SVG, metadata present, custom params accepted

### 4. Validation rejects bad input

1. `cd engine && .venv/bin/python -m pytest tests/test_api.py::TestTraceEndpointValidation -v`
2. **Expected:** 7 tests pass — invalid mode (422), unsupported output format (422), invalid params JSON (422), empty file (422), corrupt image (422), defaults to potrace, preset ignored

### 5. Preprocessing pipeline stages are individually testable

1. `cd engine && .venv/bin/python -m pytest tests/test_preprocessing.py -v`
2. **Expected:** 24 tests pass covering decode, grayscale, denoise, CLAHE, threshold, edge detect, morphological ops, and full pipeline composition

### 6. Potrace and VTracer produce different output from same input

1. `cd engine && .venv/bin/python -m pytest tests/test_vectorize.py::TestVtracerVsPotraceComparison -v`
2. **Expected:** 2 tests pass — both produce valid SVG from same input, outputs differ

### 7. API response shape matches contract

1. `cd engine && .venv/bin/python -c "
from fastapi.testclient import TestClient
from main import app
import numpy as np, cv2, json
client = TestClient(app)
img = np.zeros((100,100,3), dtype=np.uint8)
cv2.rectangle(img, (20,20), (80,80), (255,255,255), -1)
_, buf = cv2.imencode('.png', img)
r = client.post('/engine/trace', files={'file': ('test.png', buf.tobytes(), 'image/png')})
data = r.json()
assert r.status_code == 200
assert set(data.keys()) == {'output', 'format', 'metadata'}
assert data['format'] == 'svg'
assert set(data['metadata'].keys()) == {'path_count', 'node_count_total', 'open_paths', 'warnings', 'processing_ms'}
assert isinstance(data['metadata']['processing_ms'], float)
assert '<svg' in data['output']
print('PASS: response shape matches contract')
"
2. **Expected:** Prints "PASS: response shape matches contract", exit code 0

## Edge Cases

### Empty file upload

1. `cd engine && .venv/bin/python -m pytest tests/test_api.py::TestTraceEndpointValidation::test_empty_file -v`
2. **Expected:** Returns 422 with "Uploaded file is empty"

### Corrupt image bytes

1. `cd engine && .venv/bin/python -m pytest tests/test_api.py::TestTraceEndpointValidation::test_corrupt_image -v`
2. **Expected:** Returns 422 with "Preprocessing failed" message

### All-black and all-white images

1. `cd engine && .venv/bin/python -m pytest tests/test_vectorize.py -v -k "all_black or all_white"`
2. **Expected:** 4 tests pass — both Potrace and VTracer handle degenerate inputs without crashing

### Potrace rejects 3D input

1. `cd engine && .venv/bin/python -m pytest tests/test_vectorize.py::TestPotraceEdgeCases::test_rejects_3d_input -v`
2. **Expected:** Passes — potrace_trace raises ValueError for non-2D input

## Failure Signals

- Any test failure in the 76-test suite indicates a regression
- `import potrace` failing means system C libraries are missing (see L001 in KNOWLEDGE.md)
- `import vtracer` failing means the vtracer pip package wasn't installed
- API returning 500 on valid PNG input indicates a pipeline wiring issue
- Metadata with all zeros (path_count=0) on a non-trivial image suggests SVG format changed

## Not Proven By This UAT

- Output visual quality — no human evaluation of SVG fidelity vs source image
- Performance under load — no concurrency or stress testing
- DXF/JSON output formats — deferred to S02
- Preset system behavior — deferred to S03
- Docker containerized deployment — deferred to S03
- Real-world image quality (photos, logos with gradients, low-res scans)

## Notes for Tester

- All tests must be run with `.venv/bin/python -m pytest`, not bare `python` — there is no system-wide Python on PATH.
- Working directory must be `engine/` for imports to resolve correctly.
- Test images are generated programmatically (numpy arrays), no external fixture files needed.
- Processing times in metadata will vary by machine but should be under 100ms for test images.
