Files
feresaria/.github/workflows/release.yml
T
Samuel Onoja 42c3b290dd Add audio and region recording; make routine CI manual (#25)
The top-bar recorder previously saved a full monitor without sound. It now lets you select a region within one monitor and choose system audio, microphone audio, or both. Audio remains off by default, and recordings with audio are saved as VP8/Opus WebM files. The portal still controls screen access and cancellation; stopping from the bar or ending the video stream finishes the recording, including its audio tracks.

Region selection accounts for fractional display scales and negative monitor coordinates. The picker keeps its action buttons visible while the display list and recording options scroll together. The picker, dependency lists, and recording documentation now explain the available choices and the slurp and audio requirements.

Routine pushes and pull requests no longer start CI runners. Workspace checks and website deployment are manual, while release checks run when requested manually, through a version tag, or through a PR labeled `release`. Publishing still requires a pushed version tag. This also fixes release asset checksums by normalizing RPM filenames before generating the checksum file.

Validated locally with a release build, portal and shell recorder tests, formatting, Clippy, actionlint, packaging tests, and mocked publishing checks. Media tests encoded and decoded cropped video with audio, checked that video termination finishes live audio, and exercised system, microphone, and combined capture against a private PipeWire-Pulse server. Mixed recordings must contain both fixture frequencies, with negative controls for either missing source. The picker was also checked on 800 × 600 and 800 × 400 desktops and opened in a live nested window.
2026-10-11 15:37:51 +01:00

185 lines
6.6 KiB
YAML

name: Release packages
on:
pull_request:
types: [opened, synchronize, reopened, labeled]
push:
tags: ['v*']
workflow_dispatch:
permissions:
contents: read
env:
CARGO_BUILD_JOBS: '2'
CARGO_INCREMENTAL: '0'
CARGO_PROFILE_RELEASE_DEBUG: '0'
concurrency:
group: release-${{ github.ref }}
cancel-in-progress: false
jobs:
checks:
if: github.event_name != 'pull_request' || contains(github.event.pull_request.labels.*.name, 'release')
uses: ./.github/workflows/release-checks.yml
source:
if: github.event_name != 'pull_request' || contains(github.event.pull_request.labels.*.name, 'release')
runs-on: ubuntu-24.04
outputs:
version: ${{ steps.version.outputs.version }}
steps:
- uses: actions/checkout@v6
- name: Read release version
id: version
env:
RELEASE_TAG: ${{ github.ref_type == 'tag' && github.ref_name || '' }}
run: |
python3 - <<'PY'
import importlib.util, os
spec = importlib.util.spec_from_file_location('package', 'scripts/package.py')
package = importlib.util.module_from_spec(spec)
spec.loader.exec_module(package)
version = package.version()
package.check_tag(os.environ['RELEASE_TAG'], version)
with open(os.environ['GITHUB_OUTPUT'], 'a') as output:
print(f'version={version}', file=output)
PY
- name: Install pinned Rust toolchain
run: rustup show
- name: Package offline sources and recipes
env:
RELEASE_TAG: ${{ github.ref_type == 'tag' && github.ref_name || '' }}
run: |
python3 -m unittest discover -s scripts/tests -p test_package.py
python3 scripts/package.py source --tag "$RELEASE_TAG"
- uses: actions/upload-artifact@v7
with:
name: release-source
path: target/dist/*
if-no-files-found: error
compression-level: 0
fedora:
needs: source
runs-on: ubuntu-24.04
container:
image: fedora:44
options: --init
steps:
- name: Install RPM tooling
run: dnf install -y rpm-build dnf5-plugins git findutils tar gzip
- uses: actions/download-artifact@v8
with:
name: release-source
path: dist
- name: Build and test Fedora package
run: |
dnf builddep -y dist/ferese.spec
mkdir -p /tmp/rpmbuild/SOURCES
cp dist/ferese-*.tar.gz /tmp/rpmbuild/SOURCES/
rpmbuild -ba --define '_topdir /tmp/rpmbuild' dist/ferese.spec
mkdir -p artifacts
find /tmp/rpmbuild/RPMS /tmp/rpmbuild/SRPMS -name '*.rpm' -exec cp '{}' artifacts/ \;
- uses: actions/upload-artifact@v7
with:
name: release-fedora
path: artifacts/*.rpm
if-no-files-found: error
compression-level: 0
arch:
needs: source
runs-on: ubuntu-24.04
container:
image: archlinux:base-devel
options: --init
steps:
- name: Prepare Arch build user and dependencies
run: |
pacman -Syu --noconfirm --needed rust cargo cmake clang pkgconf python git desktop-file-utils \
wayland libxkbcommon libinput systemd seatd mesa vulkan-swrast libdrm fontconfig freetype2 expat dbus \
pam polkit foot pipewire wireplumber libpipewire gstreamer xdg-desktop-portal xdg-desktop-portal-gtk xorg-xauth
useradd --create-home builder
- uses: actions/download-artifact@v8
with:
name: release-source
path: dist
- name: Build and test Arch package
run: |
mkdir -p /home/builder/package
cp dist/PKGBUILD dist/ferese-*.tar.gz /home/builder/package/
chown -R builder:builder /home/builder/package
runuser -u builder -- bash -c 'cd /home/builder/package && makepkg --cleanbuild --noconfirm'
mkdir -p artifacts
cp /home/builder/package/*.pkg.tar.zst artifacts/
runuser -u builder -- bash -c 'cd /home/builder/package && makepkg --printsrcinfo' > artifacts/ferese.SRCINFO
- uses: actions/upload-artifact@v7
with:
name: release-arch
path: artifacts/*
if-no-files-found: error
compression-level: 0
publish:
if: github.event_name == 'push' && github.ref_type == 'tag'
needs: [source, checks, fedora, arch]
runs-on: ubuntu-24.04
permissions:
contents: write
steps:
- uses: actions/download-artifact@v8
with:
pattern: release-*
merge-multiple: true
path: artifacts
- name: Prepare draft release
uses: actions/github-script@v8
with:
script: |
const tag = context.ref.slice('refs/tags/'.length);
const repo = context.repo;
const commit = await github.rest.repos.getCommit({...repo, ref: tag});
if (commit.data.sha !== context.sha) {
throw new Error('Release tag moved after validation');
}
let release;
try {
release = (await github.rest.repos.getReleaseByTag({...repo, tag})).data;
} catch (error) {
if (error.status !== 404) throw error;
}
if (release && !release.draft) {
throw new Error(`Release ${tag} is already published`);
}
if (!release) {
await github.rest.repos.createRelease({
...repo, tag_name: tag, name: tag, draft: true,
generate_release_notes: true, prerelease: tag.includes('-')
});
}
- name: Upload packages and publish completed release
env:
GH_TOKEN: ${{ github.token }}
GH_REPO: ${{ github.repository }}
RELEASE_TAG: ${{ github.ref_name }}
run: |
cd artifacts
# GitHub replaces '~' in uploaded filenames. Use those same download
# names in SHA256SUMS so verification works after downloading RPMs.
python3 - <<'PY'
from pathlib import Path
for source in Path('.').glob('*.rpm'):
destination = source.with_name(source.name.replace('~', '.'))
if source != destination:
if destination.exists():
raise SystemExit(f'Duplicate release asset: {destination}')
source.rename(destination)
PY
rm SHA256SUMS
sha256sum * > SHA256SUMS
gh release upload "$RELEASE_TAG" ./* --clobber
test "$(gh api "repos/$GH_REPO/commits/$RELEASE_TAG" --jq .sha)" = "$GITHUB_SHA"
gh release edit "$RELEASE_TAG" --draft=false