Skip to content

Commit

Permalink
Add wheel building machinery and workflow.
Browse files Browse the repository at this point in the history
  • Loading branch information
bwoodsend committed Jun 30, 2021
1 parent df76c5f commit 48b49b9
Show file tree
Hide file tree
Showing 2 changed files with 158 additions and 0 deletions.
119 changes: 119 additions & 0 deletions .github/workflows/build-wheels.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,119 @@
---
name: Build Wheels

on:
workflow_dispatch:

jobs:
Standard:
runs-on: ${{ matrix.os }}
strategy:
fail-fast: false
matrix:
os: [macos-11.0, windows-latest, ubuntu-latest]
architecture: [x64]
include:
- os: windows-latest
architecture: x86
steps:

- uses: actions/checkout@v2

- uses: actions/setup-python@v1
with:
python-version: 3.9
architecture: ${{ matrix.architecture }}

- name: Install clang
if: startsWith(matrix.os, 'windows')
uses: bwoodsend/setup-winlibs-action@v1
with:
architecture: ${{ matrix.architecture }}
with_clang: true

# Compile with clang by default which produces faster binaries.
- run: echo CC=clang >> $GITHUB_ENV
# macOS needs special compiler flags to enable 'universal2' binaries.
- if: startsWith(matrix.os, 'macos')
run: CC_FLAGS='-arch x86_64 -arch arm64' >> $GITHUB_ENV

# Check the compiler. Don't fail if CC isn't set.
- run: ${CC:-echo} -v
shell: bash

- run: pip wheel --no-deps -w dist .

# Build a universal2 wheel for macOS to support both arm64 and x86_64.
# Hopefully I'll think of a better way to do this and add it to cslug.
- if: startsWith(matrix.os, 'macos')
run: |
mv dist/*.whl "dist/$(ls dist/ | sed 's/x86_64/universal2/')"
# Build a wheel for modern x86_64 Linux using clang (which produces
# a faster binary than gcc).
- if: startsWith(matrix.os, 'ubuntu')
run: |
pip install auditwheel
export OLD_WHEEL="$(echo dist/*.whl)"
# When glibc on CI updates, update the manylinux variant as needed.
auditwheel repair "$OLD_WHEEL" --plat=manylinux2014_x86_64 -w dist
rm $OLD_WHEEL
- name: Upload wheel(s) as build artifacts
uses: actions/upload-artifact@v2
with:
name: wheels
path: dist/*.whl

- name: Test Wheel
run: |
pip install "$(echo dist/*.whl)[test]" &&
rm -rf motmot &&
pytest --no-cov
shell: bash

Whacky-Linux:
runs-on: ubuntu-latest
strategy:
matrix:
base: [
manylinux1_x86_64,
manylinux1_i686,
manylinux2014_aarch64,
# Support these when NumPy provides wheels for them.
# manylinux2014_ppc64le,
# manylinux2014_s390x,
]
steps:

- uses: actions/checkout@v2
- uses: crazy-max/ghaction-docker-buildx@v3.3.0

- name: Build docker image
run: |
docker build -t bob-the-builder --build-arg BASE=${{ matrix.base }} .
- name: Build wheel
run: |
docker run -v "$(pwd):/io" bob-the-builder bash -c "
rm -rf build /tmp/dist
python setup.py -q bdist_wheel -d /tmp/dist
auditwheel repair /tmp/dist/*.whl -w dist
"
- name: Upload wheel(s) as build artifacts
uses: actions/upload-artifact@v2
with:
name: wheels
path: dist/*.whl

- name: Install and test wheel
run: |
docker run -v "$(pwd)/tests:/tests" -v "$(pwd)/dist:/dist" \
-t bob-the-builder bash -c "
cd ~ &&
pip uninstall -y motmot &&
# Note that this assumes that there is only one wheel in dist.
pip install /dist/motmot*manylinux*.whl &&
pytest /tests
"
39 changes: 39 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
# Docker image generator for manylinux. See:
# https://github.com/pypa/manylinux/tree/manylinux1

# Build with: (note the -t motmot-manylinux1_x86_64 is just an arbitrary name)
# $ docker build -t motmot-manylinux1_x86_64 .
# Or to specify an alternative base (say manylinux1_i686 for 32bit Linux):
# $ docker build -t motmot-manylinux1_i686 --build-arg BASE=manylinux1_i686 .

# Then boot into your new image with:
# $ docker run -v `pwd`:/io -it motmot-manylinux1_x86_64
# The above launches bash inside the image. You can append arbitrary shell
# commands to run those instead such as the following to launch Python:
# $ docker run -v `pwd`:/io -it motmot-manylinux1_x86_64 python
# Or to run pytest:
# $ docker run -v `pwd`:/io -it motmot-manylinux1_x86_64 pytest

ARG BASE=manylinux1_x86_64
FROM quay.io/pypa/${BASE}

# Choosing a Python version is done just by prepending its bin dir to PATH.
ENV PATH=/opt/python/cp39-cp39/bin:$PATH

# Install dependencies. Do this before COPY to encourage caching.
RUN pip install --prefer-binary wheel auditwheel numpy
RUN pip install cslug coverage

# Copy across enough of this repo to build from.
RUN mkdir -p /io/motmot
COPY setup.py /io
COPY pyproject.toml /io
COPY README.md /io
COPY motmot/_version.py /io/motmot
# The rest is expected to be -v mounted at runtime.

# Set this repo's root as the cwd.
WORKDIR /io

# Install it. Skip build isolation for speed (and sanity).
RUN pip install --prefer-binary --no-build-isolation -e .[test]

0 comments on commit 48b49b9

Please sign in to comment.