wrapper-manager-fds/modules: init setting XDG desktop entries

This commit is contained in:
Gabriel Arazas 2024-07-09 16:03:30 +08:00
parent 6916b09349
commit 2cdb569462
5 changed files with 147 additions and 1 deletions

View File

@ -6,6 +6,7 @@
type = with lib.types; attrsOf (submoduleWith { type = with lib.types; attrsOf (submoduleWith {
modules = [ ./shared/wrappers.nix ]; modules = [ ./shared/wrappers.nix ];
specialArgs.envConfig = config; specialArgs.envConfig = config;
shorthandOnlyDefinesConfig = true;
}); });
description = '' description = ''
A set of wrappers to be included in the resulting derivation from A set of wrappers to be included in the resulting derivation from

View File

@ -36,6 +36,9 @@
lib.concatMapStrings (v: '' lib.concatMapStrings (v: ''
makeWrapper "${v.arg0}" "${builtins.placeholder "out"}/bin/${v.executableName}" ${lib.concatStringsSep " " v.makeWrapperArgs} makeWrapper "${v.arg0}" "${builtins.placeholder "out"}/bin/${v.executableName}" ${lib.concatStringsSep " " v.makeWrapperArgs}
'') wrappers; '') wrappers;
mkDesktopEntries = desktopEntries:
builtins.map (entry: pkgs.makeDesktopItem entry) desktopEntries;
in in
pkgs.symlinkJoin { pkgs.symlinkJoin {
name = "wrapper-manager-fds-wrapped-package"; name = "wrapper-manager-fds-wrapped-package";
@ -43,11 +46,14 @@
nativeBuildInputs = nativeBuildInputs =
if config.build.isBinary if config.build.isBinary
then [ pkgs.makeBinaryWrapper ] then [ pkgs.makeBinaryWrapper ]
else [ pkgs.makeWrapper ]; else [ pkgs.makeWrapper ]
++ lib.optionals (pkgs.stdenv.isLinux && config.xdg.desktopEntries != { }) [ pkgs.copyDesktopItems ];
postBuild = '' postBuild = ''
${config.build.extraSetup} ${config.build.extraSetup}
${mkWrapBuild (lib.attrValues config.wrappers)} ${mkWrapBuild (lib.attrValues config.wrappers)}
''; '';
desktopItems =
mkDesktopEntries (lib.attrValues config.xdg.desktopEntries);
}; };
}; };
}; };

View File

@ -1,6 +1,7 @@
{ {
imports = [ imports = [
./base.nix ./base.nix
./xdg-desktop-entries.nix
./build.nix ./build.nix
./extra-args.nix ./extra-args.nix
]; ];

View File

@ -0,0 +1,137 @@
{ config, lib, pkgs, ... }:
let
# We're only setting up options for the most common keys typically used to
# set up a desktop entry. Everything else is acceptable under a freeform
# module anyways.
xdgDesktopEntry = { name, lib, pkgs, ... }: {
freeformType = with lib.types; attrsOf anything;
options = {
name = lib.mkOption {
type = lib.types.nonEmptyStr;
description = "The name of the desktop file.";
default = name;
example = "firefox";
};
desktopName = lib.mkOption {
type = lib.types.nonEmptyStr;
description = "Specific name of the application";
default = name;
example = "Firefox";
};
exec = lib.mkOption {
type = with lib.types; nullOr nonEmptyStr;
description = "Program with execute along with its arguments.";
default = null;
example = "firefox %U";
};
genericName = lib.mkOption {
type = with lib.types; nullOr nonEmptyStr;
description = "Generic name of the application";
default = null;
example = "Web browser";
};
terminal = lib.mkOption {
type = lib.types.bool;
description = "Whether the program runs in a terminal window.";
default = false;
example = true;
};
categories = lib.mkOption {
type = with lib.types; listOf nonEmptyStr;
description = "List of categories should the application be shown in a menu.";
default = [ ];
example = [ "Applications" "Network" ];
};
mimeTypes = lib.mkOption {
type = with lib.types; listOf nonEmptyStr;
description = "The MIME types supported by the application.";
default = [ ];
example = [ "text/html" "text/xml" ];
};
};
};
in
{
options.xdg.desktopEntries = lib.mkOption {
type = with lib.types; attrsOf (submodule xdgDesktopEntry);
description = ''
A set of desktop entries to be exported along with the wrapped package.
'';
default = { };
example = lib.literalExpression ''
{
firefox = {
name = "Firefox";
genericName = "Web browser";
exec = "firefox %u";
terminal = false;
categories = [ "Application" "Network" "WebBrowser" ];
mimeTypes = [ "text/html" "text/xml" ];
extraConfig."X-GNOME-Autostart-Phase" = "WindowManager";
keywords = [ "Web" "Browser" ];
startupNotify = false;
startupWMClass = "MyOwnClass";
};
}
'';
};
options.wrappers = lib.mkOption {
type =
let
xdgDesktopEntryWrapperSubmodule = { name, config, lib, ... }: {
options.xdg.desktopEntry = {
enable =
lib.mkEnableOption "automatic creation of a desktop entry for the wrapper";
settings = lib.mkOption {
type = lib.types.submodule xdgDesktopEntry;
description = ''
Settings to be passed to the `makeDesktopItem` builder.
'';
example = lib.literalExpression ''
{
mimeTypes = [ "text/html" "text/xml" ];
categories = [ "Applications" "Network" ];
}
'';
};
};
config.xdg.desktopEntry.settings = lib.mkIf config.xdg.desktopEntry.enable {
name = lib.mkDefault name;
desktopName = lib.mkDefault name;
type = lib.mkDefault "Application";
# Welp, we could set it to the absolute location of the wrapper
# executable in the final output but it's a big pain the ass to do
# so but we're opting to the executable name instead. This current
# way of doing it is simply the next (and the simplest) best thing.
# We just have to make sure the build step for the wrapper script
# is consistent throughout the entire module environment.
#
# Besides, if the user wants a desktop entry along with the wrapper
# script, it will be included alongside in whatever environment
# they are using it for anyways.
exec = config.executableName;
};
};
in
with lib.types; attrsOf (submodule xdgDesktopEntryWrapperSubmodule);
};
config = {
xdg.desktopEntries =
let
wrappersWithDesktopEntries = lib.filterAttrs (_: v: v.xdg.desktopEntry.enable) config.wrappers;
in
lib.mapAttrs (_: v: v.xdg.desktopEntry.settings) wrappersWithDesktopEntries;
};
}

View File

@ -5,5 +5,6 @@
arg0 = lib.getExe' pkgs.fastfetch "fastfetch"; arg0 = lib.getExe' pkgs.fastfetch "fastfetch";
appendArgs = [ "--logo" "Guix" ]; appendArgs = [ "--logo" "Guix" ];
env.NO_COLOR = "1"; env.NO_COLOR = "1";
xdg.desktopEntry.enable = true;
}; };
} }