Spaces:
Sleeping
Sleeping
| """Tests for core/validator.py — CNC manufacturability validation. | |
| These tests require CadQuery to be installed. | |
| """ | |
| import pytest | |
| from core.executor import execute_cadquery | |
| from core.validator import validate_for_cnc, CNCValidationResult, CNCIssue | |
| pytestmark = pytest.mark.requires_cadquery | |
| def _make_solid(code: str): | |
| """Helper to create a CadQuery Workplane from code.""" | |
| result = execute_cadquery(code) | |
| assert result.success, f"Code failed: {result.error}" | |
| return result.result | |
| class TestValidateForCnc: | |
| def test_simple_box_is_machinable(self): | |
| solid = _make_solid("result = cq.Workplane('XY').box(50, 30, 10)") | |
| val = validate_for_cnc(solid, "test_box") | |
| assert val.machinable is True | |
| assert val.error_count == 0 | |
| def test_result_has_part_name(self): | |
| solid = _make_solid("result = cq.Workplane('XY').box(50, 30, 10)") | |
| val = validate_for_cnc(solid, "my_part") | |
| assert val.part_name == "my_part" | |
| def test_axis_recommendation_default_3axis(self): | |
| solid = _make_solid("result = cq.Workplane('XY').box(50, 30, 10)") | |
| val = validate_for_cnc(solid) | |
| assert "3-axis" in val.axis_recommendation or "3" in val.axis_recommendation | |
| def test_complex_part_gets_higher_axis(self): | |
| code = ''' | |
| result = cq.Workplane('XY').box(50, 50, 50) | |
| for i in range(5): | |
| result = result.faces('>Z').workplane().pushPoints([(i*8-16, 0)]).hole(3) | |
| for i in range(5): | |
| result = result.faces('>X').workplane().pushPoints([(i*8-16, 0)]).hole(3) | |
| ''' | |
| solid = _make_solid(code) | |
| val = validate_for_cnc(solid) | |
| assert val.part_name is not None | |
| def test_oversized_part_flagged(self): | |
| solid = _make_solid("result = cq.Workplane('XY').box(600, 600, 600)") | |
| val = validate_for_cnc(solid, config={"max_part_size_mm": 500.0}) | |
| assert any(i.category == "Size" for i in val.issues) | |
| def test_tiny_part_flagged(self): | |
| solid = _make_solid("result = cq.Workplane('XY').box(0.5, 0.5, 0.5)") | |
| val = validate_for_cnc(solid, config={"min_part_size_mm": 1.0}) | |
| assert any(i.category == "Size" for i in val.issues) | |
| def test_summary_format(self): | |
| solid = _make_solid("result = cq.Workplane('XY').box(50, 30, 10)") | |
| val = validate_for_cnc(solid, "test") | |
| summary = val.summary() | |
| assert isinstance(summary, str) | |
| assert "test" in summary | |
| def test_custom_config(self): | |
| solid = _make_solid("result = cq.Workplane('XY').box(50, 30, 10)") | |
| val = validate_for_cnc(solid, config={"min_wall_thickness_mm": 0.5}) | |
| assert isinstance(val, CNCValidationResult) | |
| def test_error_and_warning_counts(self): | |
| solid = _make_solid("result = cq.Workplane('XY').box(50, 30, 10)") | |
| val = validate_for_cnc(solid) | |
| assert val.error_count >= 0 | |
| assert val.warning_count >= 0 | |
| assert val.error_count + val.warning_count <= len(val.issues) | |