From 8014edf91c37b456ce52331aa4b5f6715bd5964c Mon Sep 17 00:00:00 2001 From: Mollusk Date: Fri, 3 Jul 2026 15:59:38 -0400 Subject: [PATCH] Release 0.6.2 + AppImage packaging Bump to 0.6.2 (Cargo + Inno .iss), promote CHANGELOG [Unreleased] -> [0.6.2]. 0.6.2 rolls up the licensing (MIT + THIRD_PARTY_LICENSES) and the friends-list liveness fixes (active offline marking, 15s refresh, manual Rescan) on the 0.6.x wire format (gossip v5, compatible with 0.6.0/0.6.1). Adds packaging/appimage: a thin AppImage recipe (linuxdeploy) that bundles the pixelpass screen-share helper in usr/bin so peerspeak's $PATH lookup finds it with no code change. Assets are include_bytes!-embedded; the graphics stack and pixelpass's gstreamer/mpv tools are left to the host. Built on Ubuntu 24.04 (glibc 2.39) for reach across Debian 13+/Fedora 40+/rolling. Co-Authored-By: Claude Opus 4.8 --- CHANGELOG.md | 4 +- Cargo.lock | 2 +- Cargo.toml | 2 +- packaging/appimage/.gitignore | 4 ++ packaging/appimage/AppRun | 11 ++++ packaging/appimage/README.md | 76 ++++++++++++++++++++++++ packaging/appimage/build-appimage.sh | 89 ++++++++++++++++++++++++++++ packaging/windows/peerspeak.iss | 2 +- 8 files changed, 186 insertions(+), 4 deletions(-) create mode 100644 packaging/appimage/.gitignore create mode 100755 packaging/appimage/AppRun create mode 100644 packaging/appimage/README.md create mode 100755 packaging/appimage/build-appimage.sh diff --git a/CHANGELOG.md b/CHANGELOG.md index 1bf7c9d..1d38065 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,7 +2,7 @@ All notable changes to PeerSpeak are documented here. -## [Unreleased] +## [0.6.2] — 2026-07-03 ### Fixed - **Friends list now reflects status changes without a restart.** A presence probe that fails now actively marks the friend **offline**, so a friend who goes offline, leaves a room, or turns invisible no longer lingers showing a stale "online" / "in a room" status until PeerSpeak is relaunched. Previously only successful probes updated the list, so it could ratchet a friend's status up but never down. The auto-refresh interval was also shortened from 60s to **15s** so the list tracks changes more closely. @@ -13,6 +13,8 @@ All notable changes to PeerSpeak are documented here. ### Licensing - **PeerSpeak is now released under the MIT License** (previously an unlicensed private build). Added a `LICENSE` file and a `THIRD_PARTY_LICENSES` file enumerating the full dependency manifest plus the canonical text of every referenced license, with notices for the statically bundled Opus codec and the embedded fonts (Iced-Icons, Cantarell/OFL-1.1). Both files ship in the Arch and Debian packages. +[0.6.2]: https://gitbutter.xyz/mollusk/peerspeak/releases/tag/v0.6.2 + ## [0.6.0] — 2026-06-28 ### Added diff --git a/Cargo.lock b/Cargo.lock index 84ca1fa..46900a7 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -4871,7 +4871,7 @@ checksum = "35fb2e5f958ec131621fdd531e9fc186ed768cbe395337403ae56c17a74c68ec" [[package]] name = "peerspeak" -version = "0.6.1" +version = "0.6.2" dependencies = [ "anyhow", "async-trait", diff --git a/Cargo.toml b/Cargo.toml index af208df..dafcc93 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "peerspeak" -version = "0.6.1" +version = "0.6.2" edition = "2024" description = "Decentralized peer-to-peer voice chat (Rust/iroh/PipeWire/Opus/iced)" license = "MIT" diff --git a/packaging/appimage/.gitignore b/packaging/appimage/.gitignore new file mode 100644 index 0000000..533b65c --- /dev/null +++ b/packaging/appimage/.gitignore @@ -0,0 +1,4 @@ +.tools/ +AppDir/ +*.AppImage +squashfs-root/ diff --git a/packaging/appimage/AppRun b/packaging/appimage/AppRun new file mode 100755 index 0000000..c2083c3 --- /dev/null +++ b/packaging/appimage/AppRun @@ -0,0 +1,11 @@ +#!/bin/sh +# AppRun for the PeerSpeak AppImage. +# +# PeerSpeak bundles the pixelpass screen-share helper in usr/bin. We prepend our +# own usr/bin to PATH so peerspeak's $PATH lookup for `pixelpass` finds the +# bundled copy, while the host's tools (gst-launch-1.0, pactl, mpv — which +# pixelpass in turn shells out to) remain reachable via the appended host PATH. +# That no-sandbox spawning is exactly why this app suits AppImage over Flatpak. +HERE="$(dirname "$(readlink -f "$0")")" +export PATH="$HERE/usr/bin:$PATH" +exec "$HERE/usr/bin/peerspeak" "$@" diff --git a/packaging/appimage/README.md b/packaging/appimage/README.md new file mode 100644 index 0000000..1b06810 --- /dev/null +++ b/packaging/appimage/README.md @@ -0,0 +1,76 @@ +# PeerSpeak AppImage + +A "thin" AppImage: the `peerspeak` binary, the bundled `pixelpass` screen-share +helper, a launcher (`AppRun`), and the desktop entry + icon. Run +`./build-appimage.sh` to produce `peerspeak--x86_64.AppImage`. + +## Why thin, and why pixelpass is bundled + +PeerSpeak owns voice; **pixelpass** owns pixels. They are never Cargo +dependencies of each other — peerspeak shells out to the `pixelpass` binary over +its CLI. The AppImage co-locates `pixelpass` in `usr/bin`, and `AppRun` prepends +`usr/bin` to `PATH`, so peerspeak's normal `$PATH` lookup finds it with no code +change. Joe gets one file, and screen-share works out of the box. + +Almost nothing is bundled: peerspeak's own assets (notification WAVs, avatar +presets, window icon, fonts) are `include_bytes!`-embedded, and the graphics +stack (`libGL`, `libvulkan`, `libwayland-*`, `libxkbcommon`, X11) is dlopen'd at +runtime and on the AppImage excludelist because it must match the host driver. +So the image carries just the two binaries plus a handful of small libs. + +## Host requirements + +The AppImage runs on any reasonably current glibc-based distro that has: + +- **A Vulkan-capable GPU + driver** (peerspeak's iced/wgpu renderer). Mesa/RADV + on AMD/Intel or the NVIDIA driver all work. +- **PipeWire** (with the PulseAudio shim, for `pactl`). +- For **screen-share only** — pixelpass shells out to these on the host `PATH`; + it prints the exact package names for your distro if any are missing: + - **GStreamer + plugins** (`gst-launch-1.0`/`gst-inspect-1.0`, base, + good/bad/ugly, libav, and the PipeWire plugin), + - **mpv** (or vlc) for the viewer side, + - on X11, `xwininfo` for single-window capture. + +On Arch/Artix that is one pacman line, e.g.: + +```sh +sudo pacman -S gstreamer gst-plugins-base gst-plugins-good gst-plugins-bad \ + gst-plugins-ugly gst-libav gst-plugin-pipewire mpv xorg-xwininfo libpulse +``` + +(Add `gstreamer-vaapi` for hardware H.264 encode on AMD/Intel; the software +x264 path always works. On XLibre / X11 the capture path uses `ximagesrc` and +needs no XDG portal — no systemd required.) + +## Building for broad compatibility (glibc baseline) + +An AppImage requires a host glibc **at least as new** as the build host's. Built +on a rolling distro (glibc 2.43) it only runs on equally-new systems. Build +inside **Ubuntu 24.04** (glibc 2.39, PipeWire 1.0.5) for wide reach — pixelpass's +`pipewire` crate binds the system PipeWire headers and needs PipeWire >= 1.0, so +the older Debian 12 `peerspeak-bookworm` box (PW 0.3.65) cannot build it. 2.39 +covers Debian 13+, Fedora 40+, and current rolling distros. + +```sh +# One-time: an Ubuntu 24.04 distrobox that reuses the host rustup toolchain. +distrobox create --yes --image ubuntu:24.04 --name peerspeak-appimage +distrobox enter peerspeak-appimage -- sudo apt-get update +distrobox enter peerspeak-appimage -- sudo apt-get install -y \ + build-essential cmake clang libclang-dev pkg-config \ + libpipewire-0.3-dev libspa-0.2-dev libasound2-dev libxcb1-dev \ + curl ca-certificates file patchelf git + +# Build (the host's ~/.rustup toolchain is glibc-2.17-baseline, so it runs in the +# box; isolated CARGO_TARGET_DIRs keep it off the host target/): +distrobox enter peerspeak-appimage -- env \ + PATH="$HOME/.rustup/toolchains/stable-x86_64-unknown-linux-gnu/bin:$PATH" \ + ./packaging/appimage/build-appimage.sh +``` + +## Caveats + +- **Hardware encode (VAAPI)** uses the host GPU driver and can't be bundled; the + software x264 path always works. +- The bundled `pixelpass` is built headless (no `gui` feature) — it is only ever + driven by peerspeak, never launched standalone from this image. diff --git a/packaging/appimage/build-appimage.sh b/packaging/appimage/build-appimage.sh new file mode 100755 index 0000000..f3d42bc --- /dev/null +++ b/packaging/appimage/build-appimage.sh @@ -0,0 +1,89 @@ +#!/usr/bin/env bash +# Build a "thin" PeerSpeak AppImage that also bundles the pixelpass screen-share +# helper. +# +# PeerSpeak is an iced/wgpu GUI app; pixelpass is the separate screen-share +# orchestrator peerspeak shells out to (never a Cargo dependency). Both link +# almost nothing — the graphics stack (libGL, libvulkan, wayland, xkbcommon, +# X11) is dlopen'd at runtime and is on the AppImage excludelist because it must +# match the host driver, and pixelpass's capture/encode tools (gst-launch-1.0, +# pactl, mpv) are expected on the host PATH. So the AppImage carries just the two +# binaries plus their handful of non-excludelisted libs. The custom AppRun +# prepends usr/bin to PATH so peerspeak's own $PATH lookup finds the bundled +# pixelpass, while the host's tools stay reachable. +# +# All runtime assets (notification WAVs, avatar presets, window icon, fonts) are +# include_bytes!-embedded in the peerspeak binary, so nothing else is bundled. +# +# Usage: packaging/appimage/build-appimage.sh +# Output: packaging/appimage/peerspeak--x86_64.AppImage +# +# Build inside an Ubuntu 24.04 distrobox (glibc 2.39, PipeWire 1.0.5) for broad +# reach — pixelpass's `pipewire` crate needs PipeWire >= 1.0 headers, so the +# older peerspeak-bookworm box (PW 0.3.65) cannot build it. The 2.39 baseline +# covers Debian 13+, Fedora 40+, and all current rolling distros. See README.md. +set -euo pipefail + +here="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +repo="$(cd "$here/../.." && pwd)" +tools="$here/.tools" +appdir="$here/AppDir" +mkdir -p "$tools" + +# linuxdeploy is itself an AppImage; run it without FUSE so this works in a +# container / on CI without libfuse2. +export APPIMAGE_EXTRACT_AND_RUN=1 +VERSION="$(grep -m1 '^version' "$repo/Cargo.toml" | sed -E 's/.*"(.*)".*/\1/')" +export VERSION + +# Isolated target dirs so an old-glibc box build never clobbers the host target/. +cache="${PEERSPEAK_APPIMAGE_CACHE:-$HOME/.cache/peerspeak-appimage}" +ps_target="$cache/peerspeak-target" +pp_target="$cache/pixelpass-target" + +# The pixelpass screen-share helper we bundle. Sibling checkout by default. +pixelpass_repo="${PIXELPASS_REPO:-$repo/../pixelpass}" +if [ ! -d "$pixelpass_repo" ]; then + echo "!! pixelpass repo not found at $pixelpass_repo (set PIXELPASS_REPO)" >&2 + exit 1 +fi + +echo ">> building peerspeak (release)" +( cd "$repo" && CARGO_TARGET_DIR="$ps_target" cargo build --release ) +ps_bin="$ps_target/release/peerspeak" + +# Headless pixelpass: peerspeak drives it via `--host`/viewer + `--output json`, +# never its GUI, so the default (no `gui` feature) keeps the GL toolkit out. +echo ">> building pixelpass (release, headless) from $pixelpass_repo" +( cd "$pixelpass_repo" && CARGO_TARGET_DIR="$pp_target" cargo build --release ) +pp_bin="$pp_target/release/pixelpass" + +echo ">> fetching linuxdeploy" +ld="$tools/linuxdeploy-x86_64.AppImage" +if [ ! -x "$ld" ]; then + curl -fL --retry 3 -o "$ld" \ + "https://github.com/linuxdeploy/linuxdeploy/releases/download/continuous/linuxdeploy-x86_64.AppImage" + chmod +x "$ld" +fi + +echo ">> assembling AppDir" +rm -rf "$appdir" +mkdir -p "$appdir/usr/bin" +install -m755 "$ps_bin" "$appdir/usr/bin/peerspeak" +install -m755 "$pp_bin" "$appdir/usr/bin/pixelpass" + +echo ">> running linuxdeploy (bundles libs, builds the AppImage)" +# -e (repeated): analyse both binaries for libraries to bundle; excludelisted +# graphics/glibc libs are skipped. -d/-i: desktop entry + icon. +# --custom-apprun: our launcher that puts the bundled pixelpass on PATH. +( cd "$here" && OUTPUT="peerspeak-${VERSION}-x86_64.AppImage" "$ld" \ + --appdir "$appdir" \ + -e "$appdir/usr/bin/peerspeak" \ + -e "$appdir/usr/bin/pixelpass" \ + -d "$repo/packaging/peerspeak.desktop" \ + -i "$repo/assets/icons/peerspeak-256.png" \ + --icon-filename peerspeak \ + --custom-apprun "$here/AppRun" \ + --output appimage ) + +echo ">> done: $here/peerspeak-${VERSION}-x86_64.AppImage" diff --git a/packaging/windows/peerspeak.iss b/packaging/windows/peerspeak.iss index 90bd949..2a6620b 100644 --- a/packaging/windows/peerspeak.iss +++ b/packaging/windows/peerspeak.iss @@ -12,7 +12,7 @@ ; (x86_64-pc-windows-gnu, statically linked -- no extra DLLs needed). #define MyAppName "PeerSpeak" -#define MyAppVersion "0.6.0" +#define MyAppVersion "0.6.2" #define MyAppPublisher "mollusk" #define MyAppExeName "peerspeak.exe"