Skip to content

Build Wheels for Sequenzo #151

Build Wheels for Sequenzo

Build Wheels for Sequenzo #151

Workflow file for this run

# GitHub Actions workflow for Sequenzo package
name: Build Wheels for Sequenzo
on:
push:
tags:
- "v*"
pull_request:
branches: [ main ]
workflow_dispatch:
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
jobs:
build:
name: Build ${{ matrix.os }} Py${{ matrix.python-version }}
runs-on: ${{ matrix.os }}
strategy:
fail-fast: false
matrix:
os: [ubuntu-latest, macos-latest, windows-latest]
python-version: ['3.9', '3.10', '3.11', '3.12']
steps:
- name: Checkout source with submodules
uses: actions/checkout@v4
with:
submodules: recursive
- name: Set up Python
uses: actions/setup-python@v4
with:
python-version: ${{ matrix.python-version }}
- name: Ensure setuptools/wheel for macOS Python 3.12
if: runner.os == 'macOS' && matrix.python-version == '3.12'
run: python -m pip install --upgrade pip setuptools wheel
# Add OpenMP support
- name: Install OpenMP (macOS)
if: runner.os == 'macOS'
run: |
brew install libomp
echo "CC=clang" >> $GITHUB_ENV
echo "CXX=clang++" >> $GITHUB_ENV
echo "LDFLAGS=-L$(brew --prefix libomp)/lib" >> $GITHUB_ENV
echo "CPPFLAGS=-I$(brew --prefix libomp)/include" >> $GITHUB_ENV
echo "SEQUENZO_ENABLE_OPENMP=1" >> $GITHUB_ENV
- name: Install OpenMP (Linux)
if: runner.os == 'Linux'
run: |
sudo apt-get update
sudo apt-get install -y libomp-dev
echo "SEQUENZO_ENABLE_OPENMP=1" >> $GITHUB_ENV
- name: Setup MSVC with OpenMP (Windows)
if: runner.os == 'Windows'
uses: ilammy/msvc-dev-cmd@v1
with:
arch: x64
- name: Enable OpenMP (Windows)
if: runner.os == 'Windows'
run: |
echo "SEQUENZO_ENABLE_OPENMP=1" >> $env:GITHUB_ENV
- name: Install R (Windows)
if: runner.os == 'Windows'
uses: r-lib/actions/setup-r@v2
with:
r-version: '4.3.1'
# Install dependencies with fallback strategy
- name: Install dependencies
run: |
python -m pip install --upgrade pip
pip install --only-binary=all "numpy<2.5" || pip install "numpy<2.5"
pip install --only-binary=all "scipy<1.16" || echo "scipy will be installed in cibuildwheel"
pip install --prefer-binary Cython pybind11 build "cibuildwheel==2.23.3" twine
pip install --prefer-binary fastcluster || echo "fastcluster installation attempted"
- name: Build Cython wheels on macOS
if: runner.os == 'macOS'
run: |
python setup.py build_ext --inplace
python -m build
- name: Clean previous build outputs
if: runner.os != 'macOS'
run: |
rm -rf build/ dist/ *.egg-info
find . -name "*.so" -delete
shell: bash
- name: Build wheels with cibuildwheel
if: runner.os != 'macOS'
run: python -m cibuildwheel --output-dir dist
env:
CIBW_SKIP: "*-musllinux* pp*" # 跳过 musllinux 和 PyPy
CIBW_ARCHS_WINDOWS: "AMD64"
CIBW_ARCHS_LINUX: "x86_64"
CIBW_BUILD_VERBOSITY: "1"
# Environment variables
CIBW_ENVIRONMENT_LINUX: SEQUENZO_ENABLE_OPENMP=1
CIBW_ENVIRONMENT_WINDOWS: SEQUENZO_ENABLE_OPENMP=1 DISTUTILS_USE_SDK=1
# Linux: install system dependencies
CIBW_BEFORE_BUILD_LINUX: |
sudo apt-get update
sudo apt-get install -y libomp-dev r-base r-base-dev
python -m pip install --upgrade pip
python -m pip install rpy2
echo "System dependencies installation attempted"
# Windows: skip all extra dependencies, let setup.py handle them
CIBW_BEFORE_BUILD_WINDOWS: |
echo "Using setup.py dependencies only"
REM --- 临时从 PATH 移除 Rtools bin ---
set PATH=%PATH:C:\rtools43\usr\bin;=%
REM --- 确保 MSVC link.exe 在 PATH 前面 ---
set PATH=C:\Program Files\Microsoft Visual Studio\2022\Enterprise\VC\Tools\MSVC\14.44.35207\bin\HostX64\x64;%PATH%
python -m pip install --upgrade pip
python -m pip install rpy2
# Universal dependency installation (fallback)
CIBW_BEFORE_BUILD: >
echo "Using setup.py dependencies only"
# Test command
CIBW_TEST_COMMAND: >
python -c "import sequenzo; print('Sequenzo import successful');
import importlib;
mod = importlib.util.find_spec('sequenzo.clustering.clustering_c_code');
print('C++ extensions loaded' if mod else 'WARNING: C++ extensions not found')"
- name: Show dist content
run: ls -lah dist/
shell: bash
- name: Check wheels
run: twine check dist/*
- name: Verify OpenMP Support
run: |
echo "=== Verifying built wheels ==="
python -c "
import subprocess
import sys
import os
wheel_files = [f for f in os.listdir('dist') if f.endswith('.whl') and 'cp${{ matrix.python-version }}' in f.replace('.', '')]
if wheel_files:
wheel_file = wheel_files[0]
print(f'Installing wheel: {wheel_file}')
subprocess.run([sys.executable, '-m', 'pip', 'install', '--force-reinstall', f'dist/{wheel_file}'], check=True)
import sequenzo
print('Sequenzo import successful')
try:
import sequenzo.clustering.clustering_c_code as cc
print('C++ extensions loaded successfully')
except ImportError as e:
print(f'WARNING: C++ extensions loading failed: {e}')
else:
print('ERROR: No matching wheel files found')
"
shell: bash
- name: Upload wheels
uses: actions/upload-artifact@v4
with:
name: wheels-${{ matrix.os }}-${{ matrix.python-version }}
path: dist/