Isolated per-app package management — no root, no containers, no daemon. Supports Arch Linux (pacman + AUR), Debian / Ubuntu (apt), and Fedora / RHEL (dnf/rpm).
wryayer installs packages into fully-isolated per-app directory trees under ~/.wryayer/<app>/. Each app and all its transitive dependencies live in their own private filesystem root and are launched inside a bubblewrap (bwrap) sandbox. No root access, no systemd units, no Flatpak runtimes — just ordinary files, hard links, and Linux namespaces.
On Arch Linux it resolves and downloads packages via pacman and the AUR. On Debian / Ubuntu it uses apt-get download and dpkg-deb. On Fedora / RHEL and derivatives it uses dnf download and rpm2cpio. The distro is detected automatically from /etc/os-release.
🛠 Curious how it works inside? The architecture, on-disk layout, sandbox internals, and developer/testing docs live in
README-CODE.md.
Arch Linux has one of the richest package ecosystems on the planet, but its single-root package model means:
- Installing an old or alternate version of an app is painful or impossible without AUR hacks.
- A poorly-packaged AUR tool can clobber shared libraries used by other apps.
- There is no per-app permission model: once installed, an app can read your entire home directory.
wryayer solves all three by extracting packages into self-contained directory trees that are bind-mounted as / at runtime. Apps can't see your home directory unless you explicitly share a folder. Conflicting dependency versions coexist without interference. Removing an app is a single rm -rf.
It is not a security sandbox. The goal is isolation and disk-space efficiency, not hardened confinement. A determined app can still escape via /proc, shared IPC, or device access; audio=off and network=off raise the bar but are not guarantees.
wryayer tui is the fastest way to browse installed apps, search and install new
ones, tweak sandbox settings, and launch everything — without memorising a single
subcommand.
wryayer tuiInstalled tab — every app with a live running-instance count and an update
dot next to anything out of date. The right panel shows version, size, the
available update, snapshots, and the full package list — and, while an app is
running, its instance count plus live RAM usage (used / limit) for apps that
have a RAM cap set. Merged-in tools (installed with --into) appear indented
under their host.
Install tab — search the official repos and the AUR at once (each result
tagged [repo] or [aur]). Press Space to mark several packages, then
Enter to install them all in sequence.
Settings tab — global defaults inherited by every newly installed app:
network and device toggles, temp mode, identity spoofing, RAM limit, the
install-behaviour switches (Confirm install / Ask shortcut / Clean
cache), and the TUI theme (default, amber, or matrix colours) and layout
(default top tab strip; sidebar — a vertical tab bar with double-line
borders and a prompt cursor; or bottom — a bottom tab strip with rounded
borders). Theme and layout are independent, so any colour combines with any
layout, applied live. Values are
colour-coded (green = on, red = off, yellow = other), with a live description
and option list on the right.
Per-app config — press s on any installed app to override the global
defaults for just that app: network/device toggles, temp mode, identity
spoofing, RAM limit, Avahi mode, and (for wine games) the exe and prefix.
Changes are saved to that app's own config.ini.
| Key | Action |
|---|---|
Tab / Shift+Tab |
Switch tabs (Installed / Install / Import / Games / Space / Settings) |
↑ / ↓ or j / k |
Navigate lists |
r |
Run selected app |
d / Delete |
Remove selected app (double-confirm) |
e |
Export selected app to a zip |
p |
Snapshot selected app (hard-linked clone) |
o |
Roll selected app back to its latest snapshot |
u |
Update selected app |
U |
Update all out-of-date apps |
c |
Check for updates |
s |
Open per-app config |
n |
Rename app (set display name) |
q / Esc |
Quit / close overlay |
t |
Toggle debug log during install/remove operations |
? |
Show key-bindings reference |
Shift+Q |
Force-quit from anywhere |
Update indicators — On startup (and after every install/update/remove) wryayer checks all apps for newer versions in the background and marks the out-of-date ones with a dot in the Installed list. u updates the selected app; Shift+U updates them all after a confirmation listing what's out of date.
Running-instance count — Apps with a live sandbox running show a count next to their name, so you can see at a glance what's open.
Multi-select install — In the Install tab, press Space to mark one or more search results, then Enter to install all marked packages one after another. Marks persist across searches, so you can queue packages from several searches before starting. Pressing Enter with no marks installs the hovered item.
Install prompts — Before an install begins, wryayer asks for a confirmation and then whether to create a ~/bin/<name> launcher shortcut. Both can be turned off in the Settings tab if you'd rather installs start immediately:
| Setting | Effect |
|---|---|
| Default shortcut | Whether the shortcut prompt pre-selects "Yes" or "No" |
| Confirm install | off skips the "Install <pkg>?" prompt and starts the install immediately |
| Ask shortcut | off skips the shortcut prompt and silently applies Default shortcut |
Settings are stored in ~/.wryayer/defaults.ini and apply as defaults to every newly installed app; per-app overrides always take precedence.
| Distribution | Support | Notes |
|---|---|---|
| Arch Linux | ✅ Fully supported | pacman + AUR backend; actively tested |
| CachyOS | ✅ Fully supported | Arch-based; primary test environment |
| Manjaro | ✅ Fully supported | Arch-based; detected via ID_LIKE=manjaro |
| EndeavourOS / Garuda / other Arch derivatives | ✅ Fully supported | Detected via ID_LIKE=arch or presence of /usr/bin/pacman |
| Debian 12 / 13 | ✅ Fully supported | apt + dpkg backend; actively tested |
| Ubuntu 22.04 / 24.04 | ✅ Expected to work | Detected via ID_LIKE=ubuntu; same apt/dpkg toolchain as Debian — not separately tested |
| Linux Mint | ✅ Expected to work | Ubuntu-based; detected via ID_LIKE=ubuntu; not separately tested |
| Fedora 38+ | ✅ Fully supported | dnf + rpm2cpio backend; actively tested |
| RHEL / AlmaLinux / Rocky | ✅ Expected to work | Same dnf/rpm backend as Fedora; detected via ID_LIKE=rhel |
| Void Linux | ❌ Not supported | Uses xbps — no supported backend |
| openSUSE | ❌ Not supported | Uses zypper — no supported backend |
Distro detection reads /etc/os-release. Distributions not listed above may work if they are closely derived from Arch, Debian, or Fedora and carry a matching ID_LIKE value, but are untested.
wryayer auto-detects your distro from /etc/os-release and uses the appropriate package backend. Install the tools for your distro before building.
| Requirement | How to install | Notes |
|---|---|---|
| bubblewrap | sudo pacman -S bubblewrap |
Required at runtime |
| Rust toolchain | curl https://sh.rustup.rs -sSf | sh |
For building |
| git | sudo pacman -S git |
AUR package builds |
| base-devel | sudo pacman -S base-devel |
AUR builds (makepkg) |
| yay (optional) | AUR | Cache reused when present; fallback is makepkg |
vercmp |
Bundled with pacman |
Version comparison |
ldconfig |
Bundled with glibc |
Library cache rebuild after install |
glib-compile-schemas |
sudo pacman -S glib2 |
Optional — GLib apps only |
update-mime-database |
sudo pacman -S shared-mime-info |
Optional — needed for GTK MIME detection (color pickers, etc.) |
gtk-update-icon-cache |
sudo pacman -S gtk-update-icon-cache |
Optional — needed for icon themes (Adwaita, hicolor) |
gdk-pixbuf-query-loaders |
sudo pacman -S gdk-pixbuf2 |
Optional — pixbuf loader cache |
xdg-dbus-proxy |
sudo pacman -S xdg-dbus-proxy |
Optional — required for the file-picker portal filter (on by default) |
dbus-daemon |
Bundled with dbus |
Optional — runs the private per-sandbox Avahi stub bus (avahi = stub, the default) that silences zeroconf errors in Electron/KDE apps without touching the host |
| Requirement | How to install | Notes |
|---|---|---|
| bubblewrap | sudo apt install bubblewrap |
Required at runtime |
| Rust toolchain | curl https://sh.rustup.rs -sSf | sh |
For building |
| binutils | sudo apt install binutils |
Provides readelf — used by soname scanner |
| dpkg | Pre-installed | Package extraction (dpkg-deb) |
| apt | Pre-installed | Dep resolution and download |
ldconfig |
sudo apt install libc-bin |
Library cache rebuild after install |
xdg-dbus-proxy |
sudo apt install xdg-dbus-proxy |
Optional — required for the file-picker portal filter (on by default) |
AUR packages are Arch-only. On Debian/Ubuntu, only packages from
aptrepos are available. Attempting to install an AUR-only package will print a warning and skip that dep.
| Requirement | How to install | Notes |
|---|---|---|
| bubblewrap | sudo dnf install bubblewrap |
Required at runtime |
| Rust toolchain | curl https://sh.rustup.rs -sSf | sh |
For building |
| binutils | sudo dnf install binutils |
Provides readelf — used by soname scanner |
| dnf | Pre-installed | Dep resolution and download |
| rpm2cpio | sudo dnf install rpm |
Package extraction |
ldconfig |
Pre-installed | Library cache rebuild after install |
xdg-dbus-proxy |
sudo dnf install xdg-dbus-proxy |
Optional — required for the file-picker portal filter (on by default) |
# Clone
git clone https://github.com/KsmBl/wryayer.git
cd wryayer
# Build release binary
cargo build --release
# Install to ~/bin/ (already on PATH if you followed setup)
cp target/release/wryayer ~/bin/For development builds (faster compile, debug symbols):
cargo build
cp target/debug/wryayer ~/bin/Generate and install completions once; they are auto-loaded by fish:
# fish
wryayer completions fish > ~/.config/fish/completions/wryayer.fish
# bash
wryayer completions bash >> ~/.bashrc
# zsh
wryayer completions zsh >> ~/.zshrcRe-run after updating the binary to pick up new subcommands.
# From the official repos or AUR — wryayer detects automatically
wryayer install firefox
wryayer install neovim
# Override the app directory name and/or the ~/bin/ launcher name
wryayer install python --app-name py312 --bin-name python3.12
# Multiple launchers from one package (e.g. a toolkit shipping several CLIs)
wryayer install imagemagick --bin-names convert,identify,mogrify
# Install additively into an existing app's directory — useful for plugins
# and multi-tool bundles. The new package's files land in the target's
# tree (sharing deps already extracted there), but the new package gets
# its own thin manifest dir at ~/.wryayer/<pkg>/ that carries an
# `alias_of` pointer back to the target. Each alias is a first-class
# entry in `wryayer list` and `wryayer tui`, gets its own ~/bin/<name>
# launcher, and can have its own sandbox config.
wryayer install neovim
wryayer install ripgrep --into neovim
wryayer install fd --into neovim
# Pick a different name for the alias dir (defaults to the package name)
wryayer install hyfetch --into fastfetch --app-name hf
# Some packages install their binary under a name that differs from the
# package name (e.g. vivaldi installs as vivaldi-stable, google-chrome as
# google-chrome-stable). If the install fails with "binary not found", the
# error lists what IS in the bin dirs — re-run with --bin-names:
wryayer install vivaldi --bin-names vivaldi-stableThe resulting layout:
~/.wryayer/
├── neovim/
│ ├── usr/bin/nvim, rg, fd ← all the real binaries live here
│ └── .manifest.toml ← lists neovim, ripgrep, fd packages
├── ripgrep/
│ └── .manifest.toml ← alias_of = "neovim", launchers = [rg]
└── fd/
└── .manifest.toml ← alias_of = "neovim", launchers = [fd]
Aliases run inside the target's tree but read their own config.ini, so
you can give a plugin a different sandbox profile (e.g. network=off) than
the host app. Removing an alias deletes only the alias dir + its launcher;
the target's tree is left intact. Removing a target while aliases still point
at it is refused with an explicit error listing the blocking aliases.
# Via the generated launcher (preferred)
firefox
# Via wryayer run
wryayer run firefox
wryayer run firefox -- --new-window # pass -- to separate wryayer flags from app flags
wryayer run firefox -- ~/Documents/doc.pdf
# Multi-binary apps installed with --bin-names: pick which binary to invoke.
# Must be one of the launchers registered for the app.
wryayer run neovim --bin nvim
# Aliases (installed via --into) are run via their own alias name, not the target.
# After: wryayer install ripgrep --into neovim
wryayer run ripgrep -- --json "TODO" . # or just: rg --json "TODO" .wryayer listOutput:
name version installed size launchers
------------------------------------------------------------------------
firefox 130.0.1-1 2026-05-10T14:23:00 847.3 MiB firefox
vlc 3.0.21-1 2026-05-11T09:01:00 312.7 MiB vlc
------------------------------------------------------------------------
apparent: 1.1 GiB on disk: 960 MiB saves: 200 MiB
wryayer remove firefox
# Remove an app and all aliases that point at it in one shot
wryayer remove firefox --cascadeIf the app has any aliases pointing at it (created via install --into),
removal is refused until those aliases are removed first — otherwise their
launcher scripts would silently target a missing directory. Use --cascade
to remove the target and all its aliases in one command. Removing the
alias itself is always safe and never touches the target tree.
wryayer update # check and update all apps
wryayer update firefox # update one app
wryayer update --check # report available updates without installingUpdates preserve your data and snapshots: the sandbox home/ (browser
profiles, settings), the per-app config.ini, and every saved snapshot survive
the re-extraction, and any programs merged in with --into are re-resolved so
their binaries are never lost. In the TUI, wryayer checks for updates on startup
and marks out-of-date apps with a dot; u updates the selected app and
Shift+U updates every out-of-date app at once.
# Pack an app's entire directory tree into a portable zip
wryayer export firefox
wryayer export firefox --output /mnt/backup/firefox-2026.zip
# Import a previously-exported zip (re-creates the app as if freshly installed)
wryayer import firefox-2026.zipThe export progress bar in the TUI is real — wryayer pre-counts entries, then emits PROGRESS n/total markers during the zip write so the gauge and ETA reflect actual work done.
Snapshots are instant and near-free in disk space — they create a hard-linked clone of the live app dir under ~/.wryayer/<app>/.snapshots/<timestamp>/. Rollbacks atomically restore the live tree from a chosen snapshot.
# Snapshot the current state of an app
wryayer snapshot firefox
# List snapshots for an app, newest first
wryayer snapshots firefox
# Roll back to the most recent snapshot
wryayer rollback firefox
# Roll back to a specific labelled snapshot
wryayer rollback firefox 20260516-141022
# Prune old snapshots, keeping the N most recent (default: 3)
wryayer snapshot-prune firefox
wryayer snapshot-prune firefox --keep 5Snapshots survive updates: a rollback after an update returns you to the pre-update version. (Extraction always writes a fresh inode, so the snapshot's hard link keeps pointing at the old content; the dedup pass at the end of every install re-establishes shared-library hard links.)
Snapshots are excluded from wryayer list size totals, wryayer dedup, and the export zip.
After installing multiple apps that share libraries, identical files are automatically hard-linked. Run manually at any time:
wryayer dedup # silent
wryayer dedup --verbose # print every file linked~/.cache/wryayer holds downloaded packages, AUR build dirs, and resolved
dependency lists — which reveal what you've installed. Wipe it at any time:
wryayer cleanSet clean_cache = on (Settings → Clean cache) to do this automatically after
every install, so nothing recording your app set is left outside ~/.wryayer.
If an app crashes with a missing .so error, this command finds and installs the missing package:
wryayer repair firefoxEach game becomes its own self-contained container at ~/.wryayer/<name>/ with
a fresh wine install and its own WINEPREFIX. Games can't interfere with each
other, removing one is a single rm -rf, and the cross-app dedup pass that
runs at the end of every import hard-links identical wine files between
containers so disk usage stays in check.
# Import a game folder (wine is installed fresh into the new container)
wryayer install-game ~/Games/NFSU2
# Override the auto-detected main .exe
wryayer install-game ~/Games/Skyrim --exe SkyrimSE.exe
# Pick a different name; delete the source after a successful copy
wryayer install-game ~/Games/NFSU2 --app-name nfsu2 --delete-source
# Run it like any other app
nfsu2
# or
wryayer run nfsu2The game folder lands at ~/.wryayer/<name>/games/<name>/ and the
WINEPREFIX at ~/.wryayer/<name>/games/<name>/.wineprefix/. The container's
manifest tracks wine and its deps as regular [[packages]] plus a wine_game
block that tells wryayer run to launch wine <exe> instead of a Linux
binary. The TUI's Games tab wraps the same flow in a 3-step wizard
(folder picker → .exe picker → name + delete-source confirm).
The full TUI walkthrough, screenshots, and key-binding reference are near the top of this page — see The interactive TUI.
# Show current config
wryayer config firefox
# Change settings
wryayer config firefox network off # block internet access
wryayer config firefox audio off # mute audio output + mic
wryayer config firefox tempmode ramdisk # private in-memory /tmp
wryayer config firefox ramlimit 2048 # limit to 2 GiB RAM
wryayer config firefox ramlimit none # remove RAM limit
# Shared directories (bind-mounted read-write into the sandbox)
wryayer config firefox share add ~/Documents
wryayer config firefox share add ~/Downloads
wryayer config firefox share remove ~/Documents
wryayer config firefox share list| Setting | Values | Default | Description |
|---|---|---|---|
tempmode |
system ramdisk local uuid |
system |
How /tmp is provided inside the sandbox |
tempdelete |
never on_start on_close |
on_start |
When to clean up local temp dirs (only with tempmode local) |
network |
on off |
on |
Allow outgoing network access |
camera |
on off |
on |
Allow /dev/video* camera access |
microphone |
on off |
on |
Mask ALSA capture devices (see caveat below) |
audio |
on off |
on |
Mask ALSA + PipeWire/PulseAudio sockets |
share add <path> |
Any existing directory | — | Bind-mount <path> read-write inside the sandbox |
ramlimit <MiB|none> |
Integer (MiB) or none |
none |
Hard cap on RAM and swap combined, enforced via systemd-run --scope -p MemoryMax=NM -p MemorySwapMax=0 (requires systemd). Both limits are necessary — without MemorySwapMax=0 the kernel silently offloads pages to swap (including zram), letting the app exceed the cap. |
portal_filter |
on off |
on |
Hide the host desktop portal so in-sandbox file pickers list only your shared directories instead of the whole home tree. Turn off if an app needs portal features (screen-share, portal-based file open). |
With portal_filter on (the default), opening a file dialog inside a sandboxed
app shows only the folders you've shared (share add …) — not your real
home directory. This needs xdg-dbus-proxy installed; without it the filter is
skipped and the app falls back to the host portal. Set portal_filter off for a
specific app if it relies on portal features that the filter blocks.
Override what the sandbox reports about the host machine. Useful for preventing apps from embedding your real hostname, username, OS identity, or machine fingerprint in logs, telemetry, or profiles.
# Spoof /etc/hostname and $HOSTNAME
wryayer config firefox spoof-hostname myworkstation
wryayer config firefox spoof-hostname sample # → "workstation"
wryayer config firefox spoof-hostname system # disable
# Spoof $USER and $LOGNAME
wryayer config firefox spoof-username sample # → "user"
wryayer config firefox spoof-username myname
# Spoof /etc/machine-id
wryayer config firefox spoof-machine-id system # use real ID (default)
wryayer config firefox spoof-machine-id random # fresh UUID every launch
wryayer config firefox spoof-machine-id sample # → cafebabe0011223344556677deadbeef
wryayer config firefox spoof-machine-id a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4
# Spoof /proc/cpuinfo
wryayer config firefox spoof-cpuinfo sample # built-in generic Intel i7
wryayer config firefox spoof-cpuinfo ~/fakecpu.txt # custom file
# Spoof /etc/os-release (hide real distro identity from the app)
wryayer config firefox spoof-os ubuntu # present as Ubuntu 24.04 LTS
wryayer config firefox spoof-os arch # present as Arch Linux
wryayer config firefox spoof-os windows # present as Windows 11
wryayer config firefox spoof-os arduinoide # present as ArduinoIDE
wryayer config firefox spoof-os fedora # custom: any name works via "input" in TUI
wryayer config firefox spoof-os system # disable
# Spoof terminal — fix fastfetch showing "bwrap" instead of your real terminal
wryayer config fastfetch spoof-terminal on # detect kitty/foot/alacritty/… and set TERM_PROGRAM
wryayer config fastfetch spoof-terminal off # disable (default)
# Disable any spoofing
wryayer config firefox spoof-hostname systemAll settings are editable in the TUI config screen (s on an installed app). Each row uses a picker; press ? on any row or option to see a description of what the setting does.
Press ? on the installed tab for a full key-bindings reference.
| CLI subcommand | Values | Effect |
|---|---|---|
spoof-hostname <value|sample|system|off> |
Any string | Writes /etc/hostname, sets $HOSTNAME |
spoof-username <value|sample|system|off> |
Any string | Sets $USER and $LOGNAME |
spoof-machine-id <system|random|sample|hex|off> |
See below | Writes /etc/machine-id |
spoof-cpuinfo <sample|path|system|off> |
Path or sample |
Binds the file over /proc/cpuinfo |
spoof-os <ubuntu|arch|windows|arduinoide|name|system|off> |
Preset or any OS name | Writes /etc/os-release and /usr/lib/os-release |
spoof-terminal <on|off> |
on or off |
Detects real terminal via process tree and sets TERM_PROGRAM inside sandbox |
Sample values:
| Setting | Sample value |
|---|---|
| hostname | workstation |
| username | user |
| machine-id | cafebabe0011223344556677deadbeef |
| cpuinfo | Built-in generic Intel Core i7-8550U on x86_64 |
| os-release presets | ubuntu → Ubuntu 24.04 LTS · arch → Arch Linux · windows → Windows 11 · arduinoide → ArduinoIDE · any other value used as a custom OS name |
machine-id modes:
| Value | Behaviour |
|---|---|
system / off |
No spoofing — real /etc/machine-id is used |
random |
Generates a fresh 32-char hex UUID on every launch |
sample |
Fixed placeholder cafebabe0011223344556677deadbeef |
| 32-char hex | Your own fixed machine-id |
The config is stored as a human-readable INI file at ~/.wryayer/<app>/config.ini.
AUR is Arch-only. On Debian/Ubuntu and Fedora/RHEL the AUR code path is never reached; deps are resolved via the native package manager only. Attempting to install an AUR-only package on a non-Arch distro will print a warning and skip that dep.
glibc version pinning. glibc is resolved and extracted as a normal dependency. The ld-linux-x86-64.so.2 loader that executes inside the sandbox is therefore the one from the app's own extracted glibc, not the host's. If the app's packages were built against a glibc version that differs significantly from the host kernel's syscall ABI, it may crash with version GLIBC_X.XX not found or Illegal instruction.
Microphone isolation is incomplete. Setting microphone=off masks ALSA capture devices (/dev/snd/pcmC*D*c). Apps using PipeWire or PulseAudio can still access the microphone socket in XDG_RUNTIME_DIR. To fully block mic access, also set audio=off.
Partial D-Bus session isolation. With portal_filter on, the sandbox's session bus is routed through a filter proxy that hides the host desktop portal (so file pickers stay confined to shared dirs) while still forwarding Notifications, secrets, MPRIS, etc. Other session services remain reachable, and with portal_filter off the app talks to the host session bus directly.
Hard links require same filesystem. Deduplication only works when all ~/.wryayer/<app>/ directories are on the same filesystem. If you mount ~/.wryayer on a separate partition from another app, dedup will silently skip cross-device hard-links.
AUR builds run makepkg as your user. This is the same trust model as using yay directly. Build scripts execute arbitrary code. Only install from AUR packages you trust.
Wayland socket not isolated. The Wayland display socket ($XDG_RUNTIME_DIR/wayland-0) is accessible inside the sandbox via /run. Apps have full Wayland access.
No SETUID/SETCAP binaries. bwrap drops most capabilities. Apps that rely on setuid helpers (e.g., some network tools) will fail unless you add the helper to your system installation.
- soname resolution occasionally misses packages. If
wryayer repaircan't find a.so, it usually means the owning package uses an unusual installation path. Workaround: install the package system-wide and copy the.sointo~/.wryayer/<app>/usr/lib/. - AUR packages with custom build steps (non-standard
PKGBUILDlayouts) may produce a.pkg.tar.zstthat doesn't extract cleanly. Check the build log with[t]in the TUI. - GLib apps may miss GSettings schemas if a dependency ships schemas that aren't compiled after extraction. wryayer runs
glib-compile-schemason the main app's schema dir, but not on dependency dirs. Workaround: runglib-compile-schemas ~/.wryayer/<app>/usr/share/glib-2.0/schemas/manually. - The TUI progress bar is indeterminate during install and update operations because pacman doesn't emit structured progress on stderr. The actual log is one
[t]keypress away. - Disk usage figures in
wryayer listare per-app apparent sizes; they don't subtract hard-linked savings. The footer line ofwryayer listand the Space tab in the TUI both show the combined total with savings noted.
- Multi-binary apps — install an app that ships more than one launcher binary (
--bin-names a,b,c) - Rollback support —
wryayer snapshot+wryayer rollback(hard-linked, instant) - Install into existing app —
wryayer install <pkg> --into <existing>for plugins and bundles; alias gets its own first-class entry under~/.wryayer/<pkg>/withalias_ofpointer - TUI install target picker — choosing Install on a search result now prompts whether to start a new app or merge into an existing one
- Wayland isolation — bind a private Wayland socket so apps can't impersonate each other
- D-Bus portal filtering — file pickers run in-sandbox and only show shared dirs, via an
xdg-dbus-proxyfilter that hides the host portal (portal_filter) - Package signing verification — validate
.pkg.tar.zstsignatures before extraction - Delta updates — only re-download changed packages instead of the full dep tree
- Export/import via SSH or SFTP —
wryayer export --remote user@host:/path - TUI package search from AUR — Install tab searches both official repos and the AUR
- Identity spoofing — spoof hostname, username, machine-id, and cpuinfo per app
- Global default settings — Settings tab in TUI and
~/.wryayer/defaults.iniset defaults inherited by all new apps - Multi-select install — mark multiple search results with
Space, install them all sequentially withEnter; marks persist across searches - Update all — check every app for updates on TUI start and update the out-of-date ones with
Shift+U - Per-app env var overrides — let users set
LANG,QT_SCALE_FACTOR, etc. inconfig.ini - Dependency graph viewer — TUI screen showing the full package tree for an installed app
- Auto-snapshot on update — capture a snapshot automatically before each update so failures can be undone with one keystroke
Architecture, on-disk layout, sandbox construction, and developer/testing docs
(build, cargo test, coverage) live in README-CODE.md.
Copyright © 2026 KsmBl and contributors.
wryayer is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
A copy of the license is included in this repository as LICENSE.
Note for package distributors: The LGPL requires that users be able to relink a modified version of the library. Because wryayer is a standalone binary application (not a shared library), this condition is satisfied by making the source code available, which this repository does.



