ebaafbe6e9
Worker: POST /dxf/preview legge il DXF con read_xld_dxf (lo stesso lettore di CompareDxf) e ritorna contorni in mm con y verso il basso, bbox, dimensioni, entita e punti (tetto 20000, decimazione uniforme). Backend: POST /api/vision/dxf-preview (Maker) che inoltra al worker; 422 inoltrato. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
91 lines
3.1 KiB
Python
91 lines
3.1 KiB
Python
"""#101: POST /api/vision/dxf-preview, anteprima del DXF nel wizard.
|
|
|
|
Il worker non gira nei test: `vision_service.dxf_preview` si sostituisce.
|
|
"""
|
|
import pytest
|
|
from fastapi import HTTPException
|
|
|
|
from src.backend.config import settings
|
|
from src.backend.services import vision_service
|
|
from src.backend.tests.conftest import auth_headers
|
|
|
|
BODY = {
|
|
"contorni": [[[0.0, 0.0], [10.0, 0.0], [10.0, 5.0], [0.0, 5.0], [0.0, 0.0]]],
|
|
"bbox": {"xmin": 0.0, "ymin": 0.0, "xmax": 10.0, "ymax": 5.0},
|
|
"larghezza_mm": 10.0, "altezza_mm": 5.0, "entita": 1, "punti": 5,
|
|
}
|
|
|
|
|
|
def _post(client, user, content=b"0\nEOF"):
|
|
return client.post(
|
|
"/api/vision/dxf-preview",
|
|
headers=auth_headers(user),
|
|
files={"dxf": ("d.dxf", content, "application/octet-stream")},
|
|
)
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_dxf_preview_forwards_the_file_and_returns_the_worker_body(
|
|
client, maker_user, monkeypatch,
|
|
):
|
|
calls = []
|
|
|
|
async def fake(dxf_bytes, worker_url=None):
|
|
calls.append(dxf_bytes)
|
|
return BODY
|
|
|
|
monkeypatch.setattr("src.backend.services.vision_service.dxf_preview", fake)
|
|
resp = await _post(client, maker_user, b"DXF-BYTES")
|
|
assert resp.status_code == 200, resp.text
|
|
assert resp.json() == BODY
|
|
assert calls == [b"DXF-BYTES"]
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_dxf_preview_forwards_the_worker_422(client, maker_user, monkeypatch):
|
|
async def fake(dxf_bytes, worker_url=None):
|
|
raise HTTPException(status_code=422, detail="DXF illeggibile: file vuoto")
|
|
|
|
monkeypatch.setattr("src.backend.services.vision_service.dxf_preview", fake)
|
|
resp = await _post(client, maker_user, b"")
|
|
assert resp.status_code == 422
|
|
assert resp.json()["detail"] == "DXF illeggibile: file vuoto"
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_dxf_preview_requires_maker(client, measurement_tec_user, monkeypatch):
|
|
async def fake(dxf_bytes, worker_url=None):
|
|
return BODY
|
|
|
|
monkeypatch.setattr("src.backend.services.vision_service.dxf_preview", fake)
|
|
resp = await _post(client, measurement_tec_user)
|
|
assert resp.status_code == 403
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_dxf_preview_too_big_is_422(client, maker_user, monkeypatch):
|
|
monkeypatch.setattr(settings, "max_upload_size_mb", 0)
|
|
resp = await _post(client, maker_user, b"x" * 10)
|
|
assert resp.status_code == 422
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_dxf_preview_service_posts_to_worker_and_checks_shape(monkeypatch):
|
|
seen = {}
|
|
|
|
async def fake_multipart(path, *, files, data, worker_url=None, timeout=120.0):
|
|
seen.update(path=path, files=files)
|
|
return BODY
|
|
|
|
monkeypatch.setattr(vision_service, "call_worker_multipart", fake_multipart)
|
|
assert await vision_service.dxf_preview(b"abc") == BODY
|
|
assert seen["path"] == "/dxf/preview" and seen["files"]["dxf"][1] == b"abc"
|
|
|
|
async def malformed(path, *, files, data, worker_url=None, timeout=120.0):
|
|
return {"contorni": []}
|
|
|
|
monkeypatch.setattr(vision_service, "call_worker_multipart", malformed)
|
|
with pytest.raises(HTTPException) as exc:
|
|
await vision_service.dxf_preview(b"abc")
|
|
assert exc.value.status_code == 502
|