Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
132 changes: 132 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,132 @@
#
# CI — Tests & Checks
#
# Runs on every push and every PR.
# - Lint (cargo clippy + rustfmt)
# - Rust unit tests (cargo test)
# - Python integration tests (pytest)
# - Build check (maturin build)
#

name: CI

on:
push:
branches: ["master", "main"]
pull_request:
branches: ["master", "main"]

env:
CARGO_TERM_COLOR: always
RUST_BACKTRACE: 1

jobs:
# Rust lint + fmt
rust-lint:
name: Rust Lint & Fmt
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4

- name: Install Rust
uses: dtolnay/rust-toolchain@stable
with:
components: clippy, rustfmt

- name: Cache Rust dependencies
uses: Swatinem/rust-cache@v2

- name: Check formatting
run: cargo fmt --all -- --check

- name: Clippy (warnings as errors)
run: cargo clippy --all-targets --all-features -- -D warnings

# Rust unit tests
rust-tests:
name: Rust Tests
runs-on: ubuntu-latest
needs: rust-lint
steps:
- uses: actions/checkout@v4

- name: Install Rust
uses: dtolnay/rust-toolchain@stable

- name: Cache Rust dependencies
uses: Swatinem/rust-cache@v2

- name: Run Rust tests
run: cargo test --all-features

# Python integration tests
python-tests:
name: Python Tests (Python ${{ matrix.python }})
runs-on: ubuntu-latest
needs: rust-lint
strategy:
fail-fast: false
matrix:
python: ["3.10", "3.11", "3.12", "3.13", "3.14"]
steps:
- uses: actions/checkout@v4

- name: Install Rust
uses: dtolnay/rust-toolchain@stable

- name: Cache Rust dependencies
uses: Swatinem/rust-cache@v2

- name: Install uv
uses: astral-sh/setup-uv@v5
with:
enable-cache: true

- name: Set up Python ${{ matrix.python }}
run: uv python install ${{ matrix.python }}

- name: Install dependencies
run: uv sync --all-extras --dev

- name: Build and install Ryx
run: uv run maturin develop --release

- name: Run pytest
run: uv run pytest tests/ -v --tb=short

