diff --git a/.github/workflows/update-nix.yaml b/.github/workflows/update-nix.yaml new file mode 100644 index 00000000..8203da51 --- /dev/null +++ b/.github/workflows/update-nix.yaml @@ -0,0 +1,19 @@ +name: "Update Flake Packages" + +on: + workflow_dispatch: + schedule: + - cron: "0 10 * * 0" # https://crontab.guru/#0_10_*_*_0 + +jobs: + updateFlakePackages: + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v3 + + - name: Install Nix + uses: cachix/install-nix-action@v20 + + - name: Update flake packages + uses: selfuryon/nix-update-action@v1 diff --git a/.license-tools-config.json b/.license-tools-config.json index c361afa7..a7c368af 100644 --- a/.license-tools-config.json +++ b/.license-tools-config.json @@ -7,10 +7,12 @@ "style_override_for_suffix": { ".yaml": "POUND_STYLE", ".ps1": "POUND_STYLE", + ".nix": "POUND_STYLE", ".bat": "BATCH_STYLE", "": "POUND_STYLE" }, "exclude": [ + "flake.lock", "^\\.[^/]+", "/\\.[^/]+", "^(.+)\\.(md|svg|png|reg|gif)", diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 6dba8378..5be5a5ab 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -2,6 +2,8 @@ ci: autoupdate_branch: "rewrite" skip: [license-tools] +exclude: ^(.+)\.patch$ + repos: - repo: https://github.com/Lucas-C/pre-commit-hooks rev: v1.5.5 diff --git a/README.md b/README.md index bde82e73..918a3918 100644 --- a/README.md +++ b/README.md @@ -462,6 +462,93 @@ The installer can be run multiple times. To update your installation of WinApps: 2. Pull the latest changes from the WinApps GitHub repository. 3. Re-install WinApps using the WinApps installer by running `winapps-setup`. +## Installation using Nix + +First, follow Step 1 of the normal installation guide to create your VM. +Then, install WinApps according to the following instructions. + +After installation, it will be available under `winapps`, with the installer being available under `winapps-setup` +and the optional launcher being available under `winapps-launcher.` + +### Using standalone Nix + +First, make sure Flakes and the `nix` command are enabled. +In your `~/.config/nix/nix.conf`: +``` +experimental-features = nix-command flakes +``` + +```bash +nix profile install github:winapps-org/winapps#winapps +nix profile install github:winapps-org/winapps#winapps-launcher # optional +``` + +### On NixOS using Flakes + +```nix +# flake.nix +{ + description = "My configuration"; + + inputs = { + nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable"; + + winapps = { + url = "github:winapps-org/winapps"; + inputs.nixpkgs.follows = "nixpkgs"; + }; + }; + + outputs = + { + nixpkgs, + winapps, + ... + }: + { + nixosConfigurations.hostname = nixpkgs.lib.nixosSystem rec { + system = "x86_64-linux"; + + modules = [ + ./configuration.nix + ( + { pkgs, ... }: + { + environment.systemPackages = [ + winapps.packages.${system}.winapps + winapps.packages.${system}.winapps-launcher # optional + ]; + } + ) + ]; + }; + }; +} +``` + +### On NixOS without Flakes + +[Flakes aren't real and they can't hurt you.](https://jade.fyi/blog/flakes-arent-real/). +However, if you still don't want to use flakes, you can use WinApps with flake-compat like: + +```nix +# configuration.nix +{ ... }: +{ + + environment.systemPackages = + let + winapps = + (import (builtins.fetchTarball "https://github.com/winapps-org/winapps/archive/main.tar.gz")) + .packages."${system}"; + in + [ + winapps.winapps + winapps.winapps-launcher # optional + ]; +} +``` + ## Star History diff --git a/default.nix b/default.nix new file mode 100644 index 00000000..0cd52418 --- /dev/null +++ b/default.nix @@ -0,0 +1,16 @@ +# Copyright (c) 2024 Oskar Manhart +# All rights reserved. +# +# SPDX-License-Identifier: AGPL-3.0-or-later + +(import ( + let + lock = builtins.fromJSON (builtins.readFile ./flake.lock); + in + fetchTarball { + url = + lock.nodes.flake-compat.locked.url + or "https://github.com/edolstra/flake-compat/archive/${lock.nodes.flake-compat.locked.rev}.tar.gz"; + sha256 = lock.nodes.flake-compat.locked.narHash; + } +) { src = ./.; }).defaultNix diff --git a/flake.lock b/flake.lock new file mode 100644 index 00000000..dc621f09 --- /dev/null +++ b/flake.lock @@ -0,0 +1,76 @@ +{ + "nodes": { + "flake-compat": { + "locked": { + "lastModified": 1696426674, + "narHash": "sha256-kvjfFW7WAETZlt09AgDn1MrtKzP7t90Vf7vypd3OL1U=", + "rev": "0f9255e01c2351cc7d116c072cb317785dd33b33", + "revCount": 57, + "type": "tarball", + "url": "https://api.flakehub.com/f/pinned/edolstra/flake-compat/1.0.1/018afb31-abd1-7bff-a5e4-cff7e18efb7a/source.tar.gz" + }, + "original": { + "type": "tarball", + "url": "https://flakehub.com/f/edolstra/flake-compat/1.tar.gz" + } + }, + "flake-utils": { + "inputs": { + "systems": "systems" + }, + "locked": { + "lastModified": 1710146030, + "narHash": "sha256-SZ5L6eA7HJ/nmkzGG7/ISclqe6oZdOZTNoesiInkXPQ=", + "owner": "numtide", + "repo": "flake-utils", + "rev": "b1d9ab70662946ef0850d488da1c9019f3a9752a", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "flake-utils", + "type": "github" + } + }, + "nixpkgs": { + "locked": { + "lastModified": 1724819573, + "narHash": "sha256-GnR7/ibgIH1vhoy8cYdmXE6iyZqKqFxQSVkFgosBh6w=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "71e91c409d1e654808b2621f28a327acfdad8dc2", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixos-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "root": { + "inputs": { + "flake-compat": "flake-compat", + "flake-utils": "flake-utils", + "nixpkgs": "nixpkgs" + } + }, + "systems": { + "locked": { + "lastModified": 1681028828, + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", + "owner": "nix-systems", + "repo": "default", + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", + "type": "github" + }, + "original": { + "owner": "nix-systems", + "repo": "default", + "type": "github" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/flake.nix b/flake.nix new file mode 100644 index 00000000..22c8b5ce --- /dev/null +++ b/flake.nix @@ -0,0 +1,34 @@ +# Copyright (c) 2024 Oskar Manhart +# All rights reserved. +# +# SPDX-License-Identifier: AGPL-3.0-or-later + +{ + description = "WinApps Nix packages & NixOS module"; + + inputs = { + nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable"; + + flake-compat.url = "https://flakehub.com/f/edolstra/flake-compat/1.tar.gz"; + flake-utils.url = "github:numtide/flake-utils"; + }; + + outputs = + { + nixpkgs, + flake-utils, + ... + }: + flake-utils.lib.eachDefaultSystem ( + system: + let + pkgs = import nixpkgs { inherit system; }; + in + { + formatter = pkgs.nixfmt-rfc-style; + + packages.winapps = pkgs.callPackage ./packages/winapps { }; + packages.winapps-launcher = pkgs.callPackage ./packages/winapps-launcher { }; + } + ); +} diff --git a/packages/winapps-launcher/WinAppsLauncher.patch b/packages/winapps-launcher/WinAppsLauncher.patch new file mode 100644 index 00000000..962b1bf0 --- /dev/null +++ b/packages/winapps-launcher/WinAppsLauncher.patch @@ -0,0 +1,11 @@ +--- a/WinAppsLauncher.sh ++++ b/WinAppsLauncher.sh +@@ -19,7 +19,7 @@ declare -rx EC_WIN_NOT_SPEC=6 + declare -rx EC_NO_WIN_FOUND=7 + + # Paths +-declare -rx ICONS_PATH="./Icons" ++declare -rx ICONS_PATH="@out@/Icons" + declare -rx APPDATA_PATH="${HOME}/.local/share/winapps" + declare -rx CONFIG_PATH="${HOME}/.config/winapps" + declare -rx CONFIG_FILE="${CONFIG_PATH}/winapps.conf" diff --git a/packages/winapps-launcher/default.nix b/packages/winapps-launcher/default.nix new file mode 100644 index 00000000..2af26aca --- /dev/null +++ b/packages/winapps-launcher/default.nix @@ -0,0 +1,77 @@ +# Copyright (c) 2024 Oskar Manhart +# All rights reserved. +# +# SPDX-License-Identifier: AGPL-3.0-or-later + +{ + stdenv, + lib, + fetchFromGitHub, + makeWrapper, + makeDesktopItem, + callPackage, + yad, + ... +}: +let + rev = "9f5fbcb57f2932b260202fb582f9adcf28df5f1c"; + hash = "sha256-cShXlcFHTryxKLKxdoqZSge2oyGgeuFPW9Nxg+gSjB4="; +in +stdenv.mkDerivation rec { + pname = "winapps-launcher"; + version = "0-unstable-2024-10-01"; + + src = fetchFromGitHub { + owner = "winapps-org"; + repo = "WinApps-Launcher"; + + inherit rev hash; + }; + + nativeBuildInputs = [ makeWrapper ]; + buildInputs = [ + yad + (callPackage ../winapps { }) + ]; + + patches = [ ./WinAppsLauncher.patch ]; + + postPatch = '' + substituteAllInPlace WinAppsLauncher.sh + ''; + + installPhase = '' + runHook preInstall + + mkdir -p $out + cp -r ./Icons $out/Icons + + install -m755 -D WinAppsLauncher.sh $out/bin/winapps-launcher + install -Dm444 -T Icons/AppIcon.svg $out/share/pixmaps/winapps.svg + + wrapProgram $out/bin/winapps-launcher \ + --set LIBVIRT_DEFAULT_URI "qemu:///system" \ + --prefix PATH : "${lib.makeBinPath buildInputs}" + + runHook postInstall + ''; + + desktopItems = [ + (makeDesktopItem { + name = "winapps"; + exec = "winapps-launcher"; + icon = "winapps"; + comment = meta.description; + desktopName = "WinApps"; + categories = [ "Utility" ]; + }) + ]; + + meta = with lib; { + homepage = "https://github.com/winapps-org/WinApps-Launcher"; + description = "Graphical launcher for WinApps. Run Windows applications (including Microsoft 365 and Adobe Creative Cloud) on GNU/Linux with KDE, GNOME or XFCE, integrated seamlessly as if they were native to the OS. Wayland is currently unsupported."; + mainProgram = "winapps-launcher"; + platforms = platforms.linux; + license = licenses.gpl3; + }; +} diff --git a/packages/winapps/default.nix b/packages/winapps/default.nix new file mode 100644 index 00000000..27bc1932 --- /dev/null +++ b/packages/winapps/default.nix @@ -0,0 +1,80 @@ +# Copyright (c) 2024 Oskar Manhart +# All rights reserved. +# +# SPDX-License-Identifier: AGPL-3.0-or-later + +{ + stdenv, + lib, + fetchFromGitHub, + makeWrapper, + freerdp3, + dialog, + libnotify, + netcat, + iproute2, + ... +}: +let + rev = "c8dcccad08b3e5489d78f2aad034189d8654745c"; + hash = "sha256-RM9jv8oS8wKcSJpvkFFG9uyiRv9EaLQWANymGTXdl4o="; +in +stdenv.mkDerivation rec { + pname = "winapps"; + version = "0-unstable-2024-10-09"; + + src = fetchFromGitHub { + owner = "winapps-org"; + repo = "winapps"; + + inherit rev hash; + }; + + nativeBuildInputs = [ makeWrapper ]; + buildInputs = [ + freerdp3 + libnotify + dialog + netcat + iproute2 + ]; + + patches = [ + ./winapps.patch + ./setup.patch + ]; + + postPatch = '' + substituteAllInPlace bin/winapps + substituteAllInPlace setup.sh + patchShebangs install/inquirer.sh + ''; + + installPhase = '' + runHook preInstall + + mkdir -p $out + mkdir -p $out/src + + cp -r ./ $out/src/ + + install -m755 -D bin/winapps $out/bin/winapps + install -m755 -D setup.sh $out/bin/winapps-setup + + for f in winapps-setup winapps; do + wrapProgram $out/bin/$f \ + --set LIBVIRT_DEFAULT_URI "qemu:///system" \ + --prefix PATH : "${lib.makeBinPath buildInputs}" + done + + runHook postInstall + ''; + + meta = with lib; { + homepage = "https://github.com/winapps-org/winapps"; + description = "Run Windows applications (including Microsoft 365 and Adobe Creative Cloud) on GNU/Linux with KDE, GNOME or XFCE, integrated seamlessly as if they were native to the OS. Wayland is currently unsupported."; + mainProgram = "winapps"; + platforms = platforms.linux; + license = licenses.agpl3Plus; + }; +} diff --git a/packages/winapps/setup.patch b/packages/winapps/setup.patch new file mode 100644 index 00000000..18124b69 --- /dev/null +++ b/packages/winapps/setup.patch @@ -0,0 +1,165 @@ +diff --git a/setup.sh b/setup.sh +index 6aa9b574..9fbefe65 100755 +--- a/setup.sh ++++ b/setup.sh +@@ -48,8 +48,8 @@ readonly SYS_BIN_PATH="/usr/local/bin" # UNIX path to 'bin' dir + readonly USER_BIN_PATH="${HOME}/.local/bin" # UNIX path to 'bin' directory for a '--user' WinApps installation. + readonly USER_BIN_PATH_WIN='\\tsclient\home\.local\bin' # WINDOWS path to 'bin' directory for a '--user' WinApps installation. + # 'SOURCE' +-readonly SYS_SOURCE_PATH="${SYS_BIN_PATH}/winapps-src" # UNIX path to WinApps source directory for a '--system' WinApps installation. +-readonly USER_SOURCE_PATH="${USER_BIN_PATH}/winapps-src" # UNIX path to WinApps source directory for a '--system' WinApps installation. ++readonly SYS_SOURCE_PATH="@out@/src" # UNIX path to WinApps source directory for a '--system' WinApps installation. ++readonly USER_SOURCE_PATH="@out@/src" # UNIX path to WinApps source directory for a '--system' WinApps installation. + # 'APP' + readonly SYS_APP_PATH="/usr/share/applications" # UNIX path to 'applications' directory for a '--system' WinApps installation. + readonly USER_APP_PATH="${HOME}/.local/share/applications" # UNIX path to 'applications' directory for a '--user' WinApps installation. +@@ -79,7 +79,7 @@ readonly TEST_PATH_WIN="${USER_APPDATA_PATH_WIN}\\FreeRDP_Connection_Test" # WIN + # 'WinApps Configuration File' + readonly CONFIG_PATH="${HOME}/.config/winapps/winapps.conf" # UNIX path to the WinApps configuration file. + # 'Inquirer Bash Script' +-readonly INQUIRER_PATH="./install/inquirer.sh" # UNIX path to the 'inquirer' script, which is used to produce selection menus. ++readonly INQUIRER_PATH="@out@/src/install/inquirer.sh" # UNIX path to the 'inquirer' script, which is used to produce selection menus. + + # REMOTE DESKTOP CONFIGURATION + readonly VM_NAME="RDPWindows" # Name of the Windows VM (FOR 'libvirt' ONLY). +@@ -139,13 +139,13 @@ function waTerminateScript() { + # Role: Displays usage information for the script. + function waUsage() { + echo -e "Usage: +- ${COMMAND_TEXT}./setup.sh --user${CLEAR_TEXT} # Install WinApps and selected applications in ${HOME} +- ${COMMAND_TEXT}./setup.sh --system${CLEAR_TEXT} # Install WinApps and selected applications in /usr +- ${COMMAND_TEXT}./setup.sh --user --setupAllOfficiallySupportedApps${CLEAR_TEXT} # Install WinApps and all officially supported applications in ${HOME} +- ${COMMAND_TEXT}./setup.sh --system --setupAllOfficiallySupportedApps${CLEAR_TEXT} # Install WinApps and all officially supported applications in /usr +- ${COMMAND_TEXT}./setup.sh --user --uninstall${CLEAR_TEXT} # Uninstall everything in ${HOME} +- ${COMMAND_TEXT}./setup.sh --system --uninstall${CLEAR_TEXT} # Uninstall everything in /usr +- ${COMMAND_TEXT}./setup.sh --help${CLEAR_TEXT} # Display this usage message." ++ ${COMMAND_TEXT}winapps-setup --user${CLEAR_TEXT} # Install WinApps and selected applications in ${HOME} ++ ${COMMAND_TEXT}winapps-setup --system${CLEAR_TEXT} # Install WinApps and selected applications in /usr ++ ${COMMAND_TEXT}winapps-setup --user --setupAllOfficiallySupportedApps${CLEAR_TEXT} # Install WinApps and all officially supported applications in ${HOME} ++ ${COMMAND_TEXT}winapps-setup --system --setupAllOfficiallySupportedApps${CLEAR_TEXT} # Install WinApps and all officially supported applications in /usr ++ ${COMMAND_TEXT}winapps-setup --user --uninstall${CLEAR_TEXT} # Uninstall everything in ${HOME} ++ ${COMMAND_TEXT}winapps-setup --system --uninstall${CLEAR_TEXT} # Uninstall everything in /usr ++ ${COMMAND_TEXT}winapps-setup --help${CLEAR_TEXT} # Display this usage message." + } + + # Name: 'waGetSourceCode' +@@ -168,7 +168,7 @@ function waGetSourceCode() { + $SUDO git clone --recurse-submodules --remote-submodules https://github.com/winapps-org/winapps.git "$SOURCE_PATH" + else + echo -e "${INFO_TEXT}WinApps installation already present at ${CLEAR_TEXT}${COMMAND_TEXT}${SOURCE_PATH}${CLEAR_TEXT}${INFO_TEXT}. Updating...${CLEAR_TEXT}" +- $SUDO git -C "$SOURCE_PATH" pull --no-rebase ++ + fi + + # Silently change the working directory. +@@ -395,7 +395,7 @@ function waCheckExistingInstall() { + + # Display the suggested action(s). + echo "--------------------------------------------------------------------------------" +- echo -e "Please remove the existing WinApps installation using ${COMMAND_TEXT}./setup.sh --user --uninstall${CLEAR_TEXT}." ++ echo -e "Please remove the existing WinApps installation using ${COMMAND_TEXT}winapps-setup --user --uninstall${CLEAR_TEXT}." + echo "--------------------------------------------------------------------------------" + + # Terminate the script. +@@ -415,7 +415,7 @@ function waCheckExistingInstall() { + + # Display the suggested action(s). + echo "--------------------------------------------------------------------------------" +- echo -e "Please remove the existing WinApps installation using ${COMMAND_TEXT}./setup.sh --system --uninstall${CLEAR_TEXT}." ++ echo -e "Please remove the existing WinApps installation using ${COMMAND_TEXT}winapps-setup --system --uninstall${CLEAR_TEXT}." + echo "--------------------------------------------------------------------------------" + + # Terminate the script. +@@ -810,7 +810,7 @@ function waCheckGroupMembership() { + # Identify groups the current user belongs to. + USER_GROUPS=$(groups "$(whoami)") + +- if ! (echo "$USER_GROUPS" | grep -q -E "\blibvirt\b") || ! (echo "$USER_GROUPS" | grep -q -E "\bkvm\b"); then ++ if ! (echo "$USER_GROUPS" | grep -q -E "\blibvirtd\b") || ! (echo "$USER_GROUPS" | grep -q -E "\bkvm\b"); then + # Complete the previous line. + echo -e "${FAIL_TEXT}Failed!${CLEAR_TEXT}\n" + +@@ -1244,11 +1244,11 @@ function waConfigureWindows() { + # Populate variables. + WIN_BASH="\ + #!/usr/bin/env bash +-${BIN_PATH}/winapps windows" ++@out@/bin/winapps windows" + WIN_DESKTOP="\ + [Desktop Entry] + Name=Windows +-Exec=${BIN_PATH}/winapps windows %F ++Exec=@out/bin/winapps windows %F + Terminal=false + Type=Application + Icon=${APPDATA_PATH}/icons/windows.svg +@@ -1295,13 +1295,13 @@ function waConfigureApp() { + # Determine the content of the bash script for the application. + APP_BASH="\ + #!/usr/bin/env bash +-${BIN_PATH}/winapps ${1}" ++@out@/bin/winapps ${1}" + + # Determine the content of the '.desktop' file for the application. + APP_DESKTOP_FILE="\ + [Desktop Entry] + Name=${NAME} +-Exec=${BIN_PATH}/winapps ${1} %F ++Exec=@out@/bin/winapps ${1} %F + Terminal=false + Type=Application + Icon=${APP_ICON} +@@ -1631,8 +1631,8 @@ function waInstall() { + waFindInstalled + + # Install the WinApps bash scripts. +- $SUDO ln -sf "${SOURCE_PATH}/bin/winapps" "${BIN_PATH}/winapps" +- $SUDO ln -sf "${SOURCE_PATH}/setup.sh" "${BIN_PATH}/winapps-setup" ++ ++ + + # Configure the Windows RDP session application launcher. + waConfigureWindows +@@ -1682,18 +1682,15 @@ function waUninstall() { + local DESKTOP_FILE_NAME="" # Stores the name of the '.desktop' file for the application. + local BASH_SCRIPT_NAME="" # Stores the name of the application. + +- # Remove the 'WinApps' bash scripts. +- $SUDO rm -f "${BIN_PATH}/winapps" +- $SUDO rm -f "${BIN_PATH}/winapps-setup" +- + # Remove WinApps configuration data, temporary files and logs. ++ chmod -R +rw "$USER_APPDATA_PATH" + rm -rf "$USER_APPDATA_PATH" + + # Remove application icons and shortcuts. + $SUDO rm -rf "$APPDATA_PATH" + + # Store '.desktop' files containing "${BIN_PATH}/winapps" in an array, returning an empty array if no such files exist. +- readarray -t WINAPPS_DESKTOP_FILES < <(grep -l -d skip "${BIN_PATH}/winapps" "${APP_PATH}/"* 2>/dev/null || true) ++ readarray -t WINAPPS_DESKTOP_FILES < <(grep -l -d skip "@out@/bin/winapps" "${APP_PATH}/"* 2>/dev/null || true) + + # Remove each '.desktop' file. + for DESKTOP_FILE_PATH in "${WINAPPS_DESKTOP_FILES[@]}"; do +@@ -1714,7 +1711,7 @@ function waUninstall() { + done + + # Store the paths of bash scripts calling 'WinApps' to launch specific applications in an array, returning an empty array if no such files exist. +- readarray -t WINAPPS_APP_BASH_SCRIPTS < <(grep -l -d skip "${BIN_PATH}/winapps" "${BIN_PATH}/"* 2>/dev/null || true) ++ readarray -t WINAPPS_APP_BASH_SCRIPTS < <(grep -l -d skip "@out@/bin/winapps" "${BIN_PATH}/"* 2>/dev/null || true) + + # Remove each bash script. + for BASH_SCRIPT_PATH in "${WINAPPS_APP_BASH_SCRIPTS[@]}"; do +@@ -1735,10 +1732,9 @@ function waUninstall() { + done + + # Print caveats. +- echo -e "\n${INFO_TEXT}Please note that your WinApps configuration and the WinApps source code were not removed.${CLEAR_TEXT}" +- echo -e "${INFO_TEXT}You can remove these manually by running:${CLEAR_TEXT}" ++ echo -e "\n${INFO_TEXT}Please note that your WinApps configuration and the WinApps package were not removed.${CLEAR_TEXT}" ++ echo -e "${INFO_TEXT}You can remove your config manually by running:${CLEAR_TEXT}" + echo -e "${COMMAND_TEXT}rm -r $(dirname "$CONFIG_PATH")${CLEAR_TEXT}" +- echo -e "${COMMAND_TEXT}rm -r ${SOURCE_PATH}${CLEAR_TEXT}\n" + + # Print feedback. + echo -e "${SUCCESS_TEXT}UNINSTALLATION COMPLETE.${CLEAR_TEXT}" diff --git a/packages/winapps/winapps.patch b/packages/winapps/winapps.patch new file mode 100644 index 00000000..478d0ac3 --- /dev/null +++ b/packages/winapps/winapps.patch @@ -0,0 +1,11 @@ +--- a/bin/winapps ++++ b/bin/winapps +@@ -295,7 +295,7 @@ function waCheckGroupMembership() { + # shellcheck disable=SC2155 # Silence warnings regarding masking return values through simultaneous declaration and assignment. + local USER_GROUPS=$(groups "$(whoami)") + +- if ! (echo "$USER_GROUPS" | grep -q -E "\blibvirt\b") || ! (echo "$USER_GROUPS" | grep -q -E "\bkvm\b"); then ++ if ! (echo "$USER_GROUPS" | grep -q -E "\blibvirtd\b") || ! (echo "$USER_GROUPS" | grep -q -E "\bkvm\b"); then + waThrowExit "$EC_NOT_IN_GROUP" + fi + }