From 6cd9e0538ca8993d66a58a75d9b12fae59360ac4 Mon Sep 17 00:00:00 2001 From: Dylan McReynolds <40469975+dylanmcreynolds@users.noreply.github.com> Date: Mon, 10 Nov 2025 16:40:42 -0800 Subject: [PATCH] CI: add container build support (#2) add container build support --- .github/workflows/container-build.yml | 82 ++++++++++++++++++ CONTAINER.md | 115 ++++++++++++++++++++++++++ Containerfile | 37 +++++++++ 3 files changed, 234 insertions(+) create mode 100644 .github/workflows/container-build.yml create mode 100644 CONTAINER.md create mode 100644 Containerfile diff --git a/.github/workflows/container-build.yml b/.github/workflows/container-build.yml new file mode 100644 index 00000000..76023cf0 --- /dev/null +++ b/.github/workflows/container-build.yml @@ -0,0 +1,82 @@ +name: Build and Publish Container Images + +on: + push: + branches: + - master + - main + tags: + - 'v*' + pull_request: + branches: + - master + - main + workflow_dispatch: + +env: + REGISTRY: ghcr.io + IMAGE_NAME: ${{ github.repository }} + +jobs: + build-and-push: + runs-on: ubuntu-latest + permissions: + contents: read + packages: write + + steps: + - name: Checkout repository + uses: actions/checkout@v4 + + - name: Free up disk space + run: | + sudo rm -rf /usr/share/dotnet + sudo rm -rf /opt/ghc + sudo rm -rf /usr/local/share/boost + sudo rm -rf "$AGENT_TOOLSDIRECTORY" + docker system prune -af + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + + - name: Log in to GitHub Container Registry + if: github.event_name != 'pull_request' + uses: docker/login-action@v3 + with: + registry: ${{ env.REGISTRY }} + username: ${{ github.actor }} + password: ${{ secrets.GITHUB_TOKEN }} + + - name: Extract metadata (tags, labels) + id: meta + uses: docker/metadata-action@v5 + with: + images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }} + tags: | + type=ref,event=branch + type=ref,event=pr + type=semver,pattern={{version}} + type=semver,pattern={{major}}.{{minor}} + type=semver,pattern={{major}} + type=raw,value=latest,enable={{is_default_branch}} + + - name: Build and push container image + id: build + uses: docker/build-push-action@v5 + with: + context: . + file: Containerfile + push: ${{ github.event_name != 'pull_request' }} + tags: ${{ steps.meta.outputs.tags }} + labels: ${{ steps.meta.outputs.labels }} + cache-from: type=gha + cache-to: type=gha,mode=max + platforms: linux/amd64,linux/arm64 + + - name: Generate artifact attestation + if: github.event_name != 'pull_request' + uses: actions/attest-build-provenance@v1 + with: + subject-name: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }} + subject-digest: ${{ steps.build.outputs.digest }} + push-to-registry: true diff --git a/CONTAINER.md b/CONTAINER.md new file mode 100644 index 00000000..5fc46c1b --- /dev/null +++ b/CONTAINER.md @@ -0,0 +1,115 @@ +# Container Images + +CDTools is available as a container image on GitHub Container Registry (ghcr.io). The image includes PyTorch with CUDA support and automatically uses GPU acceleration when available, or falls back to CPU mode on systems without GPUs (like Macs). + +## Available Image + +- **Universal image**: `ghcr.io/als-computing/cdtools:latest` + - ~3GB with CUDA support + - Auto-detects and uses GPU when available + - Falls back to CPU on Macs and systems without GPUs + +## Quick Start + +### Using with Podman + +```bash +# Pull the image +podman pull ghcr.io/als-computing/cdtools:latest + +# Run in CPU mode (no GPU flags needed) +podman run -it ghcr.io/als-computing/cdtools:latest + +# Run with GPU support (Linux with NVIDIA GPU - requires nvidia-container-toolkit) +podman run --device nvidia.com/gpu=all -it ghcr.io/als-computing/cdtools:latest + +# Run an example (CPU mode) +podman run -it ghcr.io/als-computing/cdtools:latest \ + python examples/simple_ptycho.py +``` + +### Using with Docker + +```bash +# Pull the image +docker pull ghcr.io/als-computing/cdtools:latest + +# Run in CPU mode (no GPU flags needed - works on Mac too) +docker run -it ghcr.io/als-computing/cdtools:latest + +# Run with GPU support (Linux with NVIDIA GPU - requires NVIDIA Container Toolkit) +docker run --gpus all -it ghcr.io/als-computing/cdtools:latest + +# Run an example (CPU mode) +docker run -it ghcr.io/als-computing/cdtools:latest \ + python examples/simple_ptycho.py +``` + +## Mounting Data + +To work with your own data files: + +```bash +# With Podman (Linux with GPU) +podman run -v /path/to/your/data:/data:z \ + --device nvidia.com/gpu=all -it \ + ghcr.io/als-computing/cdtools:latest \ + python -c "from cdtools.datasets import Ptycho2DDataset; dataset = Ptycho2DDataset.from_cxi('/data/your_file.cxi')" + +# With Docker (Linux with GPU) +docker run -v /path/to/your/data:/data \ + --gpus all -it \ + ghcr.io/als-computing/cdtools:latest \ + python -c "from cdtools.datasets import Ptycho2DDataset; dataset = Ptycho2DDataset.from_cxi('/data/your_file.cxi')" + +# Without GPU (Podman or Docker) +podman run -v /path/to/your/data:/data:z -it ghcr.io/als-computing/cdtools:latest +docker run -v /path/to/your/data:/data -it ghcr.io/als-computing/cdtools:latest +``` + +## Interactive Development + +```bash +# Start an interactive Python session +podman run -it ghcr.io/als-computing/cdtools:latest + +# Start with a bash shell +podman run -it --entrypoint bash ghcr.io/als-computing/cdtools:latest +``` + +## Version Tags + +Images are tagged with: +- `latest` - Latest stable release +- `v0.3.1` - Specific version +- `master` - Latest from master branch + +## Platform Support + +The image works on: +- ✅ **Linux with NVIDIA GPU** - Full CUDA acceleration +- ✅ **Linux without GPU** - CPU mode (automatic fallback) +- ✅ **macOS (Intel/Apple Silicon)** - CPU mode (automatic fallback) +- ✅ **Windows with WSL2** - GPU or CPU mode + +## Image Size + +- **Universal image**: ~3.0 GB (includes CUDA libraries for GPU support) + +## Building Locally + +To build the image locally: + +```bash +# Using Podman +podman build -t cdtools:local . + +# Using Docker +docker build -t cdtools:local . +``` + +## Requirements + +- **For GPU support**: NVIDIA GPU with CUDA support and nvidia-container-toolkit +- **For CPU mode**: No special requirements (works on any system) +- **Mac users**: The image works out of the box in CPU mode diff --git a/Containerfile b/Containerfile new file mode 100644 index 00000000..14afe09d --- /dev/null +++ b/Containerfile @@ -0,0 +1,37 @@ +# Multi-stage build for CDTools - Python library for ptychography and CDI reconstructions +FROM python:3.11-slim as builder + +# Set working directory +WORKDIR /build + +# Install build dependencies +RUN apt-get update && apt-get install -y --no-install-recommends \ + gcc \ + g++ \ + && rm -rf /var/lib/apt/lists/* + +# Copy project files +COPY pyproject.toml setup.py requirements.txt README.md ./ +COPY src/ ./src/ +COPY examples/ ./examples/ + +# Install Python dependencies +RUN pip install --no-cache-dir --upgrade pip setuptools wheel && \ + pip install --no-cache-dir . + +# Final stage - lightweight runtime image +FROM python:3.11-slim + +# Set working directory +WORKDIR /app + +# Copy installed packages from builder +COPY --from=builder /usr/local/lib/python3.11/site-packages /usr/local/lib/python3.11/site-packages +COPY --from=builder /usr/local/bin /usr/local/bin + +# Copy source code (optional, for development) +COPY src/ ./src/ + +# Set Python to run in unbuffered mode +ENV PYTHONUNBUFFERED=1 +