- name: Run examples smoke test
run: |
for f in examples/*.py; do
echo "Running $f ..."
uv run python "$f"
done

# Maturin build check
build-check:
name: Build Check (wheel)
runs-on: ubuntu-latest
needs: [rust-tests, python-tests]
steps:
- uses: actions/checkout@v4

- name: Install Rust
uses: dtolnay/rust-toolchain@stable

- name: Cache Rust dependencies
uses: Swatinem/rust-cache@v2

- name: Install uv
uses: astral-sh/setup-uv@v5

- name: Build wheel
uses: PyO3/maturin-action@v1
with:
command: build
args: --release --out dist
manylinux: auto

- name: Upload wheel artifact
uses: actions/upload-artifact@v4
with:
name: wheels-linux
path: dist/
68 changes: 68 additions & 0 deletions .github/workflows/docs.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
#
# Docs — Build & Deploy Docusaurus
#
# Builds the Docusaurus documentation and deploys to GitHub Pages.
# Triggers on pushes to the docs/ directory or the master branch.
# Also available as a manual dispatch.
#

name: Docs

on:
push:
branches: ["master", "main"]
paths:
- "docs/**"
- ".github/workflows/docs.yml"
workflow_dispatch:

# Grant GITHUB_TOKEN permission to deploy to GitHub Pages
permissions:
contents: read
pages: write
id-token: write

# Only one deployment at a time; auto-cancel in-progress runs
concurrency:
group: pages
cancel-in-progress: true

jobs:
build:
name: Build Docusaurus Docs
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4

- name: Setup Node.js
uses: actions/setup-node@v4
with:
node-version: "20"
cache: npm
cache-dependency-path: docs/package-lock.json

- name: Install dependencies
working-directory: docs
run: npm ci

- name: Build docs
working-directory: docs
run: npm run build

- name: Upload build artifact
uses: actions/upload-pages-artifact@v3
with:
path: docs/build

deploy:
name: Deploy to GitHub Pages
runs-on: ubuntu-latest
needs: build
if: github.event_name != 'pull_request'
environment:
name: github-pages
url: ${{ steps.deployment.outputs.page_url }}
steps:
- name: Deploy to GitHub Pages
id: deployment
uses: actions/deploy-pages@v4
165 changes: 165 additions & 0 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,165 @@
#
# Release — Build Wheels & Publish to PyPI
#
# Triggered automatically when a Git tag is pushed (e.g. v0.1.0).
# Builds wheels for all major platforms via Maturin's manylinux Docker images
# and native macOS/Windows runners, then publishes to PyPI.
#
# Tag format: v* (e.g. v0.1.0, v1.0.0, v0.2.0-beta.1)
#

name: Release

on:
push:
tags:
- "v*"
workflow_dispatch:

env:
CARGO_TERM_COLOR: always

jobs:
# Build wheels for all platforms
build-wheels:
name: Build Wheels — ${{ matrix.os }} (${{ matrix.target }})
runs-on: ${{ matrix.os }}
strategy:
fail-fast: false
matrix:
include:
# Linux (manylinux) — x86_64
- os: ubuntu-latest
target: x86_64-unknown-linux-gnu
manylinux: auto
# Linux (manylinux) — aarch64
- os: ubuntu-latest
target: aarch64-unknown-linux-gnu
manylinux: auto
# macOS — x86_64 (Intel)
- os: macos-13
target: x86_64-apple-darwin
manylinux: auto
# macOS — aarch64 (Apple Silicon)
- os: macos-latest
target: aarch64-apple-darwin
manylinux: auto
# Windows — x86_64
- os: windows-latest
target: x86_64-pc-windows-msvc
manylinux: auto

steps:
- uses: actions/checkout@v4

- name: Install Rust
uses: dtolnay/rust-toolchain@stable
with:
targets: ${{ matrix.target }}

- name: Cache Rust dependencies
uses: Swatinem/rust-cache@v2

- name: Build wheels
uses: PyO3/maturin-action@v1
with:
target: ${{ matrix.target }}
args: --release --out dist --interpreter 3.10 3.11 3.12 3.13 3.14
manylinux: ${{ matrix.manylinux }}
rust-toolchain: stable

- name: Upload wheel artifact
uses: actions/upload-artifact@v4
with:
name: wheels-${{ matrix.os }}-${{ matrix.target }}
path: dist/

# Build source distribution
build-sdist:
name: Build Source Distribution
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4

- name: Install Rust
uses: dtolnay/rust-toolchain@stable

- name: Cache Rust dependencies
uses: Swatinem/rust-cache@v2

- name: Build sdist
uses: PyO3/maturin-action@v1
with:
command: sdist
args: --out dist

- name: Upload sdist artifact
uses: actions/upload-artifact@v4
with:
name: sdist
path: dist/

# Create GitHub Release
github-release:
name: Create GitHub Release
runs-on: ubuntu-latest
needs: [build-wheels, build-sdist]
if: startsWith(github.ref, 'refs/tags/')
permissions:
contents: write
steps:
- uses: actions/checkout@v4

- name: Download all artifacts
uses: actions/download-artifact@v4
with:
path: dist/
pattern: wheels-*
merge-multiple: true

- name: Download sdist
uses: actions/download-artifact@v4
with:
name: sdist
path: dist/

- name: Create GitHub Release
env:
GH_TOKEN: ${{ github.token }}
run: |
TAG_NAME="${GITHUB_REF#refs/tags/}"
gh release create "$TAG_NAME" dist/* \
--title "Ryx $TAG_NAME" \
--generate-notes \
--draft

# Publish to PyPI
publish-pypi:
name: Publish to PyPI
runs-on: ubuntu-latest
needs: [build-wheels, build-sdist]
if: startsWith(github.ref, 'refs/tags/')
environment:
name: pypi
url: https://pypi.org/p/ryx
permissions:
id-token: write # OIDC token for trusted publishing
steps:
- name: Download all artifacts
uses: actions/download-artifact@v4
with:
path: dist/
pattern: wheels-*
merge-multiple: true

- name: Download sdist
uses: actions/download-artifact@v4
with:
name: sdist
path: dist/

- name: Publish to PyPI
uses: pypa/gh-action-pypi-publish@release/v1
with:
packages-dir: dist/
skip-existing: true