Skip to content

Merge pull request #36 from bhack/issue-35-auto-preset-startup-scope #229

Merge pull request #36 from bhack/issue-35-auto-preset-startup-scope

Merge pull request #36 from bhack/issue-35-auto-preset-startup-scope #229

Workflow file for this run

name: CI
on:
push:
branches:
- main
pull_request:
workflow_dispatch:
inputs:
flatpak_runtime_smoke:
description: Run the experimental Flatpak PipeWire routing smoke test
type: boolean
default: false
headless_pipewire_runtime_smoke:
description: Run the headless PipeWire/WirePlumber controller smoke test
type: boolean
default: false
live_ui_runtime_smoke:
description: Run the live GTK/AT-SPI/PipeWire smoke test
type: boolean
default: false
smoke_only:
description: Skip ordinary CI work and run only the requested experimental smoke job
type: boolean
default: false
flatpak_runtime_build:
description: Build and reinstall the local Flatpak before the runtime smoke test
type: boolean
default: true
flatpak_runtime_install_remote:
description: Install the smoke target from Flathub instead of using a local build
type: boolean
default: false
flatpak_runtime_app_ref:
description: Optional Flatpak app ref to run; blank infers the build or install ref
type: string
default: ""
flatpak_runtime_install_ref:
description: Flathub ref to install when flatpak_runtime_install_remote is enabled
type: string
default: io.github.bhack.mini-eq
flatpak_runtime_expected_version:
description: Optional installed Flatpak version expected by the runtime smoke test
type: string
default: ""
permissions:
contents: read
pull-requests: read
concurrency:
group: ${{ github.workflow }}-${{ github.event_name }}-${{ github.event.pull_request.number || github.ref }}
cancel-in-progress: true
env:
PWG_VERSION: "0.3.9"
PWG_REQUIREMENT: "pipewire-gobject>=0.3.9,<0.4"
jobs:
changes:
runs-on: ubuntu-24.04
outputs:
flatpak: ${{ steps.filter.outputs.flatpak }}
release_metadata: ${{ steps.filter.outputs.release_metadata }}
test: ${{ steps.filter.outputs.test }}
tooling: ${{ steps.filter.outputs.tooling }}
pwg: ${{ steps.filter.outputs.pwg }}
steps:
- name: Check out repository
uses: actions/checkout@v6
with:
ref: ${{ github.event_name == 'pull_request' && github.base_ref || github.ref }}
- name: Detect changed files
id: filter
env:
BEFORE: ${{ github.event.before }}
GH_TOKEN: ${{ github.token }}
PR_NUMBER: ${{ github.event.pull_request.number }}
SMOKE_ONLY: ${{ inputs.smoke_only }}
run: |
set -euo pipefail
files="$(mktemp)"
fallback_scopes() {
local value="$1"
{
echo "test=$value"
echo "tooling=$value"
echo "pwg=$value"
echo "flatpak=$value"
echo "release_metadata=$value"
} >> "$GITHUB_OUTPUT"
{
echo "### CI scope"
echo
echo "tools/ci_scope.py is not available in the checked-out base branch; falling back to \`$value\` for every scope."
echo
echo "- test: \`$value\`"
echo "- tooling: \`$value\`"
echo "- pipewire-gobject: \`$value\`"
echo "- flatpak: \`$value\`"
echo "- release metadata: \`$value\`"
} >> "$GITHUB_STEP_SUMMARY"
}
set_scopes() {
if [[ -f tools/ci_scope.py ]]; then
python3 tools/ci_scope.py "$@" \
--github-output "$GITHUB_OUTPUT" \
--github-summary "$GITHUB_STEP_SUMMARY"
return
fi
if [[ "${1:-}" == "--none" ]]; then
fallback_scopes false
else
fallback_scopes true
fi
}
case "$GITHUB_EVENT_NAME" in
workflow_dispatch)
if [[ "${SMOKE_ONLY:-false}" == "true" ]]; then
set_scopes --none
exit 0
fi
set_scopes --all
exit 0
;;
pull_request)
gh api --paginate "repos/$GITHUB_REPOSITORY/pulls/$PR_NUMBER/files" --jq '.[].filename' > "$files"
;;
push)
if [[ -z "${BEFORE:-}" || "$BEFORE" =~ ^0+$ ]]; then
set_scopes --all
exit 0
fi
gh api "repos/$GITHUB_REPOSITORY/compare/$BEFORE...$GITHUB_SHA" --jq '.files[].filename' > "$files"
;;
*)
set_scopes --all
exit 0
;;
esac
set_scopes "$files"
release-metadata:
needs: changes
if: ${{ always() && !(github.event_name == 'workflow_dispatch' && inputs.smoke_only) }}
runs-on: ubuntu-24.04
steps:
- name: Require change detection
if: ${{ needs.changes.result != 'success' }}
run: exit 1
- name: Skip unchanged scope
if: ${{ needs.changes.outputs.release_metadata != 'true' }}
run: echo "No release metadata changes detected; skipping release metadata status check."
- name: Check out repository
if: ${{ needs.changes.outputs.release_metadata == 'true' }}
uses: actions/checkout@v6
- name: Check local release metadata status
if: ${{ needs.changes.outputs.release_metadata == 'true' }}
run: python3 tools/release_status.py --no-network
tooling:
needs: changes
if: ${{ always() && !(github.event_name == 'workflow_dispatch' && inputs.smoke_only) }}
runs-on: ubuntu-24.04
steps:
- name: Require change detection
if: ${{ needs.changes.result != 'success' }}
run: exit 1
- name: Skip unchanged scope
if: ${{ needs.changes.outputs.tooling != 'true' }}
run: echo "No maintainer-tooling changes detected; skipping tooling job work."
- name: Check out repository
if: ${{ needs.changes.outputs.tooling == 'true' }}
uses: actions/checkout@v6
- name: Cache pip downloads
if: ${{ needs.changes.outputs.tooling == 'true' }}
uses: actions/cache@v5
with:
path: ~/.cache/pip
key: tooling-pip-${{ runner.os }}-${{ hashFiles('pyproject.toml') }}
restore-keys: tooling-pip-${{ runner.os }}-
- name: Install Python tooling
if: ${{ needs.changes.outputs.tooling == 'true' }}
run: |
python3 -m venv .venv
.venv/bin/python -m pip install --upgrade pip
.venv/bin/python -m pip install ruff
- name: Lint
if: ${{ needs.changes.outputs.tooling == 'true' }}
run: .venv/bin/python -m ruff check .
- name: Check formatting
if: ${{ needs.changes.outputs.tooling == 'true' }}
run: .venv/bin/python -m ruff format --check .
test:
needs: changes
if: ${{ always() && !(github.event_name == 'workflow_dispatch' && inputs.smoke_only) }}
runs-on: ubuntu-24.04
steps:
- name: Require change detection
if: ${{ needs.changes.result != 'success' }}
run: exit 1
- name: Skip unchanged scope
if: ${{ needs.changes.outputs.test != 'true' }}
run: echo "No Python/package changes detected; skipping test job work."
- name: Check out repository
if: ${{ needs.changes.outputs.test == 'true' }}
uses: actions/checkout@v6
- name: Cache pip downloads and wheels
if: ${{ needs.changes.outputs.test == 'true' }}
uses: actions/cache@v5
with:
path: ~/.cache/pip
key: test-pip-${{ runner.os }}-py3-${{ hashFiles('pyproject.toml') }}
restore-keys: test-pip-${{ runner.os }}-py3-
- name: Install system dependencies
if: ${{ needs.changes.outputs.test == 'true' }}
run: |
sudo apt-get update
sudo apt-get install -y \
gir1.2-adw-1 \
gir1.2-gtk-4.0 \
gobject-introspection \
libgirepository1.0-dev \
libglib2.0-dev \
libpipewire-0.3-dev \
meson \
ninja-build \
pipewire \
python3-cairo \
python3-dev \
python3-gi \
python3-pip \
python3-setuptools \
python3-venv \
wireplumber
- name: Install Python dependencies
if: ${{ needs.changes.outputs.test == 'true' }}
run: |
python3 -m venv /tmp/mini-eq-pwg-build
/tmp/mini-eq-pwg-build/bin/python -m pip install --upgrade pip
/tmp/mini-eq-pwg-build/bin/python -m pip wheel "$PWG_REQUIREMENT" -w /tmp/mini-eq-wheelhouse
python3 -m venv --system-site-packages .venv
.venv/bin/python -m pip install --upgrade pip
.venv/bin/python -m pip install --no-index --find-links /tmp/mini-eq-wheelhouse "$PWG_REQUIREMENT"
.venv/bin/python -m pip install -e '.[dev]'
- name: Lint
if: ${{ needs.changes.outputs.test == 'true' }}
run: .venv/bin/python -m ruff check .
- name: Check formatting
if: ${{ needs.changes.outputs.test == 'true' }}
run: .venv/bin/python -m ruff format --check .
- name: Test
if: ${{ needs.changes.outputs.test == 'true' }}
run: .venv/bin/python -m pytest -q
- name: Build package
if: ${{ needs.changes.outputs.test == 'true' }}
run: .venv/bin/python -m build
- name: Check package metadata
if: ${{ needs.changes.outputs.test == 'true' }}
run: .venv/bin/python -m twine check dist/*
- name: Smoke-test wheel CLI
if: ${{ needs.changes.outputs.test == 'true' }}
run: |
python3 -m venv --system-site-packages /tmp/mini-eq-wheel-test
/tmp/mini-eq-wheel-test/bin/python -m pip install --upgrade pip
/tmp/mini-eq-wheel-test/bin/python -m pip install --no-index --find-links /tmp/mini-eq-wheelhouse "$PWG_REQUIREMENT"
/tmp/mini-eq-wheel-test/bin/python -m pip install dist/mini_eq-*.whl
/tmp/mini-eq-wheel-test/bin/mini-eq --help
- name: Upload package artifacts
if: ${{ needs.changes.outputs.test == 'true' }}
uses: actions/upload-artifact@v7
with:
name: mini-eq-dist
path: dist/*
if-no-files-found: error
flatpak-build:
needs: changes
if: ${{ always() && !(github.event_name == 'workflow_dispatch' && inputs.smoke_only) && needs.changes.result == 'success' && needs.changes.outputs.flatpak == 'true' }}
runs-on: ubuntu-24.04
timeout-minutes: 60
container:
image: ghcr.io/flathub-infra/flatpak-github-actions:gnome-50@sha256:9d3a99bef793cf99f55b0106130e68a781fd0815c8d2954f26e1ac9253b19e57
options: --privileged
steps:
- name: Check out repository
uses: actions/checkout@v6
- name: Configure Flathub remote
run: |
flatpak remote-add --if-not-exists flathub https://flathub.org/repo/flathub.flatpakrepo
flatpak --user remote-add --if-not-exists flathub https://flathub.org/repo/flathub.flatpakrepo
- name: Build Flatpak
uses: flatpak/flatpak-github-actions/flatpak-builder@401fe28a8384095fc1531b9d320b292f0ee45adb
with:
bundle: mini-eq.flatpak
manifest-path: io.github.bhack.mini-eq.yaml
upload-artifact: false
- name: Install built Flatpak
run: flatpak --user install -y ./mini-eq.flatpak
- name: Smoke-test Flatpak CLI
run: flatpak run io.github.bhack.mini-eq --help
- name: Check pipewire-gobject GI compatibility
run: |
flatpak run --filesystem="$PWD":ro --command=python3 io.github.bhack.mini-eq \
"$PWD/tools/check_pipewire_gobject.py" --expect-version "$PWG_VERSION"
- name: Smoke-test Flatpak runtime modules
run: |
flatpak run --command=python3 io.github.bhack.mini-eq - <<'PY'
from pathlib import Path
required_files = [
"/app/lib/pipewire-0.3/libpipewire-module-filter-chain.so",
"/app/lib/spa-0.2/filter-graph/libspa-filter-graph.so",
"/app/lib/spa-0.2/filter-graph/libspa-filter-graph-plugin-builtin.so",
]
missing = [path for path in required_files if not Path(path).exists()]
if missing:
raise SystemExit(f"missing Flatpak runtime file(s): {', '.join(missing)}")
PY
flatpak run --command=python3 io.github.bhack.mini-eq - <<'PY'
from pathlib import Path
required_license_files = [
"/app/share/licenses/io.github.bhack.mini-eq/mini-eq/LICENSE",
"/app/share/licenses/io.github.bhack.mini-eq/pipewire-filter-chain-module/COPYING",
"/app/share/licenses/io.github.bhack.mini-eq/pipewire-filter-chain-module/LICENSE",
"/app/share/licenses/io.github.bhack.mini-eq/pipewire-gobject/LICENSE",
]
missing = [path for path in required_license_files if not Path(path).exists()]
if missing:
raise SystemExit(f"missing Flatpak license file(s): {', '.join(missing)}")
PY
flatpak run --command=python3 io.github.bhack.mini-eq - <<'PY'
import importlib
required_modules = ["numpy", "pipewire_gobject"]
missing = []
for name in required_modules:
try:
importlib.import_module(name)
except Exception as exc:
missing.append(f"{name}: {exc}")
if missing:
raise SystemExit(f"missing Python analyzer module(s): {', '.join(missing)}")
PY
flatpak:
needs:
- changes
- flatpak-build
if: ${{ always() && !(github.event_name == 'workflow_dispatch' && inputs.smoke_only) }}
runs-on: ubuntu-24.04
steps:
- name: Require change detection
if: ${{ needs.changes.result != 'success' }}
run: exit 1
- name: Skip unchanged scope
if: ${{ needs.changes.outputs.flatpak != 'true' }}
run: echo "No Flatpak-relevant changes detected; skipping Flatpak build."
- name: Require Flatpak build
if: ${{ needs.changes.outputs.flatpak == 'true' && needs['flatpak-build'].result != 'success' }}
run: exit 1
- name: Confirm Flatpak build
if: ${{ needs.changes.outputs.flatpak == 'true' && needs['flatpak-build'].result == 'success' }}
run: echo "Flatpak build passed."
flatpak-runtime-smoke:
needs: changes
if: ${{ github.event_name == 'workflow_dispatch' && inputs.flatpak_runtime_smoke }}
runs-on: ubuntu-24.04
timeout-minutes: 90
continue-on-error: true
steps:
- name: Require change detection
if: ${{ needs.changes.result != 'success' }}
run: exit 1
- name: Check out repository
uses: actions/checkout@v6
- name: Install Flatpak and PipeWire test dependencies
run: |
sudo apt-get update
sudo apt-get install -y \
dbus-user-session \
flatpak \
jq \
pipewire \
pipewire-bin \
wireplumber
- name: Build and run experimental Flatpak runtime smoke
env:
MINI_EQ_FLATPAK_BUILD: ${{ inputs.flatpak_runtime_build && '1' || '0' }}
MINI_EQ_FLATPAK_INSTALL_REMOTE: ${{ inputs.flatpak_runtime_install_remote && '1' || '0' }}
MINI_EQ_FLATPAK_APP_REF: ${{ inputs.flatpak_runtime_app_ref }}
MINI_EQ_FLATPAK_INSTALL_REF: ${{ inputs.flatpak_runtime_install_ref }}
MINI_EQ_FLATPAK_EXPECT_VERSION: ${{ inputs.flatpak_runtime_expected_version }}
run: tools/run_flatpak_runtime_smoke_ci.sh
headless-pipewire-runtime-smoke:
needs: changes
if: ${{ github.event_name == 'workflow_dispatch' && inputs.headless_pipewire_runtime_smoke }}
runs-on: ubuntu-24.04
timeout-minutes: 45
steps:
- name: Require change detection
if: ${{ needs.changes.result != 'success' }}
run: exit 1
- name: Check out repository
uses: actions/checkout@v6
- name: Install headless PipeWire runtime dependencies
run: |
sudo apt-get update
sudo apt-get install -y \
build-essential \
dbus-user-session \
gobject-introspection \
libebur128-1 \
libgirepository1.0-dev \
libglib2.0-dev \
libpipewire-0.3-dev \
libspa-0.2-modules \
meson \
ninja-build \
pipewire \
pipewire-bin \
pkg-config \
python3 \
python3-dev \
python3-gi \
python3-numpy \
python3-pip \
python3-setuptools \
python3-venv \
wireplumber
- name: Build source environment and run headless PipeWire smoke
run: tools/run_headless_pipewire_runtime_smoke_ci.sh
live-ui-runtime-smoke:
needs: changes
if: ${{ github.event_name == 'workflow_dispatch' && inputs.live_ui_runtime_smoke }}
runs-on: ubuntu-24.04
timeout-minutes: 90
steps:
- name: Require change detection
if: ${{ needs.changes.result != 'success' }}
run: exit 1
- name: Check out repository
uses: actions/checkout@v6
- name: Install live UI runtime dependencies
run: |
sudo apt-get update
sudo apt-get install -y \
appstream \
at-spi2-core \
build-essential \
dbus-user-session \
desktop-file-utils \
gir1.2-adw-1 \
gir1.2-gtk-4.0 \
git \
gnome-shell \
gobject-introspection \
libebur128-1 \
libgirepository1.0-dev \
libglib2.0-dev \
libpipewire-0.3-dev \
libspa-0.2-modules \
meson \
ninja-build \
pipewire \
pipewire-bin \
pkg-config \
python3 \
python3-cairo \
python3-dev \
python3-gi \
python3-numpy \
python3-pip \
python3-pyatspi \
python3-setuptools \
python3-venv \
patchelf \
wireplumber
- name: Build source environment and run live UI smoke
run: tools/run_live_ui_runtime_smoke_ci.sh