import base64 import pytest from app.domain.models import DesignBrief, StructureAnalysis from app.services.design_pipeline import ( create_style_directions, fallback_structure, generated_image_bytes, resolve_model_instance, ) @pytest.mark.asyncio async def test_manual_model_routing_uses_selected_pool_item() -> None: values = { "image_routing_mode": "manual", "image_model_id": "image-2", "model_pool": [ { "id": "image-2", "enabled": True, "capabilities": ["image_generation"], } ], } assert await resolve_model_instance(values, "image") == "image-2" @pytest.mark.asyncio async def test_generated_image_bytes_accepts_verified_inline_image() -> None: content = b"\x89PNG\r\n\x1a\n" + b"x" * 2048 payload = { "data": [ { "url": "data:image/png;base64," + base64.b64encode(content).decode("ascii") } ] } image, content_type = await generated_image_bytes(payload) assert image == content assert content_type == "image/png" @pytest.mark.asyncio async def test_style_direction_generation_has_non_blocking_fallback() -> None: brief = DesignBrief(preferred_styles=["现代简约"], disliked_elements=["复杂吊顶"]) directions, model_name = await create_style_directions({}, brief, StructureAnalysis()) assert len(directions) == 3 assert all(direction.prompt for direction in directions) assert "降级" in model_name def test_spatial_fallback_remains_editable() -> None: analysis = fallback_structure("provider unavailable") assert analysis.degraded is True assert analysis.status == "needs_review" assert len(analysis.rooms) >= 6 assert analysis.risks == ["provider unavailable"]