diff options
Diffstat (limited to 'nixpkgs/nixos/modules/programs')
84 files changed, 5689 insertions, 0 deletions
diff --git a/nixpkgs/nixos/modules/programs/adb.nix b/nixpkgs/nixos/modules/programs/adb.nix new file mode 100644 index 000000000000..250d8c252a3b --- /dev/null +++ b/nixpkgs/nixos/modules/programs/adb.nix @@ -0,0 +1,29 @@ +{ config, lib, pkgs, ... }: + +with lib; + +{ + meta.maintainers = [ maintainers.mic92 ]; + + ###### interface + options = { + programs.adb = { + enable = mkOption { + default = false; + type = types.bool; + description = '' + Whether to configure system to use Android Debug Bridge (adb). + To grant access to a user, it must be part of adbusers group: + <code>users.users.alice.extraGroups = ["adbusers"];</code> + ''; + }; + }; + }; + + ###### implementation + config = mkIf config.programs.adb.enable { + services.udev.packages = [ pkgs.android-udev-rules ]; + environment.systemPackages = [ pkgs.androidenv.androidPkgs_9_0.platform-tools ]; + users.groups.adbusers = {}; + }; +} diff --git a/nixpkgs/nixos/modules/programs/atop.nix b/nixpkgs/nixos/modules/programs/atop.nix new file mode 100644 index 000000000000..4651cdb76e0b --- /dev/null +++ b/nixpkgs/nixos/modules/programs/atop.nix @@ -0,0 +1,36 @@ +# Global configuration for atop. + +{ config, lib, ... }: + +with lib; + +let cfg = config.programs.atop; + +in +{ + ###### interface + + options = { + + programs.atop = { + + settings = mkOption { + type = types.attrs; + default = {}; + example = { + flags = "a1f"; + interval = 5; + }; + description = '' + Parameters to be written to <filename>/etc/atoprc</filename>. + ''; + }; + + }; + }; + + config = mkIf (cfg.settings != {}) { + environment.etc."atoprc".text = + concatStrings (mapAttrsToList (n: v: "${n} ${toString v}\n") cfg.settings); + }; +} diff --git a/nixpkgs/nixos/modules/programs/autojump.nix b/nixpkgs/nixos/modules/programs/autojump.nix new file mode 100644 index 000000000000..3a8feec4bb45 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/autojump.nix @@ -0,0 +1,33 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.autojump; + prg = config.programs; +in +{ + options = { + programs.autojump = { + + enable = mkOption { + type = types.bool; + default = false; + description = '' + Whether to enable autojump. + ''; + }; + }; + }; + + ###### implementation + + config = mkIf cfg.enable { + environment.pathsToLink = [ "/share/autojump" ]; + environment.systemPackages = [ pkgs.autojump ]; + + programs.bash.interactiveShellInit = "source ${pkgs.autojump}/share/autojump/autojump.bash"; + programs.zsh.interactiveShellInit = mkIf prg.zsh.enable "source ${pkgs.autojump}/share/autojump/autojump.zsh"; + programs.fish.interactiveShellInit = mkIf prg.fish.enable "source ${pkgs.autojump}/share/autojump/autojump.fish"; + }; +} diff --git a/nixpkgs/nixos/modules/programs/bash/bash.nix b/nixpkgs/nixos/modules/programs/bash/bash.nix new file mode 100644 index 000000000000..a7e57b8608d7 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/bash/bash.nix @@ -0,0 +1,236 @@ +# This module defines global configuration for the Bash shell, in +# particular /etc/bashrc and /etc/profile. + +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfge = config.environment; + + cfg = config.programs.bash; + + bashCompletion = optionalString cfg.enableCompletion '' + # Check whether we're running a version of Bash that has support for + # programmable completion. If we do, enable all modules installed in + # the system and user profile in obsolete /etc/bash_completion.d/ + # directories. Bash loads completions in all + # $XDG_DATA_DIRS/bash-completion/completions/ + # on demand, so they do not need to be sourced here. + if shopt -q progcomp &>/dev/null; then + . "${pkgs.bash-completion}/etc/profile.d/bash_completion.sh" + nullglobStatus=$(shopt -p nullglob) + shopt -s nullglob + for p in $NIX_PROFILES; do + for m in "$p/etc/bash_completion.d/"*; do + . $m + done + done + eval "$nullglobStatus" + unset nullglobStatus p m + fi + ''; + + bashAliases = concatStringsSep "\n" ( + mapAttrsFlatten (k: v: "alias ${k}=${escapeShellArg v}") + (filterAttrs (k: v: v != null) cfg.shellAliases) + ); + +in + +{ + options = { + + programs.bash = { + + /* + enable = mkOption { + default = true; + description = '' + Whenever to configure Bash as an interactive shell. + Note that this tries to make Bash the default + <option>users.defaultUserShell</option>, + which in turn means that you might need to explicitly + set this variable if you have another shell configured + with NixOS. + ''; + type = types.bool; + }; + */ + + shellAliases = mkOption { + default = {}; + description = '' + Set of aliases for bash shell, which overrides <option>environment.shellAliases</option>. + See <option>environment.shellAliases</option> for an option format description. + ''; + type = with types; attrsOf (nullOr (either str path)); + }; + + shellInit = mkOption { + default = ""; + description = '' + Shell script code called during bash shell initialisation. + ''; + type = types.lines; + }; + + loginShellInit = mkOption { + default = ""; + description = '' + Shell script code called during login bash shell initialisation. + ''; + type = types.lines; + }; + + interactiveShellInit = mkOption { + default = ""; + description = '' + Shell script code called during interactive bash shell initialisation. + ''; + type = types.lines; + }; + + promptInit = mkOption { + default = '' + # Provide a nice prompt if the terminal supports it. + if [ "$TERM" != "dumb" -o -n "$INSIDE_EMACS" ]; then + PROMPT_COLOR="1;31m" + let $UID && PROMPT_COLOR="1;32m" + if [ -n "$INSIDE_EMACS" ]; then + # Emacs term mode doesn't support xterm title escape sequence (\e]0;) + PS1="\n\[\033[$PROMPT_COLOR\][\u@\h:\w]\\$\[\033[0m\] " + else + PS1="\n\[\033[$PROMPT_COLOR\][\[\e]0;\u@\h: \w\a\]\u@\h:\w]\\$\[\033[0m\] " + fi + if test "$TERM" = "xterm"; then + PS1="\[\033]2;\h:\u:\w\007\]$PS1" + fi + fi + ''; + description = '' + Shell script code used to initialise the bash prompt. + ''; + type = types.lines; + }; + + enableCompletion = mkOption { + default = true; + description = '' + Enable Bash completion for all interactive bash shells. + ''; + type = types.bool; + }; + + }; + + }; + + config = /* mkIf cfg.enable */ { + + programs.bash = { + + shellAliases = mapAttrs (name: mkDefault) cfge.shellAliases; + + shellInit = '' + if [ -z "$__NIXOS_SET_ENVIRONMENT_DONE" ]; then + . ${config.system.build.setEnvironment} + fi + + ${cfge.shellInit} + ''; + + loginShellInit = cfge.loginShellInit; + + interactiveShellInit = '' + # Check the window size after every command. + shopt -s checkwinsize + + # Disable hashing (i.e. caching) of command lookups. + set +h + + ${cfg.promptInit} + ${bashCompletion} + ${bashAliases} + + ${cfge.interactiveShellInit} + ''; + + }; + + environment.etc."profile".text = + '' + # /etc/profile: DO NOT EDIT -- this file has been generated automatically. + # This file is read for login shells. + + # Only execute this file once per shell. + if [ -n "$__ETC_PROFILE_SOURCED" ]; then return; fi + __ETC_PROFILE_SOURCED=1 + + # Prevent this file from being sourced by interactive non-login child shells. + export __ETC_PROFILE_DONE=1 + + ${cfg.shellInit} + ${cfg.loginShellInit} + + # Read system-wide modifications. + if test -f /etc/profile.local; then + . /etc/profile.local + fi + + if [ -n "''${BASH_VERSION:-}" ]; then + . /etc/bashrc + fi + ''; + + environment.etc."bashrc".text = + '' + # /etc/bashrc: DO NOT EDIT -- this file has been generated automatically. + + # Only execute this file once per shell. + if [ -n "$__ETC_BASHRC_SOURCED" -o -n "$NOSYSBASHRC" ]; then return; fi + __ETC_BASHRC_SOURCED=1 + + # If the profile was not loaded in a parent process, source + # it. But otherwise don't do it because we don't want to + # clobber overridden values of $PATH, etc. + if [ -z "$__ETC_PROFILE_DONE" ]; then + . /etc/profile + fi + + # We are not always an interactive shell. + if [ -n "$PS1" ]; then + ${cfg.interactiveShellInit} + fi + + # Read system-wide modifications. + if test -f /etc/bashrc.local; then + . /etc/bashrc.local + fi + ''; + + # Configuration for readline in bash. We use "option default" + # priority to allow user override using both .text and .source. + environment.etc."inputrc".source = mkOptionDefault ./inputrc; + + users.defaultUserShell = mkDefault pkgs.bashInteractive; + + environment.pathsToLink = optionals cfg.enableCompletion [ + "/etc/bash_completion.d" + "/share/bash-completion" + ]; + + environment.systemPackages = optional cfg.enableCompletion + pkgs.nix-bash-completions; + + environment.shells = + [ "/run/current-system/sw/bin/bash" + "/run/current-system/sw/bin/sh" + "${pkgs.bashInteractive}/bin/bash" + "${pkgs.bashInteractive}/bin/sh" + ]; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/bash/inputrc b/nixpkgs/nixos/modules/programs/bash/inputrc new file mode 100644 index 000000000000..f339eb649ed8 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/bash/inputrc @@ -0,0 +1,37 @@ +# inputrc borrowed from CentOS (RHEL). + +set bell-style none + +set meta-flag on +set input-meta on +set convert-meta off +set output-meta on +set colored-stats on + +#set mark-symlinked-directories on + +$if mode=emacs + +# for linux console and RH/Debian xterm +"\e[1~": beginning-of-line +"\e[4~": end-of-line +"\e[5~": beginning-of-history +"\e[6~": end-of-history +"\e[3~": delete-char +"\e[2~": quoted-insert +"\e[5C": forward-word +"\e[5D": backward-word +"\e[1;5C": forward-word +"\e[1;5D": backward-word + +# for rxvt +"\e[8~": end-of-line + +# for non RH/Debian xterm, can't hurt for RH/DEbian xterm +"\eOH": beginning-of-line +"\eOF": end-of-line + +# for freebsd console +"\e[H": beginning-of-line +"\e[F": end-of-line +$endif diff --git a/nixpkgs/nixos/modules/programs/bcc.nix b/nixpkgs/nixos/modules/programs/bcc.nix new file mode 100644 index 000000000000..d76249bb5cab --- /dev/null +++ b/nixpkgs/nixos/modules/programs/bcc.nix @@ -0,0 +1,9 @@ +{ config, lib, ... }: +{ + options.programs.bcc.enable = lib.mkEnableOption "bcc"; + + config = lib.mkIf config.programs.bcc.enable { + environment.systemPackages = [ config.boot.kernelPackages.bcc ]; + boot.extraModulePackages = [ config.boot.kernelPackages.bcc ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/blcr.nix b/nixpkgs/nixos/modules/programs/blcr.nix new file mode 100644 index 000000000000..804e1d01f12b --- /dev/null +++ b/nixpkgs/nixos/modules/programs/blcr.nix @@ -0,0 +1,27 @@ +{ config, lib, ... }: + +let + inherit (lib) mkOption mkIf; + cfg = config.environment.blcr; + blcrPkg = config.boot.kernelPackages.blcr; +in + +{ + ###### interface + + options = { + environment.blcr.enable = mkOption { + default = false; + description = + "Whether to enable support for the BLCR checkpointing tool."; + }; + }; + + ###### implementation + + config = mkIf cfg.enable { + boot.kernelModules = [ "blcr" "blcr_imports" ]; + boot.extraModulePackages = [ blcrPkg ]; + environment.systemPackages = [ blcrPkg ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/browserpass.nix b/nixpkgs/nixos/modules/programs/browserpass.nix new file mode 100644 index 000000000000..e1456d3c1848 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/browserpass.nix @@ -0,0 +1,32 @@ +{ config, lib, pkgs, ... }: + +with lib; + +{ + + options.programs.browserpass.enable = mkEnableOption "Browserpass native messaging host"; + + config = mkIf config.programs.browserpass.enable { + environment.etc = let + appId = "com.github.browserpass.native.json"; + source = part: "${pkgs.browserpass}/lib/browserpass/${part}/${appId}"; + in { + # chromium + "chromium/native-messaging-hosts/${appId}".source = source "hosts/chromium"; + "chromium/policies/managed/${appId}".source = source "policies/chromium"; + + # chrome + "opt/chrome/native-messaging-hosts/${appId}".source = source "hosts/chromium"; + "opt/chrome/policies/managed/${appId}".source = source "policies/chromium"; + + # vivaldi + "opt/vivaldi/native-messaging-hosts/${appId}".source = source "hosts/chromium"; + "opt/vivaldi/policies/managed/${appId}".source = source "policies/chromium"; + + # brave + "opt/brave/native-messaging-hosts/${appId}".source = source "hosts/chromium"; + "opt/brave/policies/managed/${appId}".source = source "policies/chromium"; + }; + nixpkgs.config.firefox.enableBrowserpass = true; + }; +} diff --git a/nixpkgs/nixos/modules/programs/captive-browser.nix b/nixpkgs/nixos/modules/programs/captive-browser.nix new file mode 100644 index 000000000000..55d474e5c9db --- /dev/null +++ b/nixpkgs/nixos/modules/programs/captive-browser.nix @@ -0,0 +1,122 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.captive-browser; +in +{ + ###### interface + + options = { + programs.captive-browser = { + enable = mkEnableOption "captive browser"; + + package = mkOption { + type = types.package; + default = pkgs.captive-browser; + defaultText = "pkgs.captive-browser"; + description = "Which package to use for captive-browser"; + }; + + interface = mkOption { + type = types.str; + description = "your public network interface (wlp3s0, wlan0, eth0, ...)"; + }; + + # the options below are the same as in "captive-browser.toml" + browser = mkOption { + type = types.str; + default = concatStringsSep " " [ ''${pkgs.chromium}/bin/chromium'' + ''--user-data-dir=$HOME/.chromium-captive'' + ''--proxy-server="socks5://$PROXY"'' + ''--host-resolver-rules="MAP * ~NOTFOUND , EXCLUDE localhost"'' + ''--no-first-run'' + ''--new-window'' + ''--incognito'' + ''http://cache.nixos.org/'' + ]; + description = '' + The shell (/bin/sh) command executed once the proxy starts. + When browser exits, the proxy exits. An extra env var PROXY is available. + + Here, we use a separate Chrome instance in Incognito mode, so that + it can run (and be waited for) alongside the default one, and that + it maintains no state across runs. To configure this browser open a + normal window in it, settings will be preserved. + + @volth: chromium is to open a plain HTTP (not HTTPS nor redirect to HTTPS!) website. + upstream uses http://example.com but I have seen captive portals whose DNS server resolves "example.com" to 127.0.0.1 + ''; + }; + + dhcp-dns = mkOption { + type = types.str; + description = '' + The shell (/bin/sh) command executed to obtain the DHCP + DNS server address. The first match of an IPv4 regex is used. + IPv4 only, because let's be real, it's a captive portal. + ''; + }; + + socks5-addr = mkOption { + type = types.str; + default = "localhost:1666"; + description = ''the listen address for the SOCKS5 proxy server''; + }; + + bindInterface = mkOption { + default = true; + type = types.bool; + description = '' + Binds <package>captive-browser</package> to the network interface declared in + <literal>cfg.interface</literal>. This can be used to avoid collisions + with private subnets. + ''; + }; + }; + }; + + ###### implementation + + config = mkIf cfg.enable { + + programs.captive-browser.dhcp-dns = mkOptionDefault ( + if config.networking.networkmanager.enable then + "${pkgs.networkmanager}/bin/nmcli dev show ${escapeShellArg cfg.interface} | ${pkgs.gnugrep}/bin/fgrep IP4.DNS" + else if config.networking.dhcpcd.enable then + "${pkgs.dhcpcd}/bin/dhcpcd -U ${escapeShellArg cfg.interface} | ${pkgs.gnugrep}/bin/fgrep domain_name_servers" + else if config.networking.useNetworkd then + "${cfg.package}/bin/systemd-networkd-dns ${escapeShellArg cfg.interface}" + else + "${config.security.wrapperDir}/udhcpc --quit --now -f -i ${escapeShellArg cfg.interface} -O dns --script ${ + pkgs.writeScript "udhcp-script" '' + #!/bin/sh + if [ "$1" = bound ]; then + echo "$dns" + fi + ''}" + ); + + security.wrappers.udhcpc = { + capabilities = "cap_net_raw+p"; + source = "${pkgs.busybox}/bin/udhcpc"; + }; + + security.wrappers.captive-browser = { + capabilities = "cap_net_raw+p"; + source = pkgs.writeScript "captive-browser" '' + #!${pkgs.bash}/bin/bash + export XDG_CONFIG_HOME=${pkgs.writeTextDir "captive-browser.toml" '' + browser = """${cfg.browser}""" + dhcp-dns = """${cfg.dhcp-dns}""" + socks5-addr = """${cfg.socks5-addr}""" + ${optionalString cfg.bindInterface '' + bind-device = """${cfg.interface}""" + ''} + ''} + exec ${cfg.package}/bin/captive-browser + ''; + }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/ccache.nix b/nixpkgs/nixos/modules/programs/ccache.nix new file mode 100644 index 000000000000..874774c72b47 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/ccache.nix @@ -0,0 +1,83 @@ +{ config, pkgs, lib, ... }: + +with lib; +let + cfg = config.programs.ccache; +in { + options.programs.ccache = { + # host configuration + enable = mkEnableOption "CCache"; + cacheDir = mkOption { + type = types.path; + description = "CCache directory"; + default = "/var/cache/ccache"; + }; + # target configuration + packageNames = mkOption { + type = types.listOf types.str; + description = "Nix top-level packages to be compiled using CCache"; + default = []; + example = [ "wxGTK30" "qt48" "ffmpeg_3_3" "libav_all" ]; + }; + }; + + config = mkMerge [ + # host configuration + (mkIf cfg.enable { + systemd.tmpfiles.rules = [ "d ${cfg.cacheDir} 0770 root nixbld -" ]; + + # "nix-ccache --show-stats" and "nix-ccache --clear" + security.wrappers.nix-ccache = { + group = "nixbld"; + setgid = true; + source = pkgs.writeScript "nix-ccache.pl" '' + #!${pkgs.perl}/bin/perl + + %ENV=( CCACHE_DIR => '${cfg.cacheDir}' ); + sub untaint { + my $v = shift; + return '-C' if $v eq '-C' || $v eq '--clear'; + return '-V' if $v eq '-V' || $v eq '--version'; + return '-s' if $v eq '-s' || $v eq '--show-stats'; + return '-z' if $v eq '-z' || $v eq '--zero-stats'; + exec('${pkgs.ccache}/bin/ccache', '-h'); + } + exec('${pkgs.ccache}/bin/ccache', map { untaint $_ } @ARGV); + ''; + }; + }) + + # target configuration + (mkIf (cfg.packageNames != []) { + nixpkgs.overlays = [ + (self: super: genAttrs cfg.packageNames (pn: super.${pn}.override { stdenv = builtins.trace "with ccache: ${pn}" self.ccacheStdenv; })) + + (self: super: { + ccacheWrapper = super.ccacheWrapper.override { + extraConfig = '' + export CCACHE_COMPRESS=1 + export CCACHE_DIR="${cfg.cacheDir}" + export CCACHE_UMASK=007 + if [ ! -d "$CCACHE_DIR" ]; then + echo "=====" + echo "Directory '$CCACHE_DIR' does not exist" + echo "Please create it with:" + echo " sudo mkdir -m0770 '$CCACHE_DIR'" + echo " sudo chown root:nixbld '$CCACHE_DIR'" + echo "=====" + exit 1 + fi + if [ ! -w "$CCACHE_DIR" ]; then + echo "=====" + echo "Directory '$CCACHE_DIR' is not accessible for user $(whoami)" + echo "Please verify its access permissions" + echo "=====" + exit 1 + fi + ''; + }; + }) + ]; + }) + ]; +} \ No newline at end of file diff --git a/nixpkgs/nixos/modules/programs/cdemu.nix b/nixpkgs/nixos/modules/programs/cdemu.nix new file mode 100644 index 000000000000..6a0185d362c5 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/cdemu.nix @@ -0,0 +1,58 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let cfg = config.programs.cdemu; +in { + + options = { + programs.cdemu = { + enable = mkOption { + default = false; + description = '' + <command>cdemu</command> for members of + <option>programs.cdemu.group</option>. + ''; + }; + group = mkOption { + default = "cdrom"; + description = '' + Group that users must be in to use <command>cdemu</command>. + ''; + }; + gui = mkOption { + default = true; + description = '' + Whether to install the <command>cdemu</command> GUI (gCDEmu). + ''; + }; + image-analyzer = mkOption { + default = true; + description = '' + Whether to install the image analyzer. + ''; + }; + }; + }; + + config = mkIf cfg.enable { + + boot = { + extraModulePackages = [ config.boot.kernelPackages.vhba ]; + kernelModules = [ "vhba" ]; + }; + + services = { + udev.extraRules = '' + KERNEL=="vhba_ctl", MODE="0660", OWNER="root", GROUP="${cfg.group}" + ''; + dbus.packages = [ pkgs.cdemu-daemon ]; + }; + + environment.systemPackages = + [ pkgs.cdemu-daemon pkgs.cdemu-client ] + ++ optional cfg.gui pkgs.gcdemu + ++ optional cfg.image-analyzer pkgs.image-analyzer; + }; + +} diff --git a/nixpkgs/nixos/modules/programs/chromium.nix b/nixpkgs/nixos/modules/programs/chromium.nix new file mode 100644 index 000000000000..41c49db8c71c --- /dev/null +++ b/nixpkgs/nixos/modules/programs/chromium.nix @@ -0,0 +1,89 @@ +{ config, lib, ... }: + +with lib; + +let + cfg = config.programs.chromium; + + defaultProfile = filterAttrs (k: v: v != null) { + HomepageLocation = cfg.homepageLocation; + DefaultSearchProviderSearchURL = cfg.defaultSearchProviderSearchURL; + DefaultSearchProviderSuggestURL = cfg.defaultSearchProviderSuggestURL; + ExtensionInstallForcelist = map (extension: + "${extension};https://clients2.google.com/service/update2/crx" + ) cfg.extensions; + }; +in + +{ + ###### interface + + options = { + programs.chromium = { + enable = mkEnableOption "<command>chromium</command> policies"; + + extensions = mkOption { + type = types.listOf types.str; + description = '' + List of chromium extensions to install. + For list of plugins ids see id in url of extensions on + <link xlink:href="https://chrome.google.com/webstore/category/extensions">chrome web store</link> + page. + ''; + default = []; + example = literalExample '' + [ + "chlffgpmiacpedhhbkiomidkjlcfhogd" # pushbullet + "mbniclmhobmnbdlbpiphghaielnnpgdp" # lightshot + "gcbommkclmclpchllfjekcdonpmejbdp" # https everywhere + "cjpalhdlnbpafiamejdnhcphjbkeiagm" # ublock origin + ] + ''; + }; + + homepageLocation = mkOption { + type = types.nullOr types.str; + description = "Chromium default homepage"; + default = null; + example = "https://nixos.org"; + }; + + defaultSearchProviderSearchURL = mkOption { + type = types.nullOr types.str; + description = "Chromium default search provider url."; + default = null; + example = + "https://encrypted.google.com/search?q={searchTerms}&{google:RLZ}{google:originalQueryForSuggestion}{google:assistedQueryStats}{google:searchFieldtrialParameter}{google:searchClient}{google:sourceId}{google:instantExtendedEnabledParameter}ie={inputEncoding}"; + }; + + defaultSearchProviderSuggestURL = mkOption { + type = types.nullOr types.str; + description = "Chromium default search provider url for suggestions."; + default = null; + example = + "https://encrypted.google.com/complete/search?output=chrome&q={searchTerms}"; + }; + + extraOpts = mkOption { + type = types.attrs; + description = '' + Extra chromium policy options, see + <link xlink:href="https://www.chromium.org/administrators/policy-list-3">https://www.chromium.org/administrators/policy-list-3</link> + for a list of avalible options + ''; + default = {}; + }; + }; + }; + + ###### implementation + + config = lib.mkIf cfg.enable { + # for chromium + environment.etc."chromium/policies/managed/default.json".text = builtins.toJSON defaultProfile; + environment.etc."chromium/policies/managed/extra.json".text = builtins.toJSON cfg.extraOpts; + # for google-chrome https://www.chromium.org/administrators/linux-quick-start + environment.etc."opt/chrome/policies/managed/default.json".text = builtins.toJSON defaultProfile; + environment.etc."opt/chrome/policies/managed/extra.json".text = builtins.toJSON cfg.extraOpts; + }; +} diff --git a/nixpkgs/nixos/modules/programs/clickshare.nix b/nixpkgs/nixos/modules/programs/clickshare.nix new file mode 100644 index 000000000000..9980a7daf525 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/clickshare.nix @@ -0,0 +1,21 @@ +{ config, lib, pkgs, ... }: + +{ + + options.programs.clickshare-csc1.enable = + lib.options.mkEnableOption '' + Barco ClickShare CSC-1 driver/client. + This allows users in the <literal>clickshare</literal> + group to access and use a ClickShare USB dongle + that is connected to the machine + ''; + + config = lib.modules.mkIf config.programs.clickshare-csc1.enable { + environment.systemPackages = [ pkgs.clickshare-csc1 ]; + services.udev.packages = [ pkgs.clickshare-csc1 ]; + users.groups.clickshare = {}; + }; + + meta.maintainers = [ lib.maintainers.yarny ]; + +} diff --git a/nixpkgs/nixos/modules/programs/command-not-found/command-not-found.nix b/nixpkgs/nixos/modules/programs/command-not-found/command-not-found.nix new file mode 100644 index 000000000000..656c255fcb18 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/command-not-found/command-not-found.nix @@ -0,0 +1,95 @@ +# This module provides suggestions of packages to install if the user +# tries to run a missing command in Bash. This is implemented using a +# SQLite database that maps program names to Nix package names (e.g., +# "pdflatex" is mapped to "tetex"). + +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.command-not-found; + commandNotFound = pkgs.substituteAll { + name = "command-not-found"; + dir = "bin"; + src = ./command-not-found.pl; + isExecutable = true; + inherit (pkgs) perl; + inherit (cfg) dbPath; + perlFlags = concatStrings (map (path: "-I ${path}/${pkgs.perl.libPrefix} ") + [ pkgs.perlPackages.DBI pkgs.perlPackages.DBDSQLite pkgs.perlPackages.StringShellQuote ]); + }; + +in + +{ + options.programs.command-not-found = { + + enable = mkOption { + type = types.bool; + default = true; + description = '' + Whether interactive shells should show which Nix package (if + any) provides a missing command. + ''; + }; + + dbPath = mkOption { + default = "/nix/var/nix/profiles/per-user/root/channels/nixos/programs.sqlite" ; + description = '' + Absolute path to programs.sqlite. + + By default this file will be provided by your channel + (nixexprs.tar.xz). + ''; + type = types.path; + }; + }; + + config = mkIf cfg.enable { + programs.bash.interactiveShellInit = + '' + # This function is called whenever a command is not found. + command_not_found_handle() { + local p=${commandNotFound}/bin/command-not-found + if [ -x $p -a -f ${cfg.dbPath} ]; then + # Run the helper program. + $p "$@" + # Retry the command if we just installed it. + if [ $? = 126 ]; then + "$@" + else + return 127 + fi + else + echo "$1: command not found" >&2 + return 127 + fi + } + ''; + + programs.zsh.interactiveShellInit = + '' + # This function is called whenever a command is not found. + command_not_found_handler() { + local p=${commandNotFound}/bin/command-not-found + if [ -x $p -a -f ${cfg.dbPath} ]; then + # Run the helper program. + $p "$@" + + # Retry the command if we just installed it. + if [ $? = 126 ]; then + "$@" + fi + else + # Indicate than there was an error so ZSH falls back to its default handler + echo "$1: command not found" >&2 + return 127 + fi + } + ''; + + environment.systemPackages = [ commandNotFound ]; + }; + +} diff --git a/nixpkgs/nixos/modules/programs/command-not-found/command-not-found.pl b/nixpkgs/nixos/modules/programs/command-not-found/command-not-found.pl new file mode 100644 index 000000000000..ab7aa204653c --- /dev/null +++ b/nixpkgs/nixos/modules/programs/command-not-found/command-not-found.pl @@ -0,0 +1,51 @@ +#! @perl@/bin/perl -w @perlFlags@ + +use strict; +use DBI; +use DBD::SQLite; +use String::ShellQuote; +use Config; + +my $program = $ARGV[0]; + +my $dbPath = "@dbPath@"; + +my $dbh = DBI->connect("dbi:SQLite:dbname=$dbPath", "", "") + or die "cannot open database `$dbPath'"; +$dbh->{RaiseError} = 0; +$dbh->{PrintError} = 0; + +my $system = $ENV{"NIX_SYSTEM"} // $Config{myarchname}; + +my $res = $dbh->selectall_arrayref( + "select package from Programs where system = ? and name = ?", + { Slice => {} }, $system, $program); + +if (!defined $res || scalar @$res == 0) { + print STDERR "$program: command not found\n"; +} elsif (scalar @$res == 1) { + my $package = @$res[0]->{package}; + if ($ENV{"NIX_AUTO_INSTALL"} // "") { + print STDERR <<EOF; +The program ‘$program’ is currently not installed. It is provided by +the package ‘$package’, which I will now install for you. +EOF + ; + exit 126 if system("nix-env", "-iA", "nixos.$package") == 0; + } elsif ($ENV{"NIX_AUTO_RUN"} // "") { + exec("nix-shell", "-p", $package, "--run", shell_quote("exec", @ARGV)); + } else { + print STDERR <<EOF; +The program ‘$program’ is currently not installed. You can install it by typing: + nix-env -iA nixos.$package +EOF + } +} else { + print STDERR <<EOF; +The program ‘$program’ is currently not installed. It is provided by +several packages. You can install it by typing one of the following: +EOF + print STDERR " nix-env -iA nixos.$_->{package}\n" foreach @$res; +} + +exit 127; diff --git a/nixpkgs/nixos/modules/programs/criu.nix b/nixpkgs/nixos/modules/programs/criu.nix new file mode 100644 index 000000000000..48cf5c88a9fc --- /dev/null +++ b/nixpkgs/nixos/modules/programs/criu.nix @@ -0,0 +1,26 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let cfg = config.programs.criu; +in { + + options = { + programs.criu = { + enable = mkOption { + default = false; + description = '' + Install <command>criu</command> along with necessary kernel options. + ''; + }; + }; + }; + config = mkIf cfg.enable { + system.requiredKernelConfig = with config.lib.kernelConfig; [ + (isYes "CHECKPOINT_RESTORE") + ]; + boot.kernel.features.criu = true; + environment.systemPackages = [ pkgs.criu ]; + }; + +} diff --git a/nixpkgs/nixos/modules/programs/dconf.nix b/nixpkgs/nixos/modules/programs/dconf.nix new file mode 100644 index 000000000000..b7bfb8504b6f --- /dev/null +++ b/nixpkgs/nixos/modules/programs/dconf.nix @@ -0,0 +1,44 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.dconf; + + mkDconfProfile = name: path: + { source = path; target = "dconf/profile/${name}"; }; + +in +{ + ###### interface + + options = { + programs.dconf = { + enable = mkEnableOption "dconf"; + + profiles = mkOption { + type = types.attrsOf types.path; + default = {}; + description = "Set of dconf profile files."; + internal = true; + }; + + }; + }; + + ###### implementation + + config = mkIf (cfg.profiles != {} || cfg.enable) { + environment.etc = optionals (cfg.profiles != {}) + (mapAttrsToList mkDconfProfile cfg.profiles); + + services.dbus.packages = [ pkgs.gnome3.dconf ]; + + environment.variables.GIO_EXTRA_MODULES = optional cfg.enable + "${pkgs.gnome3.dconf.lib}/lib/gio/modules"; + # https://github.com/NixOS/nixpkgs/pull/31891 + #environment.variables.XDG_DATA_DIRS = optional cfg.enable + # "$(echo ${pkgs.gsettings-desktop-schemas}/share/gsettings-schemas/gsettings-desktop-schemas-*)"; + }; + +} diff --git a/nixpkgs/nixos/modules/programs/digitalbitbox/default.nix b/nixpkgs/nixos/modules/programs/digitalbitbox/default.nix new file mode 100644 index 000000000000..2fe0a14412c5 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/digitalbitbox/default.nix @@ -0,0 +1,39 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.digitalbitbox; +in + +{ + options.programs.digitalbitbox = { + enable = mkOption { + type = types.bool; + default = false; + description = '' + Installs the Digital Bitbox application and enables the complementary hardware module. + ''; + }; + + package = mkOption { + type = types.package; + default = pkgs.digitalbitbox; + defaultText = "pkgs.digitalbitbox"; + description = "The Digital Bitbox package to use. This can be used to install a package with udev rules that differ from the defaults."; + }; + }; + + config = mkIf cfg.enable { + environment.systemPackages = [ cfg.package ]; + hardware.digitalbitbox = { + enable = true; + package = cfg.package; + }; + }; + + meta = { + doc = ./doc.xml; + maintainers = with lib.maintainers; [ vidbina ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/digitalbitbox/doc.xml b/nixpkgs/nixos/modules/programs/digitalbitbox/doc.xml new file mode 100644 index 000000000000..c63201628dbd --- /dev/null +++ b/nixpkgs/nixos/modules/programs/digitalbitbox/doc.xml @@ -0,0 +1,74 @@ +<chapter xmlns="http://docbook.org/ns/docbook" + xmlns:xlink="http://www.w3.org/1999/xlink" + xmlns:xi="http://www.w3.org/2001/XInclude" + version="5.0" + xml:id="module-programs-digitalbitbox"> + <title>Digital Bitbox</title> + <para> + Digital Bitbox is a hardware wallet and second-factor authenticator. + </para> + <para> + The <literal>digitalbitbox</literal> programs module may be installed by + setting <literal>programs.digitalbitbox</literal> to <literal>true</literal> + in a manner similar to +<programlisting> +<xref linkend="opt-programs.digitalbitbox.enable"/> = true; +</programlisting> + and bundles the <literal>digitalbitbox</literal> package (see + <xref + linkend="sec-digitalbitbox-package" />), which contains the + <literal>dbb-app</literal> and <literal>dbb-cli</literal> binaries, along + with the hardware module (see + <xref + linkend="sec-digitalbitbox-hardware-module" />) which sets up the + necessary udev rules to access the device. + </para> + <para> + Enabling the digitalbitbox module is pretty much the easiest way to get a + Digital Bitbox device working on your system. + </para> + <para> + For more information, see + <link xlink:href="https://digitalbitbox.com/start_linux" />. + </para> + <section xml:id="sec-digitalbitbox-package"> + <title>Package</title> + + <para> + The binaries, <literal>dbb-app</literal> (a GUI tool) and + <literal>dbb-cli</literal> (a CLI tool), are available through the + <literal>digitalbitbox</literal> package which could be installed as + follows: +<programlisting> +<xref linkend="opt-environment.systemPackages"/> = [ + pkgs.digitalbitbox +]; +</programlisting> + </para> + </section> + <section xml:id="sec-digitalbitbox-hardware-module"> + <title>Hardware</title> + + <para> + The digitalbitbox hardware package enables the udev rules for Digital Bitbox + devices and may be installed as follows: +<programlisting> +<xref linkend="opt-hardware.digitalbitbox.enable"/> = true; +</programlisting> + </para> + + <para> + In order to alter the udev rules, one may provide different values for the + <literal>udevRule51</literal> and <literal>udevRule52</literal> attributes + by means of overriding as follows: +<programlisting> +programs.digitalbitbox = { + <link linkend="opt-programs.digitalbitbox.enable">enable</link> = true; + <link linkend="opt-programs.digitalbitbox.package">package</link> = pkgs.digitalbitbox.override { + udevRule51 = "something else"; + }; +}; +</programlisting> + </para> + </section> +</chapter> diff --git a/nixpkgs/nixos/modules/programs/dmrconfig.nix b/nixpkgs/nixos/modules/programs/dmrconfig.nix new file mode 100644 index 000000000000..e48a4f318370 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/dmrconfig.nix @@ -0,0 +1,38 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.dmrconfig; + +in { + meta.maintainers = [ maintainers.etu ]; + + ###### interface + options = { + programs.dmrconfig = { + enable = mkOption { + default = false; + type = types.bool; + description = '' + Whether to configure system to enable use of dmrconfig. This + enables the required udev rules and installs the program. + ''; + relatedPackages = [ "dmrconfig" ]; + }; + + package = mkOption { + default = pkgs.dmrconfig; + type = types.package; + defaultText = "pkgs.dmrconfig"; + description = "dmrconfig derivation to use"; + }; + }; + }; + + ###### implementation + config = mkIf cfg.enable { + environment.systemPackages = [ cfg.package ]; + services.udev.packages = [ cfg.package ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/environment.nix b/nixpkgs/nixos/modules/programs/environment.nix new file mode 100644 index 000000000000..4d762314298d --- /dev/null +++ b/nixpkgs/nixos/modules/programs/environment.nix @@ -0,0 +1,61 @@ +# This module defines a standard configuration for NixOS global environment. + +# Most of the stuff here should probably be moved elsewhere sometime. + +{ config, lib, ... }: + +with lib; + +let + + cfg = config.environment; + +in + +{ + + config = { + + environment.variables = + { NIXPKGS_CONFIG = "/etc/nix/nixpkgs-config.nix"; + PAGER = mkDefault "less -R"; + EDITOR = mkDefault "nano"; + XCURSOR_PATH = [ "$HOME/.icons" ]; + }; + + environment.profiles = mkAfter + [ "/nix/var/nix/profiles/default" + "/run/current-system/sw" + ]; + + # TODO: move most of these elsewhere + environment.profileRelativeEnvVars = + { PATH = [ "/bin" ]; + INFOPATH = [ "/info" "/share/info" ]; + KDEDIRS = [ "" ]; + STRIGI_PLUGIN_PATH = [ "/lib/strigi/" ]; + QT_PLUGIN_PATH = [ "/lib/qt4/plugins" "/lib/kde4/plugins" ]; + QTWEBKIT_PLUGIN_PATH = [ "/lib/mozilla/plugins/" ]; + GTK_PATH = [ "/lib/gtk-2.0" "/lib/gtk-3.0" ]; + XDG_CONFIG_DIRS = [ "/etc/xdg" ]; + XDG_DATA_DIRS = [ "/share" ]; + MOZ_PLUGIN_PATH = [ "/lib/mozilla/plugins" ]; + LIBEXEC_PATH = [ "/lib/libexec" ]; + }; + + environment.extraInit = + '' + unset ASPELL_CONF + for i in ${concatStringsSep " " (reverseList cfg.profiles)} ; do + if [ -d "$i/lib/aspell" ]; then + export ASPELL_CONF="dict-dir $i/lib/aspell" + fi + done + + export NIX_USER_PROFILE_DIR="/nix/var/nix/profiles/per-user/$USER" + export NIX_PROFILES="${concatStringsSep " " (reverseList cfg.profiles)}" + ''; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/evince.nix b/nixpkgs/nixos/modules/programs/evince.nix new file mode 100644 index 000000000000..473fddb09d02 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/evince.nix @@ -0,0 +1,42 @@ +# Evince. + +{ config, pkgs, lib, ... }: + +with lib; + +{ + + # Added 2019-08-09 + imports = [ + (mkRenamedOptionModule + [ "services" "gnome3" "evince" "enable" ] + [ "programs" "evince" "enable" ]) + ]; + + ###### interface + + options = { + + programs.evince = { + + enable = mkEnableOption + "Evince, the GNOME document viewer"; + + }; + + }; + + + ###### implementation + + config = mkIf config.programs.evince.enable { + + environment.systemPackages = [ pkgs.evince ]; + + services.dbus.packages = [ pkgs.evince ]; + + systemd.packages = [ pkgs.evince ]; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/file-roller.nix b/nixpkgs/nixos/modules/programs/file-roller.nix new file mode 100644 index 000000000000..64f6a94e7641 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/file-roller.nix @@ -0,0 +1,39 @@ +# File Roller. + +{ config, pkgs, lib, ... }: + +with lib; + +{ + + # Added 2019-08-09 + imports = [ + (mkRenamedOptionModule + [ "services" "gnome3" "file-roller" "enable" ] + [ "programs" "file-roller" "enable" ]) + ]; + + ###### interface + + options = { + + programs.file-roller = { + + enable = mkEnableOption "File Roller, an archive manager for GNOME"; + + }; + + }; + + + ###### implementation + + config = mkIf config.programs.file-roller.enable { + + environment.systemPackages = [ pkgs.gnome3.file-roller ]; + + services.dbus.packages = [ pkgs.gnome3.file-roller ]; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/firejail.nix b/nixpkgs/nixos/modules/programs/firejail.nix new file mode 100644 index 000000000000..46ee4bc0f7a0 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/firejail.nix @@ -0,0 +1,48 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.firejail; + + wrappedBins = pkgs.stdenv.mkDerivation rec { + name = "firejail-wrapped-binaries"; + nativeBuildInputs = with pkgs; [ makeWrapper ]; + buildCommand = '' + mkdir -p $out/bin + ${lib.concatStringsSep "\n" (lib.mapAttrsToList (command: binary: '' + cat <<_EOF >$out/bin/${command} + #!${pkgs.stdenv.shell} -e + /run/wrappers/bin/firejail ${binary} "\$@" + _EOF + chmod 0755 $out/bin/${command} + '') cfg.wrappedBinaries)} + ''; + }; + +in { + options.programs.firejail = { + enable = mkEnableOption "firejail"; + + wrappedBinaries = mkOption { + type = types.attrs; + default = {}; + description = '' + Wrap the binaries in firejail and place them in the global path. + </para> + <para> + You will get file collisions if you put the actual application binary in + the global environment and applications started via .desktop files are + not wrapped if they specify the absolute path to the binary. + ''; + }; + }; + + config = mkIf cfg.enable { + security.wrappers.firejail.source = "${lib.getBin pkgs.firejail}/bin/firejail"; + + environment.systemPackages = [ wrappedBins ]; + }; + + meta.maintainers = with maintainers; [ peterhoeg ]; +} diff --git a/nixpkgs/nixos/modules/programs/fish.nix b/nixpkgs/nixos/modules/programs/fish.nix new file mode 100644 index 000000000000..87f6816e4ac0 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/fish.nix @@ -0,0 +1,240 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfge = config.environment; + + cfg = config.programs.fish; + + fishAliases = concatStringsSep "\n" ( + mapAttrsFlatten (k: v: "alias ${k} ${escapeShellArg v}") + (filterAttrs (k: v: v != null) cfg.shellAliases) + ); + +in + +{ + + options = { + + programs.fish = { + + enable = mkOption { + default = false; + description = '' + Whether to configure fish as an interactive shell. + ''; + type = types.bool; + }; + + vendor.config.enable = mkOption { + type = types.bool; + default = true; + description = '' + Whether fish should source configuration snippets provided by other packages. + ''; + }; + + vendor.completions.enable = mkOption { + type = types.bool; + default = true; + description = '' + Whether fish should use completion files provided by other packages. + ''; + }; + + vendor.functions.enable = mkOption { + type = types.bool; + default = true; + description = '' + Whether fish should autoload fish functions provided by other packages. + ''; + }; + + shellAliases = mkOption { + default = {}; + description = '' + Set of aliases for fish shell, which overrides <option>environment.shellAliases</option>. + See <option>environment.shellAliases</option> for an option format description. + ''; + type = with types; attrsOf (nullOr (either str path)); + }; + + shellInit = mkOption { + default = ""; + description = '' + Shell script code called during fish shell initialisation. + ''; + type = types.lines; + }; + + loginShellInit = mkOption { + default = ""; + description = '' + Shell script code called during fish login shell initialisation. + ''; + type = types.lines; + }; + + interactiveShellInit = mkOption { + default = ""; + description = '' + Shell script code called during interactive fish shell initialisation. + ''; + type = types.lines; + }; + + promptInit = mkOption { + default = ""; + description = '' + Shell script code used to initialise fish prompt. + ''; + type = types.lines; + }; + + }; + + }; + + config = mkIf cfg.enable { + + programs.fish.shellAliases = mapAttrs (name: mkDefault) cfge.shellAliases; + + environment.etc."fish/foreign-env/shellInit".text = cfge.shellInit; + environment.etc."fish/foreign-env/loginShellInit".text = cfge.loginShellInit; + environment.etc."fish/foreign-env/interactiveShellInit".text = cfge.interactiveShellInit; + + environment.etc."fish/nixos-env-preinit.fish".text = '' + # This happens before $__fish_datadir/config.fish sets fish_function_path, so it is currently + # unset. We set it and then completely erase it, leaving its configuration to $__fish_datadir/config.fish + set fish_function_path ${pkgs.fish-foreign-env}/share/fish-foreign-env/functions $__fish_datadir/functions + + # source the NixOS environment config + if [ -z "$__NIXOS_SET_ENVIRONMENT_DONE" ] + fenv source ${config.system.build.setEnvironment} + end + + # clear fish_function_path so that it will be correctly set when we return to $__fish_datadir/config.fish + set -e fish_function_path + ''; + + environment.etc."fish/config.fish".text = '' + # /etc/fish/config.fish: DO NOT EDIT -- this file has been generated automatically. + + # if we haven't sourced the general config, do it + if not set -q __fish_nixos_general_config_sourced + set fish_function_path ${pkgs.fish-foreign-env}/share/fish-foreign-env/functions $fish_function_path + fenv source /etc/fish/foreign-env/shellInit > /dev/null + set -e fish_function_path[1] + + ${cfg.shellInit} + + # and leave a note so we don't source this config section again from + # this very shell (children will source the general config anew) + set -g __fish_nixos_general_config_sourced 1 + end + + # if we haven't sourced the login config, do it + status --is-login; and not set -q __fish_nixos_login_config_sourced + and begin + set fish_function_path ${pkgs.fish-foreign-env}/share/fish-foreign-env/functions $fish_function_path + fenv source /etc/fish/foreign-env/loginShellInit > /dev/null + set -e fish_function_path[1] + + ${cfg.loginShellInit} + + # and leave a note so we don't source this config section again from + # this very shell (children will source the general config anew) + set -g __fish_nixos_login_config_sourced 1 + end + + # if we haven't sourced the interactive config, do it + status --is-interactive; and not set -q __fish_nixos_interactive_config_sourced + and begin + ${fishAliases} + + set fish_function_path ${pkgs.fish-foreign-env}/share/fish-foreign-env/functions $fish_function_path + fenv source /etc/fish/foreign-env/interactiveShellInit > /dev/null + set -e fish_function_path[1] + + ${cfg.promptInit} + ${cfg.interactiveShellInit} + + # and leave a note so we don't source this config section again from + # this very shell (children will source the general config anew, + # allowing configuration changes in, e.g, aliases, to propagate) + set -g __fish_nixos_interactive_config_sourced 1 + end + ''; + + programs.fish.interactiveShellInit = '' + # add completions generated by NixOS to $fish_complete_path + begin + # joins with null byte to acommodate all characters in paths, then respectively gets all paths before (exclusive) / after (inclusive) the first one including "generated_completions", + # splits by null byte, and then removes all empty lines produced by using 'string' + set -l prev (string join0 $fish_complete_path | string match --regex "^.*?(?=\x00[^\x00]*generated_completions.*)" | string split0 | string match -er ".") + set -l post (string join0 $fish_complete_path | string match --regex "[^\x00]*generated_completions.*" | string split0 | string match -er ".") + set fish_complete_path $prev "/etc/fish/generated_completions" $post + end + ''; + + environment.etc."fish/generated_completions".source = + let + patchedGenerator = pkgs.stdenv.mkDerivation { + name = "fish_patched-completion-generator"; + srcs = [ + "${pkgs.fish}/share/fish/tools/create_manpage_completions.py" + "${pkgs.fish}/share/fish/tools/deroff.py" + ]; + unpackCmd = "cp $curSrc $(basename $curSrc)"; + sourceRoot = "."; + patches = [ ./fish_completion-generator.patch ]; # to prevent collisions of identical completion files + dontBuild = true; + installPhase = '' + mkdir -p $out + cp * $out/ + ''; + preferLocalBuild = true; + allowSubstitutes = false; + }; + generateCompletions = package: pkgs.runCommand + "${package.name}_fish-completions" + ( + { + inherit package; + preferLocalBuild = true; + allowSubstitutes = false; + } + // optionalAttrs (package ? meta.priority) { meta.priority = package.meta.priority; } + ) + '' + mkdir -p $out + if [ -d $package/share/man ]; then + find $package/share/man -type f | xargs ${pkgs.python3.interpreter} ${patchedGenerator}/create_manpage_completions.py --directory $out >/dev/null + fi + ''; + in + pkgs.buildEnv { + name = "system_fish-completions"; + ignoreCollisions = true; + paths = map generateCompletions config.environment.systemPackages; + }; + + # include programs that bring their own completions + environment.pathsToLink = [] + ++ optional cfg.vendor.config.enable "/share/fish/vendor_conf.d" + ++ optional cfg.vendor.completions.enable "/share/fish/vendor_completions.d" + ++ optional cfg.vendor.functions.enable "/share/fish/vendor_functions.d"; + + environment.systemPackages = [ pkgs.fish ]; + + environment.shells = [ + "/run/current-system/sw/bin/fish" + "${pkgs.fish}/bin/fish" + ]; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/fish_completion-generator.patch b/nixpkgs/nixos/modules/programs/fish_completion-generator.patch new file mode 100644 index 000000000000..a8c797d185a6 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/fish_completion-generator.patch @@ -0,0 +1,11 @@ +--- a/create_manpage_completions.py ++++ b/create_manpage_completions.py +@@ -776,8 +776,6 @@ def parse_manpage_at_path(manpage_path, output_directory): + + built_command_output.insert(0, "# " + CMDNAME) + +- # Output the magic word Autogenerated so we can tell if we can overwrite this +- built_command_output.insert(1, "# Autogenerated from man page " + manpage_path) + # built_command_output.insert(2, "# using " + parser.__class__.__name__) # XXX MISATTRIBUTES THE CULPABILE PARSER! Was really using Type2 but reporting TypeDeroffManParser + + for line in built_command_output: diff --git a/nixpkgs/nixos/modules/programs/freetds.nix b/nixpkgs/nixos/modules/programs/freetds.nix new file mode 100644 index 000000000000..e0860a242b74 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/freetds.nix @@ -0,0 +1,61 @@ +# Global configuration for freetds environment. + +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfg = config.environment.freetds; + +in +{ + ###### interface + + options = { + + environment.freetds = mkOption { + type = types.attrsOf types.str; + default = {}; + example = literalExample '' + { MYDATABASE = ''' + host = 10.0.2.100 + port = 1433 + tds version = 7.2 + '''; + } + ''; + description = + '' + Configure freetds database entries. Each attribute denotes + a section within freetds.conf, and the value (a string) is the config + content for that section. When at least one entry is configured + the global environment variables FREETDSCONF, FREETDS and SYBASE + will be configured to allow the programs that use freetds to find the + library and config. + ''; + + }; + + }; + + ###### implementation + + config = mkIf (length (attrNames cfg) > 0) { + + environment.variables.FREETDSCONF = "/etc/freetds.conf"; + environment.variables.FREETDS = "/etc/freetds.conf"; + environment.variables.SYBASE = "${pkgs.freetds}"; + + environment.etc."freetds.conf" = { text = + (concatStrings (mapAttrsToList (name: value: + '' + [${name}] + ${value} + '' + ) cfg)); + }; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/fuse.nix b/nixpkgs/nixos/modules/programs/fuse.nix new file mode 100644 index 000000000000..c15896efbb51 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/fuse.nix @@ -0,0 +1,37 @@ +{ config, lib, ... }: + +with lib; + +let + cfg = config.programs.fuse; +in { + meta.maintainers = with maintainers; [ primeos ]; + + options.programs.fuse = { + mountMax = mkOption { + # In the C code it's an "int" (i.e. signed and at least 16 bit), but + # negative numbers obviously make no sense: + type = types.ints.between 0 32767; # 2^15 - 1 + default = 1000; + description = '' + Set the maximum number of FUSE mounts allowed to non-root users. + ''; + }; + + userAllowOther = mkOption { + type = types.bool; + default = false; + description = '' + Allow non-root users to specify the allow_other or allow_root mount + options, see mount.fuse3(8). + ''; + }; + }; + + config = { + environment.etc."fuse.conf".text = '' + ${optionalString (!cfg.userAllowOther) "#"}user_allow_other + mount_max = ${toString cfg.mountMax} + ''; + }; +} diff --git a/nixpkgs/nixos/modules/programs/gnome-disks.nix b/nixpkgs/nixos/modules/programs/gnome-disks.nix new file mode 100644 index 000000000000..1cf839a6ddb0 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/gnome-disks.nix @@ -0,0 +1,46 @@ +# GNOME Disks. + +{ config, pkgs, lib, ... }: + +with lib; + +{ + + # Added 2019-08-09 + imports = [ + (mkRenamedOptionModule + [ "services" "gnome3" "gnome-disks" "enable" ] + [ "programs" "gnome-disks" "enable" ]) + ]; + + ###### interface + + options = { + + programs.gnome-disks = { + + enable = mkOption { + type = types.bool; + default = false; + description = '' + Whether to enable GNOME Disks daemon, a program designed to + be a UDisks2 graphical front-end. + ''; + }; + + }; + + }; + + + ###### implementation + + config = mkIf config.programs.gnome-disks.enable { + + environment.systemPackages = [ pkgs.gnome3.gnome-disk-utility ]; + + services.dbus.packages = [ pkgs.gnome3.gnome-disk-utility ]; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/gnome-documents.nix b/nixpkgs/nixos/modules/programs/gnome-documents.nix new file mode 100644 index 000000000000..bfa3d409ee30 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/gnome-documents.nix @@ -0,0 +1,50 @@ +# GNOME Documents. + +{ config, pkgs, lib, ... }: + +with lib; + +{ + + # Added 2019-08-09 + imports = [ + (mkRenamedOptionModule + [ "services" "gnome3" "gnome-documents" "enable" ] + [ "programs" "gnome-documents" "enable" ]) + ]; + + ###### interface + + options = { + + programs.gnome-documents = { + + enable = mkOption { + type = types.bool; + default = false; + description = '' + Whether to enable GNOME Documents, a document + manager application for GNOME. + ''; + }; + + }; + + }; + + + ###### implementation + + config = mkIf config.programs.gnome-documents.enable { + + environment.systemPackages = [ pkgs.gnome3.gnome-documents ]; + + services.dbus.packages = [ pkgs.gnome3.gnome-documents ]; + + services.gnome3.gnome-online-accounts.enable = true; + + services.gnome3.gnome-online-miners.enable = true; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/gnupg.nix b/nixpkgs/nixos/modules/programs/gnupg.nix new file mode 100644 index 000000000000..9618d61a1f5b --- /dev/null +++ b/nixpkgs/nixos/modules/programs/gnupg.nix @@ -0,0 +1,112 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfg = config.programs.gnupg; + +in + +{ + + options.programs.gnupg = { + package = mkOption { + type = types.package; + default = pkgs.gnupg; + defaultText = "pkgs.gnupg"; + description = '' + The gpg package that should be used. + ''; + }; + + agent.enable = mkOption { + type = types.bool; + default = false; + description = '' + Enables GnuPG agent with socket-activation for every user session. + ''; + }; + + agent.enableSSHSupport = mkOption { + type = types.bool; + default = false; + description = '' + Enable SSH agent support in GnuPG agent. Also sets SSH_AUTH_SOCK + environment variable correctly. This will disable socket-activation + and thus always start a GnuPG agent per user session. + ''; + }; + + agent.enableExtraSocket = mkOption { + type = types.bool; + default = false; + description = '' + Enable extra socket for GnuPG agent. + ''; + }; + + agent.enableBrowserSocket = mkOption { + type = types.bool; + default = false; + description = '' + Enable browser socket for GnuPG agent. + ''; + }; + + dirmngr.enable = mkOption { + type = types.bool; + default = false; + description = '' + Enables GnuPG network certificate management daemon with socket-activation for every user session. + ''; + }; + }; + + config = mkIf cfg.agent.enable { + systemd.user.sockets.gpg-agent = { + wantedBy = [ "sockets.target" ]; + }; + + systemd.user.sockets.gpg-agent-ssh = mkIf cfg.agent.enableSSHSupport { + wantedBy = [ "sockets.target" ]; + }; + + systemd.user.sockets.gpg-agent-extra = mkIf cfg.agent.enableExtraSocket { + wantedBy = [ "sockets.target" ]; + }; + + systemd.user.sockets.gpg-agent-browser = mkIf cfg.agent.enableBrowserSocket { + wantedBy = [ "sockets.target" ]; + }; + + systemd.user.sockets.dirmngr = mkIf cfg.dirmngr.enable { + wantedBy = [ "sockets.target" ]; + }; + + systemd.packages = [ cfg.package ]; + + environment.interactiveShellInit = '' + # Bind gpg-agent to this TTY if gpg commands are used. + export GPG_TTY=$(tty) + + '' + (optionalString cfg.agent.enableSSHSupport '' + # SSH agent protocol doesn't support changing TTYs, so bind the agent + # to every new TTY. + ${cfg.package}/bin/gpg-connect-agent --quiet updatestartuptty /bye > /dev/null + ''); + + environment.extraInit = mkIf cfg.agent.enableSSHSupport '' + if [ -z "$SSH_AUTH_SOCK" ]; then + export SSH_AUTH_SOCK=$(${cfg.package}/bin/gpgconf --list-dirs agent-ssh-socket) + fi + ''; + + assertions = [ + { assertion = cfg.agent.enableSSHSupport -> !config.programs.ssh.startAgent; + message = "You can't use ssh-agent and GnuPG agent with SSH support enabled at the same time!"; + } + ]; + }; + +} diff --git a/nixpkgs/nixos/modules/programs/gpaste.nix b/nixpkgs/nixos/modules/programs/gpaste.nix new file mode 100644 index 000000000000..4f6deb77e5eb --- /dev/null +++ b/nixpkgs/nixos/modules/programs/gpaste.nix @@ -0,0 +1,34 @@ +# GPaste. +{ config, lib, pkgs, ... }: + +with lib; + +{ + + # Added 2019-08-09 + imports = [ + (mkRenamedOptionModule + [ "services" "gnome3" "gpaste" "enable" ] + [ "programs" "gpaste" "enable" ]) + ]; + + ###### interface + options = { + programs.gpaste = { + enable = mkOption { + type = types.bool; + default = false; + description = '' + Whether to enable GPaste, a clipboard manager. + ''; + }; + }; + }; + + ###### implementation + config = mkIf config.programs.gpaste.enable { + environment.systemPackages = [ pkgs.gnome3.gpaste ]; + services.dbus.packages = [ pkgs.gnome3.gpaste ]; + systemd.packages = [ pkgs.gnome3.gpaste ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/gphoto2.nix b/nixpkgs/nixos/modules/programs/gphoto2.nix new file mode 100644 index 000000000000..93923ff3133c --- /dev/null +++ b/nixpkgs/nixos/modules/programs/gphoto2.nix @@ -0,0 +1,30 @@ +{ config, lib, pkgs, ... }: + +with lib; + +{ + meta.maintainers = [ maintainers.league ]; + + ###### interface + options = { + programs.gphoto2 = { + enable = mkOption { + default = false; + type = types.bool; + description = '' + Whether to configure system to use gphoto2. + To grant digital camera access to a user, the user must + be part of the camera group: + <code>users.users.alice.extraGroups = ["camera"];</code> + ''; + }; + }; + }; + + ###### implementation + config = mkIf config.programs.gphoto2.enable { + services.udev.packages = [ pkgs.libgphoto2 ]; + environment.systemPackages = [ pkgs.gphoto2 ]; + users.groups.camera = {}; + }; +} diff --git a/nixpkgs/nixos/modules/programs/iftop.nix b/nixpkgs/nixos/modules/programs/iftop.nix new file mode 100644 index 000000000000..a98a9a8187d4 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/iftop.nix @@ -0,0 +1,18 @@ +{ config, pkgs, lib, ... }: + +with lib; + +let + cfg = config.programs.iftop; +in { + options = { + programs.iftop.enable = mkEnableOption "iftop + setcap wrapper"; + }; + config = mkIf cfg.enable { + environment.systemPackages = [ pkgs.iftop ]; + security.wrappers.iftop = { + source = "${pkgs.iftop}/bin/iftop"; + capabilities = "cap_net_raw+p"; + }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/iotop.nix b/nixpkgs/nixos/modules/programs/iotop.nix new file mode 100644 index 000000000000..5512dbc62f72 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/iotop.nix @@ -0,0 +1,17 @@ +{ config, pkgs, lib, ... }: + +with lib; + +let + cfg = config.programs.iotop; +in { + options = { + programs.iotop.enable = mkEnableOption "iotop + setcap wrapper"; + }; + config = mkIf cfg.enable { + security.wrappers.iotop = { + source = "${pkgs.iotop}/bin/iotop"; + capabilities = "cap_net_admin+p"; + }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/java.nix b/nixpkgs/nixos/modules/programs/java.nix new file mode 100644 index 000000000000..d31698c3b392 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/java.nix @@ -0,0 +1,58 @@ +# This module provides JAVA_HOME, with a different way to install java +# system-wide. + +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.java; +in + +{ + + options = { + + programs.java = { + + enable = mkEnableOption "java" // { + description = '' + Install and setup the Java development kit. + <note> + <para>This adds JAVA_HOME to the global environment, by sourcing the + jdk's setup-hook on shell init. It is equivalent to starting a shell + through 'nix-shell -p jdk', or roughly the following system-wide + configuration: + </para> + <programlisting> + environment.variables.JAVA_HOME = ''${pkgs.jdk.home}/lib/openjdk; + environment.systemPackages = [ pkgs.jdk ]; + </programlisting> + </note> + ''; + }; + + package = mkOption { + default = pkgs.jdk; + defaultText = "pkgs.jdk"; + description = '' + Java package to install. Typical values are pkgs.jdk or pkgs.jre. + ''; + type = types.package; + }; + + }; + + }; + + config = mkIf cfg.enable { + + environment.systemPackages = [ cfg.package ]; + + environment.shellInit = '' + test -e ${cfg.package}/nix-support/setup-hook && source ${cfg.package}/nix-support/setup-hook + ''; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/kbdlight.nix b/nixpkgs/nixos/modules/programs/kbdlight.nix new file mode 100644 index 000000000000..58e45872fac8 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/kbdlight.nix @@ -0,0 +1,16 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.kbdlight; + +in +{ + options.programs.kbdlight.enable = mkEnableOption "kbdlight"; + + config = mkIf cfg.enable { + environment.systemPackages = [ pkgs.kbdlight ]; + security.wrappers.kbdlight.source = "${pkgs.kbdlight.out}/bin/kbdlight"; + }; +} diff --git a/nixpkgs/nixos/modules/programs/less.nix b/nixpkgs/nixos/modules/programs/less.nix new file mode 100644 index 000000000000..9fdf99e9c694 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/less.nix @@ -0,0 +1,131 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfg = config.programs.less; + + configText = if (cfg.configFile != null) then (builtins.readFile cfg.configFile) else '' + #command + ${concatStringsSep "\n" + (mapAttrsToList (command: action: "${command} ${action}") cfg.commands) + } + ${if cfg.clearDefaultCommands then "#stop" else ""} + + #line-edit + ${concatStringsSep "\n" + (mapAttrsToList (command: action: "${command} ${action}") cfg.lineEditingKeys) + } + + #env + ${concatStringsSep "\n" + (mapAttrsToList (variable: values: "${variable}=${values}") cfg.envVariables) + } + ''; + + lessKey = pkgs.runCommand "lesskey" + { src = pkgs.writeText "lessconfig" configText; preferLocalBuild = true; } + "${pkgs.less}/bin/lesskey -o $out $src"; + +in + +{ + options = { + + programs.less = { + + enable = mkEnableOption "less"; + + configFile = mkOption { + type = types.nullOr types.path; + default = null; + example = literalExample "$${pkgs.my-configs}/lesskey"; + description = '' + Path to lesskey configuration file. + + <option>configFile</option> takes precedence over <option>commands</option>, + <option>clearDefaultCommands</option>, <option>lineEditingKeys</option>, and + <option>envVariables</option>. + ''; + }; + + commands = mkOption { + type = types.attrsOf types.str; + default = {}; + example = { + "h" = "noaction 5\e("; + "l" = "noaction 5\e)"; + }; + description = "Defines new command keys."; + }; + + clearDefaultCommands = mkOption { + type = types.bool; + default = false; + description = '' + Clear all default commands. + You should remember to set the quit key. + Otherwise you will not be able to leave less without killing it. + ''; + }; + + lineEditingKeys = mkOption { + type = types.attrsOf types.str; + default = {}; + example = { + "\e" = "abort"; + }; + description = "Defines new line-editing keys."; + }; + + envVariables = mkOption { + type = types.attrsOf types.str; + default = {}; + example = { + LESS = "--quit-if-one-screen"; + }; + description = "Defines environment variables."; + }; + + lessopen = mkOption { + type = types.nullOr types.str; + default = "|${pkgs.lesspipe}/bin/lesspipe.sh %s"; + description = '' + Before less opens a file, it first gives your input preprocessor a chance to modify the way the contents of the file are displayed. + ''; + }; + + lessclose = mkOption { + type = types.nullOr types.str; + default = null; + description = '' + When less closes a file opened in such a way, it will call another program, called the input postprocessor, which may perform any desired clean-up action (such as deleting the replacement file created by LESSOPEN). + ''; + }; + }; + }; + + config = mkIf cfg.enable { + + environment.systemPackages = [ pkgs.less ]; + + environment.variables = { + "LESSKEY_SYSTEM" = toString lessKey; + } // optionalAttrs (cfg.lessopen != null) { + "LESSOPEN" = cfg.lessopen; + } // optionalAttrs (cfg.lessclose != null) { + "LESSCLOSE" = cfg.lessclose; + }; + + warnings = optional ( + cfg.clearDefaultCommands && (all (x: x != "quit") (attrValues cfg.commands)) + ) '' + config.programs.less.clearDefaultCommands clears all default commands of less but there is no alternative binding for exiting. + Consider adding a binding for 'quit'. + ''; + }; + + meta.maintainers = with maintainers; [ johnazoidberg ]; + +} diff --git a/nixpkgs/nixos/modules/programs/light.nix b/nixpkgs/nixos/modules/programs/light.nix new file mode 100644 index 000000000000..9f2a03e7e763 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/light.nix @@ -0,0 +1,27 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.light; + +in +{ + options = { + programs.light = { + enable = mkOption { + default = false; + type = types.bool; + description = '' + Whether to install Light backlight control command + and udev rules granting access to members of the "video" group. + ''; + }; + }; + }; + + config = mkIf cfg.enable { + environment.systemPackages = [ pkgs.light ]; + services.udev.packages = [ pkgs.light ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/mininet.nix b/nixpkgs/nixos/modules/programs/mininet.nix new file mode 100644 index 000000000000..ecc924325e6b --- /dev/null +++ b/nixpkgs/nixos/modules/programs/mininet.nix @@ -0,0 +1,39 @@ +# Global configuration for mininet +# kernel must have NETNS/VETH/SCHED +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.mininet; + + generatedPath = with pkgs; makeSearchPath "bin" [ + iperf ethtool iproute socat + ]; + + pyEnv = pkgs.python.withPackages(ps: [ ps.mininet-python ]); + + mnexecWrapped = pkgs.runCommand "mnexec-wrapper" + { buildInputs = [ pkgs.makeWrapper pkgs.pythonPackages.wrapPython ]; } + '' + makeWrapper ${pkgs.mininet}/bin/mnexec \ + $out/bin/mnexec \ + --prefix PATH : "${generatedPath}" + + ln -s ${pyEnv}/bin/mn $out/bin/mn + + # mn errors out without a telnet binary + # pkgs.telnet brings an undesired ifconfig into PATH see #43105 + ln -s ${pkgs.telnet}/bin/telnet $out/bin/telnet + ''; +in +{ + options.programs.mininet.enable = mkEnableOption "Mininet"; + + config = mkIf cfg.enable { + + virtualisation.vswitch.enable = true; + + environment.systemPackages = [ mnexecWrapped ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/mosh.nix b/nixpkgs/nixos/modules/programs/mosh.nix new file mode 100644 index 000000000000..359fe23e0ecd --- /dev/null +++ b/nixpkgs/nixos/modules/programs/mosh.nix @@ -0,0 +1,43 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfg = config.programs.mosh; + +in +{ + options.programs.mosh = { + enable = mkOption { + description = '' + Whether to enable mosh. Note, this will open ports in your firewall! + ''; + default = false; + type = lib.types.bool; + }; + withUtempter = mkOption { + description = '' + Whether to enable libutempter for mosh. + This is required so that mosh can write to /var/run/utmp (which can be queried with `who` to display currently connected user sessions). + Note, this will add a guid wrapper for the group utmp! + ''; + default = true; + type = lib.types.bool; + }; + }; + + config = mkIf cfg.enable { + environment.systemPackages = with pkgs; [ mosh ]; + networking.firewall.allowedUDPPortRanges = [ { from = 60000; to = 61000; } ]; + security.wrappers = mkIf cfg.withUtempter { + utempter = { + source = "${pkgs.libutempter}/lib/utempter/utempter"; + owner = "nobody"; + group = "utmp"; + setuid = false; + setgid = true; + }; + }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/mtr.nix b/nixpkgs/nixos/modules/programs/mtr.nix new file mode 100644 index 000000000000..1fdec4c04f68 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/mtr.nix @@ -0,0 +1,28 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.mtr; +in { + options = { + programs.mtr = { + enable = mkOption { + type = types.bool; + default = false; + description = '' + Whether to add mtr to the global environment and configure a + setcap wrapper for it. + ''; + }; + }; + }; + + config = mkIf cfg.enable { + environment.systemPackages = with pkgs; [ mtr ]; + security.wrappers.mtr-packet = { + source = "${pkgs.mtr}/bin/mtr-packet"; + capabilities = "cap_net_raw+p"; + }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/nano.nix b/nixpkgs/nixos/modules/programs/nano.nix new file mode 100644 index 000000000000..6a4d46338e19 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/nano.nix @@ -0,0 +1,42 @@ +{ config, lib, pkgs, ... }: + +let + cfg = config.programs.nano; + LF = "\n"; +in + +{ + ###### interface + + options = { + programs.nano = { + + nanorc = lib.mkOption { + type = lib.types.lines; + default = ""; + description = '' + The system-wide nano configuration. + See <citerefentry><refentrytitle>nanorc</refentrytitle><manvolnum>5</manvolnum></citerefentry>. + ''; + example = '' + set nowrap + set tabstospaces + set tabsize 2 + ''; + }; + syntaxHighlight = lib.mkOption { + type = lib.types.bool; + default = true; + description = "Whether to enable syntax highlight for various languages."; + }; + }; + }; + + ###### implementation + + config = lib.mkIf (cfg.nanorc != "" || cfg.syntaxHighlight) { + environment.etc."nanorc".text = lib.concatStrings [ cfg.nanorc + (lib.optionalString cfg.syntaxHighlight ''${LF}include "${pkgs.nano}/share/nano/*.nanorc"'') ]; + }; + +} diff --git a/nixpkgs/nixos/modules/programs/nm-applet.nix b/nixpkgs/nixos/modules/programs/nm-applet.nix new file mode 100644 index 000000000000..e42219e9638c --- /dev/null +++ b/nixpkgs/nixos/modules/programs/nm-applet.nix @@ -0,0 +1,14 @@ +{ config, lib, pkgs, ... }: + +{ + options.programs.nm-applet.enable = lib.mkEnableOption "nm-applet"; + + config = lib.mkIf config.programs.nm-applet.enable { + systemd.user.services.nm-applet = { + description = "Network manager applet"; + wantedBy = [ "graphical-session.target" ]; + partOf = [ "graphical-session.target" ]; + serviceConfig.ExecStart = "${pkgs.networkmanagerapplet}/bin/nm-applet"; + }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/npm.nix b/nixpkgs/nixos/modules/programs/npm.nix new file mode 100644 index 000000000000..5fdd4fa841a1 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/npm.nix @@ -0,0 +1,46 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.npm; +in + +{ + ###### interface + + options = { + programs.npm = { + enable = mkEnableOption "<command>npm</command> global config"; + + npmrc = lib.mkOption { + type = lib.types.lines; + description = '' + The system-wide npm configuration. + See <link xlink:href="https://docs.npmjs.com/misc/config"/>. + ''; + default = '' + prefix = ''${HOME}/.npm + ''; + example = '' + prefix = ''${HOME}/.npm + https-proxy=proxy.example.com + init-license=MIT + init-author-url=http://npmjs.org + color=true + ''; + }; + }; + }; + + ###### implementation + + config = lib.mkIf cfg.enable { + environment.etc."npmrc".text = cfg.npmrc; + + environment.variables.NPM_CONFIG_GLOBALCONFIG = "/etc/npmrc"; + + environment.systemPackages = [ pkgs.nodePackages.npm ]; + }; + +} diff --git a/nixpkgs/nixos/modules/programs/oblogout.nix b/nixpkgs/nixos/modules/programs/oblogout.nix new file mode 100644 index 000000000000..720c29b1eaee --- /dev/null +++ b/nixpkgs/nixos/modules/programs/oblogout.nix @@ -0,0 +1,176 @@ +# Global configuration for oblogout. + +{ config, lib, pkgs, ... }: + +with lib; + +let cfg = config.programs.oblogout; + +in +{ + ###### interface + + options = { + + programs.oblogout = { + + enable = mkOption { + type = types.bool; + default = false; + description = '' + Whether to install OBLogout and create <filename>/etc/oblogout.conf</filename>. + See <filename>${pkgs.oblogout}/share/doc/README</filename>. + ''; + }; + + opacity = mkOption { + type = types.int; + default = 70; + description = '' + Opacity percentage of Cairo rendered backgrounds. + ''; + }; + + bgcolor = mkOption { + type = types.str; + default = "black"; + description = '' + Colour name or hex code (#ffffff) of the background color. + ''; + }; + + buttontheme = mkOption { + type = types.str; + default = "simplistic"; + description = '' + Icon theme for the buttons, must be in the themes folder of + the package, or in + <filename>~/.themes/<name>/oblogout/</filename>. + ''; + }; + + buttons = mkOption { + type = types.str; + default = "cancel, logout, restart, shutdown, suspend, hibernate"; + description = '' + List and order of buttons to show. + ''; + }; + + cancel = mkOption { + type = types.str; + default = "Escape"; + description = '' + Cancel logout/shutdown shortcut. + ''; + }; + + shutdown = mkOption { + type = types.str; + default = "S"; + description = '' + Shutdown shortcut. + ''; + }; + + restart = mkOption { + type = types.str; + default = "R"; + description = '' + Restart shortcut. + ''; + }; + + suspend = mkOption { + type = types.str; + default = "U"; + description = '' + Suspend shortcut. + ''; + }; + + logout = mkOption { + type = types.str; + default = "L"; + description = '' + Logout shortcut. + ''; + }; + + lock = mkOption { + type = types.str; + default = "K"; + description = '' + Lock session shortcut. + ''; + }; + + hibernate = mkOption { + type = types.str; + default = "H"; + description = '' + Hibernate shortcut. + ''; + }; + + clogout = mkOption { + type = types.str; + default = "openbox --exit"; + description = '' + Command to logout. + ''; + }; + + clock = mkOption { + type = types.str; + default = ""; + description = '' + Command to lock screen. + ''; + }; + + cswitchuser = mkOption { + type = types.str; + default = ""; + description = '' + Command to switch user. + ''; + }; + }; + }; + + ###### implementation + + config = mkIf cfg.enable { + environment.systemPackages = [ pkgs.oblogout ]; + + environment.etc."oblogout.conf".text = '' + [settings] + usehal = false + + [looks] + opacity = ${toString cfg.opacity} + bgcolor = ${cfg.bgcolor} + buttontheme = ${cfg.buttontheme} + buttons = ${cfg.buttons} + + [shortcuts] + cancel = ${cfg.cancel} + shutdown = ${cfg.shutdown} + restart = ${cfg.restart} + suspend = ${cfg.suspend} + logout = ${cfg.logout} + lock = ${cfg.lock} + hibernate = ${cfg.hibernate} + + [commands] + shutdown = systemctl poweroff + restart = systemctl reboot + suspend = systemctl suspend + hibernate = systemctl hibernate + logout = ${cfg.clogout} + lock = ${cfg.clock} + switchuser = ${cfg.cswitchuser} + ''; + }; +} diff --git a/nixpkgs/nixos/modules/programs/plotinus.nix b/nixpkgs/nixos/modules/programs/plotinus.nix new file mode 100644 index 000000000000..065e72d6c374 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/plotinus.nix @@ -0,0 +1,36 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.plotinus; +in +{ + meta = { + maintainers = pkgs.plotinus.meta.maintainers; + doc = ./plotinus.xml; + }; + + ###### interface + + options = { + programs.plotinus = { + enable = mkOption { + default = false; + description = '' + Whether to enable the Plotinus GTK+3 plugin. Plotinus provides a + popup (triggered by Ctrl-Shift-P) to search the menus of a + compatible application. + ''; + type = types.bool; + }; + }; + }; + + ###### implementation + + config = mkIf cfg.enable { + environment.variables.XDG_DATA_DIRS = [ "${pkgs.plotinus}/share/gsettings-schemas/${pkgs.plotinus.name}" ]; + environment.variables.GTK3_MODULES = [ "${pkgs.plotinus}/lib/libplotinus.so" ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/plotinus.xml b/nixpkgs/nixos/modules/programs/plotinus.xml new file mode 100644 index 000000000000..902cd89e0c49 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/plotinus.xml @@ -0,0 +1,30 @@ +<chapter xmlns="http://docbook.org/ns/docbook" + xmlns:xlink="http://www.w3.org/1999/xlink" + xmlns:xi="http://www.w3.org/2001/XInclude" + version="5.0" + xml:id="module-program-plotinus"> + <title>Plotinus</title> + <para> + <emphasis>Source:</emphasis> + <filename>modules/programs/plotinus.nix</filename> + </para> + <para> + <emphasis>Upstream documentation:</emphasis> + <link xlink:href="https://github.com/p-e-w/plotinus"/> + </para> + <para> + Plotinus is a searchable command palette in every modern GTK+ application. + </para> + <para> + When in a GTK+3 application and Plotinus is enabled, you can press + <literal>Ctrl+Shift+P</literal> to open the command palette. The command + palette provides a searchable list of of all menu items in the application. + </para> + <para> + To enable Plotinus, add the following to your + <filename>configuration.nix</filename>: +<programlisting> +<xref linkend="opt-programs.plotinus.enable"/> = true; +</programlisting> + </para> +</chapter> diff --git a/nixpkgs/nixos/modules/programs/qt5ct.nix b/nixpkgs/nixos/modules/programs/qt5ct.nix new file mode 100644 index 000000000000..aeb7fc508495 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/qt5ct.nix @@ -0,0 +1,31 @@ +{ config, lib, pkgs, ... }: + +with lib; + +{ + meta.maintainers = [ maintainers.romildo ]; + + ###### interface + options = { + programs.qt5ct = { + enable = mkOption { + default = false; + type = types.bool; + description = '' + Whether to enable the Qt5 Configuration Tool (qt5ct), a + program that allows users to configure Qt5 settings (theme, + font, icons, etc.) under desktop environments or window + manager without Qt integration. + + Official home page: <link xlink:href="https://sourceforge.net/projects/qt5ct/">https://sourceforge.net/projects/qt5ct/</link> + ''; + }; + }; + }; + + ###### implementation + config = mkIf config.programs.qt5ct.enable { + environment.variables.QT_QPA_PLATFORMTHEME = "qt5ct"; + environment.systemPackages = with pkgs; [ qt5ct libsForQt5.qtstyleplugins ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/screen.nix b/nixpkgs/nixos/modules/programs/screen.nix new file mode 100644 index 000000000000..c1daaa58f16f --- /dev/null +++ b/nixpkgs/nixos/modules/programs/screen.nix @@ -0,0 +1,32 @@ +{ config, lib, pkgs, ... }: + +let + inherit (lib) mkOption mkIf types; + cfg = config.programs.screen; +in + +{ + ###### interface + + options = { + programs.screen = { + + screenrc = mkOption { + default = ""; + description = '' + The contents of /etc/screenrc file. + ''; + type = types.lines; + }; + }; + }; + + ###### implementation + + config = mkIf (cfg.screenrc != "") { + environment.etc."screenrc".text = cfg.screenrc; + + environment.systemPackages = [ pkgs.screen ]; + }; + +} diff --git a/nixpkgs/nixos/modules/programs/sedutil.nix b/nixpkgs/nixos/modules/programs/sedutil.nix new file mode 100644 index 000000000000..7efc80f4abba --- /dev/null +++ b/nixpkgs/nixos/modules/programs/sedutil.nix @@ -0,0 +1,18 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.sedutil; + +in { + options.programs.sedutil.enable = mkEnableOption "sedutil"; + + config = mkIf cfg.enable { + boot.kernelParams = [ + "libata.allow_tpm=1" + ]; + + environment.systemPackages = with pkgs; [ sedutil ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/shadow.nix b/nixpkgs/nixos/modules/programs/shadow.nix new file mode 100644 index 000000000000..8ec4169207db --- /dev/null +++ b/nixpkgs/nixos/modules/programs/shadow.nix @@ -0,0 +1,115 @@ +# Configuration for the pwdutils suite of tools: passwd, useradd, etc. + +{ config, lib, utils, pkgs, ... }: + +with lib; + +let + + loginDefs = + '' + DEFAULT_HOME yes + + SYS_UID_MIN 400 + SYS_UID_MAX 499 + UID_MIN 1000 + UID_MAX 29999 + + SYS_GID_MIN 400 + SYS_GID_MAX 499 + GID_MIN 1000 + GID_MAX 29999 + + TTYGROUP tty + TTYPERM 0620 + + # Ensure privacy for newly created home directories. + UMASK 077 + + # Uncomment this and install chfn SUID to allow non-root + # users to change their account GECOS information. + # This should be made configurable. + #CHFN_RESTRICT frwh + + ''; + +in + +{ + + ###### interface + + options = { + + users.defaultUserShell = lib.mkOption { + description = '' + This option defines the default shell assigned to user + accounts. This can be either a full system path or a shell package. + + This must not be a store path, since the path is + used outside the store (in particular in /etc/passwd). + ''; + example = literalExample "pkgs.zsh"; + type = types.either types.path types.shellPackage; + }; + + }; + + + ###### implementation + + config = { + + environment.systemPackages = + lib.optional config.users.mutableUsers pkgs.shadow ++ + lib.optional (types.shellPackage.check config.users.defaultUserShell) + config.users.defaultUserShell; + + environment.etc = + [ { # /etc/login.defs: global configuration for pwdutils. You + # cannot login without it! + source = pkgs.writeText "login.defs" loginDefs; + target = "login.defs"; + } + + { # /etc/default/useradd: configuration for useradd. + source = pkgs.writeText "useradd" + '' + GROUP=100 + HOME=/home + SHELL=${utils.toShellPath config.users.defaultUserShell} + ''; + target = "default/useradd"; + } + ]; + + security.pam.services = + { chsh = { rootOK = true; }; + chfn = { rootOK = true; }; + su = { rootOK = true; forwardXAuth = true; logFailures = true; }; + passwd = {}; + # Note: useradd, groupadd etc. aren't setuid root, so it + # doesn't really matter what the PAM config says as long as it + # lets root in. + useradd = { rootOK = true; }; + usermod = { rootOK = true; }; + userdel = { rootOK = true; }; + groupadd = { rootOK = true; }; + groupmod = { rootOK = true; }; + groupmems = { rootOK = true; }; + groupdel = { rootOK = true; }; + login = { startSession = true; allowNullPassword = true; showMotd = true; updateWtmp = true; }; + chpasswd = { rootOK = true; }; + }; + + security.wrappers = { + su.source = "${pkgs.shadow.su}/bin/su"; + sg.source = "${pkgs.shadow.out}/bin/sg"; + newgrp.source = "${pkgs.shadow.out}/bin/newgrp"; + newuidmap.source = "${pkgs.shadow.out}/bin/newuidmap"; + newgidmap.source = "${pkgs.shadow.out}/bin/newgidmap"; + } // (if config.users.mutableUsers then { + passwd.source = "${pkgs.shadow.out}/bin/passwd"; + } else {}); + }; +} diff --git a/nixpkgs/nixos/modules/programs/shell.nix b/nixpkgs/nixos/modules/programs/shell.nix new file mode 100644 index 000000000000..b7f7b91b5fbe --- /dev/null +++ b/nixpkgs/nixos/modules/programs/shell.nix @@ -0,0 +1,54 @@ +# This module defines a standard configuration for NixOS shells. + +{ config, lib, ... }: + +with lib; + +{ + + config = { + + environment.shellInit = + '' + # Set up the per-user profile. + mkdir -m 0755 -p "$NIX_USER_PROFILE_DIR" + if [ "$(stat -c '%u' "$NIX_USER_PROFILE_DIR")" != "$(id -u)" ]; then + echo "WARNING: the per-user profile dir $NIX_USER_PROFILE_DIR should belong to user id $(id -u)" >&2 + fi + + if [ -w "$HOME" ]; then + if ! [ -L "$HOME/.nix-profile" ]; then + if [ "$USER" != root ]; then + ln -s "$NIX_USER_PROFILE_DIR/profile" "$HOME/.nix-profile" + else + # Root installs in the system-wide profile by default. + ln -s /nix/var/nix/profiles/default "$HOME/.nix-profile" + fi + fi + + # Subscribe the root user to the NixOS channel by default. + if [ "$USER" = root -a ! -e "$HOME/.nix-channels" ]; then + echo "${config.system.defaultChannel} nixos" > "$HOME/.nix-channels" + fi + + # Create the per-user garbage collector roots directory. + NIX_USER_GCROOTS_DIR="/nix/var/nix/gcroots/per-user/$USER" + mkdir -m 0755 -p "$NIX_USER_GCROOTS_DIR" + if [ "$(stat -c '%u' "$NIX_USER_GCROOTS_DIR")" != "$(id -u)" ]; then + echo "WARNING: the per-user gcroots dir $NIX_USER_GCROOTS_DIR should belong to user id $(id -u)" >&2 + fi + + # Set up a default Nix expression from which to install stuff. + if [ ! -e "$HOME/.nix-defexpr" -o -L "$HOME/.nix-defexpr" ]; then + rm -f "$HOME/.nix-defexpr" + mkdir -p "$HOME/.nix-defexpr" + if [ "$USER" != root ]; then + ln -s /nix/var/nix/profiles/per-user/root/channels "$HOME/.nix-defexpr/channels_root" + fi + fi + fi + ''; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/singularity.nix b/nixpkgs/nixos/modules/programs/singularity.nix new file mode 100644 index 000000000000..b27e122bd1d9 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/singularity.nix @@ -0,0 +1,29 @@ +{ config, pkgs, lib, ... }: + +with lib; +let + cfg = config.programs.singularity; + singularity = pkgs.singularity.overrideAttrs (attrs : { + installPhase = attrs.installPhase + '' + mv $bin/libexec/singularity/bin/starter-suid $bin/libexec/singularity/bin/starter-suid.orig + ln -s /run/wrappers/bin/singularity-suid $bin/libexec/singularity/bin/starter-suid + ''; + }); +in { + options.programs.singularity = { + enable = mkEnableOption "Singularity"; + }; + + config = mkIf cfg.enable { + environment.systemPackages = [ singularity ]; + security.wrappers.singularity-suid.source = "${singularity}/libexec/singularity/bin/starter-suid.orig"; + systemd.tmpfiles.rules = [ + "d /var/singularity/mnt/session 0770 root root -" + "d /var/singularity/mnt/final 0770 root root -" + "d /var/singularity/mnt/overlay 0770 root root -" + "d /var/singularity/mnt/container 0770 root root -" + "d /var/singularity/mnt/source 0770 root root -" + ]; + }; + +} diff --git a/nixpkgs/nixos/modules/programs/slock.nix b/nixpkgs/nixos/modules/programs/slock.nix new file mode 100644 index 000000000000..0e1281e62cd7 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/slock.nix @@ -0,0 +1,26 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.slock; + +in +{ + options = { + programs.slock = { + enable = mkOption { + default = false; + type = types.bool; + description = '' + Whether to install slock screen locker with setuid wrapper. + ''; + }; + }; + }; + + config = mkIf cfg.enable { + environment.systemPackages = [ pkgs.slock ]; + security.wrappers.slock.source = "${pkgs.slock.out}/bin/slock"; + }; +} diff --git a/nixpkgs/nixos/modules/programs/spacefm.nix b/nixpkgs/nixos/modules/programs/spacefm.nix new file mode 100644 index 000000000000..6d03608402fc --- /dev/null +++ b/nixpkgs/nixos/modules/programs/spacefm.nix @@ -0,0 +1,55 @@ +# Global configuration for spacefm. + +{ config, lib, pkgs, ... }: + +with lib; + +let cfg = config.programs.spacefm; + +in +{ + ###### interface + + options = { + + programs.spacefm = { + + enable = mkOption { + type = types.bool; + default = false; + description = '' + Whether to install SpaceFM and create <filename>/etc/spacefm/spacefm.conf</filename>. + ''; + }; + + settings = mkOption { + type = types.attrs; + default = { + tmp_dir = "/tmp"; + terminal_su = "${pkgs.sudo}/bin/sudo"; + graphical_su = "${pkgs.gksu}/bin/gksu"; + }; + example = literalExample ''{ + tmp_dir = "/tmp"; + terminal_su = "''${pkgs.sudo}/bin/sudo"; + graphical_su = "''${pkgs.gksu}/bin/gksu"; + }''; + description = '' + The system-wide spacefm configuration. + Parameters to be written to <filename>/etc/spacefm/spacefm.conf</filename>. + Refer to the <link xlink:href="https://ignorantguru.github.io/spacefm/spacefm-manual-en.html#programfiles-etc">relevant entry</link> in the SpaceFM manual. + ''; + }; + + }; + }; + + ###### implementation + + config = mkIf cfg.enable { + environment.systemPackages = [ pkgs.spaceFM ]; + + environment.etc."spacefm/spacefm.conf".text = + concatStrings (mapAttrsToList (n: v: "${n}=${toString v}\n") cfg.settings); + }; +} diff --git a/nixpkgs/nixos/modules/programs/ssh.nix b/nixpkgs/nixos/modules/programs/ssh.nix new file mode 100644 index 000000000000..733b8f7636fd --- /dev/null +++ b/nixpkgs/nixos/modules/programs/ssh.nix @@ -0,0 +1,267 @@ +# Global configuration for the SSH client. + +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfg = config.programs.ssh; + + askPassword = cfg.askPassword; + + askPasswordWrapper = pkgs.writeScript "ssh-askpass-wrapper" + '' + #! ${pkgs.runtimeShell} -e + export DISPLAY="$(systemctl --user show-environment | ${pkgs.gnused}/bin/sed 's/^DISPLAY=\(.*\)/\1/; t; d')" + exec ${askPassword} + ''; + + knownHosts = map (h: getAttr h cfg.knownHosts) (attrNames cfg.knownHosts); + + knownHostsText = (flip (concatMapStringsSep "\n") knownHosts + (h: assert h.hostNames != []; + optionalString h.certAuthority "@cert-authority " + concatStringsSep "," h.hostNames + " " + + (if h.publicKey != null then h.publicKey else readFile h.publicKeyFile) + )) + "\n"; + +in +{ + ###### interface + + options = { + + programs.ssh = { + + askPassword = mkOption { + type = types.str; + default = "${pkgs.x11_ssh_askpass}/libexec/x11-ssh-askpass"; + description = ''Program used by SSH to ask for passwords.''; + }; + + forwardX11 = mkOption { + type = types.bool; + default = false; + description = '' + Whether to request X11 forwarding on outgoing connections by default. + This is useful for running graphical programs on the remote machine and have them display to your local X11 server. + Historically, this value has depended on the value used by the local sshd daemon, but there really isn't a relation between the two. + Note: there are some security risks to forwarding an X11 connection. + NixOS's X server is built with the SECURITY extension, which prevents some obvious attacks. + To enable or disable forwarding on a per-connection basis, see the -X and -x options to ssh. + The -Y option to ssh enables trusted forwarding, which bypasses the SECURITY extension. + ''; + }; + + setXAuthLocation = mkOption { + type = types.bool; + description = '' + Whether to set the path to <command>xauth</command> for X11-forwarded connections. + This causes a dependency on X11 packages. + ''; + }; + + # Allow DSA keys for now. (These were deprecated in OpenSSH 7.0.) + pubkeyAcceptedKeyTypes = mkOption { + type = types.listOf types.str; + default = [ + "+ssh-dss" + ]; + example = [ "ssh-ed25519" "ssh-rsa" ]; + description = '' + Specifies the key types that will be used for public key authentication. + ''; + }; + + hostKeyAlgorithms = mkOption { + type = types.listOf types.str; + default = [ + "+ssh-dss" + ]; + example = [ "ssh-ed25519" "ssh-rsa" ]; + description = '' + Specifies the host key algorithms that the client wants to use in order of preference. + ''; + }; + + extraConfig = mkOption { + type = types.lines; + default = ""; + description = '' + Extra configuration text prepended to <filename>ssh_config</filename>. Other generated + options will be added after a <code>Host *</code> pattern. + See <citerefentry><refentrytitle>ssh_config</refentrytitle><manvolnum>5</manvolnum></citerefentry> + for help. + ''; + }; + + startAgent = mkOption { + type = types.bool; + default = false; + description = '' + Whether to start the OpenSSH agent when you log in. The OpenSSH agent + remembers private keys for you so that you don't have to type in + passphrases every time you make an SSH connection. Use + <command>ssh-add</command> to add a key to the agent. + ''; + }; + + agentTimeout = mkOption { + type = types.nullOr types.str; + default = null; + example = "1h"; + description = '' + How long to keep the private keys in memory. Use null to keep them forever. + ''; + }; + + package = mkOption { + type = types.package; + default = pkgs.openssh; + defaultText = "pkgs.openssh"; + description = '' + The package used for the openssh client and daemon. + ''; + }; + + knownHosts = mkOption { + default = {}; + type = types.loaOf (types.submodule ({ name, ... }: { + options = { + certAuthority = mkOption { + type = types.bool; + default = false; + description = '' + This public key is an SSH certificate authority, rather than an + individual host's key. + ''; + }; + hostNames = mkOption { + type = types.listOf types.str; + default = []; + description = '' + A list of host names and/or IP numbers used for accessing + the host's ssh service. + ''; + }; + publicKey = mkOption { + default = null; + type = types.nullOr types.str; + example = "ecdsa-sha2-nistp521 AAAAE2VjZHN...UEPg=="; + description = '' + The public key data for the host. You can fetch a public key + from a running SSH server with the <command>ssh-keyscan</command> + command. The public key should not include any host names, only + the key type and the key itself. + ''; + }; + publicKeyFile = mkOption { + default = null; + type = types.nullOr types.path; + description = '' + The path to the public key file for the host. The public + key file is read at build time and saved in the Nix store. + You can fetch a public key file from a running SSH server + with the <command>ssh-keyscan</command> command. The content + of the file should follow the same format as described for + the <literal>publicKey</literal> option. + ''; + }; + }; + config = { + hostNames = mkDefault [ name ]; + }; + })); + description = '' + The set of system-wide known SSH hosts. + ''; + example = literalExample '' + { + myhost = { + hostNames = [ "myhost" "myhost.mydomain.com" "10.10.1.4" ]; + publicKeyFile = ./pubkeys/myhost_ssh_host_dsa_key.pub; + }; + myhost2 = { + hostNames = [ "myhost2" ]; + publicKeyFile = ./pubkeys/myhost2_ssh_host_dsa_key.pub; + }; + } + ''; + }; + + }; + + }; + + config = { + + programs.ssh.setXAuthLocation = + mkDefault (config.services.xserver.enable || config.programs.ssh.forwardX11 || config.services.openssh.forwardX11); + + assertions = + [ { assertion = cfg.forwardX11 -> cfg.setXAuthLocation; + message = "cannot enable X11 forwarding without setting XAuth location"; + } + ] ++ flip mapAttrsToList cfg.knownHosts (name: data: { + assertion = (data.publicKey == null && data.publicKeyFile != null) || + (data.publicKey != null && data.publicKeyFile == null); + message = "knownHost ${name} must contain either a publicKey or publicKeyFile"; + }); + + # SSH configuration. Slight duplication of the sshd_config + # generation in the sshd service. + environment.etc."ssh/ssh_config".text = + '' + # Custom options from `extraConfig`, to override generated options + ${cfg.extraConfig} + + # Generated options from other settings + Host * + AddressFamily ${if config.networking.enableIPv6 then "any" else "inet"} + + ${optionalString cfg.setXAuthLocation '' + XAuthLocation ${pkgs.xorg.xauth}/bin/xauth + ''} + + ForwardX11 ${if cfg.forwardX11 then "yes" else "no"} + + ${optionalString (cfg.pubkeyAcceptedKeyTypes != []) "PubkeyAcceptedKeyTypes ${concatStringsSep "," cfg.pubkeyAcceptedKeyTypes}"} + ${optionalString (cfg.hostKeyAlgorithms != []) "HostKeyAlgorithms ${concatStringsSep "," cfg.hostKeyAlgorithms}"} + ''; + + environment.etc."ssh/ssh_known_hosts".text = knownHostsText; + + # FIXME: this should really be socket-activated for über-awesomeness. + systemd.user.services.ssh-agent = mkIf cfg.startAgent + { description = "SSH Agent"; + wantedBy = [ "default.target" ]; + unitConfig.ConditionUser = "!@system"; + serviceConfig = + { ExecStartPre = "${pkgs.coreutils}/bin/rm -f %t/ssh-agent"; + ExecStart = + "${cfg.package}/bin/ssh-agent " + + optionalString (cfg.agentTimeout != null) ("-t ${cfg.agentTimeout} ") + + "-a %t/ssh-agent"; + StandardOutput = "null"; + Type = "forking"; + Restart = "on-failure"; + SuccessExitStatus = "0 2"; + }; + # Allow ssh-agent to ask for confirmation. This requires the + # unit to know about the user's $DISPLAY (via ‘systemctl + # import-environment’). + environment.SSH_ASKPASS = optionalString config.services.xserver.enable askPasswordWrapper; + environment.DISPLAY = "fake"; # required to make ssh-agent start $SSH_ASKPASS + }; + + environment.extraInit = optionalString cfg.startAgent + '' + if [ -z "$SSH_AUTH_SOCK" -a -n "$XDG_RUNTIME_DIR" ]; then + export SSH_AUTH_SOCK="$XDG_RUNTIME_DIR/ssh-agent" + fi + ''; + + environment.variables.SSH_ASKPASS = optionalString config.services.xserver.enable askPassword; + + }; +} diff --git a/nixpkgs/nixos/modules/programs/ssmtp.nix b/nixpkgs/nixos/modules/programs/ssmtp.nix new file mode 100644 index 000000000000..0e060e3f5226 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/ssmtp.nix @@ -0,0 +1,165 @@ +# Configuration for `ssmtp', a trivial mail transfer agent that can +# replace sendmail/postfix on simple systems. It delivers email +# directly to an SMTP server defined in its configuration file, wihout +# queueing mail locally. + +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfg = config.networking.defaultMailServer; + +in + +{ + + options = { + + networking.defaultMailServer = { + + directDelivery = mkOption { + type = types.bool; + default = false; + description = '' + Use the trivial Mail Transfer Agent (MTA) + <command>ssmtp</command> package to allow programs to send + e-mail. If you don't want to run a “real” MTA like + <command>sendmail</command> or <command>postfix</command> on + your machine, set this option to <literal>true</literal>, and + set the option + <option>networking.defaultMailServer.hostName</option> to the + host name of your preferred mail server. + ''; + }; + + hostName = mkOption { + type = types.str; + example = "mail.example.org"; + description = '' + The host name of the default mail server to use to deliver + e-mail. Can also contain a port number (ex: mail.example.org:587), + defaults to port 25 if no port is given. + ''; + }; + + root = mkOption { + type = types.str; + default = ""; + example = "root@example.org"; + description = '' + The e-mail to which mail for users with UID < 1000 is forwarded. + ''; + }; + + domain = mkOption { + type = types.str; + default = ""; + example = "example.org"; + description = '' + The domain from which mail will appear to be sent. + ''; + }; + + useTLS = mkOption { + type = types.bool; + default = false; + description = '' + Whether TLS should be used to connect to the default mail + server. + ''; + }; + + useSTARTTLS = mkOption { + type = types.bool; + default = false; + description = '' + Whether the STARTTLS should be used to connect to the default + mail server. (This is needed for TLS-capable mail servers + running on the default SMTP port 25.) + ''; + }; + + authUser = mkOption { + type = types.str; + default = ""; + example = "foo@example.org"; + description = '' + Username used for SMTP auth. Leave blank to disable. + ''; + }; + + authPass = mkOption { + type = types.str; + default = ""; + example = "correctHorseBatteryStaple"; + description = '' + Password used for SMTP auth. (STORED PLAIN TEXT, WORLD-READABLE IN NIX STORE) + + It's recommended to use <option>authPassFile</option> + which takes precedence over <option>authPass</option>. + ''; + }; + + authPassFile = mkOption { + type = types.nullOr types.str; + default = null; + example = "/run/keys/ssmtp-authpass"; + description = '' + Path to a file that contains the password used for SMTP auth. The file + should not contain a trailing newline, if the password does not contain one. + This file should be readable by the users that need to execute ssmtp. + + <option>authPassFile</option> takes precedence over <option>authPass</option>. + + Warning: when <option>authPass</option> is non-empty <option>authPassFile</option> + defaults to a file in the WORLD-READABLE Nix store containing that password. + ''; + }; + + setSendmail = mkOption { + type = types.bool; + default = true; + description = "Whether to set the system sendmail to ssmtp's."; + }; + + }; + + }; + + + config = mkIf cfg.directDelivery { + + networking.defaultMailServer.authPassFile = mkIf (cfg.authPass != "") + (mkDefault (toString (pkgs.writeTextFile { + name = "ssmtp-authpass"; + text = cfg.authPass; + }))); + + environment.etc."ssmtp/ssmtp.conf".text = + let yesNo = yes : if yes then "YES" else "NO"; in + '' + MailHub=${cfg.hostName} + FromLineOverride=YES + ${optionalString (cfg.root != "") "root=${cfg.root}"} + ${optionalString (cfg.domain != "") "rewriteDomain=${cfg.domain}"} + UseTLS=${yesNo cfg.useTLS} + UseSTARTTLS=${yesNo cfg.useSTARTTLS} + #Debug=YES + ${optionalString (cfg.authUser != "") "AuthUser=${cfg.authUser}"} + ${optionalString (cfg.authPassFile != null) "AuthPassFile=${cfg.authPassFile}"} + ''; + + environment.systemPackages = [pkgs.ssmtp]; + + services.mail.sendmailSetuidWrapper = mkIf cfg.setSendmail { + program = "sendmail"; + source = "${pkgs.ssmtp}/bin/sendmail"; + setuid = false; + setgid = false; + }; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/sway.nix b/nixpkgs/nixos/modules/programs/sway.nix new file mode 100644 index 000000000000..b4f03151cdc1 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/sway.nix @@ -0,0 +1,93 @@ +{ config, pkgs, lib, ... }: + +with lib; + +let + cfg = config.programs.sway; + swayPackage = pkgs.sway; + + swayWrapped = pkgs.writeShellScriptBin "sway" '' + set -o errexit + + if [ ! "$_SWAY_WRAPPER_ALREADY_EXECUTED" ]; then + export _SWAY_WRAPPER_ALREADY_EXECUTED=1 + ${cfg.extraSessionCommands} + fi + + if [ "$DBUS_SESSION_BUS_ADDRESS" ]; then + export DBUS_SESSION_BUS_ADDRESS + exec ${swayPackage}/bin/sway "$@" + else + exec ${pkgs.dbus}/bin/dbus-run-session ${swayPackage}/bin/sway "$@" + fi + ''; + swayJoined = pkgs.symlinkJoin { + name = "sway-joined"; + paths = [ swayWrapped swayPackage ]; + }; +in { + options.programs.sway = { + enable = mkEnableOption '' + Sway, the i3-compatible tiling Wayland compositor. You can manually launch + Sway by executing "exec sway" on a TTY. Copy /etc/sway/config to + ~/.config/sway/config to modify the default configuration. See + https://github.com/swaywm/sway/wiki and "man 5 sway" for more information. + Please have a look at the "extraSessionCommands" example for running + programs natively under Wayland''; + + extraSessionCommands = mkOption { + type = types.lines; + default = ""; + example = '' + export SDL_VIDEODRIVER=wayland + # needs qt5.qtwayland in systemPackages + export QT_QPA_PLATFORM=wayland + export QT_WAYLAND_DISABLE_WINDOWDECORATION="1" + # Fix for some Java AWT applications (e.g. Android Studio), + # use this if they aren't displayed properly: + export _JAVA_AWT_WM_NONREPARENTING=1 + ''; + description = '' + Shell commands executed just before Sway is started. + ''; + }; + + extraPackages = mkOption { + type = with types; listOf package; + default = with pkgs; [ + swaylock swayidle + xwayland rxvt_unicode dmenu + ]; + defaultText = literalExample '' + with pkgs; [ swaylock swayidle xwayland rxvt_unicode dmenu ]; + ''; + example = literalExample '' + with pkgs; [ + xwayland + i3status i3status-rust + termite rofi light + ] + ''; + description = '' + Extra packages to be installed system wide. + ''; + }; + }; + + config = mkIf cfg.enable { + environment = { + systemPackages = [ swayJoined ] ++ cfg.extraPackages; + etc = { + "sway/config".source = mkOptionDefault "${swayPackage}/etc/sway/config"; + #"sway/security.d".source = mkOptionDefault "${swayPackage}/etc/sway/security.d/"; + #"sway/config.d".source = mkOptionDefault "${swayPackage}/etc/sway/config.d/"; + }; + }; + security.pam.services.swaylock = {}; + hardware.opengl.enable = mkDefault true; + fonts.enableDefaultFonts = mkDefault true; + programs.dconf.enable = mkDefault true; + }; + + meta.maintainers = with lib.maintainers; [ gnidorah primeos colemickens ]; +} diff --git a/nixpkgs/nixos/modules/programs/sysdig.nix b/nixpkgs/nixos/modules/programs/sysdig.nix new file mode 100644 index 000000000000..fbbf29065564 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/sysdig.nix @@ -0,0 +1,14 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.sysdig; +in { + options.programs.sysdig.enable = mkEnableOption "sysdig"; + + config = mkIf cfg.enable { + environment.systemPackages = [ pkgs.sysdig ]; + boot.extraModulePackages = [ config.boot.kernelPackages.sysdig ]; + }; +} diff --git a/nixpkgs/nixos/modules/programs/systemtap.nix b/nixpkgs/nixos/modules/programs/systemtap.nix new file mode 100644 index 000000000000..ca81e018c9dc --- /dev/null +++ b/nixpkgs/nixos/modules/programs/systemtap.nix @@ -0,0 +1,28 @@ +{ config, lib, ... }: + +with lib; + +let cfg = config.programs.systemtap; +in { + + options = { + programs.systemtap = { + enable = mkOption { + default = false; + description = '' + Install <command>systemtap</command> along with necessary kernel options. + ''; + }; + }; + }; + config = mkIf cfg.enable { + system.requiredKernelConfig = with config.lib.kernelConfig; [ + (isYes "DEBUG") + ]; + boot.kernel.features.debug = true; + environment.systemPackages = [ + config.boot.kernelPackages.systemtap + ]; + }; + +} diff --git a/nixpkgs/nixos/modules/programs/thefuck.nix b/nixpkgs/nixos/modules/programs/thefuck.nix new file mode 100644 index 000000000000..21ed6603c1bd --- /dev/null +++ b/nixpkgs/nixos/modules/programs/thefuck.nix @@ -0,0 +1,39 @@ +{ config, pkgs, lib, ... }: + +with lib; + +let + prg = config.programs; + cfg = prg.thefuck; + + initScript = '' + eval $(${pkgs.thefuck}/bin/thefuck --alias ${cfg.alias}) + ''; +in + { + options = { + programs.thefuck = { + enable = mkEnableOption "thefuck"; + + alias = mkOption { + default = "fuck"; + type = types.string; + + description = '' + `thefuck` needs an alias to be configured. + The default value is `fuck`, but you can use anything else as well. + ''; + }; + }; + }; + + config = mkIf cfg.enable { + environment.systemPackages = with pkgs; [ thefuck ]; + + programs.bash.interactiveShellInit = initScript; + programs.zsh.interactiveShellInit = mkIf prg.zsh.enable initScript; + programs.fish.interactiveShellInit = mkIf prg.fish.enable '' + ${pkgs.thefuck}/bin/thefuck --alias | source + ''; + }; + } diff --git a/nixpkgs/nixos/modules/programs/tmux.nix b/nixpkgs/nixos/modules/programs/tmux.nix new file mode 100644 index 000000000000..ed077e3daa76 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/tmux.nix @@ -0,0 +1,184 @@ +{ config, pkgs, lib, ... }: + +let + inherit (lib) mkOption mkIf types; + + cfg = config.programs.tmux; + + defaultKeyMode = "emacs"; + defaultResize = 5; + defaultShortcut = "b"; + defaultTerminal = "screen"; + + boolToStr = value: if value then "on" else "off"; + + tmuxConf = '' + set -g default-terminal "${cfg.terminal}" + set -g base-index ${toString cfg.baseIndex} + setw -g pane-base-index ${toString cfg.baseIndex} + + ${if cfg.newSession then "new-session" else ""} + + ${if cfg.reverseSplit then '' + bind v split-window -h + bind s split-window -v + '' else ""} + + set -g status-keys ${cfg.keyMode} + set -g mode-keys ${cfg.keyMode} + + ${if cfg.keyMode == "vi" && cfg.customPaneNavigationAndResize then '' + bind h select-pane -L + bind j select-pane -D + bind k select-pane -U + bind l select-pane -R + + bind -r H resize-pane -L ${toString cfg.resizeAmount} + bind -r J resize-pane -D ${toString cfg.resizeAmount} + bind -r K resize-pane -U ${toString cfg.resizeAmount} + bind -r L resize-pane -R ${toString cfg.resizeAmount} + '' else ""} + + ${if (cfg.shortcut != defaultShortcut) then '' + # rebind main key: C-${cfg.shortcut} + unbind C-${defaultShortcut} + set -g prefix C-${cfg.shortcut} + bind ${cfg.shortcut} send-prefix + bind C-${cfg.shortcut} last-window + '' else ""} + + setw -g aggressive-resize ${boolToStr cfg.aggressiveResize} + setw -g clock-mode-style ${if cfg.clock24 then "24" else "12"} + set -s escape-time ${toString cfg.escapeTime} + set -g history-limit ${toString cfg.historyLimit} + + ${cfg.extraTmuxConf} + ''; + +in { + ###### interface + + options = { + programs.tmux = { + + enable = mkOption { + type = types.bool; + default = false; + description = "Whenever to configure <command>tmux</command> system-wide."; + relatedPackages = [ "tmux" ]; + }; + + aggressiveResize = mkOption { + default = false; + type = types.bool; + description = '' + Resize the window to the size of the smallest session for which it is the current window. + ''; + }; + + baseIndex = mkOption { + default = 0; + example = 1; + type = types.int; + description = "Base index for windows and panes."; + }; + + clock24 = mkOption { + default = false; + type = types.bool; + description = "Use 24 hour clock."; + }; + + customPaneNavigationAndResize = mkOption { + default = false; + type = types.bool; + description = "Override the hjkl and HJKL bindings for pane navigation and resizing in VI mode."; + }; + + escapeTime = mkOption { + default = 500; + example = 0; + type = types.int; + description = "Time in milliseconds for which tmux waits after an escape is input."; + }; + + extraTmuxConf = mkOption { + default = ""; + description = '' + Additional contents of /etc/tmux.conf + ''; + type = types.lines; + }; + + historyLimit = mkOption { + default = 2000; + example = 5000; + type = types.int; + description = "Maximum number of lines held in window history."; + }; + + keyMode = mkOption { + default = defaultKeyMode; + example = "vi"; + type = types.enum [ "emacs" "vi" ]; + description = "VI or Emacs style shortcuts."; + }; + + newSession = mkOption { + default = false; + type = types.bool; + description = "Automatically spawn a session if trying to attach and none are running."; + }; + + reverseSplit = mkOption { + default = false; + type = types.bool; + description = "Reverse the window split shortcuts."; + }; + + resizeAmount = mkOption { + default = defaultResize; + example = 10; + type = types.int; + description = "Number of lines/columns when resizing."; + }; + + shortcut = mkOption { + default = defaultShortcut; + example = "a"; + type = types.str; + description = "Ctrl following by this key is used as the main shortcut."; + }; + + terminal = mkOption { + default = defaultTerminal; + example = "screen-256color"; + type = types.str; + description = "Set the $TERM variable."; + }; + + secureSocket = mkOption { + default = true; + type = types.bool; + description = '' + Store tmux socket under /run, which is more secure than /tmp, but as a + downside it doesn't survive user logout. + ''; + }; + }; + }; + + ###### implementation + + config = mkIf cfg.enable { + environment = { + etc."tmux.conf".text = tmuxConf; + + systemPackages = [ pkgs.tmux ]; + + variables = { + TMUX_TMPDIR = lib.optional cfg.secureSocket ''''${XDG_RUNTIME_DIR:-"/run/user/$(id -u)"}''; + }; + }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/tsm-client.nix b/nixpkgs/nixos/modules/programs/tsm-client.nix new file mode 100644 index 000000000000..eb6f12475286 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/tsm-client.nix @@ -0,0 +1,287 @@ +{ config, lib, pkgs, ... }: + +let + + inherit (builtins) length map; + inherit (lib.attrsets) attrNames filterAttrs hasAttr mapAttrs mapAttrsToList optionalAttrs; + inherit (lib.modules) mkDefault mkIf; + inherit (lib.options) literalExample mkEnableOption mkOption; + inherit (lib.strings) concatStringsSep optionalString toLower; + inherit (lib.types) addCheck attrsOf lines loaOf nullOr package path port str strMatching submodule; + + # Checks if given list of strings contains unique + # elements when compared without considering case. + # Type: checkIUnique :: [string] -> bool + # Example: checkIUnique ["foo" "Foo"] => false + checkIUnique = lst: + let + lenUniq = l: length (lib.lists.unique l); + in + lenUniq lst == lenUniq (map toLower lst); + + # TSM rejects servername strings longer than 64 chars. + servernameType = strMatching ".{1,64}"; + + serverOptions = { name, config, ... }: { + options.name = mkOption { + type = servernameType; + example = "mainTsmServer"; + description = '' + Local name of the IBM TSM server, + must be uncapitalized and no longer than 64 chars. + The value will be used for the + <literal>server</literal> + directive in <filename>dsm.sys</filename>. + ''; + }; + options.server = mkOption { + type = strMatching ".+"; + example = "tsmserver.company.com"; + description = '' + Host/domain name or IP address of the IBM TSM server. + The value will be used for the + <literal>tcpserveraddress</literal> + directive in <filename>dsm.sys</filename>. + ''; + }; + options.port = mkOption { + type = addCheck port (p: p<=32767); + default = 1500; # official default + description = '' + TCP port of the IBM TSM server. + The value will be used for the + <literal>tcpport</literal> + directive in <filename>dsm.sys</filename>. + TSM does not support ports above 32767. + ''; + }; + options.node = mkOption { + type = strMatching ".+"; + example = "MY-TSM-NODE"; + description = '' + Target node name on the IBM TSM server. + The value will be used for the + <literal>nodename</literal> + directive in <filename>dsm.sys</filename>. + ''; + }; + options.genPasswd = mkEnableOption '' + automatic client password generation. + This option influences the + <literal>passwordaccess</literal> + directive in <filename>dsm.sys</filename>. + The password will be stored in the directory + given by the option <option>passwdDir</option>. + <emphasis>Caution</emphasis>: + If this option is enabled and the server forces + to renew the password (e.g. on first connection), + a random password will be generated and stored + ''; + options.passwdDir = mkOption { + type = path; + example = "/home/alice/tsm-password"; + description = '' + Directory that holds the TSM + node's password information. + The value will be used for the + <literal>passworddir</literal> + directive in <filename>dsm.sys</filename>. + ''; + }; + options.includeExclude = mkOption { + type = lines; + default = ""; + example = '' + exclude.dir /nix/store + include.encrypt /home/.../* + ''; + description = '' + <literal>include.*</literal> and + <literal>exclude.*</literal> directives to be + used when sending files to the IBM TSM server. + The lines will be written into a file that the + <literal>inclexcl</literal> + directive in <filename>dsm.sys</filename> points to. + ''; + }; + options.extraConfig = mkOption { + # TSM option keys are case insensitive; + # we have to ensure there are no keys that + # differ only by upper and lower case. + type = addCheck + (attrsOf (nullOr str)) + (attrs: checkIUnique (attrNames attrs)); + default = {}; + example.compression = "yes"; + example.passwordaccess = null; + description = '' + Additional key-value pairs for the server stanza. + Values must be strings, or <literal>null</literal> + for the key not to be used in the stanza + (e.g. to overrule values generated by other options). + ''; + }; + options.text = mkOption { + type = lines; + example = literalExample + ''lib.modules.mkAfter "compression no"''; + description = '' + Additional text lines for the server stanza. + This option can be used if certion configuration keys + must be used multiple times or ordered in a certain way + as the <option>extraConfig</option> option can't + control the order of lines in the resulting stanza. + Note that the <literal>server</literal> + line at the beginning of the stanza is + not part of this option's value. + ''; + }; + options.stanza = mkOption { + type = str; + internal = true; + visible = false; + description = "Server stanza text generated from the options."; + }; + config.name = mkDefault name; + # Client system-options file directives are explained here: + # https://www.ibm.com/support/knowledgecenter/SSEQVQ_8.1.8/client/c_opt_usingopts.html + config.extraConfig = + mapAttrs (lib.trivial.const mkDefault) ( + { + commmethod = "v6tcpip"; # uses v4 or v6, based on dns lookup result + tcpserveraddress = config.server; + tcpport = builtins.toString config.port; + nodename = config.node; + passwordaccess = if config.genPasswd then "generate" else "prompt"; + passworddir = ''"${config.passwdDir}"''; + } // optionalAttrs (config.includeExclude!="") { + inclexcl = ''"${pkgs.writeText "inclexcl.dsm.sys" config.includeExclude}"''; + } + ); + config.text = + let + attrset = filterAttrs (k: v: v!=null) config.extraConfig; + mkLine = k: v: k + optionalString (v!="") " ${v}"; + lines = mapAttrsToList mkLine attrset; + in + concatStringsSep "\n" lines; + config.stanza = '' + server ${config.name} + ${config.text} + ''; + }; + + options.programs.tsmClient = { + enable = mkEnableOption '' + IBM Spectrum Protect (Tivoli Storage Manager, TSM) + client command line applications with a + client system-options file "dsm.sys" + ''; + servers = mkOption { + type = loaOf (submodule [ serverOptions ]); + default = {}; + example.mainTsmServer = { + server = "tsmserver.company.com"; + node = "MY-TSM-NODE"; + extraConfig.compression = "yes"; + }; + description = '' + Server definitions ("stanzas") + for the client system-options file. + ''; + }; + defaultServername = mkOption { + type = nullOr servernameType; + default = null; + example = "mainTsmServer"; + description = '' + If multiple server stanzas are declared with + <option>programs.tsmClient.servers</option>, + this option may be used to name a default + server stanza that IBM TSM uses in the absence of + a user-defined <filename>dsm.opt</filename> file. + This option translates to a + <literal>defaultserver</literal> configuration line. + ''; + }; + dsmSysText = mkOption { + type = lines; + readOnly = true; + description = '' + This configuration key contains the effective text + of the client system-options file "dsm.sys". + It should not be changed, but may be + used to feed the configuration into other + TSM-depending packages used on the system. + ''; + }; + package = mkOption { + type = package; + default = pkgs.tsm-client; + defaultText = "pkgs.tsm-client"; + example = literalExample "pkgs.tsm-client-withGui"; + description = '' + The TSM client derivation to be + added to the system environment. + It will called with <literal>.override</literal> + to add paths to the client system-options file. + ''; + }; + wrappedPackage = mkOption { + type = package; + readOnly = true; + description = '' + The TSM client derivation, wrapped with the path + to the client system-options file "dsm.sys". + This option is to provide the effective derivation + for other modules that want to call TSM executables. + ''; + }; + }; + + cfg = config.programs.tsmClient; + + assertions = [ + { + assertion = checkIUnique (mapAttrsToList (k: v: v.name) cfg.servers); + message = '' + TSM servernames contain duplicate name + (note that case doesn't matter!) + ''; + } + { + assertion = (cfg.defaultServername!=null)->(hasAttr cfg.defaultServername cfg.servers); + message = "TSM defaultServername not found in list of servers"; + } + ]; + + dsmSysText = '' + **** IBM Spectrum Protect (Tivoli Storage Manager) + **** client system-options file "dsm.sys". + **** Do not edit! + **** This file is generated by NixOS configuration. + + ${optionalString (cfg.defaultServername!=null) "defaultserver ${cfg.defaultServername}"} + + ${concatStringsSep "\n" (mapAttrsToList (k: v: v.stanza) cfg.servers)} + ''; + +in + +{ + + inherit options; + + config = mkIf cfg.enable { + inherit assertions; + programs.tsmClient.dsmSysText = dsmSysText; + programs.tsmClient.wrappedPackage = cfg.package.override rec { + dsmSysCli = pkgs.writeText "dsm.sys" cfg.dsmSysText; + dsmSysApi = dsmSysCli; + }; + environment.systemPackages = [ cfg.wrappedPackage ]; + }; + + meta.maintainers = [ lib.maintainers.yarny ]; + +} diff --git a/nixpkgs/nixos/modules/programs/udevil.nix b/nixpkgs/nixos/modules/programs/udevil.nix new file mode 100644 index 000000000000..ba5670f9dfe9 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/udevil.nix @@ -0,0 +1,14 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.udevil; + +in { + options.programs.udevil.enable = mkEnableOption "udevil"; + + config = mkIf cfg.enable { + security.wrappers.udevil.source = "${lib.getBin pkgs.udevil}/bin/udevil"; + }; +} diff --git a/nixpkgs/nixos/modules/programs/venus.nix b/nixpkgs/nixos/modules/programs/venus.nix new file mode 100644 index 000000000000..110570ac3f06 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/venus.nix @@ -0,0 +1,173 @@ +{ config, lib, pkgs, ... }: + +with lib; +let + cfg = config.services.venus; + + configFile = pkgs.writeText "venus.ini" + '' + [Planet] + name = ${cfg.name} + link = ${cfg.link} + owner_name = ${cfg.ownerName} + owner_email = ${cfg.ownerEmail} + output_theme = ${cfg.cacheDirectory}/theme + output_dir = ${cfg.outputDirectory} + cache_directory = ${cfg.cacheDirectory} + items_per_page = ${toString cfg.itemsPerPage} + ${(concatStringsSep "\n\n" + (map ({ name, feedUrl, homepageUrl }: + '' + [${feedUrl}] + name = ${name} + link = ${homepageUrl} + '') cfg.feeds))} + ''; + +in +{ + + options = { + services.venus = { + enable = mkOption { + default = false; + type = types.bool; + description = '' + Planet Venus is an awesome ‘river of news’ feed reader. It downloads + news feeds published by web sites and aggregates their content + together into a single combined feed, latest news first. + ''; + }; + + dates = mkOption { + default = "*:0/15"; + type = types.str; + description = '' + Specification (in the format described by + <citerefentry><refentrytitle>systemd.time</refentrytitle> + <manvolnum>7</manvolnum></citerefentry>) of the time at + which the Venus will collect feeds. + ''; + }; + + user = mkOption { + default = "root"; + type = types.str; + description = '' + User for running venus script. + ''; + }; + + group = mkOption { + default = "root"; + type = types.str; + description = '' + Group for running venus script. + ''; + }; + + name = mkOption { + default = "NixOS Planet"; + type = types.str; + description = '' + Your planet's name. + ''; + }; + + link = mkOption { + default = "http://planet.nixos.org"; + type = types.str; + description = '' + Link to the main page. + ''; + }; + + ownerName = mkOption { + default = "Rok Garbas"; + type = types.str; + description = '' + Your name. + ''; + }; + + ownerEmail = mkOption { + default = "some@example.com"; + type = types.str; + description = '' + Your e-mail address. + ''; + }; + + outputTheme = mkOption { + default = "${pkgs.venus}/themes/classic_fancy"; + type = types.path; + description = '' + Directory containing a config.ini file which is merged with this one. + This is typically used to specify templating and bill of material + information. + ''; + }; + + outputDirectory = mkOption { + type = types.path; + description = '' + Directory to place output files. + ''; + }; + + cacheDirectory = mkOption { + default = "/var/cache/venus"; + type = types.path; + description = '' + Where cached feeds are stored. + ''; + }; + + itemsPerPage = mkOption { + default = 15; + type = types.int; + description = '' + How many items to put on each page. + ''; + }; + + feeds = mkOption { + default = []; + example = [ + { + name = "Rok Garbas"; + feedUrl= "http://url/to/rss/feed.xml"; + homepageUrl = "http://garbas.si"; + } + ]; + description = '' + List of feeds. + ''; + }; + + }; + }; + + config = mkIf cfg.enable { + + system.activationScripts.venus = + '' + mkdir -p ${cfg.outputDirectory} + chown ${cfg.user}:${cfg.group} ${cfg.outputDirectory} -R + rm -rf ${cfg.cacheDirectory}/theme + mkdir -p ${cfg.cacheDirectory}/theme + cp -R ${cfg.outputTheme}/* ${cfg.cacheDirectory}/theme + chown ${cfg.user}:${cfg.group} ${cfg.cacheDirectory} -R + ''; + + systemd.services.venus = + { description = "Planet Venus Feed Reader"; + path = [ pkgs.venus ]; + script = "exec venus-planet ${configFile}"; + serviceConfig.User = "${cfg.user}"; + serviceConfig.Group = "${cfg.group}"; + startAt = cfg.dates; + }; + + }; +} diff --git a/nixpkgs/nixos/modules/programs/vim.nix b/nixpkgs/nixos/modules/programs/vim.nix new file mode 100644 index 000000000000..fe0e7f2c6d6b --- /dev/null +++ b/nixpkgs/nixos/modules/programs/vim.nix @@ -0,0 +1,23 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.vim; +in { + options.programs.vim = { + defaultEditor = mkOption { + type = types.bool; + default = false; + description = '' + When enabled, installs vim and configures vim to be the default editor + using the EDITOR environment variable. + ''; + }; + }; + + config = mkIf cfg.defaultEditor { + environment.systemPackages = [ pkgs.vim ]; + environment.variables = { EDITOR = mkOverride 900 "vim"; }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/virtualbox.nix b/nixpkgs/nixos/modules/programs/virtualbox.nix new file mode 100644 index 000000000000..be96cf23b396 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/virtualbox.nix @@ -0,0 +1,8 @@ +let + msg = "Importing <nixpkgs/nixos/modules/programs/virtualbox.nix> is " + + "deprecated, please use `virtualisation.virtualbox.host.enable = true' " + + "instead."; +in { + config.warnings = [ msg ]; + config.virtualisation.virtualbox.host.enable = true; +} diff --git a/nixpkgs/nixos/modules/programs/wavemon.nix b/nixpkgs/nixos/modules/programs/wavemon.nix new file mode 100644 index 000000000000..ac665fe4a023 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/wavemon.nix @@ -0,0 +1,28 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.wavemon; +in { + options = { + programs.wavemon = { + enable = mkOption { + type = types.bool; + default = false; + description = '' + Whether to add wavemon to the global environment and configure a + setcap wrapper for it. + ''; + }; + }; + }; + + config = mkIf cfg.enable { + environment.systemPackages = with pkgs; [ wavemon ]; + security.wrappers.wavemon = { + source = "${pkgs.wavemon}/bin/wavemon"; + capabilities = "cap_net_admin+ep"; + }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/way-cooler.nix b/nixpkgs/nixos/modules/programs/way-cooler.nix new file mode 100644 index 000000000000..f27bd42bd764 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/way-cooler.nix @@ -0,0 +1,78 @@ +{ config, pkgs, lib, ... }: + +with lib; + +let + cfg = config.programs.way-cooler; + way-cooler = pkgs.way-cooler; + + wcWrapped = pkgs.writeShellScriptBin "way-cooler" '' + ${cfg.extraSessionCommands} + exec ${pkgs.dbus}/bin/dbus-run-session ${way-cooler}/bin/way-cooler + ''; + wcJoined = pkgs.symlinkJoin { + name = "way-cooler-wrapped"; + paths = [ wcWrapped way-cooler ]; + }; + configFile = readFile "${way-cooler}/etc/way-cooler/init.lua"; + spawnBar = '' + util.program.spawn_at_startup("lemonbar"); + ''; +in +{ + options.programs.way-cooler = { + enable = mkEnableOption "way-cooler"; + + extraSessionCommands = mkOption { + default = ""; + type = types.lines; + example = '' + export XKB_DEFAULT_LAYOUT=us,de + export XKB_DEFAULT_VARIANT=,nodeadkeys + export XKB_DEFAULT_OPTIONS=grp:caps_toggle, + ''; + description = '' + Shell commands executed just before way-cooler is started. + ''; + }; + + extraPackages = mkOption { + type = with types; listOf package; + default = with pkgs; [ + westonLite xwayland dmenu + ]; + example = literalExample '' + with pkgs; [ + westonLite xwayland dmenu + ] + ''; + description = '' + Extra packages to be installed system wide. + ''; + }; + + enableBar = mkOption { + type = types.bool; + default = true; + description = '' + Whether to enable an unofficial bar. + ''; + }; + }; + + config = mkIf cfg.enable { + environment.systemPackages = [ wcJoined ] ++ cfg.extraPackages; + + security.pam.services.wc-lock = {}; + environment.etc."way-cooler/init.lua".text = '' + ${configFile} + ${optionalString cfg.enableBar spawnBar} + ''; + + hardware.opengl.enable = mkDefault true; + fonts.enableDefaultFonts = mkDefault true; + programs.dconf.enable = mkDefault true; + }; + + meta.maintainers = with maintainers; [ gnidorah ]; +} diff --git a/nixpkgs/nixos/modules/programs/waybar.nix b/nixpkgs/nixos/modules/programs/waybar.nix new file mode 100644 index 000000000000..22530e6c7d4d --- /dev/null +++ b/nixpkgs/nixos/modules/programs/waybar.nix @@ -0,0 +1,20 @@ +{ lib, pkgs, config, ... }: + +with lib; + +{ + options.programs.waybar = { + enable = mkEnableOption "waybar"; + }; + + config = mkIf config.programs.waybar.enable { + systemd.user.services.waybar = { + description = "Waybar as systemd service"; + wantedBy = [ "graphical-session.target" ]; + partOf = [ "graphical-session.target" ]; + script = "${pkgs.waybar}/bin/waybar"; + }; + }; + + meta.maintainers = [ maintainers.FlorianFranzen ]; +} diff --git a/nixpkgs/nixos/modules/programs/wireshark.nix b/nixpkgs/nixos/modules/programs/wireshark.nix new file mode 100644 index 000000000000..819f15b98a05 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/wireshark.nix @@ -0,0 +1,42 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.wireshark; + wireshark = cfg.package; +in { + options = { + programs.wireshark = { + enable = mkOption { + type = types.bool; + default = false; + description = '' + Whether to add Wireshark to the global environment and configure a + setcap wrapper for 'dumpcap' for users in the 'wireshark' group. + ''; + }; + package = mkOption { + type = types.package; + default = pkgs.wireshark-cli; + defaultText = "pkgs.wireshark-cli"; + description = '' + Which Wireshark package to install in the global environment. + ''; + }; + }; + }; + + config = mkIf cfg.enable { + environment.systemPackages = [ wireshark ]; + users.groups.wireshark = {}; + + security.wrappers.dumpcap = { + source = "${wireshark}/bin/dumpcap"; + capabilities = "cap_net_raw+p"; + owner = "root"; + group = "wireshark"; + permissions = "u+rx,g+x"; + }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/xfs_quota.nix b/nixpkgs/nixos/modules/programs/xfs_quota.nix new file mode 100644 index 000000000000..648fd9a8a94f --- /dev/null +++ b/nixpkgs/nixos/modules/programs/xfs_quota.nix @@ -0,0 +1,110 @@ +# Configuration for the xfs_quota command + +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfg = config.programs.xfs_quota; + + limitOptions = opts: concatStringsSep " " [ + (optionalString (opts.sizeSoftLimit != null) "bsoft=${opts.sizeSoftLimit}") + (optionalString (opts.sizeHardLimit != null) "bhard=${opts.sizeHardLimit}") + ]; + +in + +{ + + ###### interface + + options = { + + programs.xfs_quota = { + projects = mkOption { + default = {}; + type = types.attrsOf (types.submodule { + options = { + id = mkOption { + type = types.int; + description = "Project ID."; + }; + + fileSystem = mkOption { + type = types.str; + description = "XFS filesystem hosting the xfs_quota project."; + default = "/"; + }; + + path = mkOption { + type = types.str; + description = "Project directory."; + }; + + sizeSoftLimit = mkOption { + type = types.nullOr types.str; + default = null; + example = "30g"; + description = "Soft limit of the project size"; + }; + + sizeHardLimit = mkOption { + type = types.nullOr types.str; + default = null; + example = "50g"; + description = "Hard limit of the project size."; + }; + }; + }); + + description = "Setup of xfs_quota projects. Make sure the filesystem is mounted with the pquota option."; + + example = { + "projname" = { + id = 50; + path = "/xfsprojects/projname"; + sizeHardLimit = "50g"; + }; + }; + }; + }; + + }; + + + ###### implementation + + config = mkIf (cfg.projects != {}) { + + environment.etc.projects.source = pkgs.writeText "etc-project" + (concatStringsSep "\n" (mapAttrsToList + (name: opts: "${toString opts.id}:${opts.path}") cfg.projects)); + + environment.etc.projid.source = pkgs.writeText "etc-projid" + (concatStringsSep "\n" (mapAttrsToList + (name: opts: "${name}:${toString opts.id}") cfg.projects)); + + systemd.services = mapAttrs' (name: opts: + nameValuePair "xfs_quota-${name}" { + description = "Setup xfs_quota for project ${name}"; + script = '' + ${pkgs.xfsprogs.bin}/bin/xfs_quota -x -c 'project -s ${name}' ${opts.fileSystem} + ${pkgs.xfsprogs.bin}/bin/xfs_quota -x -c 'limit -p ${limitOptions opts} ${name}' ${opts.fileSystem} + ''; + + wantedBy = [ "multi-user.target" ]; + after = [ ((replaceChars [ "/" ] [ "-" ] opts.fileSystem) + ".mount") ]; + + restartTriggers = [ config.environment.etc.projects.source ]; + + serviceConfig = { + Type = "oneshot"; + RemainAfterExit = true; + }; + } + ) cfg.projects; + + }; + +} diff --git a/nixpkgs/nixos/modules/programs/xonsh.nix b/nixpkgs/nixos/modules/programs/xonsh.nix new file mode 100644 index 000000000000..5cd2a49f8073 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/xonsh.nix @@ -0,0 +1,60 @@ +# This module defines global configuration for the xonsh. + +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfg = config.programs.xonsh; + +in + +{ + + options = { + + programs.xonsh = { + + enable = mkOption { + default = false; + description = '' + Whether to configure xonsh as an interactive shell. + ''; + type = types.bool; + }; + + package = mkOption { + type = types.package; + default = pkgs.xonsh; + example = literalExample "pkgs.xonsh.override { configFile = \"/path/to/xonshrc\"; }"; + description = '' + xonsh package to use. + ''; + }; + + config = mkOption { + default = ""; + description = "Control file to customize your shell behavior."; + type = types.lines; + }; + + }; + + }; + + config = mkIf cfg.enable { + + environment.etc."xonshrc".text = cfg.config; + + environment.systemPackages = [ cfg.package ]; + + environment.shells = + [ "/run/current-system/sw/bin/xonsh" + "${cfg.package}/bin/xonsh" + ]; + + }; + +} + diff --git a/nixpkgs/nixos/modules/programs/xss-lock.nix b/nixpkgs/nixos/modules/programs/xss-lock.nix new file mode 100644 index 000000000000..070463311db5 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/xss-lock.nix @@ -0,0 +1,44 @@ +{ config, pkgs, lib, ... }: + +with lib; + +let + cfg = config.programs.xss-lock; +in +{ + options.programs.xss-lock = { + enable = mkEnableOption "xss-lock"; + + lockerCommand = mkOption { + default = "${pkgs.i3lock}/bin/i3lock"; + example = literalExample ''''${pkgs.i3lock-fancy}/bin/i3lock-fancy''; + type = types.string; + description = "Locker to be used with xsslock"; + }; + + extraOptions = mkOption { + default = [ ]; + example = [ "--ignore-sleep" ]; + type = types.listOf types.str; + description = '' + Additional command-line arguments to pass to + <command>xss-lock</command>. + ''; + }; + }; + + config = mkIf cfg.enable { + systemd.user.services.xss-lock = { + description = "XSS Lock Daemon"; + wantedBy = [ "graphical-session.target" ]; + partOf = [ "graphical-session.target" ]; + serviceConfig.ExecStart = with lib; + strings.concatStringsSep " " ([ + "${pkgs.xss-lock}/bin/xss-lock" + ] ++ (map escapeShellArg cfg.extraOptions) ++ [ + "--" + cfg.lockerCommand + ]); + }; + }; +} diff --git a/nixpkgs/nixos/modules/programs/yabar.nix b/nixpkgs/nixos/modules/programs/yabar.nix new file mode 100644 index 000000000000..db085211366e --- /dev/null +++ b/nixpkgs/nixos/modules/programs/yabar.nix @@ -0,0 +1,162 @@ +{ lib, pkgs, config, ... }: + +with lib; + +let + cfg = config.programs.yabar; + + mapExtra = v: lib.concatStringsSep "\n" (mapAttrsToList ( + key: val: "${key} = ${if (isString val) then "\"${val}\"" else "${builtins.toString val}"};" + ) v); + + listKeys = r: concatStringsSep "," (map (n: "\"${n}\"") (attrNames r)); + + configFile = let + bars = mapAttrsToList ( + name: cfg: '' + ${name}: { + font: "${cfg.font}"; + position: "${cfg.position}"; + + ${mapExtra cfg.extra} + + block-list: [${listKeys cfg.indicators}] + + ${concatStringsSep "\n" (mapAttrsToList ( + name: cfg: '' + ${name}: { + exec: "${cfg.exec}"; + align: "${cfg.align}"; + ${mapExtra cfg.extra} + }; + '' + ) cfg.indicators)} + }; + '' + ) cfg.bars; + in pkgs.writeText "yabar.conf" '' + bar-list = [${listKeys cfg.bars}]; + ${concatStringsSep "\n" bars} + ''; +in + { + options.programs.yabar = { + enable = mkEnableOption "yabar"; + + package = mkOption { + default = pkgs.yabar-unstable; + example = literalExample "pkgs.yabar"; + type = types.package; + + # `yabar-stable` segfaults under certain conditions. + apply = x: if x == pkgs.yabar-unstable then x else flip warn x '' + It's not recommended to use `yabar' with `programs.yabar', the (old) stable release + tends to segfault under certain circumstances: + + * https://github.com/geommer/yabar/issues/86 + * https://github.com/geommer/yabar/issues/68 + * https://github.com/geommer/yabar/issues/143 + + Most of them don't occur on master anymore, until a new release is published, it's recommended + to use `yabar-unstable'. + ''; + + description = '' + The package which contains the `yabar` binary. + + Nixpkgs provides the `yabar` and `yabar-unstable` + derivations since 18.03, so it's possible to choose. + ''; + }; + + bars = mkOption { + default = {}; + type = types.attrsOf(types.submodule { + options = { + font = mkOption { + default = "sans bold 9"; + example = "Droid Sans, FontAwesome Bold 9"; + type = types.string; + + description = '' + The font that will be used to draw the status bar. + ''; + }; + + position = mkOption { + default = "top"; + example = "bottom"; + type = types.enum [ "top" "bottom" ]; + + description = '' + The position where the bar will be rendered. + ''; + }; + + extra = mkOption { + default = {}; + type = types.attrsOf types.string; + + description = '' + An attribute set which contains further attributes of a bar. + ''; + }; + + indicators = mkOption { + default = {}; + type = types.attrsOf(types.submodule { + options.exec = mkOption { + example = "YABAR_DATE"; + type = types.string; + description = '' + The type of the indicator to be executed. + ''; + }; + + options.align = mkOption { + default = "left"; + example = "right"; + type = types.enum [ "left" "center" "right" ]; + + description = '' + Whether to align the indicator at the left or right of the bar. + ''; + }; + + options.extra = mkOption { + default = {}; + type = types.attrsOf (types.either types.string types.int); + + description = '' + An attribute set which contains further attributes of a indicator. + ''; + }; + }); + + description = '' + Indicators that should be rendered by yabar. + ''; + }; + }; + }); + + description = '' + List of bars that should be rendered by yabar. + ''; + }; + }; + + config = mkIf cfg.enable { + systemd.user.services.yabar = { + description = "yabar service"; + wantedBy = [ "graphical-session.target" ]; + partOf = [ "graphical-session.target" ]; + + script = '' + ${cfg.package}/bin/yabar -c ${configFile} + ''; + + serviceConfig.Restart = "always"; + }; + }; + } diff --git a/nixpkgs/nixos/modules/programs/zmap.nix b/nixpkgs/nixos/modules/programs/zmap.nix new file mode 100644 index 000000000000..2e27fce4d7c6 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/zmap.nix @@ -0,0 +1,18 @@ +{ pkgs, config, lib, ... }: + +with lib; + +let + cfg = config.programs.zmap; +in { + options.programs.zmap = { + enable = mkEnableOption "ZMap"; + }; + + config = mkIf cfg.enable { + environment.systemPackages = [ pkgs.zmap ]; + + environment.etc."zmap/blacklist.conf".source = "${pkgs.zmap}/etc/zmap/blacklist.conf"; + environment.etc."zmap/zmap.conf".source = "${pkgs.zmap}/etc/zmap.conf"; + }; +} diff --git a/nixpkgs/nixos/modules/programs/zsh/oh-my-zsh.nix b/nixpkgs/nixos/modules/programs/zsh/oh-my-zsh.nix new file mode 100644 index 000000000000..f4df4e983e42 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/zsh/oh-my-zsh.nix @@ -0,0 +1,138 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfg = config.programs.zsh.ohMyZsh; + + mkLinkFarmEntry = name: dir: + let + env = pkgs.buildEnv { + name = "zsh-${name}-env"; + paths = cfg.customPkgs; + pathsToLink = "/share/zsh/${dir}"; + }; + in + { inherit name; path = "${env}/share/zsh/${dir}"; }; + + mkLinkFarmEntry' = name: mkLinkFarmEntry name name; + + custom = + if cfg.custom != null then cfg.custom + else if length cfg.customPkgs == 0 then null + else pkgs.linkFarm "oh-my-zsh-custom" [ + (mkLinkFarmEntry' "themes") + (mkLinkFarmEntry "completions" "site-functions") + (mkLinkFarmEntry' "plugins") + ]; + +in + { + options = { + programs.zsh.ohMyZsh = { + enable = mkOption { + default = false; + description = '' + Enable oh-my-zsh. + ''; + }; + + package = mkOption { + default = pkgs.oh-my-zsh; + defaultText = "pkgs.oh-my-zsh"; + description = '' + Package to install for `oh-my-zsh` usage. + ''; + + type = types.package; + }; + + plugins = mkOption { + default = []; + type = types.listOf(types.str); + description = '' + List of oh-my-zsh plugins + ''; + }; + + custom = mkOption { + default = null; + type = with types; nullOr str; + description = '' + Path to a custom oh-my-zsh package to override config of oh-my-zsh. + (Can't be used along with `customPkgs`). + ''; + }; + + customPkgs = mkOption { + default = []; + type = types.listOf types.package; + description = '' + List of custom packages that should be loaded into `oh-my-zsh`. + ''; + }; + + theme = mkOption { + default = ""; + type = types.str; + description = '' + Name of the theme to be used by oh-my-zsh. + ''; + }; + + cacheDir = mkOption { + default = "$HOME/.cache/oh-my-zsh"; + type = types.str; + description = '' + Cache directory to be used by `oh-my-zsh`. + Without this option it would default to the read-only nix store. + ''; + }; + }; + }; + + config = mkIf cfg.enable { + + # Prevent zsh from overwriting oh-my-zsh's prompt + programs.zsh.promptInit = mkDefault ""; + + environment.systemPackages = [ cfg.package ]; + + programs.zsh.interactiveShellInit = '' + # oh-my-zsh configuration generated by NixOS + export ZSH=${cfg.package}/share/oh-my-zsh + + ${optionalString (length(cfg.plugins) > 0) + "plugins=(${concatStringsSep " " cfg.plugins})" + } + + ${optionalString (custom != null) + "ZSH_CUSTOM=\"${custom}\"" + } + + ${optionalString (stringLength(cfg.theme) > 0) + "ZSH_THEME=\"${cfg.theme}\"" + } + + ${optionalString (cfg.cacheDir != null) '' + if [[ ! -d "${cfg.cacheDir}" ]]; then + mkdir -p "${cfg.cacheDir}" + fi + ZSH_CACHE_DIR=${cfg.cacheDir} + ''} + + source $ZSH/oh-my-zsh.sh + ''; + + assertions = [ + { + assertion = cfg.custom != null -> cfg.customPkgs == []; + message = "If `cfg.custom` is set for `ZSH_CUSTOM`, `customPkgs` can't be used!"; + } + ]; + + }; + + meta.doc = ./oh-my-zsh.xml; + } diff --git a/nixpkgs/nixos/modules/programs/zsh/oh-my-zsh.xml b/nixpkgs/nixos/modules/programs/zsh/oh-my-zsh.xml new file mode 100644 index 000000000000..568c2de65576 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/zsh/oh-my-zsh.xml @@ -0,0 +1,155 @@ +<chapter xmlns="http://docbook.org/ns/docbook" + xmlns:xlink="http://www.w3.org/1999/xlink" + xmlns:xi="http://www.w3.org/2001/XInclude" + version="5.0" + xml:id="module-programs-zsh-ohmyzsh"> + <title>Oh my ZSH</title> + <para> + <literal><link xlink:href="https://ohmyz.sh/">oh-my-zsh</link></literal> is a + framework to manage your <link xlink:href="https://www.zsh.org/">ZSH</link> + configuration including completion scripts for several CLI tools or custom + prompt themes. + </para> + <section xml:id="module-programs-oh-my-zsh-usage"> + <title>Basic usage</title> + + <para> + The module uses the <literal>oh-my-zsh</literal> package with all available + features. The initial setup using Nix expressions is fairly similar to the + configuration format of <literal>oh-my-zsh</literal>. +<programlisting> +{ + programs.zsh.ohMyZsh = { + enable = true; + plugins = [ "git" "python" "man" ]; + theme = "agnoster"; + }; +} +</programlisting> + For a detailed explanation of these arguments please refer to the + <link xlink:href="https://github.com/robbyrussell/oh-my-zsh/wiki"><literal>oh-my-zsh</literal> + docs</link>. + </para> + + <para> + The expression generates the needed configuration and writes it into your + <literal>/etc/zshrc</literal>. + </para> + </section> + <section xml:id="module-programs-oh-my-zsh-additions"> + <title>Custom additions</title> + + <para> + Sometimes third-party or custom scripts such as a modified theme may be + needed. <literal>oh-my-zsh</literal> provides the + <link xlink:href="https://github.com/robbyrussell/oh-my-zsh/wiki/Customization#overriding-internals"><literal>ZSH_CUSTOM</literal></link> + environment variable for this which points to a directory with additional + scripts. + </para> + + <para> + The module can do this as well: +<programlisting> +{ + programs.zsh.ohMyZsh.custom = "~/path/to/custom/scripts"; +} +</programlisting> + </para> + </section> + <section xml:id="module-programs-oh-my-zsh-environments"> + <title>Custom environments</title> + + <para> + There are several extensions for <literal>oh-my-zsh</literal> packaged in + <literal>nixpkgs</literal>. One of them is + <link xlink:href="https://github.com/spwhitt/nix-zsh-completions">nix-zsh-completions</link> + which bundles completion scripts and a plugin for + <literal>oh-my-zsh</literal>. + </para> + + <para> + Rather than using a single mutable path for <literal>ZSH_CUSTOM</literal>, + it's also possible to generate this path from a list of Nix packages: +<programlisting> +{ pkgs, ... }: +{ + programs.zsh.ohMyZsh.customPkgs = with pkgs; [ + pkgs.nix-zsh-completions + # and even more... + ]; +} +</programlisting> + Internally a single store path will be created using + <literal>buildEnv</literal>. Please refer to the docs of + <link xlink:href="https://nixos.org/nixpkgs/manual/#sec-building-environment"><literal>buildEnv</literal></link> + for further reference. + </para> + + <para> + <emphasis>Please keep in mind that this is not compatible with + <literal>programs.zsh.ohMyZsh.custom</literal> as it requires an immutable + store path while <literal>custom</literal> shall remain mutable! An + evaluation failure will be thrown if both <literal>custom</literal> and + <literal>customPkgs</literal> are set.</emphasis> + </para> + </section> + <section xml:id="module-programs-oh-my-zsh-packaging-customizations"> + <title>Package your own customizations</title> + + <para> + If third-party customizations (e.g. new themes) are supposed to be added to + <literal>oh-my-zsh</literal> there are several pitfalls to keep in mind: + </para> + + <itemizedlist> + <listitem> + <para> + To comply with the default structure of <literal>ZSH</literal> the entire + output needs to be written to <literal>$out/share/zsh.</literal> + </para> + </listitem> + <listitem> + <para> + Completion scripts are supposed to be stored at + <literal>$out/share/zsh/site-functions</literal>. This directory is part + of the + <literal><link xlink:href="http://zsh.sourceforge.net/Doc/Release/Functions.html">fpath</link></literal> + and the package should be compatible with pure <literal>ZSH</literal> + setups. The module will automatically link the contents of + <literal>site-functions</literal> to completions directory in the proper + store path. + </para> + </listitem> + <listitem> + <para> + The <literal>plugins</literal> directory needs the structure + <literal>pluginname/pluginname.plugin.zsh</literal> as structured in the + <link xlink:href="https://github.com/robbyrussell/oh-my-zsh/tree/91b771914bc7c43dd7c7a43b586c5de2c225ceb7/plugins">upstream + repo.</link> + </para> + </listitem> + </itemizedlist> + + <para> + A derivation for <literal>oh-my-zsh</literal> may look like this: +<programlisting> +{ stdenv, fetchFromGitHub }: + +stdenv.mkDerivation rec { + name = "exemplary-zsh-customization-${version}"; + version = "1.0.0"; + src = fetchFromGitHub { + # path to the upstream repository + }; + + dontBuild = true; + installPhase = '' + mkdir -p $out/share/zsh/site-functions + cp {themes,plugins} $out/share/zsh + cp completions $out/share/zsh/site-functions + ''; +} +</programlisting> + </para> + </section> +</chapter> diff --git a/nixpkgs/nixos/modules/programs/zsh/zinputrc b/nixpkgs/nixos/modules/programs/zsh/zinputrc new file mode 100644 index 000000000000..6121f3e21f16 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/zsh/zinputrc @@ -0,0 +1,42 @@ +# Stolen from ArchWiki + +# create a zkbd compatible hash; +# to add other keys to this hash, see: man 5 terminfo +typeset -A key + +key[Home]=${terminfo[khome]} + +key[End]=${terminfo[kend]} +key[Insert]=${terminfo[kich1]} +key[Delete]=${terminfo[kdch1]} +key[Up]=${terminfo[kcuu1]} +key[Down]=${terminfo[kcud1]} +key[Left]=${terminfo[kcub1]} +key[Right]=${terminfo[kcuf1]} +key[PageUp]=${terminfo[kpp]} +key[PageDown]=${terminfo[knp]} + +# setup key accordingly +[[ -n "${key[Home]}" ]] && bindkey "${key[Home]}" beginning-of-line +[[ -n "${key[End]}" ]] && bindkey "${key[End]}" end-of-line +[[ -n "${key[Insert]}" ]] && bindkey "${key[Insert]}" overwrite-mode +[[ -n "${key[Delete]}" ]] && bindkey "${key[Delete]}" delete-char +[[ -n "${key[Up]}" ]] && bindkey "${key[Up]}" up-line-or-history +[[ -n "${key[Down]}" ]] && bindkey "${key[Down]}" down-line-or-history +[[ -n "${key[Left]}" ]] && bindkey "${key[Left]}" backward-char +[[ -n "${key[Right]}" ]] && bindkey "${key[Right]}" forward-char +[[ -n "${key[PageUp]}" ]] && bindkey "${key[PageUp]}" beginning-of-buffer-or-history +[[ -n "${key[PageDown]}" ]] && bindkey "${key[PageDown]}" end-of-buffer-or-history + +# Finally, make sure the terminal is in application mode, when zle is +# active. Only then are the values from $terminfo valid. +if (( ${+terminfo[smkx]} )) && (( ${+terminfo[rmkx]} )); then + function zle-line-init () { + printf '%s' "${terminfo[smkx]}" + } + function zle-line-finish () { + printf '%s' "${terminfo[rmkx]}" + } + zle -N zle-line-init + zle -N zle-line-finish +fi diff --git a/nixpkgs/nixos/modules/programs/zsh/zsh-autoenv.nix b/nixpkgs/nixos/modules/programs/zsh/zsh-autoenv.nix new file mode 100644 index 000000000000..630114bcda9f --- /dev/null +++ b/nixpkgs/nixos/modules/programs/zsh/zsh-autoenv.nix @@ -0,0 +1,28 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.zsh.zsh-autoenv; +in { + options = { + programs.zsh.zsh-autoenv = { + enable = mkEnableOption "zsh-autoenv"; + package = mkOption { + default = pkgs.zsh-autoenv; + defaultText = "pkgs.zsh-autoenv"; + description = '' + Package to install for `zsh-autoenv` usage. + ''; + + type = types.package; + }; + }; + }; + + config = mkIf cfg.enable { + programs.zsh.interactiveShellInit = '' + source ${cfg.package}/share/zsh-autoenv/autoenv.zsh + ''; + }; +} diff --git a/nixpkgs/nixos/modules/programs/zsh/zsh-autosuggestions.nix b/nixpkgs/nixos/modules/programs/zsh/zsh-autosuggestions.nix new file mode 100644 index 000000000000..ded17f38a618 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/zsh/zsh-autosuggestions.nix @@ -0,0 +1,60 @@ +{ config, pkgs, lib, ... }: + +with lib; + +let + cfg = config.programs.zsh.autosuggestions; +in +{ + options.programs.zsh.autosuggestions = { + + enable = mkEnableOption "zsh-autosuggestions"; + + highlightStyle = mkOption { + type = types.str; + default = "fg=8"; # https://github.com/zsh-users/zsh-autosuggestions/tree/v0.4.3#suggestion-highlight-style + description = "Highlight style for suggestions ({fore,back}ground color)"; + example = "fg=cyan"; + }; + + strategy = mkOption { + type = types.enum [ "history" "match_prev_cmd" ]; + default = "history"; + description = '' + Set ZSH_AUTOSUGGEST_STRATEGY to choose the strategy for generating suggestions. + There are currently two to choose from: + + * history: Chooses the most recent match. + * match_prev_cmd: Chooses the most recent match whose preceding history item matches + the most recently executed command (more info). Note that this strategy won't work as + expected with ZSH options that don't preserve the history order such as + HIST_IGNORE_ALL_DUPS or HIST_EXPIRE_DUPS_FIRST. + ''; + }; + + extraConfig = mkOption { + type = with types; attrsOf str; + default = {}; + description = "Attribute set with additional configuration values"; + example = literalExample '' + { + "ZSH_AUTOSUGGEST_BUFFER_MAX_SIZE" = "20"; + } + ''; + }; + + }; + + config = mkIf cfg.enable { + + programs.zsh.interactiveShellInit = '' + source ${pkgs.zsh-autosuggestions}/share/zsh-autosuggestions/zsh-autosuggestions.zsh + + export ZSH_AUTOSUGGEST_HIGHLIGHT_STYLE="${cfg.highlightStyle}" + export ZSH_AUTOSUGGEST_STRATEGY=("${cfg.strategy}") + + ${concatStringsSep "\n" (mapAttrsToList (key: value: ''export ${key}="${value}"'') cfg.extraConfig)} + ''; + + }; +} diff --git a/nixpkgs/nixos/modules/programs/zsh/zsh-syntax-highlighting.nix b/nixpkgs/nixos/modules/programs/zsh/zsh-syntax-highlighting.nix new file mode 100644 index 000000000000..89087a229eb7 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/zsh/zsh-syntax-highlighting.nix @@ -0,0 +1,100 @@ +{ config, lib, pkgs, ... }: + +with lib; + +let + cfg = config.programs.zsh.syntaxHighlighting; +in +{ + options = { + programs.zsh.syntaxHighlighting = { + enable = mkEnableOption "zsh-syntax-highlighting"; + + highlighters = mkOption { + default = [ "main" ]; + + # https://github.com/zsh-users/zsh-syntax-highlighting/blob/master/docs/highlighters.md + type = types.listOf(types.enum([ + "main" + "brackets" + "pattern" + "cursor" + "root" + "line" + ])); + + description = '' + Specifies the highlighters to be used by zsh-syntax-highlighting. + + The following defined options can be found here: + https://github.com/zsh-users/zsh-syntax-highlighting/blob/master/docs/highlighters.md + ''; + }; + + patterns = mkOption { + default = {}; + type = types.attrsOf types.string; + + example = literalExample '' + { + "rm -rf *" = "fg=white,bold,bg=red"; + } + ''; + + description = '' + Specifies custom patterns to be highlighted by zsh-syntax-highlighting. + + Please refer to the docs for more information about the usage: + https://github.com/zsh-users/zsh-syntax-highlighting/blob/master/docs/highlighters/pattern.md + ''; + }; + styles = mkOption { + default = {}; + type = types.attrsOf types.string; + + example = literalExample '' + { + "alias" = "fg=magenta,bold"; + } + ''; + + description = '' + Specifies custom styles to be highlighted by zsh-syntax-highlighting. + + Please refer to the docs for more information about the usage: + https://github.com/zsh-users/zsh-syntax-highlighting/blob/master/docs/highlighters/main.md + ''; + }; + }; + }; + + config = mkIf cfg.enable { + environment.systemPackages = with pkgs; [ zsh-syntax-highlighting ]; + + assertions = [ + { + assertion = length(attrNames cfg.patterns) > 0 -> elem "pattern" cfg.highlighters; + message = '' + When highlighting patterns, "pattern" needs to be included in the list of highlighters. + ''; + } + ]; + + programs.zsh.interactiveShellInit = with pkgs; + lib.concatStringsSep "\n" ([ + "source ${zsh-syntax-highlighting}/share/zsh-syntax-highlighting/zsh-syntax-highlighting.zsh" + ] ++ optional (length(cfg.highlighters) > 0) + "ZSH_HIGHLIGHT_HIGHLIGHTERS=(${concatStringsSep " " cfg.highlighters})" + ++ optionals (length(attrNames cfg.patterns) > 0) + (mapAttrsToList ( + pattern: design: + "ZSH_HIGHLIGHT_PATTERNS+=('${pattern}' '${design}')" + ) cfg.patterns) + ++ optionals (length(attrNames cfg.styles) > 0) + (mapAttrsToList ( + styles: design: + "ZSH_HIGHLIGHT_STYLES[${styles}]='${design}'" + ) cfg.styles) + ); + }; +} diff --git a/nixpkgs/nixos/modules/programs/zsh/zsh.nix b/nixpkgs/nixos/modules/programs/zsh/zsh.nix new file mode 100644 index 000000000000..bd1a77680663 --- /dev/null +++ b/nixpkgs/nixos/modules/programs/zsh/zsh.nix @@ -0,0 +1,238 @@ +# This module defines global configuration for the zshell. + +{ config, lib, pkgs, ... }: + +with lib; + +let + + cfge = config.environment; + + cfg = config.programs.zsh; + + zshAliases = concatStringsSep "\n" ( + mapAttrsFlatten (k: v: "alias ${k}=${escapeShellArg v}") + (filterAttrs (k: v: v != null) cfg.shellAliases) + ); + +in + +{ + + options = { + + programs.zsh = { + + enable = mkOption { + default = false; + description = '' + Whether to configure zsh as an interactive shell. To enable zsh for + a particular user, use the <option>users.users.<name?>.shell</option> + option for that user. To enable zsh system-wide use the + <option>users.defaultUserShell</option> option. + ''; + type = types.bool; + }; + + shellAliases = mkOption { + default = {}; + description = '' + Set of aliases for zsh shell, which overrides <option>environment.shellAliases</option>. + See <option>environment.shellAliases</option> for an option format description. + ''; + type = with types; attrsOf (nullOr (either str path)); + }; + + shellInit = mkOption { + default = ""; + description = '' + Shell script code called during zsh shell initialisation. + ''; + type = types.lines; + }; + + loginShellInit = mkOption { + default = ""; + description = '' + Shell script code called during zsh login shell initialisation. + ''; + type = types.lines; + }; + + interactiveShellInit = mkOption { + default = ""; + description = '' + Shell script code called during interactive zsh shell initialisation. + ''; + type = types.lines; + }; + + promptInit = mkOption { + default = '' + if [ "$TERM" != dumb ]; then + autoload -U promptinit && promptinit && prompt walters + fi + ''; + description = '' + Shell script code used to initialise the zsh prompt. + ''; + type = types.lines; + }; + + histSize = mkOption { + default = 2000; + description = '' + Change history size. + ''; + type = types.int; + }; + + histFile = mkOption { + default = "$HOME/.zsh_history"; + description = '' + Change history file. + ''; + type = types.str; + }; + + setOptions = mkOption { + type = types.listOf types.str; + default = [ + "HIST_IGNORE_DUPS" "SHARE_HISTORY" "HIST_FCNTL_LOCK" + ]; + example = [ "EXTENDED_HISTORY" "RM_STAR_WAIT" ]; + description = '' + Configure zsh options. + ''; + }; + + enableCompletion = mkOption { + default = true; + description = '' + Enable zsh completion for all interactive zsh shells. + ''; + type = types.bool; + }; + + + enableGlobalCompInit = mkOption { + default = cfg.enableCompletion; + description = '' + Enable execution of compinit call for all interactive zsh shells. + + This option can be disabled if the user wants to extend its + <literal>fpath</literal> and a custom <literal>compinit</literal> + call in the local config is required. + ''; + type = types.bool; + }; + + }; + + }; + + config = mkIf cfg.enable { + + programs.zsh.shellAliases = mapAttrs (name: mkDefault) cfge.shellAliases; + + environment.etc."zshenv".text = + '' + # /etc/zshenv: DO NOT EDIT -- this file has been generated automatically. + # This file is read for all shells. + + # Only execute this file once per shell. + # But don't clobber the environment of interactive non-login children! + if [ -n "$__ETC_ZSHENV_SOURCED" ]; then return; fi + export __ETC_ZSHENV_SOURCED=1 + + if [ -z "$__NIXOS_SET_ENVIRONMENT_DONE" ]; then + . ${config.system.build.setEnvironment} + fi + + ${cfge.shellInit} + + ${cfg.shellInit} + + # Read system-wide modifications. + if test -f /etc/zshenv.local; then + . /etc/zshenv.local + fi + ''; + + environment.etc."zprofile".text = + '' + # /etc/zprofile: DO NOT EDIT -- this file has been generated automatically. + # This file is read for login shells. + + # Only execute this file once per shell. + if [ -n "$__ETC_ZPROFILE_SOURCED" ]; then return; fi + __ETC_ZPROFILE_SOURCED=1 + + ${cfge.loginShellInit} + + ${cfg.loginShellInit} + + # Read system-wide modifications. + if test -f /etc/zprofile.local; then + . /etc/zprofile.local + fi + ''; + + environment.etc."zshrc".text = + '' + # /etc/zshrc: DO NOT EDIT -- this file has been generated automatically. + # This file is read for interactive shells. + + # Only execute this file once per shell. + if [ -n "$__ETC_ZSHRC_SOURCED" -o -n "$NOSYSZSHRC" ]; then return; fi + __ETC_ZSHRC_SOURCED=1 + + . /etc/zinputrc + + # Don't export these, otherwise other shells (bash) will try to use same histfile + SAVEHIST=${toString cfg.histSize} + HISTSIZE=${toString cfg.histSize} + HISTFILE=${cfg.histFile} + + HELPDIR="${pkgs.zsh}/share/zsh/$ZSH_VERSION/help" + + # Tell zsh how to find installed completions + for p in ''${(z)NIX_PROFILES}; do + fpath+=($p/share/zsh/site-functions $p/share/zsh/$ZSH_VERSION/functions $p/share/zsh/vendor-completions) + done + + ${optionalString cfg.enableGlobalCompInit "autoload -U compinit && compinit"} + + ${cfge.interactiveShellInit} + + ${cfg.interactiveShellInit} + + ${optionalString (cfg.setOptions != []) "setopt ${concatStringsSep " " cfg.setOptions}"} + + ${zshAliases} + + ${cfg.promptInit} + + # Read system-wide modifications. + if test -f /etc/zshrc.local; then + . /etc/zshrc.local + fi + ''; + + environment.etc."zinputrc".source = ./zinputrc; + + environment.systemPackages = [ pkgs.zsh ] + ++ optional cfg.enableCompletion pkgs.nix-zsh-completions; + + environment.pathsToLink = optional cfg.enableCompletion "/share/zsh"; + + #users.defaultUserShell = mkDefault "/run/current-system/sw/bin/zsh"; + + environment.shells = + [ "/run/current-system/sw/bin/zsh" + "${pkgs.zsh}/bin/zsh" + ]; + + }; + +} |