1+ name : Build Wheels
2+
3+ on :
4+ push :
5+ tags : [ 'v*' ]
6+ workflow_dispatch :
7+
8+ jobs :
9+ build_wheels :
10+ name : Build wheels on ${{ matrix.os }}
11+ runs-on : ${{ matrix.os }}
12+ strategy :
13+ matrix :
14+ include :
15+ - os : ubuntu-24.04
16+ arch : x86_64
17+ - os : windows-2022
18+ arch : AMD64
19+ - os : macos-13
20+ arch : x86_64
21+ - os : macos-14
22+ arch : arm64
23+
24+ steps :
25+ - name : Checkout PyHelios
26+ uses : actions/checkout@v4
27+ with :
28+ submodules : recursive
29+ fetch-depth : 0 # Required for setuptools-scm
30+
31+ - name : Set up Python
32+ uses : actions/setup-python@v4
33+ with :
34+ python-version : ' 3.8' # Use lowest supported version for compatibility
35+
36+ - name : Setup MSVC (Windows)
37+ if : runner.os == 'Windows'
38+ uses : ilammy/msvc-dev-cmd@v1
39+
40+ - name : Install Helios dependencies (Linux)
41+ if : runner.os == 'Linux'
42+ run : |
43+ cd helios-core/utilities
44+ sudo bash dependencies.sh ALL
45+
46+ - name : Install Helios dependencies (macOS)
47+ if : runner.os == 'macOS'
48+ run : |
49+ cd helios-core/utilities
50+ # Install base + visualization dependencies (no GPU/CUDA for macOS builds)
51+ bash dependencies.sh BASE
52+ bash dependencies.sh VIS
53+
54+ - name : Debug environment (macOS)
55+ if : runner.os == 'macOS'
56+ run : |
57+ echo "=== Directory structure ==="
58+ ls -la
59+ echo "=== PyHelios build scripts ==="
60+ ls -la build_scripts/
61+ echo "=== Helios core ==="
62+ ls -la helios-core/ || echo "helios-core not found"
63+ echo "=== Python version and location ==="
64+ python --version
65+ which python
66+ echo "=== Environment ==="
67+ env | grep -E "(PYTHON|PATH)" | head -10
68+
69+ - name : Install CUDA Toolkit (Windows)
70+ if : runner.os == 'Windows'
71+ shell : powershell
72+ run : |
73+ # Download CUDA 12.6 installer
74+ Invoke-WebRequest -Uri "https://developer.download.nvidia.com/compute/cuda/12.6.2/network_installers/cuda_12.6.2_windows_network.exe" -OutFile "cuda_installer.exe"
75+ # Install CUDA toolkit components needed for compilation
76+ Start-Process -FilePath ".\cuda_installer.exe" -ArgumentList "-s","nvcc_12.6","cudart_12.6","nvrtc_12.6","nvrtc_dev_12.6","visual_studio_integration_12.6" -Wait
77+ # Add CUDA to PATH for subsequent steps
78+ echo "C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v12.6\bin" | Out-File -FilePath $env:GITHUB_PATH -Encoding utf8 -Append
79+
80+ - name : Install cibuildwheel and repair tools
81+ run : |
82+ python -m pip install --upgrade pip
83+ python -m pip install cibuildwheel
84+ # Install platform-specific wheel repair tools
85+ if [ "${{ runner.os }}" = "Linux" ]; then
86+ python -m pip install auditwheel
87+ elif [ "${{ runner.os }}" = "macOS" ]; then
88+ python -m pip install delocate
89+ fi
90+
91+ - name : Build wheels
92+ run : python -m cibuildwheel --output-dir wheelhouse
93+ env :
94+ # Build for Python 3.8+ on all platforms
95+ CIBW_BUILD : cp38-* cp39-* cp310-* cp311-* cp312-*
96+
97+ # Skip 32-bit builds and PyPy
98+ CIBW_SKIP : " *-win32 *-manylinux_i686 *-musllinux* pp*"
99+
100+ # Architecture configuration based on runner
101+ CIBW_ARCHS : ${{ matrix.arch }}
102+
103+ # Platform-specific build commands with broad CUDA compatibility
104+ CIBW_BEFORE_BUILD_MACOS : " python build_scripts/prepare_wheel.py --buildmode release --nogpu --verbose"
105+ CIBW_BEFORE_BUILD_WINDOWS : " set CMAKE_RC_COMPILER= && set PYHELIOS_CUDA_ARCHITECTURES=50;60;70;75;80;86;90 && python build_scripts/prepare_wheel.py --buildmode release --verbose"
106+ CIBW_BEFORE_BUILD_LINUX : " export PYHELIOS_CUDA_ARCHITECTURES=50;60;70;75;80;86;90 && python build_scripts/prepare_wheel.py --buildmode release --verbose"
107+
108+ # Test wheel installation
109+ CIBW_TEST_COMMAND : " python -c 'import pyhelios; print(f\" PyHelios {pyhelios.__version__} imported successfully\" )'"
110+ CIBW_TEST_REQUIRES : " pytest"
111+
112+ # Repair wheels to bundle dependencies
113+ CIBW_REPAIR_WHEEL_COMMAND_MACOS : " delocate-wheel --require-archs {delocate_archs} -w {dest_dir} -v {wheel}"
114+ CIBW_REPAIR_WHEEL_COMMAND_LINUX : " auditwheel repair -w {dest_dir} {wheel}"
115+
116+ - name : Debug build failure
117+ if : failure()
118+ run : |
119+ echo "=== Build Failure Diagnostics ==="
120+ echo "Build directory contents:"
121+ find pyhelios_build -name "*.so" -o -name "*.dll" -o -name "*.dylib" 2>/dev/null || echo "No build directory found"
122+ echo ""
123+ echo "Plugin directory contents:"
124+ ls -la pyhelios/plugins/ 2>/dev/null || echo "No plugins directory found"
125+ echo ""
126+ echo "Wheel directory contents:"
127+ ls -la wheelhouse/ 2>/dev/null || echo "No wheelhouse directory found"
128+ echo ""
129+ echo "Python environment:"
130+ python --version
131+ pip list | grep -E "(cibuildwheel|auditwheel|delocate)" || echo "Wheel tools not found"
132+
133+ - name : Upload wheels as artifacts
134+ uses : actions/upload-artifact@v4
135+ with :
136+ name : wheels-${{ matrix.os }}-${{ matrix.arch }}
137+ path : wheelhouse/*.whl
138+ retention-days : 7
139+
140+ test_wheels :
141+ name : Test wheels on ${{ matrix.os }} Python ${{ matrix.python-version }}
142+ runs-on : ${{ matrix.os }}
143+ needs : build_wheels
144+ strategy :
145+ matrix :
146+ include :
147+ - os : ubuntu-24.04
148+ python-version : ' 3.8'
149+ - os : ubuntu-24.04
150+ python-version : ' 3.11'
151+ - os : windows-2022
152+ python-version : ' 3.8'
153+ - os : windows-2022
154+ python-version : ' 3.11'
155+ - os : macos-13
156+ python-version : ' 3.8'
157+ - os : macos-13
158+ python-version : ' 3.11'
159+ - os : macos-14
160+ python-version : ' 3.8'
161+ - os : macos-14
162+ python-version : ' 3.11'
163+
164+ steps :
165+ - name : Set up Python ${{ matrix.python-version }}
166+ uses : actions/setup-python@v4
167+ with :
168+ python-version : ${{ matrix.python-version }}
169+
170+ - name : Download wheels
171+ uses : actions/download-artifact@v4
172+ with :
173+ pattern : wheels-*
174+ merge-multiple : true
175+ path : wheelhouse
176+
177+ - name : Install wheel
178+ run : |
179+ python -m pip install --upgrade pip
180+ python -m pip install --find-links wheelhouse --no-index pyhelios
181+
182+ - name : Test basic functionality
183+ run : |
184+ python -c "
185+ import pyhelios
186+ from pyhelios import Context, WeberPennTree, WPTType
187+ from pyhelios.types import vec2, vec3, RGBcolor
188+ print(f'PyHelios version: {pyhelios.__version__}')
189+
190+ # Test basic Context operations
191+ context = Context()
192+ center = vec3(1, 2, 3)
193+ color = RGBcolor(0.5, 0.5, 0.5)
194+ uuid = context.addPatch(center=center, size=vec2(1, 1), color=color)
195+ print(f'Added patch with UUID: {uuid}')
196+
197+ # Test plugin availability reporting
198+ from pyhelios.plugins import print_plugin_status
199+ print_plugin_status()
200+ "
201+
202+ publish :
203+ name : Publish to PyPI
204+ runs-on : ubuntu-latest
205+ needs : [build_wheels, test_wheels]
206+ if : github.event_name == 'push' && startsWith(github.ref, 'refs/tags/v')
207+ environment :
208+ name : pypi
209+ url : https://pypi.org/p/pyhelios
210+ permissions :
211+ id-token : write # Required for trusted publishing
212+
213+ steps :
214+ - name : Download all wheels
215+ uses : actions/download-artifact@v4
216+ with :
217+ pattern : wheels-*
218+ merge-multiple : true
219+ path : wheelhouse
220+
221+ - name : Publish to PyPI
222+ uses : pypa/gh-action-pypi-publish@release/v1
223+ with :
224+ packages-dir : wheelhouse/
225+ verify-metadata : false # Skip metadata verification due to dynamic versioning
0 commit comments