a5b99b2928
apple / swift (push) Successful in 55s
deb / build-publish (push) Successful in 2m26s
decky / build-publish (push) Successful in 10s
ci / web (push) Successful in 29s
ci / docs-site (push) Successful in 33s
android / android (push) Successful in 1m52s
ci / bench (push) Has been cancelled
docker / build-push (., web/Dockerfile, punktfunk-web) (push) Successful in 5s
docker / build-push (ci, ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Successful in 35s
docker / build-push (--build-arg FEDORA_VERSION=44, ci, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm) (push) Successful in 3m4s
docker / build-push (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Successful in 4s
docker / build-push (ci, ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Successful in 2m18s
flatpak / build-publish (push) Failing after 2m43s
rpm / build-publish (bazzite, punktfunk-fedora-rpm) (push) Successful in 8m15s
rpm / build-publish (fedora-44, punktfunk-fedora44-rpm) (push) Successful in 8m7s
docker / deploy-docs (push) Has been cancelled
ci / rust (push) Failing after 48s
The flatpak CI was failing at "Downloading sources" with "No space left
on device": flatpak-cargo-generator walks the whole workspace Cargo.lock
and emits a `type: git` source for the windows-rs crates (windows +
windows-reactor + ~12 sub-crates, pinned by punktfunk-client-windows),
and flatpak-builder then FULL-clones that multi-GB repo — for a bundle
that only ever compiles `-p punktfunk-client-linux` and never touches a
windows-* crate.
New packaging/flatpak/prune-windows-lock.py writes a copy of Cargo.lock
with the windows-rs git packages stripped (matches on the `source =`
line, so a crate that merely lists a windows dependency is kept;
dependency-free so it also runs on the Deck's stock python). Both the CI
and build-flatpak.sh feed that pruned lock to the generator. The
committed Cargo.lock is untouched — cargo --offline only needs vendored
sources for the crates it actually builds, and the windows-rs crates are
not in the Linux client's dependency closure.
Verified locally: 14 crates pruned (507 -> 493 packages), zero windows-rs
`source =` lines remain, output parses as TOML, all Linux-client deps
(gtk4/ffmpeg-sys-next/sdl3/pipewire) intact.
This unblocks the flatpak build carrying the VAAPI green-screen fix
(64b1679) for the Steam Deck.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
151 lines
7.6 KiB
YAML
151 lines
7.6 KiB
YAML
# Build the native punktfunk Linux CLIENT as a single-file Flatpak bundle and publish it to
|
|
# Gitea's GENERIC package registry, so the Steam Deck (and any flatpak distro) installs it
|
|
# the SteamOS-native, update-survivable way: `flatpak install --user <downloaded>.flatpak`.
|
|
# (The HOST stays an RPM/deb — it needs unsandboxed /dev/uinput + zero-copy NVENC; only the
|
|
# CLIENT is sandbox-friendly. See packaging/README.md and packaging/flatpak/README.md.)
|
|
#
|
|
# Gitea has NO flatpak/ostree registry, so the bundle lives in the generic registry:
|
|
# PUT https://git.unom.io/api/packages/unom/generic/punktfunk-client-flatpak/<version>/<file>
|
|
# GET https://git.unom.io/api/packages/unom/generic/punktfunk-client-flatpak/<version>/<file>
|
|
# On tags the bundle is ALSO attached to the Gitea release (mirrors release.yml's DMG).
|
|
#
|
|
# PRIVILEGED-BUILD CONSTRAINT: flatpak-builder runs bubblewrap, which needs user namespaces.
|
|
# In a Gitea/act_runner Docker executor that means the job container must be --privileged
|
|
# (the same runner already runs `docker build` in docker.yml, so its Docker daemon allows it).
|
|
# If your runner CANNOT grant --privileged, this job will fail at `flatpak-builder` with
|
|
# "Creating new namespace failed: Operation not permitted" — see the fallback in
|
|
# packaging/flatpak/README.md (build on the Deck via org.flatpak.Builder, or on a Linux box,
|
|
# then upload with the curl line below).
|
|
#
|
|
# REGISTRY_TOKEN: repo Actions secret, a PAT with write:package scope (shared with deb/rpm/docker).
|
|
name: flatpak
|
|
|
|
on:
|
|
push:
|
|
branches: [main]
|
|
# The flatpak is the CLIENT — only rebuild when the client/core/manifest change, not on every
|
|
# docs/host push (this is a heavy flatpak-builder run). Tags (v*, the client release) build too.
|
|
paths:
|
|
- 'crates/punktfunk-client-linux/**'
|
|
- 'crates/punktfunk-core/**'
|
|
- 'packaging/flatpak/**'
|
|
- 'Cargo.lock'
|
|
- '.gitea/workflows/flatpak.yml'
|
|
tags: ['v*']
|
|
workflow_dispatch:
|
|
|
|
env:
|
|
REGISTRY: git.unom.io
|
|
OWNER: unom
|
|
APP_ID: io.unom.Punktfunk
|
|
MANIFEST: packaging/flatpak/io.unom.Punktfunk.yml
|
|
PACKAGE: punktfunk-client-flatpak # generic-registry package name
|
|
|
|
jobs:
|
|
build-publish:
|
|
runs-on: ubuntu-24.04
|
|
timeout-minutes: 120
|
|
container:
|
|
# Fedora ships a recent flatpak + flatpak-builder + the kernel userns support.
|
|
# --privileged is required for bubblewrap inside the Docker executor (see header).
|
|
image: fedora:43
|
|
options: --privileged
|
|
steps:
|
|
# fedora:43 has no node, but actions/checkout (a JS action) needs it. A plain `run:` step
|
|
# executes via the container shell (no node needed), so install node BEFORE checkout.
|
|
- name: node for the JS actions
|
|
run: dnf -y install nodejs
|
|
|
|
- uses: actions/checkout@v4
|
|
|
|
- name: Tooling
|
|
run: |
|
|
# flatpak-cargo-generator.py (master) needs aiohttp + tomlkit (NOT the old `toml`).
|
|
dnf -y install flatpak flatpak-builder git python3 python3-aiohttp python3-tomlkit curl jq
|
|
# Flathub provides the GNOME runtime/SDK + the rust-stable + ffmpeg-full extensions.
|
|
flatpak remote-add --user --if-not-exists flathub \
|
|
https://dl.flathub.org/repo/flathub.flatpakrepo
|
|
git config --global --add safe.directory "$PWD"
|
|
|
|
- name: Version
|
|
# Tag v1.2.3 -> 1.2.3; a main push -> 0.0.1-ciN.g<sha> (sorts before a real release,
|
|
# increases by run number — newest main build always wins). The generic registry
|
|
# version string allows letters/dots/hyphens.
|
|
run: |
|
|
SHORT=$(echo "$GITHUB_SHA" | cut -c1-8)
|
|
case "$GITHUB_REF" in
|
|
refs/tags/v*) V="${GITHUB_REF_NAME#v}" ;;
|
|
*) V="0.0.1-ci${GITHUB_RUN_NUMBER}.g${SHORT}" ;;
|
|
esac
|
|
echo "VERSION=$V" >> "$GITHUB_ENV"
|
|
echo "BUNDLE=punktfunk-client-${V}.flatpak" >> "$GITHUB_ENV"
|
|
echo "flatpak version $V"
|
|
|
|
- name: Generate offline cargo sources
|
|
# flatpak builds with no network; vendor every crate from Cargo.lock into
|
|
# cargo-sources.json next to the manifest (referenced by the manifest's
|
|
# punktfunk-client module).
|
|
#
|
|
# Prune the microsoft/windows-rs git crates first: they belong to
|
|
# punktfunk-client-windows, which the flatpak never builds, and leaving them in makes
|
|
# flatpak-builder full-clone that multi-GB repo at build time → "No space left on
|
|
# device" (see packaging/flatpak/prune-windows-lock.py). The committed Cargo.lock is
|
|
# untouched; cargo --offline only needs sources for the crates it compiles.
|
|
run: |
|
|
curl -fsSL -o /tmp/flatpak-cargo-generator.py \
|
|
https://raw.githubusercontent.com/flatpak/flatpak-builder-tools/master/cargo/flatpak-cargo-generator.py
|
|
python3 packaging/flatpak/prune-windows-lock.py Cargo.lock /tmp/Cargo.flatpak.lock
|
|
python3 /tmp/flatpak-cargo-generator.py /tmp/Cargo.flatpak.lock \
|
|
-o packaging/flatpak/cargo-sources.json
|
|
|
|
- name: Build the flatpak (install deps from Flathub, offline build)
|
|
run: |
|
|
# --install-deps-from=flathub pulls everything the manifest declares: the GNOME 50
|
|
# runtime/SDK + the rust-stable (//25.08, rustc 1.96) and llvm20 SDK extensions, plus
|
|
# the runtime's auto codecs-extra (HEVC libavcodec). --disable-rofiles-fuse is the
|
|
# container-safe path (no FUSE).
|
|
flatpak-builder --user --force-clean --disable-rofiles-fuse \
|
|
--install-deps-from=flathub \
|
|
--repo="$PWD/repo" \
|
|
"$PWD/build-dir" "$MANIFEST"
|
|
|
|
- name: Export single-file bundle
|
|
run: |
|
|
flatpak build-bundle "$PWD/repo" "$BUNDLE" "$APP_ID"
|
|
ls -lh "$BUNDLE"
|
|
|
|
- name: Publish to the Gitea generic registry
|
|
env:
|
|
TOKEN: ${{ secrets.REGISTRY_TOKEN }}
|
|
run: |
|
|
BASE="https://$REGISTRY/api/packages/$OWNER/generic/$PACKAGE"
|
|
# 1) Immutable, versioned URL.
|
|
curl -fsS --user "enricobuehler:$TOKEN" --upload-file "$BUNDLE" \
|
|
"$BASE/$VERSION/$BUNDLE"
|
|
echo "published $BASE/$VERSION/$BUNDLE"
|
|
# 2) Stable `latest/punktfunk-client.flatpak` alias for the Decky fallback + scripts.
|
|
# The generic registry rejects re-uploading an existing version/file (409), so
|
|
# delete the prior `latest` file first (ignore 404 on the first ever run).
|
|
curl -fsS -o /dev/null --user "enricobuehler:$TOKEN" -X DELETE \
|
|
"$BASE/latest/punktfunk-client.flatpak" || true
|
|
curl -fsS --user "enricobuehler:$TOKEN" --upload-file "$BUNDLE" \
|
|
"$BASE/latest/punktfunk-client.flatpak"
|
|
echo "published $BASE/latest/punktfunk-client.flatpak"
|
|
|
|
- name: Attach bundle to the Gitea release (tags only)
|
|
if: startsWith(gitea.ref, 'refs/tags/')
|
|
env:
|
|
TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
run: |
|
|
API="${{ gitea.server_url }}/api/v1/repos/${{ gitea.repository }}"
|
|
ID=$(curl -sf -X POST "$API/releases" \
|
|
-H "Authorization: token $TOKEN" -H 'Content-Type: application/json' \
|
|
-d "{\"tag_name\":\"$GITHUB_REF_NAME\",\"name\":\"$GITHUB_REF_NAME\"}" \
|
|
| python3 -c 'import json,sys;print(json.load(sys.stdin)["id"])' \
|
|
|| curl -sf "$API/releases/tags/$GITHUB_REF_NAME" -H "Authorization: token $TOKEN" \
|
|
| python3 -c 'import json,sys;print(json.load(sys.stdin)["id"])')
|
|
curl -sf -X POST "$API/releases/$ID/assets?name=$BUNDLE" \
|
|
-H "Authorization: token $TOKEN" \
|
|
-F "attachment=@$BUNDLE" >/dev/null
|
|
echo "attached $BUNDLE to release $GITHUB_REF_NAME"
|