Project import generated by Copybara.

GitOrigin-RevId: 00d80d13810dbfea8ab4ed1009b09100cca86ba8
This commit is contained in:
Default email 2024-07-01 15:47:52 +00:00
parent 868d4c8931
commit 98eb3e9ef5
1816 changed files with 38300 additions and 42492 deletions

View file

@ -11,11 +11,14 @@
# This also holds true for GitHub teams. Since almost none of our teams have write # This also holds true for GitHub teams. Since almost none of our teams have write
# permissions, you need to list all members of the team with commit access individually. # permissions, you need to list all members of the team with commit access individually.
# GitHub actions # CI
/.github/workflows @NixOS/Security @Mic92 @zowoq /.github/workflows @NixOS/Security @Mic92 @zowoq
/.github/workflows/check-nix-format.yml @infinisil
/ci @infinisil
# EditorConfig # Develompent support
/.editorconfig @Mic92 @zowoq /.editorconfig @Mic92 @zowoq
/shell.nix @infinisil @NixOS/Security
# Libraries # Libraries
/lib @infinisil /lib @infinisil
@ -115,8 +118,8 @@ nixos/modules/installer/tools/nix-fallback-paths.nix @raitobezarius
/nixos/modules/system/boot/loader/systemd-boot @JulienMalka /nixos/modules/system/boot/loader/systemd-boot @JulienMalka
# Images and installer media # Images and installer media
/nixos/modules/installer/cd-dvd/ @samueldr /nixos/modules/installer/cd-dvd/
/nixos/modules/installer/sd-card/ @samueldr /nixos/modules/installer/sd-card/
# Updaters # Updaters
## update.nix ## update.nix
@ -127,7 +130,7 @@ nixos/modules/installer/tools/nix-fallback-paths.nix @raitobezarius
# Python-related code and docs # Python-related code and docs
/doc/languages-frameworks/python.section.md @mweinelt /doc/languages-frameworks/python.section.md @mweinelt
/pkgs/development/interpreters/python/hooks @jonringer /pkgs/development/interpreters/python/hooks
# Haskell # Haskell
/doc/languages-frameworks/haskell.section.md @sternenseemann @maralorn @ncfavier /doc/languages-frameworks/haskell.section.md @sternenseemann @maralorn @ncfavier
@ -262,13 +265,13 @@ nixos/modules/services/networking/networkmanager.nix @Janik-Haag
/pkgs/top-level/emacs-packages.nix @adisbladis /pkgs/top-level/emacs-packages.nix @adisbladis
# Neovim # Neovim
/pkgs/applications/editors/neovim @figsoda @jonringer @teto /pkgs/applications/editors/neovim @figsoda @teto
# VimPlugins # VimPlugins
/pkgs/applications/editors/vim/plugins @figsoda @jonringer /pkgs/applications/editors/vim/plugins @figsoda
# VsCode Extensions # VsCode Extensions
/pkgs/applications/editors/vscode/extensions @jonringer /pkgs/applications/editors/vscode/extensions
# PHP interpreter, packages, extensions, tests and documentation # PHP interpreter, packages, extensions, tests and documentation
/doc/languages-frameworks/php.section.md @aanderse @drupol @globin @ma27 @talyz /doc/languages-frameworks/php.section.md @aanderse @drupol @globin @ma27 @talyz
@ -288,9 +291,9 @@ nixos/modules/services/networking/networkmanager.nix @Janik-Haag
/pkgs/applications/blockchains @mmahut @RaghavSood /pkgs/applications/blockchains @mmahut @RaghavSood
# Go # Go
/doc/languages-frameworks/go.section.md @kalbasit @Mic92 @zowoq /doc/languages-frameworks/go.section.md @kalbasit @katexochen @Mic92 @zowoq
/pkgs/build-support/go @kalbasit @Mic92 @zowoq /pkgs/build-support/go @kalbasit @katexochen @Mic92 @zowoq
/pkgs/development/compilers/go @kalbasit @Mic92 @zowoq /pkgs/development/compilers/go @kalbasit @katexochen @Mic92 @zowoq
# GNOME # GNOME
/pkgs/desktops/gnome @jtojnar /pkgs/desktops/gnome @jtojnar
@ -313,10 +316,10 @@ nixos/modules/services/misc/forgejo.nix @adamcstephens @bendlas @emilylange
pkgs/by-name/fo/forgejo/package.nix @adamcstephens @bendlas @emilylange pkgs/by-name/fo/forgejo/package.nix @adamcstephens @bendlas @emilylange
# Dotnet # Dotnet
/pkgs/build-support/dotnet @IvarWithoutBones /pkgs/build-support/dotnet @corngood
/pkgs/development/compilers/dotnet @IvarWithoutBones /pkgs/development/compilers/dotnet @corngood
/pkgs/test/dotnet @IvarWithoutBones /pkgs/test/dotnet @corngood
/doc/languages-frameworks/dotnet.section.md @IvarWithoutBones /doc/languages-frameworks/dotnet.section.md @corngood
# Node.js # Node.js
/pkgs/build-support/node/build-npm-package @lilyinstarlight @winterqt /pkgs/build-support/node/build-npm-package @lilyinstarlight @winterqt
@ -378,4 +381,3 @@ pkgs/os-specific/linux/lxc/ @adamcstephens
/pkgs/os-specific/linux/checkpolicy @RossComputerGuy /pkgs/os-specific/linux/checkpolicy @RossComputerGuy
/pkgs/os-specific/linux/libselinux @RossComputerGuy /pkgs/os-specific/linux/libselinux @RossComputerGuy
/pkgs/os-specific/linux/libsepol @RossComputerGuy /pkgs/os-specific/linux/libsepol @RossComputerGuy

View file

@ -20,7 +20,7 @@ jobs:
if: github.repository_owner == 'NixOS' && github.event.pull_request.merged == true && (github.event_name != 'labeled' || startsWith('backport', github.event.label.name)) if: github.repository_owner == 'NixOS' && github.event.pull_request.merged == true && (github.event_name != 'labeled' || startsWith('backport', github.event.label.name))
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
with: with:
ref: ${{ github.event.pull_request.head.sha }} ref: ${{ github.event.pull_request.head.sha }}
- name: Create backport PRs - name: Create backport PRs

View file

@ -18,7 +18,7 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
# we don't limit this action to only NixOS repo since the checks are cheap and useful developer feedback # we don't limit this action to only NixOS repo since the checks are cheap and useful developer feedback
steps: steps:
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
- uses: cachix/install-nix-action@8887e596b4ee1134dae06b98d573bd674693f47c # v26 - uses: cachix/install-nix-action@8887e596b4ee1134dae06b98d573bd674693f47c # v26
- uses: cachix/cachix-action@ad2ddac53f961de1989924296a1f236fcfbaa4fc # v15 - uses: cachix/cachix-action@ad2ddac53f961de1989924296a1f236fcfbaa4fc # v15
with: with:

View file

@ -81,7 +81,7 @@ jobs:
else else
echo "The PR cannot be merged, it has a merge conflict, skipping the rest.." echo "The PR cannot be merged, it has a merge conflict, skipping the rest.."
fi fi
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
if: env.mergedSha if: env.mergedSha
with: with:
# pull_request_target checks out the base branch by default # pull_request_target checks out the base branch by default

View file

@ -13,7 +13,7 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
if: github.repository_owner == 'NixOS' if: github.repository_owner == 'NixOS'
steps: steps:
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
with: with:
fetch-depth: 0 fetch-depth: 0
filter: blob:none filter: blob:none

View file

@ -12,7 +12,7 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
if: github.repository_owner == 'NixOS' if: github.repository_owner == 'NixOS'
steps: steps:
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
with: with:
# pull_request_target checks out the base branch by default # pull_request_target checks out the base branch by default
ref: refs/pull/${{ github.event.pull_request.number }}/merge ref: refs/pull/${{ github.event.pull_request.number }}/merge

View file

@ -15,17 +15,22 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
if: github.repository_owner == 'NixOS' if: github.repository_owner == 'NixOS'
steps: steps:
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
with: with:
# pull_request_target checks out the base branch by default # pull_request_target checks out the base branch by default
ref: refs/pull/${{ github.event.pull_request.number }}/merge ref: refs/pull/${{ github.event.pull_request.number }}/merge
- name: Get Nixpkgs revision for nixfmt
run: |
# pin to a commit from nixpkgs-unstable to avoid e.g. building nixfmt
# from staging
# This should not be a URL, because it would allow PRs to run arbitrary code in CI!
rev=$(jq -r .rev ci/pinned-nixpkgs.json)
echo "url=https://github.com/NixOS/nixpkgs/archive/$rev.tar.gz" >> "$GITHUB_ENV"
- uses: cachix/install-nix-action@8887e596b4ee1134dae06b98d573bd674693f47c # v26 - uses: cachix/install-nix-action@8887e596b4ee1134dae06b98d573bd674693f47c # v26
with: with:
# explicitly enable sandbox # explicitly enable sandbox
extra_nix_config: sandbox = true extra_nix_config: sandbox = true
# fix a commit from nixpkgs-unstable to avoid e.g. building nixfmt nix_path: nixpkgs=${{ env.url }}
# from staging
nix_path: nixpkgs=https://github.com/NixOS/nixpkgs/archive/4b455dc2048f73a79eb3713f342369ff58f93e0b.tar.gz
- name: Install nixfmt - name: Install nixfmt
run: "nix-env -f '<nixpkgs>' -iAP nixfmt-rfc-style" run: "nix-env -f '<nixpkgs>' -iAP nixfmt-rfc-style"
- name: Check that Nix files are formatted according to the RFC style - name: Check that Nix files are formatted according to the RFC style
@ -35,14 +40,14 @@ jobs:
NIX_FMT_PATHS_BSD: pkgs/os-specific/bsd NIX_FMT_PATHS_BSD: pkgs/os-specific/bsd
NIX_FMT_PATHS_MPVSCRIPTS: pkgs/applications/video/mpv/scripts NIX_FMT_PATHS_MPVSCRIPTS: pkgs/applications/video/mpv/scripts
# Format paths related to the Nixpkgs CUDA ecosystem. # Format paths related to the Nixpkgs CUDA ecosystem.
NIX_FMT_PATHS_CUDA: | NIX_FMT_PATHS_CUDA: |-
pkgs/development/cuda-modules pkgs/development/cuda-modules
pkgs/test/cuda pkgs/test/cuda
pkgs/top-level/cuda-packages.nix pkgs/top-level/cuda-packages.nix
NIX_FMT_PATHS_MAINTAINERS: | NIX_FMT_PATHS_MAINTAINERS: |-
maintainers/maintainer-list.nix maintainers/maintainer-list.nix
maintainers/team-list.nix maintainers/team-list.nix
NIX_FMT_PATHS_K3S: | NIX_FMT_PATHS_K3S: |-
nixos/modules/services/cluster/k3s nixos/modules/services/cluster/k3s
nixos/tests/k3s nixos/tests/k3s
pkgs/applications/networking/cluster/k3s pkgs/applications/networking/cluster/k3s
@ -51,6 +56,7 @@ jobs:
NIX_FMT_PATHS_BUILD_SUPPORT_PHP: pkgs/build-support/php NIX_FMT_PATHS_BUILD_SUPPORT_PHP: pkgs/build-support/php
# Iterate over all environment variables beginning with NIX_FMT_PATHS_. # Iterate over all environment variables beginning with NIX_FMT_PATHS_.
run: | run: |
unformattedPaths=()
for env_var in "${!NIX_FMT_PATHS_@}"; do for env_var in "${!NIX_FMT_PATHS_@}"; do
readarray -t paths <<< "${!env_var}" readarray -t paths <<< "${!env_var}"
if [[ "${paths[*]}" == "" ]]; then if [[ "${paths[*]}" == "" ]]; then
@ -59,7 +65,12 @@ jobs:
fi fi
echo "Checking paths: ${paths[@]}" echo "Checking paths: ${paths[@]}"
if ! nixfmt --check "${paths[@]}"; then if ! nixfmt --check "${paths[@]}"; then
echo "Error: nixfmt failed." unformattedPaths+=("${paths[@]}")
exit 1
fi fi
done done
if (( "${#unformattedPaths[@]}" > 0 )); then
echo "Some required Nix files are not properly formatted"
echo "Please run the following in \`nix-shell\`:"
echo "nixfmt ${unformattedPaths[*]@Q}"
exit 1
fi

View file

@ -0,0 +1,29 @@
name: "Check shell"
on:
pull_request_target:
permissions: {}
jobs:
x86_64-linux:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
with:
# pull_request_target checks out the base branch by default
ref: refs/pull/${{ github.event.pull_request.number }}/merge
- uses: cachix/install-nix-action@8887e596b4ee1134dae06b98d573bd674693f47c # v26
- name: Build shell
run: nix-build shell.nix
aarch64-darwin:
runs-on: macos-latest
steps:
- uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
with:
# pull_request_target checks out the base branch by default
ref: refs/pull/${{ github.event.pull_request.number }}/merge
- uses: cachix/install-nix-action@8887e596b4ee1134dae06b98d573bd674693f47c # v26
- name: Build shell
run: nix-build shell.nix

View file

@ -24,7 +24,7 @@ jobs:
- name: print list of changed files - name: print list of changed files
run: | run: |
cat "$HOME/changed_files" cat "$HOME/changed_files"
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
with: with:
# pull_request_target checks out the base branch by default # pull_request_target checks out the base branch by default
ref: refs/pull/${{ github.event.pull_request.number }}/merge ref: refs/pull/${{ github.event.pull_request.number }}/merge

View file

@ -14,7 +14,7 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
if: github.repository_owner == 'NixOS' if: github.repository_owner == 'NixOS'
steps: steps:
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
with: with:
# pull_request_target checks out the base branch by default # pull_request_target checks out the base branch by default
ref: refs/pull/${{ github.event.pull_request.number }}/merge ref: refs/pull/${{ github.event.pull_request.number }}/merge

View file

@ -16,7 +16,7 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
if: github.repository_owner == 'NixOS' if: github.repository_owner == 'NixOS'
steps: steps:
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
with: with:
# pull_request_target checks out the base branch by default # pull_request_target checks out the base branch by default
ref: refs/pull/${{ github.event.pull_request.number }}/merge ref: refs/pull/${{ github.event.pull_request.number }}/merge

View file

@ -24,7 +24,7 @@ jobs:
if [[ -s "$HOME/changed_files" ]]; then if [[ -s "$HOME/changed_files" ]]; then
echo "CHANGED_FILES=$HOME/changed_files" > "$GITHUB_ENV" echo "CHANGED_FILES=$HOME/changed_files" > "$GITHUB_ENV"
fi fi
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
with: with:
# pull_request_target checks out the base branch by default # pull_request_target checks out the base branch by default
ref: refs/pull/${{ github.event.pull_request.number }}/merge ref: refs/pull/${{ github.event.pull_request.number }}/merge

View file

@ -35,17 +35,13 @@ jobs:
pairs: pairs:
- from: master - from: master
into: haskell-updates into: haskell-updates
- from: release-23.11
into: staging-next-23.11
- from: staging-next-23.11
into: staging-23.11
- from: release-24.05 - from: release-24.05
into: staging-next-24.05 into: staging-next-24.05
- from: staging-next-24.05 - from: staging-next-24.05
into: staging-24.05 into: staging-24.05
name: ${{ matrix.pairs.from }} → ${{ matrix.pairs.into }} name: ${{ matrix.pairs.from }} → ${{ matrix.pairs.into }}
steps: steps:
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
- name: ${{ matrix.pairs.from }} → ${{ matrix.pairs.into }} - name: ${{ matrix.pairs.from }} → ${{ matrix.pairs.into }}
uses: devmasx/merge-branch@854d3ac71ed1e9deb668e0074781b81fdd6e771f # 1.4.0 uses: devmasx/merge-branch@854d3ac71ed1e9deb668e0074781b81fdd6e771f # 1.4.0

View file

@ -39,7 +39,7 @@ jobs:
into: staging into: staging
name: ${{ matrix.pairs.from }} → ${{ matrix.pairs.into }} name: ${{ matrix.pairs.from }} → ${{ matrix.pairs.into }}
steps: steps:
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
- name: ${{ matrix.pairs.from }} → ${{ matrix.pairs.into }} - name: ${{ matrix.pairs.from }} → ${{ matrix.pairs.into }}
uses: devmasx/merge-branch@854d3ac71ed1e9deb668e0074781b81fdd6e771f # 1.4.0 uses: devmasx/merge-branch@854d3ac71ed1e9deb668e0074781b81fdd6e771f # 1.4.0

View file

@ -16,7 +16,7 @@ jobs:
if: github.repository_owner == 'NixOS' && github.ref == 'refs/heads/master' # ensure workflow_dispatch only runs on master if: github.repository_owner == 'NixOS' && github.ref == 'refs/heads/master' # ensure workflow_dispatch only runs on master
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- uses: actions/checkout@44c2b7a8a4ea60a981eaca3cf939b5f4305c123b # v4.1.5 - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7
- uses: cachix/install-nix-action@8887e596b4ee1134dae06b98d573bd674693f47c # v26 - uses: cachix/install-nix-action@8887e596b4ee1134dae06b98d573bd674693f47c # v26
with: with:
nix_path: nixpkgs=channel:nixpkgs-unstable nix_path: nixpkgs=channel:nixpkgs-unstable

12
third_party/nixpkgs/ci/README.md vendored Normal file
View file

@ -0,0 +1,12 @@
# CI support files
This directory contains files to support CI, such as [GitHub Actions](https://github.com/NixOS/nixpkgs/tree/master/.github/workflows) and [Ofborg](https://github.com/nixos/ofborg).
This is in contrast with [`maintainers/scripts`](`../maintainers/scripts`) which is for human use instead.
## Pinned Nixpkgs
CI may need certain packages from Nixpkgs.
In order to ensure that the needed packages are generally available without building,
[`pinned-nixpkgs.json`](./pinned-nixpkgs.json) contains a pinned Nixpkgs version tested by Hydra.
Run [`update-pinned-nixpkgs.sh`](./update-pinned-nixpkgs.sh) to update it.

View file

@ -0,0 +1,4 @@
{
"rev": "cfb89a95f19bea461fc37228dc4d07b22fe617c2",
"sha256": "1yhsacvry6j8r02lk70p9dphjpi8lpzgq2qay8hiy4nqlys0mrch"
}

View file

@ -0,0 +1,16 @@
#!/usr/bin/env nix-shell
#!nix-shell -i bash -p jq
set -euo pipefail
# https://stackoverflow.com/a/246128
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
repo=https://github.com/nixos/nixpkgs
branch=nixpkgs-unstable
file=$SCRIPT_DIR/pinned-nixpkgs.json
rev=$(git ls-remote "$repo" refs/heads/"$branch" | cut -f1)
sha256=$(nix-prefetch-url --unpack "$repo/archive/$rev.tar.gz" --name source)
jq -n --arg rev "$rev" --arg sha256 "$sha256" '$ARGS.named' | tee /dev/stderr > $file

View file

@ -23,6 +23,7 @@ let
{ name = "fileset"; description = "file set functions"; } { name = "fileset"; description = "file set functions"; }
{ name = "sources"; description = "source filtering functions"; } { name = "sources"; description = "source filtering functions"; }
{ name = "cli"; description = "command-line serialization functions"; } { name = "cli"; description = "command-line serialization functions"; }
{ name = "generators"; description = "functions that create file formats from nix data structures"; }
{ name = "gvariant"; description = "GVariant formatted string serialization functions"; } { name = "gvariant"; description = "GVariant formatted string serialization functions"; }
{ name = "customisation"; description = "Functions to customise (derivation-related) functions, derivatons, or attribute sets"; } { name = "customisation"; description = "Functions to customise (derivation-related) functions, derivatons, or attribute sets"; }
{ name = "meta"; description = "functions for derivation metadata"; } { name = "meta"; description = "functions for derivation metadata"; }

View file

@ -54,4 +54,4 @@ merge:"diff3"
Nix store paths can be converted to strings by enclosing a derivation attribute like so: `"${drv}"`. Nix store paths can be converted to strings by enclosing a derivation attribute like so: `"${drv}"`.
::: :::
Detailed documentation for each generator can be found in `lib/generators.nix`. Detailed documentation for each generator can be found [here](#sec-functions-library-generators)

View file

@ -232,11 +232,11 @@ In addition to prebuilt APKs, you can also bind the APK parameter to a
## Notes on environment variables in Android projects {#notes-on-environment-variables-in-android-projects} ## Notes on environment variables in Android projects {#notes-on-environment-variables-in-android-projects}
* `ANDROID_SDK_ROOT` should point to the Android SDK. In your Nix expressions, this should be * `ANDROID_HOME` should point to the Android SDK. In your Nix expressions, this should be
`${androidComposition.androidsdk}/libexec/android-sdk`. Note that `ANDROID_HOME` is deprecated, `${androidComposition.androidsdk}/libexec/android-sdk`. Note that `ANDROID_SDK_ROOT` is deprecated,
but if you rely on tools that need it, you can export it too. but if you rely on tools that need it, you can export it too.
* `ANDROID_NDK_ROOT` should point to the Android NDK, if you're doing NDK development. * `ANDROID_NDK_ROOT` should point to the Android NDK, if you're doing NDK development.
In your Nix expressions, this should be `${ANDROID_SDK_ROOT}/ndk-bundle`. In your Nix expressions, this should be `${ANDROID_HOME}/ndk-bundle`.
If you are running the Android Gradle plugin, you need to export GRADLE_OPTS to override aapt2 If you are running the Android Gradle plugin, you need to export GRADLE_OPTS to override aapt2
to point to the aapt2 binary in the Nix store as well, or use a FHS environment so the packaged to point to the aapt2 binary in the Nix store as well, or use a FHS environment so the packaged
@ -250,11 +250,11 @@ let
androidComposition = <...>; androidComposition = <...>;
in in
pkgs.mkShell rec { pkgs.mkShell rec {
ANDROID_SDK_ROOT = "${androidComposition.androidsdk}/libexec/android-sdk"; ANDROID_HOME = "${androidComposition.androidsdk}/libexec/android-sdk";
ANDROID_NDK_ROOT = "${ANDROID_SDK_ROOT}/ndk-bundle"; ANDROID_NDK_ROOT = "${ANDROID_HOME}/ndk-bundle";
# Use the same buildToolsVersion here # Use the same buildToolsVersion here
GRADLE_OPTS = "-Dorg.gradle.project.android.aapt2FromMavenOverride=${ANDROID_SDK_ROOT}/build-tools/${buildToolsVersion}/aapt2"; GRADLE_OPTS = "-Dorg.gradle.project.android.aapt2FromMavenOverride=${ANDROID_HOME}/build-tools/${buildToolsVersion}/aapt2";
} }
``` ```
@ -270,18 +270,18 @@ let
androidComposition = <...>; androidComposition = <...>;
in in
pkgs.mkShell rec { pkgs.mkShell rec {
ANDROID_SDK_ROOT = "${androidComposition.androidsdk}/libexec/android-sdk"; ANDROID_HOME = "${androidComposition.androidsdk}/libexec/android-sdk";
ANDROID_NDK_ROOT = "${ANDROID_SDK_ROOT}/ndk-bundle"; ANDROID_NDK_ROOT = "${ANDROID_HOME}/ndk-bundle";
# Use the same cmakeVersion here # Use the same cmakeVersion here
shellHook = '' shellHook = ''
export PATH="$(echo "$ANDROID_SDK_ROOT/cmake/${cmakeVersion}".*/bin):$PATH" export PATH="$(echo "$ANDROID_HOME/cmake/${cmakeVersion}".*/bin):$PATH"
''; '';
} }
``` ```
Note that running Android Studio with ANDROID_SDK_ROOT set will automatically write a Note that running Android Studio with ANDROID_HOME set will automatically write a
`local.properties` file with `sdk.dir` set to $ANDROID_SDK_ROOT if one does not already `local.properties` file with `sdk.dir` set to $ANDROID_HOME if one does not already
exist. If you are using the NDK as well, you may have to add `ndk.dir` to this file. exist. If you are using the NDK as well, you may have to add `ndk.dir` to this file.
An example shell.nix that does all this for you is provided in examples/shell.nix. An example shell.nix that does all this for you is provided in examples/shell.nix.

View file

@ -141,9 +141,7 @@ in buildDotnetModule rec {
src = ./.; src = ./.;
projectFile = "src/project.sln"; projectFile = "src/project.sln";
# File generated with `nix-build -A package.passthru.fetch-deps`. nugetDeps = ./deps.nix; # see "Generating and updating NuGet dependencies" section for details
# To run fetch-deps when this file does not yet exist, set nugetDeps to null
nugetDeps = ./deps.nix;
projectReferences = [ referencedProject ]; # `referencedProject` must contain `nupkg` in the folder structure. projectReferences = [ referencedProject ]; # `referencedProject` must contain `nupkg` in the folder structure.
@ -219,6 +217,12 @@ buildDotnetGlobalTool {
``` ```
## Generating and updating NuGet dependencies {#generating-and-updating-nuget-dependencies} ## Generating and updating NuGet dependencies {#generating-and-updating-nuget-dependencies}
When writing a new expression, you can use the generated `fetch-deps` script to initialise the lockfile.
After creating a blank `deps.nix` and pointing `nugetDeps` to it,
build the script with `nix-build -A package.fetch-deps` and then run the result.
(When the root attr is your package, it's simply `nix-build -A fetch-deps`.)
There is also a manual method:
First, restore the packages to the `out` directory, ensure you have cloned First, restore the packages to the `out` directory, ensure you have cloned
the upstream repository and you are inside it. the upstream repository and you are inside it.
@ -254,6 +258,5 @@ Finally, you move the `deps.nix` file to the appropriate location to be used by
If you ever need to update the dependencies of a package, you instead do If you ever need to update the dependencies of a package, you instead do
* `nix-build -A package.fetch-deps` to generate the update script for `package` * `nix-build -A package.fetch-deps` to generate the update script for `package`
* Run `./result deps.nix` to regenerate the lockfile to `deps.nix`, keep in mind if a location isn't provided, it will write to a temporary path instead * Run `./result` to regenerate the lockfile to the path passed for `nugetDeps` (keep in mind if it can't be resolved to a local path, the script will write to `$1` or a temporary path instead)
* Finally, move the file where needed and look at its contents to confirm it has updated the dependencies. * Finally, ensure the correct file was written and the derivation can be built.

View file

@ -21,25 +21,14 @@ Many “normal” user facing packages written in Haskell, like `niv` or `cachix
are also exposed at the top level, and there is nothing Haskell specific to are also exposed at the top level, and there is nothing Haskell specific to
installing and using them. installing and using them.
All of these packages are originally defined in the `haskellPackages` package All of these packages are originally defined in the `haskellPackages` package set.
set and are re-exposed with a reduced dependency closure for convenience. The same packages are re-exposed with a reduced dependency closure for convenience (see `justStaticExecutables` or `separateBinOutput` below).
(see `justStaticExecutables` or `separateBinOutput` below)
The `haskellPackages` set includes at least one version of every package from :::{.note}
Hackage as well as some manually injected packages. This amounts to a lot of See [](#chap-language-support) for techniques to explore package sets.
packages, so it is hidden from `nix-env -qa` by default for performance reasons. :::
You can still list all packages in the set like this:
```console The `haskellPackages` set includes at least one version of every package from [Hackage](https://hackage.haskell.org/) as well as some manually injected packages.
$ nix-env -f '<nixpkgs>' -qaP -A haskellPackages
haskellPackages.a50 a50-0.5
haskellPackages.AAI AAI-0.2.0.1
haskellPackages.aasam aasam-0.2.0.0
haskellPackages.abacate abacate-0.0.0.0
haskellPackages.abc-puzzle abc-puzzle-0.2.1
```
Also, the `haskellPackages` set is included on [search.nixos.org].
The attribute names in `haskellPackages` always correspond with their name on The attribute names in `haskellPackages` always correspond with their name on
Hackage. Since Hackage allows names that are not valid Nix without escaping, Hackage. Since Hackage allows names that are not valid Nix without escaping,
@ -49,8 +38,7 @@ For packages that are part of [Stackage] (a curated set of known to be
compatible packages), we use the version prescribed by a Stackage snapshot compatible packages), we use the version prescribed by a Stackage snapshot
(usually the current LTS one) as the default version. For all other packages we (usually the current LTS one) as the default version. For all other packages we
use the latest version from [Hackage](https://hackage.org) (the repository of use the latest version from [Hackage](https://hackage.org) (the repository of
basically all open source Haskell packages). See [below](#haskell-available- basically all open source Haskell packages). See [below](#haskell-available-versions) for a few more details on this.
versions) for a few more details on this.
Roughly half of the 16K packages contained in `haskellPackages` dont actually Roughly half of the 16K packages contained in `haskellPackages` dont actually
build and are [marked as broken semi-automatically](https://github.com/NixOS/nixpkgs/blob/haskell-updates/pkgs/development/haskell-modules/configuration-hackage2nix/broken.yaml). build and are [marked as broken semi-automatically](https://github.com/NixOS/nixpkgs/blob/haskell-updates/pkgs/development/haskell-modules/configuration-hackage2nix/broken.yaml).
@ -63,68 +51,15 @@ How you can help with that is
described in [Fixing a broken package](#haskell-fixing-a-broken-package). described in [Fixing a broken package](#haskell-fixing-a-broken-package).
--> -->
`haskellPackages` is built with our default compiler, but we also provide other `haskellPackages` is built with our default compiler, but we also provide other releases of GHC and package sets built with them.
releases of GHC and package sets built with them. You can list all available Available compilers are collected under `haskell.compiler`.
compilers like this:
```console Each of those compiler versions has a corresponding attribute set `packages` built with
$ nix-env -f '<nixpkgs>' -qaP -A haskell.compiler
haskell.compiler.ghc810 ghc-8.10.7
haskell.compiler.ghc90 ghc-9.0.2
haskell.compiler.ghc925 ghc-9.2.5
haskell.compiler.ghc926 ghc-9.2.6
haskell.compiler.ghc927 ghc-9.2.7
haskell.compiler.ghc92 ghc-9.2.8
haskell.compiler.ghc945 ghc-9.4.5
haskell.compiler.ghc946 ghc-9.4.6
haskell.compiler.ghc947 ghc-9.4.7
haskell.compiler.ghc94 ghc-9.4.8
haskell.compiler.ghc963 ghc-9.6.3
haskell.compiler.ghc96 ghc-9.6.4
haskell.compiler.ghc98 ghc-9.8.1
haskell.compiler.ghcHEAD ghc-9.9.20231121
haskell.compiler.ghc8107Binary ghc-binary-8.10.7
haskell.compiler.ghc865Binary ghc-binary-8.6.5
haskell.compiler.ghc924Binary ghc-binary-9.2.4
haskell.compiler.integer-simple.ghc8107 ghc-integer-simple-8.10.7
haskell.compiler.integer-simple.ghc810 ghc-integer-simple-8.10.7
haskell.compiler.native-bignum.ghc90 ghc-native-bignum-9.0.2
haskell.compiler.native-bignum.ghc902 ghc-native-bignum-9.0.2
haskell.compiler.native-bignum.ghc925 ghc-native-bignum-9.2.5
haskell.compiler.native-bignum.ghc926 ghc-native-bignum-9.2.6
haskell.compiler.native-bignum.ghc927 ghc-native-bignum-9.2.7
haskell.compiler.native-bignum.ghc92 ghc-native-bignum-9.2.8
haskell.compiler.native-bignum.ghc928 ghc-native-bignum-9.2.8
haskell.compiler.native-bignum.ghc945 ghc-native-bignum-9.4.5
haskell.compiler.native-bignum.ghc946 ghc-native-bignum-9.4.6
haskell.compiler.native-bignum.ghc947 ghc-native-bignum-9.4.7
haskell.compiler.native-bignum.ghc94 ghc-native-bignum-9.4.8
haskell.compiler.native-bignum.ghc948 ghc-native-bignum-9.4.8
haskell.compiler.native-bignum.ghc963 ghc-native-bignum-9.6.3
haskell.compiler.native-bignum.ghc96 ghc-native-bignum-9.6.4
haskell.compiler.native-bignum.ghc964 ghc-native-bignum-9.6.4
haskell.compiler.native-bignum.ghc98 ghc-native-bignum-9.8.1
haskell.compiler.native-bignum.ghc981 ghc-native-bignum-9.8.1
haskell.compiler.native-bignum.ghcHEAD ghc-native-bignum-9.9.20231121
haskell.compiler.ghcjs ghcjs-8.10.7
```
Each of those compiler versions has a corresponding attribute set built using
it. However, the non-standard package sets are not tested regularly and, as a it. However, the non-standard package sets are not tested regularly and, as a
result, contain fewer working packages. The corresponding package set for GHC result, contain fewer working packages. The corresponding package set for GHC
9.4.5 is `haskell.packages.ghc945`. In fact `haskellPackages` is just an alias 9.4.5 is `haskell.packages.ghc945`. In fact `haskellPackages` is just an alias
for `haskell.packages.ghc964`: for `haskell.packages.ghc964`:
```console
$ nix-env -f '<nixpkgs>' -qaP -A haskell.packages.ghc927
haskell.packages.ghc927.a50 a50-0.5
haskell.packages.ghc927.AAI AAI-0.2.0.1
haskell.packages.ghc927.aasam aasam-0.2.0.0
haskell.packages.ghc927.abacate abacate-0.0.0.0
haskell.packages.ghc927.abc-puzzle abc-puzzle-0.2.1
```
Every package set also re-exposes the GHC used to build its packages as `haskell.packages.*.ghc`. Every package set also re-exposes the GHC used to build its packages as `haskell.packages.*.ghc`.
### Available package versions {#haskell-available-versions} ### Available package versions {#haskell-available-versions}

View file

@ -19,7 +19,7 @@ let lspLibPkg = idris2Packages.buildIdris {
}; };
idrisLibraries = [ ]; idrisLibraries = [ ];
}; };
in lspLibPkg.library in lspLibPkg.library { withSource = true; }
``` ```
The above results in a derivation with the installed library results (with sourcecode). The above results in a derivation with the installed library results (with sourcecode).
@ -30,6 +30,7 @@ A slightly more involved example of a fully packaged executable would be the [`i
# Assuming the previous example lives in `lsp-lib.nix`: # Assuming the previous example lives in `lsp-lib.nix`:
let lspLib = callPackage ./lsp-lib.nix { }; let lspLib = callPackage ./lsp-lib.nix { };
inherit (idris2Packages) idris2Api;
lspPkg = idris2Packages.buildIdris { lspPkg = idris2Packages.buildIdris {
ipkgName = "idris2-lsp"; ipkgName = "idris2-lsp";
src = fetchFromGitHub { src = fetchFromGitHub {
@ -38,10 +39,9 @@ let lspLib = callPackage ./lsp-lib.nix { };
rev = "main"; rev = "main";
hash = "sha256-vQTzEltkx7uelDtXOHc6QRWZ4cSlhhm5ziOqWA+aujk="; hash = "sha256-vQTzEltkx7uelDtXOHc6QRWZ4cSlhhm5ziOqWA+aujk=";
}; };
idrisLibraries = [(idris2Packages.idris2Api { }) (lspLib { })]; idrisLibraries = [idris2Api lspLib];
}; };
in lspPkg.executable in lspPkg.executable
``` ```
The above uses the default value of `withSource = false` for both of the two required Idris libraries that the `idris2-lsp` executable depends on. `idris2Api` in the above derivation comes built in with `idris2Packages`. This library exposes many of the otherwise internal APIs of the Idris2 compiler. The above uses the default value of `withSource = false` for the `idris2Api` but could be modified to include that library's source by passing `(idris2Api { withSource = true; })` to `idrisLibraries` instead. `idris2Api` in the above derivation comes built in with `idris2Packages`. This library exposes many of the otherwise internal APIs of the Idris2 compiler.

View file

@ -2,6 +2,54 @@
The [standard build environment](#chap-stdenv) makes it easy to build typical Autotools-based packages with very little code. Any other kind of package can be accommodated by overriding the appropriate phases of `stdenv`. However, there are specialised functions in Nixpkgs to easily build packages for other programming languages, such as Perl or Haskell. These are described in this chapter. The [standard build environment](#chap-stdenv) makes it easy to build typical Autotools-based packages with very little code. Any other kind of package can be accommodated by overriding the appropriate phases of `stdenv`. However, there are specialised functions in Nixpkgs to easily build packages for other programming languages, such as Perl or Haskell. These are described in this chapter.
Each supported language or software ecosystem has its own package set named `<language or ecosystem>Packages`, which can be explored in various ways:
- Search on [search.nixos.org](https://search.nixos.org/packages)
For example, search for [`haskellPackages`](https://search.nixos.org/packages?query=haskellPackages) or [`rubyPackages`](https://search.nixos.org/packages?query=rubyPackages).
- Navigate attribute sets with [`nix repl`](https://nixos.org/manual/nix/stable/command-ref/new-cli/nix3-repl).
This technique is generally useful to inspect Nix language data structures.
:::{.example #example-navigte-nix-repl}
# Navigate Java compiler variants in `javaPackages` with `nix repl`
```shell-session
$ nix repl '<nixpkgs>' -I nixpkgs=channel:nixpkgs-unstable
nix-repl> javaPackages.<tab>
javaPackages.compiler javaPackages.openjfx15 javaPackages.openjfx21 javaPackages.recurseForDerivations
javaPackages.jogl_2_4_0 javaPackages.openjfx17 javaPackages.openjfx22
javaPackages.mavenfod javaPackages.openjfx19 javaPackages.override
javaPackages.openjfx11 javaPackages.openjfx20 javaPackages.overrideDerivation
```
:::
- List all derivations on the command line with [`nix-env --query`](https://nixos.org/manual/nix/stable/command-ref/nix-env/query).
`nix-env` is the only convenient way to do that, as it will skip attributes that fail [assertions](https://nixos.org/manual/nix/stable/language/constructs#assertions), such as when a package is [marked as broken](#var-meta-broken), rather than failing the entire evaluation.
:::{.example #example-list-haskellPackages}
# List all Python packages in Nixpkgs
The following command lists all [derivations names](https://nixos.org/manual/nix/stable/language/derivations#attr-name) with their attribute path from the latest Nixpkgs rolling release (`nixpkgs-unstable`).
```shell-session
$ nix-env -qaP -f '<nixpkgs>' -A pythonPackages -I nixpkgs=channel:nixpkgs-unstable
```
```console
pythonPackages.avahi avahi-0.8
pythonPackages.boost boost-1.81.0
pythonPackages.caffe caffe-1.0
pythonPackages.caffeWithCuda caffe-1.0
pythonPackages.cbeams cbeams-1.0.3
```
:::
```{=include=} sections ```{=include=} sections
agda.section.md agda.section.md
android.section.md android.section.md

View file

@ -40,20 +40,6 @@ Use `programs.steam.enable = true;` if you want to add steam to `systemPackages`
have a look at [this pull request](https://github.com/NixOS/nixpkgs/pull/20269). have a look at [this pull request](https://github.com/NixOS/nixpkgs/pull/20269).
- **Java**
1. There is no java in steam chrootenv by default. If you get a message like:
```
/home/foo/.local/share/Steam/SteamApps/common/towns/towns.sh: line 1: java: command not found
```
you need to add:
```nix
steam.override { withJava = true; }
```
## steam-run {#sec-steam-run} ## steam-run {#sec-steam-run}
The FHS-compatible chroot used for Steam can also be used to run other Linux games that expect a FHS environment. To use it, install the `steam-run` package and run the game with: The FHS-compatible chroot used for Steam can also be used to run other Linux games that expect a FHS environment. To use it, install the `steam-run` package and run the game with:

View file

@ -7,8 +7,6 @@ rec {
This helps protect against malformed command lines and also to reduce This helps protect against malformed command lines and also to reduce
boilerplate related to command-line construction for simple use cases. boilerplate related to command-line construction for simple use cases.
`toGNUCommandLine` returns a list of nix strings.
`toGNUCommandLineShell` returns an escaped shell string. `toGNUCommandLineShell` returns an escaped shell string.
@ -16,17 +14,86 @@ rec {
`options` `options`
: 1\. Function argument : How to format the arguments, see `toGNUCommandLine`
`attrs` `attrs`
: 2\. Function argument : The attributes to transform into arguments.
# Examples # Examples
:::{.example} :::{.example}
## `lib.cli.toGNUCommandLineShell` usage example ## `lib.cli.toGNUCommandLineShell` usage example
```nix
cli.toGNUCommandLineShell {} {
data = builtins.toJSON { id = 0; };
X = "PUT";
retry = 3;
retry-delay = null;
url = [ "https://example.com/foo" "https://example.com/bar" ];
silent = false;
verbose = true;
}
=> "'-X' 'PUT' '--data' '{\"id\":0}' '--retry' '3' '--url' 'https://example.com/foo' '--url' 'https://example.com/bar' '--verbose'";
```
:::
*/
toGNUCommandLineShell =
options: attrs: lib.escapeShellArgs (toGNUCommandLine options attrs);
/**
Automatically convert an attribute set to a list of command-line options.
`toGNUCommandLine` returns a list of string arguments.
# Inputs
`options`
: How to format the arguments, see below.
`attrs`
: The attributes to transform into arguments.
# Options
`mkOptionName`
: How to string-format the option name;
By default one character is a short option (`-`), more than one characters a long option (`--`).
`mkBool`
: How to format a boolean value to a command list;
By default its a flag option (only the option name if true, left out completely if false).
`mkList`
: How to format a list value to a command list;
By default the option name is repeated for each value and `mkOption` is applied to the values themselves.
`mkOption`
: How to format any remaining value to a command list;
On the toplevel, booleans and lists are handled by `mkBool` and `mkList`, though they can still appear as values of a list.
By default, everything is printed verbatim and complex types are forbidden (lists, attrsets, functions). `null` values are omitted.
`optionValueSeparator`
: How to separate an option from its flag;
By default, there is no separator, so option `-c` and value `5` would become ["-c" "5"].
This is useful if the command requires equals, for example, `-c=5`.
# Examples
:::{.example}
## `lib.cli.toGNUCommandLine` usage example
```nix ```nix
cli.toGNUCommandLine {} { cli.toGNUCommandLine {} {
data = builtins.toJSON { id = 0; }; data = builtins.toJSON { id = 0; };
@ -45,48 +112,20 @@ rec {
"--url" "https://example.com/bar" "--url" "https://example.com/bar"
"--verbose" "--verbose"
] ]
cli.toGNUCommandLineShell {} {
data = builtins.toJSON { id = 0; };
X = "PUT";
retry = 3;
retry-delay = null;
url = [ "https://example.com/foo" "https://example.com/bar" ];
silent = false;
verbose = true;
}
=> "'-X' 'PUT' '--data' '{\"id\":0}' '--retry' '3' '--url' 'https://example.com/foo' '--url' 'https://example.com/bar' '--verbose'";
``` ```
::: :::
*/ */
toGNUCommandLineShell =
options: attrs: lib.escapeShellArgs (toGNUCommandLine options attrs);
toGNUCommandLine = { toGNUCommandLine = {
# how to string-format the option name;
# by default one character is a short option (`-`),
# more than one characters a long option (`--`).
mkOptionName ? mkOptionName ?
k: if builtins.stringLength k == 1 k: if builtins.stringLength k == 1
then "-${k}" then "-${k}"
else "--${k}", else "--${k}",
# how to format a boolean value to a command list;
# by default its a flag option
# (only the option name if true, left out completely if false).
mkBool ? k: v: lib.optional v (mkOptionName k), mkBool ? k: v: lib.optional v (mkOptionName k),
# how to format a list value to a command list;
# by default the option name is repeated for each value
# and `mkOption` is applied to the values themselves.
mkList ? k: v: lib.concatMap (mkOption k) v, mkList ? k: v: lib.concatMap (mkOption k) v,
# how to format any remaining value to a command list;
# on the toplevel, booleans and lists are handled by `mkBool` and `mkList`,
# though they can still appear as values of a list.
# By default, everything is printed verbatim and complex types
# are forbidden (lists, attrsets, functions). `null` values are omitted.
mkOption ? mkOption ?
k: v: if v == null k: v: if v == null
then [] then []
@ -95,10 +134,6 @@ rec {
else else
[ "${mkOptionName k}${optionValueSeparator}${lib.generators.mkValueStringDefault {} v}" ], [ "${mkOptionName k}${optionValueSeparator}${lib.generators.mkValueStringDefault {} v}" ],
# how to separate an option from its flag;
# by default, there is no separator, so option `-c` and value `5`
# would become ["-c" "5"].
# This is useful if the command requires equals, for example, `-c=5`.
optionValueSeparator ? null optionValueSeparator ? null
}: }:
options: options:

View file

@ -17,7 +17,7 @@ let
else ""; else "";
in in
{ {
/* /**
Restrict a derivation to a predictable set of attribute names, so Restrict a derivation to a predictable set of attribute names, so
that the returned attrset is not strict in the actual derivation, that the returned attrset is not strict in the actual derivation,
saving a lot of computation when the derivation is non-trivial. saving a lot of computation when the derivation is non-trivial.
@ -62,25 +62,36 @@ in
(lazyDerivation { inherit derivation }).pythonPath (lazyDerivation { inherit derivation }).pythonPath
# Inputs
Takes an attribute set with the following attributes
`derivation`
: The derivation to be wrapped.
`meta`
: Optional meta attribute.
While this function is primarily about derivations, it can improve
the `meta` package attribute, which is usually specified through
`mkDerivation`.
`passthru`
: Optional extra values to add to the returned attrset.
This can be used for adding package attributes, such as `tests`.
`outputs`
: Optional list of assumed outputs. Default: ["out"]
This must match the set of outputs that the returned derivation has.
You must use this when the derivation has multiple outputs.
*/ */
lazyDerivation = lazyDerivation =
args@{ args@{
# The derivation to be wrapped. derivation,
derivation meta ? null,
, # Optional meta attribute. passthru ? { },
#
# While this function is primarily about derivations, it can improve
# the `meta` package attribute, which is usually specified through
# `mkDerivation`.
meta ? null
, # Optional extra values to add to the returned attrset.
#
# This can be used for adding package attributes, such as `tests`.
passthru ? { }
, # Optional list of assumed outputs. Default: ["out"]
#
# This must match the set of outputs that the returned derivation has.
# You must use this when the derivation has multiple outputs.
outputs ? [ "out" ] outputs ? [ "out" ]
}: }:
let let
@ -149,29 +160,50 @@ in
// genAttrs outputs (outputName: checked.${outputName}) // genAttrs outputs (outputName: checked.${outputName})
// passthru; // passthru;
/* Conditionally set a derivation attribute. /**
Conditionally set a derivation attribute.
Because `mkDerivation` sets `__ignoreNulls = true`, a derivation Because `mkDerivation` sets `__ignoreNulls = true`, a derivation
attribute set to `null` will not impact the derivation output hash. attribute set to `null` will not impact the derivation output hash.
Thus, this function passes through its `value` argument if the `cond` Thus, this function passes through its `value` argument if the `cond`
is `true`, but returns `null` if not. is `true`, but returns `null` if not.
Type: optionalDrvAttr :: Bool -> a -> a | Null
Example: # Inputs
(stdenv.mkDerivation {
name = "foo"; `cond`
x = optionalDrvAttr true 1;
y = optionalDrvAttr false 1; : Condition
}).drvPath == (stdenv.mkDerivation {
name = "foo"; `value`
x = 1;
}).drvPath : Attribute value
=> true
# Type
```
optionalDrvAttr :: Bool -> a -> a | Null
```
# Examples
:::{.example}
## `lib.derivations.optionalDrvAttr` usage example
```nix
(stdenv.mkDerivation {
name = "foo";
x = optionalDrvAttr true 1;
y = optionalDrvAttr false 1;
}).drvPath == (stdenv.mkDerivation {
name = "foo";
x = 1;
}).drvPath
=> true
```
:::
*/ */
optionalDrvAttr = optionalDrvAttr =
# Condition
cond: cond:
# Attribute value
value: if cond then value else null; value: if cond then value else null;
} }

View file

@ -1,4 +1,4 @@
/* /**
Functions for querying information about the filesystem Functions for querying information about the filesystem
without copying any files to the Nix store. without copying any files to the Nix store.
*/ */
@ -29,19 +29,35 @@ in
{ {
/* /**
The type of a path. The path needs to exist and be accessible. The type of a path. The path needs to exist and be accessible.
The result is either "directory" for a directory, "regular" for a regular file, "symlink" for a symlink, or "unknown" for anything else. The result is either "directory" for a directory, "regular" for a regular file, "symlink" for a symlink, or "unknown" for anything else.
Type: # Inputs
pathType :: Path -> String
Example: path
pathType /.
=> "directory"
pathType /some/file.nix : The path to query
=> "regular"
# Type
```
pathType :: Path -> String
```
# Examples
:::{.example}
## `lib.filesystem.pathType` usage example
```nix
pathType /.
=> "directory"
pathType /some/file.nix
=> "regular"
```
:::
*/ */
pathType = pathType =
builtins.readFileType or builtins.readFileType or
@ -59,53 +75,97 @@ in
else (readDir (dirOf path)).${baseNameOf path} else (readDir (dirOf path)).${baseNameOf path}
); );
/* /**
Whether a path exists and is a directory. Whether a path exists and is a directory.
Type:
pathIsDirectory :: Path -> Bool
Example: # Inputs
pathIsDirectory /.
=> true
pathIsDirectory /this/does/not/exist `path`
=> false
pathIsDirectory /some/file.nix : 1\. Function argument
=> false
# Type
```
pathIsDirectory :: Path -> Bool
```
# Examples
:::{.example}
## `lib.filesystem.pathIsDirectory` usage example
```nix
pathIsDirectory /.
=> true
pathIsDirectory /this/does/not/exist
=> false
pathIsDirectory /some/file.nix
=> false
```
:::
*/ */
pathIsDirectory = path: pathIsDirectory = path:
pathExists path && pathType path == "directory"; pathExists path && pathType path == "directory";
/* /**
Whether a path exists and is a regular file, meaning not a symlink or any other special file type. Whether a path exists and is a regular file, meaning not a symlink or any other special file type.
Type:
pathIsRegularFile :: Path -> Bool
Example: # Inputs
pathIsRegularFile /.
=> false
pathIsRegularFile /this/does/not/exist `path`
=> false
pathIsRegularFile /some/file.nix : 1\. Function argument
=> true
# Type
```
pathIsRegularFile :: Path -> Bool
```
# Examples
:::{.example}
## `lib.filesystem.pathIsRegularFile` usage example
```nix
pathIsRegularFile /.
=> false
pathIsRegularFile /this/does/not/exist
=> false
pathIsRegularFile /some/file.nix
=> true
```
:::
*/ */
pathIsRegularFile = path: pathIsRegularFile = path:
pathExists path && pathType path == "regular"; pathExists path && pathType path == "regular";
/* /**
A map of all haskell packages defined in the given path, A map of all haskell packages defined in the given path,
identified by having a cabal file with the same name as the identified by having a cabal file with the same name as the
directory itself. directory itself.
Type: Path -> Map String Path
# Inputs
`root`
: The directory within to search
# Type
```
Path -> Map String Path
```
*/ */
haskellPathsInDir = haskellPathsInDir =
# The directory within to search
root: root:
let # Files in the root let # Files in the root
root-files = builtins.attrNames (builtins.readDir root); root-files = builtins.attrNames (builtins.readDir root);
@ -120,17 +180,30 @@ in
builtins.pathExists (value + "/${name}.cabal") builtins.pathExists (value + "/${name}.cabal")
) root-files-with-paths; ) root-files-with-paths;
in builtins.listToAttrs cabal-subdirs; in builtins.listToAttrs cabal-subdirs;
/* /**
Find the first directory containing a file matching 'pattern' Find the first directory containing a file matching 'pattern'
upward from a given 'file'. upward from a given 'file'.
Returns 'null' if no directories contain a file matching 'pattern'. Returns 'null' if no directories contain a file matching 'pattern'.
Type: RegExp -> Path -> Nullable { path : Path; matches : [ MatchResults ]; }
# Inputs
`pattern`
: The pattern to search for
`file`
: The file to start searching upward from
# Type
```
RegExp -> Path -> Nullable { path : Path; matches : [ MatchResults ]; }
```
*/ */
locateDominatingFile = locateDominatingFile =
# The pattern to search for
pattern: pattern:
# The file to start searching upward from
file: file:
let go = path: let go = path:
let files = builtins.attrNames (builtins.readDir path); let files = builtins.attrNames (builtins.readDir path);
@ -150,13 +223,23 @@ in
in go (if isDir then file else parent); in go (if isDir then file else parent);
/* /**
Given a directory, return a flattened list of all files within it recursively. Given a directory, return a flattened list of all files within it recursively.
Type: Path -> [ Path ]
# Inputs
`dir`
: The path to recursively list
# Type
```
Path -> [ Path ]
```
*/ */
listFilesRecursive = listFilesRecursive =
# The path to recursively list
dir: dir:
lib.flatten (lib.mapAttrsToList (name: type: lib.flatten (lib.mapAttrsToList (name: type:
if type == "directory" then if type == "directory" then
@ -165,7 +248,7 @@ in
dir + "/${name}" dir + "/${name}"
) (builtins.readDir dir)); ) (builtins.readDir dir));
/* /**
Transform a directory tree containing package files suitable for Transform a directory tree containing package files suitable for
`callPackage` into a matching nested attribute set of derivations. `callPackage` into a matching nested attribute set of derivations.
@ -223,40 +306,57 @@ in
As a result, directories with no `.nix` files (including empty As a result, directories with no `.nix` files (including empty
directories) will be transformed into empty attribute sets. directories) will be transformed into empty attribute sets.
Example: # Inputs
packagesFromDirectoryRecursive {
inherit (pkgs) callPackage; Structured function argument
: Attribute set containing the following attributes.
Additional attributes are ignored.
`callPackage`
: `pkgs.callPackage`
Type: `Path -> AttrSet -> a`
`directory`
: The directory to read package files from
Type: `Path`
# Type
```
packagesFromDirectoryRecursive :: AttrSet -> AttrSet
```
# Examples
:::{.example}
## `lib.filesystem.packagesFromDirectoryRecursive` usage example
```nix
packagesFromDirectoryRecursive {
inherit (pkgs) callPackage;
directory = ./my-packages;
}
=> { ... }
lib.makeScope pkgs.newScope (
self: packagesFromDirectoryRecursive {
callPackage = self.callPackage;
directory = ./my-packages; directory = ./my-packages;
} }
=> { ... } )
=> { ... }
```
lib.makeScope pkgs.newScope ( :::
self: packagesFromDirectoryRecursive {
callPackage = self.callPackage;
directory = ./my-packages;
}
)
=> { ... }
Type:
packagesFromDirectoryRecursive :: AttrSet -> AttrSet
*/ */
packagesFromDirectoryRecursive = packagesFromDirectoryRecursive =
# Options.
{ {
/*
`pkgs.callPackage`
Type:
Path -> AttrSet -> a
*/
callPackage, callPackage,
/*
The directory to read package files from
Type:
Path
*/
directory, directory,
... ...
}: }:

View file

@ -1,18 +1,23 @@
/* Functions that generate widespread file /**
* formats from nix data structures. Functions that generate widespread file
* formats from nix data structures.
* They all follow a similar interface:
* generator { config-attrs } data They all follow a similar interface:
*
* `config-attrs` are holes in the generators ```nix
* with sensible default implementations that generator { config-attrs } data
* can be overwritten. The default implementations ```
* are mostly generators themselves, called with
* their respective default values; they can be reused. `config-attrs` are holes in the generators
* with sensible default implementations that
* Tests can be found in ./tests/misc.nix can be overwritten. The default implementations
* Documentation in the manual, #sec-generators are mostly generators themselves, called with
*/ their respective default values; they can be reused.
Tests can be found in ./tests/misc.nix
Further Documentation can be found [here](#sec-generators).
*/
{ lib }: { lib }:
let let
@ -68,11 +73,20 @@ let
; ;
## -- HELPER FUNCTIONS & DEFAULTS -- ## -- HELPER FUNCTIONS & DEFAULTS --
in rec {
/**
Convert a value to a sensible default string representation.
The builtin `toString` function has some strange defaults,
suitable for bash scripts but not much else.
/* Convert a value to a sensible default string representation. # Inputs
* The builtin `toString` function has some strange defaults,
* suitable for bash scripts but not much else. Options
*/ : Empty set, there may be configuration options in the future
`v`
: 2\. Function argument
*/
mkValueStringDefault = {}: v: mkValueStringDefault = {}: v:
let err = t: v: abort let err = t: v: abort
("generators.mkValueStringDefault: " + ("generators.mkValueStringDefault: " +
@ -100,15 +114,36 @@ let
else err "this value is" (toString v); else err "this value is" (toString v);
/* Generate a line of key k and value v, separated by /**
* character sep. If sep appears in k, it is escaped. Generate a line of key k and value v, separated by
* Helper for synaxes with different separators. character sep. If sep appears in k, it is escaped.
* Helper for synaxes with different separators.
* mkValueString specifies how values should be formatted.
* mkValueString specifies how values should be formatted.
* mkKeyValueDefault {} ":" "f:oo" "bar"
* > "f\:oo:bar" ```nix
*/ mkKeyValueDefault {} ":" "f:oo" "bar"
> "f\:oo:bar"
```
# Inputs
Structured function argument
: mkValueString (optional, default: `mkValueStringDefault {}`)
: Function to convert values to strings
`sep`
: 2\. Function argument
`k`
: 3\. Function argument
`v`
: 4\. Function argument
*/
mkKeyValueDefault = { mkKeyValueDefault = {
mkValueString ? mkValueStringDefault {} mkValueString ? mkValueStringDefault {}
}: sep: k: v: }: sep: k: v:
@ -118,10 +153,23 @@ let
## -- FILE FORMAT GENERATORS -- ## -- FILE FORMAT GENERATORS --
/* Generate a key-value-style config file from an attrset. /**
* Generate a key-value-style config file from an attrset.
* mkKeyValue is the same as in toINI.
*/ # Inputs
Structured function argument
: mkKeyValue (optional, default: `mkKeyValueDefault {} "="`)
: format a setting line from key and value
: listsAsDuplicateKeys (optional, default: `false`)
: allow lists as values for duplicate keys
: indent (optional, default: `""`)
: Initial indentation level
*/
toKeyValue = { toKeyValue = {
mkKeyValue ? mkKeyValueDefault {} "=", mkKeyValue ? mkKeyValueDefault {} "=",
listsAsDuplicateKeys ? false, listsAsDuplicateKeys ? false,
@ -134,32 +182,51 @@ let
in attrs: concatStrings (concatLists (mapAttrsToList mkLines attrs)); in attrs: concatStrings (concatLists (mapAttrsToList mkLines attrs));
/* Generate an INI-style config file from an /**
* attrset of sections to an attrset of key-value pairs. Generate an INI-style config file from an
* attrset of sections to an attrset of key-value pairs.
* generators.toINI {} {
* foo = { hi = "${pkgs.hello}"; ciao = "bar"; }; # Inputs
* baz = { "also, integers" = 42; };
* } Structured function argument
*
*> [baz] : mkSectionName (optional, default: `(name: escape [ "[" "]" ] name)`)
*> also, integers=42 : apply transformations (e.g. escapes) to section names
*>
*> [foo] : mkKeyValue (optional, default: `{} "="`)
*> ciao=bar : format a setting line from key and value
*> hi=/nix/store/y93qql1p5ggfnaqjjqhxcw0vqw95rlz0-hello-2.10
* : listsAsDuplicateKeys (optional, default: `false`)
* The mk* configuration attributes can generically change : allow lists as values for duplicate keys
* the way sections and key-value strings are generated.
* # Examples
* For more examples see the test cases in ./tests/misc.nix. :::{.example}
*/ ## `lib.generators.toINI` usage example
```nix
generators.toINI {} {
foo = { hi = "${pkgs.hello}"; ciao = "bar"; };
baz = { "also, integers" = 42; };
}
> [baz]
> also, integers=42
>
> [foo]
> ciao=bar
> hi=/nix/store/y93qql1p5ggfnaqjjqhxcw0vqw95rlz0-hello-2.10
```
The mk* configuration attributes can generically change
the way sections and key-value strings are generated.
For more examples see the test cases in ./tests/misc.nix.
:::
*/
toINI = { toINI = {
# apply transformations (e.g. escapes) to section names
mkSectionName ? (name: escape [ "[" "]" ] name), mkSectionName ? (name: escape [ "[" "]" ] name),
# format a setting line from key and value
mkKeyValue ? mkKeyValueDefault {} "=", mkKeyValue ? mkKeyValueDefault {} "=",
# allow lists as values for duplicate keys
listsAsDuplicateKeys ? false listsAsDuplicateKeys ? false
}: attrsOfAttrs: }: attrsOfAttrs:
let let
@ -174,43 +241,70 @@ let
# map input to ini sections # map input to ini sections
mapAttrsToStringsSep "\n" mkSection attrsOfAttrs; mapAttrsToStringsSep "\n" mkSection attrsOfAttrs;
/* Generate an INI-style config file from an attrset /**
* specifying the global section (no header), and an Generate an INI-style config file from an attrset
* attrset of sections to an attrset of key-value pairs. specifying the global section (no header), and an
* attrset of sections to an attrset of key-value pairs.
* generators.toINIWithGlobalSection {} {
* globalSection = { # Inputs
* someGlobalKey = "hi";
* }; 1\. Structured function argument
* sections = {
* foo = { hi = "${pkgs.hello}"; ciao = "bar"; }; : mkSectionName (optional, default: `(name: escape [ "[" "]" ] name)`)
* baz = { "also, integers" = 42; }; : apply transformations (e.g. escapes) to section names
* }
* : mkKeyValue (optional, default: `{} "="`)
*> someGlobalKey=hi : format a setting line from key and value
*>
*> [baz] : listsAsDuplicateKeys (optional, default: `false`)
*> also, integers=42 : allow lists as values for duplicate keys
*>
*> [foo] 2\. Structured function argument
*> ciao=bar
*> hi=/nix/store/y93qql1p5ggfnaqjjqhxcw0vqw95rlz0-hello-2.10 : globalSection (required)
* : global section key-value pairs
* The mk* configuration attributes can generically change
* the way sections and key-value strings are generated. : sections (optional, default: `{}`)
* : attrset of sections to key-value pairs
* For more examples see the test cases in ./tests/misc.nix.
* # Examples
* If you dont need a global section, you can also use :::{.example}
* `generators.toINI` directly, which only takes ## `lib.generators.toINIWithGlobalSection` usage example
* the part in `sections`.
*/ ```nix
generators.toINIWithGlobalSection {} {
globalSection = {
someGlobalKey = "hi";
};
sections = {
foo = { hi = "${pkgs.hello}"; ciao = "bar"; };
baz = { "also, integers" = 42; };
}
> someGlobalKey=hi
>
> [baz]
> also, integers=42
>
> [foo]
> ciao=bar
> hi=/nix/store/y93qql1p5ggfnaqjjqhxcw0vqw95rlz0-hello-2.10
```
The mk* configuration attributes can generically change
the way sections and key-value strings are generated.
For more examples see the test cases in ./tests/misc.nix.
:::
If you dont need a global section, you can also use
`generators.toINI` directly, which only takes
the part in `sections`.
*/
toINIWithGlobalSection = { toINIWithGlobalSection = {
# apply transformations (e.g. escapes) to section names
mkSectionName ? (name: escape [ "[" "]" ] name), mkSectionName ? (name: escape [ "[" "]" ] name),
# format a setting line from key and value
mkKeyValue ? mkKeyValueDefault {} "=", mkKeyValue ? mkKeyValueDefault {} "=",
# allow lists as values for duplicate keys
listsAsDuplicateKeys ? false listsAsDuplicateKeys ? false
}: { globalSection, sections ? {} }: }: { globalSection, sections ? {} }:
( if globalSection == {} ( if globalSection == {}
@ -219,24 +313,43 @@ let
+ "\n") + "\n")
+ (toINI { inherit mkSectionName mkKeyValue listsAsDuplicateKeys; } sections); + (toINI { inherit mkSectionName mkKeyValue listsAsDuplicateKeys; } sections);
/* Generate a git-config file from an attrset. /**
* Generate a git-config file from an attrset.
* It has two major differences from the regular INI format:
* It has two major differences from the regular INI format:
* 1. values are indented with tabs
* 2. sections can have sub-sections 1. values are indented with tabs
* 2. sections can have sub-sections
* generators.toGitINI {
* url."ssh://git@github.com/".insteadOf = "https://github.com"; Further: https://git-scm.com/docs/git-config#EXAMPLES
* user.name = "edolstra";
* } # Examples
* :::{.example}
*> [url "ssh://git@github.com/"] ## `lib.generators.toGitINI` usage example
*> insteadOf = "https://github.com"
*> ```nix
*> [user] generators.toGitINI {
*> name = "edolstra" url."ssh://git@github.com/".insteadOf = "https://github.com";
*/ user.name = "edolstra";
}
> [url "ssh://git@github.com/"]
> insteadOf = "https://github.com"
>
> [user]
> name = "edolstra"
```
:::
# Inputs
`attrs`
: Key-value pairs to be converted to a git-config file.
See: https://git-scm.com/docs/git-config#_variables for possible values.
*/
toGitINI = attrs: toGitINI = attrs:
let let
mkSectionName = name: mkSectionName = name:
@ -280,20 +393,40 @@ let
in in
toINI_ (gitFlattenAttrs attrs); toINI_ (gitFlattenAttrs attrs);
# mkKeyValueDefault wrapper that handles dconf INI quirks. /**
# The main differences of the format is that it requires strings to be quoted. mkKeyValueDefault wrapper that handles dconf INI quirks.
The main differences of the format is that it requires strings to be quoted.
*/
mkDconfKeyValue = mkKeyValueDefault { mkValueString = v: toString (gvariant.mkValue v); } "="; mkDconfKeyValue = mkKeyValueDefault { mkValueString = v: toString (gvariant.mkValue v); } "=";
# Generates INI in dconf keyfile style. See https://help.gnome.org/admin/system-admin-guide/stable/dconf-keyfiles.html.en /**
# for details. Generates INI in dconf keyfile style. See https://help.gnome.org/admin/system-admin-guide/stable/dconf-keyfiles.html.en
for details.
*/
toDconfINI = toINI { mkKeyValue = mkDconfKeyValue; }; toDconfINI = toINI { mkKeyValue = mkDconfKeyValue; };
/**
Recurses through a `Value` limited to a certain depth. (`depthLimit`)
If the depth is exceeded, an error is thrown, unless `throwOnDepthLimit` is set to `false`.
# Inputs
Structured function argument
: depthLimit (required)
: If this option is not null, the given value will stop evaluating at a certain depth
: throwOnDepthLimit (optional, default: `true`)
: If this option is true, an error will be thrown, if a certain given depth is exceeded
Value
: The value to be evaluated recursively
*/
withRecursion = withRecursion =
{ {
/* If this option is not null, the given value will stop evaluating at a certain depth */ depthLimit,
depthLimit throwOnDepthLimit ? true
/* If this option is true, an error will be thrown, if a certain given depth is exceeded */
, throwOnDepthLimit ? true
}: }:
assert isInt depthLimit; assert isInt depthLimit;
let let
@ -323,20 +456,33 @@ let
in in
mapAny 0; mapAny 0;
/* Pretty print a value, akin to `builtins.trace`. /**
* Should probably be a builtin as well. Pretty print a value, akin to `builtins.trace`.
* The pretty-printed string should be suitable for rendering default values
* in the NixOS manual. In particular, it should be as close to a valid Nix expression Should probably be a builtin as well.
* as possible.
*/ The pretty-printed string should be suitable for rendering default values
in the NixOS manual. In particular, it should be as close to a valid Nix expression
as possible.
# Inputs
Structured function argument
: allowPrettyValues
: If this option is true, attrsets like { __pretty = fn; val = ; }
will use fn to convert val to a pretty printed representation.
(This means fn is type Val -> String.)
: multiline
: If this option is true, the output is indented with newlines for attribute sets and lists
: indent
: Initial indentation level
Value
: The value to be pretty printed
*/
toPretty = { toPretty = {
/* If this option is true, attrsets like { __pretty = fn; val = ; }
will use fn to convert val to a pretty printed representation.
(This means fn is type Val -> String.) */
allowPrettyValues ? false, allowPrettyValues ? false,
/* If this option is true, the output is indented with newlines for attribute sets and lists */
multiline ? true, multiline ? true,
/* Initial indentation level */
indent ? "" indent ? ""
}: }:
let let
@ -397,7 +543,17 @@ let
else abort "generators.toPretty: should never happen (v = ${v})"; else abort "generators.toPretty: should never happen (v = ${v})";
in go indent; in go indent;
# PLIST handling /**
Translate a simple Nix expression to [Plist notation](https://en.wikipedia.org/wiki/Property_list).
# Inputs
Options
: Empty set, there may be configuration options in the future
Value
: The value to be converted to Plist
*/
toPlist = {}: v: let toPlist = {}: v: let
expr = ind: x: expr = ind: x:
if x == null then "" else if x == null then "" else
@ -447,9 +603,21 @@ let
${expr "" v} ${expr "" v}
</plist>''; </plist>'';
/* Translate a simple Nix expression to Dhall notation. /**
* Note that integers are translated to Integer and never Translate a simple Nix expression to Dhall notation.
* the Natural type.
Note that integers are translated to Integer and never
the Natural type.
# Inputs
Options
: Empty set, there may be configuration options in the future
Value
: The value to be converted to Dhall
*/ */
toDhall = { }@args: v: toDhall = { }@args: v:
let concatItems = concatStringsSep ", "; let concatItems = concatStringsSep ", ";
@ -471,46 +639,71 @@ ${expr "" v}
else else
toJSON v; toJSON v;
/* /**
Translate a simple Nix expression to Lua representation with occasional Translate a simple Nix expression to Lua representation with occasional
Lua-inlines that can be constructed by mkLuaInline function. Lua-inlines that can be constructed by mkLuaInline function.
Configuration: Configuration:
* multiline - by default is true which results in indented block-like view.
* indent - initial indent.
* asBindings - by default generate single value, but with this use attrset to set global vars.
Attention: * multiline - by default is true which results in indented block-like view.
Regardless of multiline parameter there is no trailing newline. * indent - initial indent.
* asBindings - by default generate single value, but with this use attrset to set global vars.
Example: Attention:
generators.toLua {}
{ Regardless of multiline parameter there is no trailing newline.
cmd = [ "typescript-language-server" "--stdio" ];
settings.workspace.library = mkLuaInline ''vim.api.nvim_get_runtime_file("", true)'';
} # Inputs
->
Structured function argument
: multiline (optional, default: `true`)
: If this option is true, the output is indented with newlines for attribute sets and lists
: indent (optional, default: `""`)
: Initial indentation level
: asBindings (optional, default: `false`)
: Interpret as variable bindings
Value
: The value to be converted to Lua
# Type
```
toLua :: AttrSet -> Any -> String
```
# Examples
:::{.example}
## `lib.generators.toLua` usage example
```nix
generators.toLua {}
{ {
["cmd"] = { cmd = [ "typescript-language-server" "--stdio" ];
"typescript-language-server", settings.workspace.library = mkLuaInline ''vim.api.nvim_get_runtime_file("", true)'';
"--stdio"
},
["settings"] = {
["workspace"] = {
["library"] = (vim.api.nvim_get_runtime_file("", true))
}
}
} }
->
{
["cmd"] = {
"typescript-language-server",
"--stdio"
},
["settings"] = {
["workspace"] = {
["library"] = (vim.api.nvim_get_runtime_file("", true))
}
}
}
```
Type: :::
toLua :: AttrSet -> Any -> String
*/ */
toLua = { toLua = {
/* If this option is true, the output is indented with newlines for attribute sets and lists */
multiline ? true, multiline ? true,
/* Initial indentation level */
indent ? "", indent ? "",
/* Interpret as variable bindings */
asBindings ? false, asBindings ? false,
}@args: v: }@args: v:
let let
@ -559,44 +752,55 @@ ${expr "" v}
else else
abort "generators.toLua: type ${typeOf v} is unsupported"; abort "generators.toLua: type ${typeOf v} is unsupported";
/* /**
Mark string as Lua expression to be inlined when processed by toLua. Mark string as Lua expression to be inlined when processed by toLua.
Type:
mkLuaInline :: String -> AttrSet # Inputs
`expr`
: 1\. Function argument
# Type
```
mkLuaInline :: String -> AttrSet
```
*/ */
mkLuaInline = expr: { _type = "lua-inline"; inherit expr; }; mkLuaInline = expr: { _type = "lua-inline"; inherit expr; };
} // {
/**
Generates JSON from an arbitrary (non-function) value.
For more information see the documentation of the builtin.
in # Inputs
# Everything in this attrset is the public interface of the file. Options
{
inherit
mkDconfKeyValue
mkKeyValueDefault
mkLuaInline
mkValueStringDefault
toDconfINI
toDhall
toGitINI
toINI
toINIWithGlobalSection
toKeyValue
toLua
toPlist
toPretty
withRecursion
;
/* Generates JSON from an arbitrary (non-function) value. : Empty set, there may be configuration options in the future
* For more information see the documentation of the builtin.
*/
toJSON = {}: toJSON;
/* YAML has been a strict superset of JSON since 1.2, so we Value
* use toJSON. Before it only had a few differences referring
* to implicit typing rules, so it should work with older : The value to be converted to JSON
* parsers as well. */
*/ toJSON = {}: lib.strings.toJSON;
toYAML = {}: toJSON;
/**
YAML has been a strict superset of JSON since 1.2, so we
use toJSON. Before it only had a few differences referring
to implicit typing rules, so it should work with older
parsers as well.
# Inputs
Options
: Empty set, there may be configuration options in the future
Value
: The value to be converted to YAML
*/
toYAML = {}: lib.strings.toJSON;
} }

View file

@ -1,4 +1,4 @@
/* /**
A partial and basic implementation of GVariant formatted strings. A partial and basic implementation of GVariant formatted strings.
See [GVariant Format Strings](https://docs.gtk.org/glib/gvariant-format-strings.html) for details. See [GVariant Format Strings](https://docs.gtk.org/glib/gvariant-format-strings.html) for details.
@ -41,17 +41,28 @@ let
variant = "v"; variant = "v";
}; };
/* Check if a value is a GVariant value
Type:
isGVariant :: Any -> Bool
*/
isGVariant = v: v._type or "" == "gvariant";
in in
rec { rec {
inherit type isGVariant; inherit type;
/**
Check if a value is a GVariant value
# Inputs
`v`
: value to check
# Type
```
isGVariant :: Any -> Bool
```
*/
isGVariant = v: v._type or "" == "gvariant";
intConstructors = [ intConstructors = [
{ {
@ -100,11 +111,22 @@ rec {
} }
]; ];
/* Returns the GVariant value that most closely matches the given Nix value. /**
If no GVariant value can be found unambiguously then error is thrown. Returns the GVariant value that most closely matches the given Nix value.
If no GVariant value can be found unambiguously then error is thrown.
Type:
mkValue :: Any -> gvariant # Inputs
`v`
: 1\. Function argument
# Type
```
mkValue :: Any -> gvariant
```
*/ */
mkValue = v: mkValue = v:
if builtins.isBool v then if builtins.isBool v then
@ -132,14 +154,32 @@ rec {
else else
throw "The GVariant type of ${builtins.typeOf v} can't be inferred."; throw "The GVariant type of ${builtins.typeOf v} can't be inferred.";
/* Returns the GVariant array from the given type of the elements and a Nix list. /**
Returns the GVariant array from the given type of the elements and a Nix list.
Type:
mkArray :: [Any] -> gvariant
Example: # Inputs
# Creating a string array
lib.gvariant.mkArray [ "a" "b" "c" ] `elems`
: 1\. Function argument
# Type
```
mkArray :: [Any] -> gvariant
```
# Examples
:::{.example}
## `lib.gvariant.mkArray` usage example
```nix
# Creating a string array
lib.gvariant.mkArray [ "a" "b" "c" ]
```
:::
*/ */
mkArray = elems: mkArray = elems:
let let
@ -153,31 +193,67 @@ rec {
"@${self.type} [${concatMapStringsSep "," toString self.value}]"; "@${self.type} [${concatMapStringsSep "," toString self.value}]";
}; };
/* Returns the GVariant array from the given empty Nix list. /**
Returns the GVariant array from the given empty Nix list.
Type:
mkEmptyArray :: gvariant.type -> gvariant
Example: # Inputs
# Creating an empty string array
lib.gvariant.mkEmptyArray (lib.gvariant.type.string) `elemType`
: 1\. Function argument
# Type
```
mkEmptyArray :: gvariant.type -> gvariant
```
# Examples
:::{.example}
## `lib.gvariant.mkEmptyArray` usage example
```nix
# Creating an empty string array
lib.gvariant.mkEmptyArray (lib.gvariant.type.string)
```
:::
*/ */
mkEmptyArray = elemType: mkPrimitive (type.arrayOf elemType) [ ] // { mkEmptyArray = elemType: mkPrimitive (type.arrayOf elemType) [ ] // {
__toString = self: "@${self.type} []"; __toString = self: "@${self.type} []";
}; };
/* Returns the GVariant variant from the given Nix value. Variants are containers /**
of different GVariant type. Returns the GVariant variant from the given Nix value. Variants are containers
of different GVariant type.
Type:
mkVariant :: Any -> gvariant
Example: # Inputs
lib.gvariant.mkArray [
(lib.gvariant.mkVariant "a string") `elem`
(lib.gvariant.mkVariant (lib.gvariant.mkInt32 1))
] : 1\. Function argument
# Type
```
mkVariant :: Any -> gvariant
```
# Examples
:::{.example}
## `lib.gvariant.mkVariant` usage example
```nix
lib.gvariant.mkArray [
(lib.gvariant.mkVariant "a string")
(lib.gvariant.mkVariant (lib.gvariant.mkInt32 1))
]
```
:::
*/ */
mkVariant = elem: mkVariant = elem:
let gvarElem = mkValue elem; let gvarElem = mkValue elem;
@ -185,23 +261,43 @@ rec {
__toString = self: "<${toString self.value}>"; __toString = self: "<${toString self.value}>";
}; };
/* Returns the GVariant dictionary entry from the given key and value. /**
Returns the GVariant dictionary entry from the given key and value.
Type:
mkDictionaryEntry :: String -> Any -> gvariant
Example: # Inputs
# A dictionary describing an Epiphanys search provider
[ `name`
(lib.gvariant.mkDictionaryEntry "url" (lib.gvariant.mkVariant "https://duckduckgo.com/?q=%s&t=epiphany"))
(lib.gvariant.mkDictionaryEntry "bang" (lib.gvariant.mkVariant "!d")) : The key of the entry
(lib.gvariant.mkDictionaryEntry "name" (lib.gvariant.mkVariant "DuckDuckGo"))
] `value`
: The value of the entry
# Type
```
mkDictionaryEntry :: String -> Any -> gvariant
```
# Examples
:::{.example}
## `lib.gvariant.mkDictionaryEntry` usage example
```nix
# A dictionary describing an Epiphanys search provider
[
(lib.gvariant.mkDictionaryEntry "url" (lib.gvariant.mkVariant "https://duckduckgo.com/?q=%s&t=epiphany"))
(lib.gvariant.mkDictionaryEntry "bang" (lib.gvariant.mkVariant "!d"))
(lib.gvariant.mkDictionaryEntry "name" (lib.gvariant.mkVariant "DuckDuckGo"))
]
```
:::
*/ */
mkDictionaryEntry = mkDictionaryEntry =
# The key of the entry
name: name:
# The value of the entry
value: value:
let let
name' = mkValue name; name' = mkValue name;
@ -212,10 +308,25 @@ rec {
__toString = self: "@${self.type} {${name'},${value'}}"; __toString = self: "@${self.type} {${name'},${value'}}";
}; };
/* Returns the GVariant maybe from the given element type. /**
Returns the GVariant maybe from the given element type.
Type:
mkMaybe :: gvariant.type -> Any -> gvariant # Inputs
`elemType`
: 1\. Function argument
`elem`
: 2\. Function argument
# Type
```
mkMaybe :: gvariant.type -> Any -> gvariant
```
*/ */
mkMaybe = elemType: elem: mkMaybe = elemType: elem:
mkPrimitive (type.maybeOf elemType) elem // { mkPrimitive (type.maybeOf elemType) elem // {
@ -226,24 +337,57 @@ rec {
"just ${toString self.value}"; "just ${toString self.value}";
}; };
/* Returns the GVariant nothing from the given element type. /**
Returns the GVariant nothing from the given element type.
Type:
mkNothing :: gvariant.type -> gvariant # Inputs
`elemType`
: 1\. Function argument
# Type
```
mkNothing :: gvariant.type -> gvariant
```
*/ */
mkNothing = elemType: mkMaybe elemType null; mkNothing = elemType: mkMaybe elemType null;
/* Returns the GVariant just from the given Nix value. /**
Returns the GVariant just from the given Nix value.
Type:
mkJust :: Any -> gvariant # Inputs
`elem`
: 1\. Function argument
# Type
```
mkJust :: Any -> gvariant
```
*/ */
mkJust = elem: let gvarElem = mkValue elem; in mkMaybe gvarElem.type gvarElem; mkJust = elem: let gvarElem = mkValue elem; in mkMaybe gvarElem.type gvarElem;
/* Returns the GVariant tuple from the given Nix list. /**
Returns the GVariant tuple from the given Nix list.
Type:
mkTuple :: [Any] -> gvariant # Inputs
`elems`
: 1\. Function argument
# Type
```
mkTuple :: [Any] -> gvariant
```
*/ */
mkTuple = elems: mkTuple = elems:
let let
@ -255,20 +399,42 @@ rec {
"@${self.type} (${concatMapStringsSep "," toString self.value})"; "@${self.type} (${concatMapStringsSep "," toString self.value})";
}; };
/* Returns the GVariant boolean from the given Nix bool value. /**
Returns the GVariant boolean from the given Nix bool value.
Type:
mkBoolean :: Bool -> gvariant # Inputs
`v`
: 1\. Function argument
# Type
```
mkBoolean :: Bool -> gvariant
```
*/ */
mkBoolean = v: mkBoolean = v:
mkPrimitive type.boolean v // { mkPrimitive type.boolean v // {
__toString = self: if self.value then "true" else "false"; __toString = self: if self.value then "true" else "false";
}; };
/* Returns the GVariant string from the given Nix string value. /**
Returns the GVariant string from the given Nix string value.
Type:
mkString :: String -> gvariant # Inputs
`v`
: 1\. Function argument
# Type
```
mkString :: String -> gvariant
```
*/ */
mkString = v: mkString = v:
let sanitize = s: replaceStrings [ "\n" ] [ "\\n" ] (escape [ "'" "\\" ] s); let sanitize = s: replaceStrings [ "\n" ] [ "\\n" ] (escape [ "'" "\\" ] s);
@ -276,72 +442,129 @@ rec {
__toString = self: "'${sanitize self.value}'"; __toString = self: "'${sanitize self.value}'";
}; };
/* Returns the GVariant object path from the given Nix string value. /**
Returns the GVariant object path from the given Nix string value.
Type:
mkObjectpath :: String -> gvariant # Inputs
`v`
: 1\. Function argument
# Type
```
mkObjectpath :: String -> gvariant
```
*/ */
mkObjectpath = v: mkObjectpath = v:
mkPrimitive type.string v // { mkPrimitive type.string v // {
__toString = self: "objectpath '${escape [ "'" ] self.value}'"; __toString = self: "objectpath '${escape [ "'" ] self.value}'";
}; };
/* Returns the GVariant uchar from the given Nix int value. /**
Returns the GVariant uchar from the given Nix int value.
Type: # Type
mkUchar :: Int -> gvariant
```
mkUchar :: Int -> gvariant
```
*/ */
mkUchar = mkPrimitive type.uchar; mkUchar = mkPrimitive type.uchar;
/* Returns the GVariant int16 from the given Nix int value. /**
Returns the GVariant int16 from the given Nix int value.
Type: # Type
mkInt16 :: Int -> gvariant
```
mkInt16 :: Int -> gvariant
```
*/ */
mkInt16 = mkPrimitive type.int16; mkInt16 = mkPrimitive type.int16;
/* Returns the GVariant uint16 from the given Nix int value. /**
Returns the GVariant uint16 from the given Nix int value.
Type: # Type
mkUint16 :: Int -> gvariant
```
mkUint16 :: Int -> gvariant
```
*/ */
mkUint16 = mkPrimitive type.uint16; mkUint16 = mkPrimitive type.uint16;
/* Returns the GVariant int32 from the given Nix int value. /**
Returns the GVariant int32 from the given Nix int value.
Type:
mkInt32 :: Int -> gvariant # Inputs
`v`
: 1\. Function argument
# Type
```
mkInt32 :: Int -> gvariant
```
*/ */
mkInt32 = v: mkInt32 = v:
mkPrimitive type.int32 v // { mkPrimitive type.int32 v // {
__toString = self: toString self.value; __toString = self: toString self.value;
}; };
/* Returns the GVariant uint32 from the given Nix int value. /**
Returns the GVariant uint32 from the given Nix int value.
Type: # Type
mkUint32 :: Int -> gvariant
```
mkUint32 :: Int -> gvariant
```
*/ */
mkUint32 = mkPrimitive type.uint32; mkUint32 = mkPrimitive type.uint32;
/* Returns the GVariant int64 from the given Nix int value. /**
Returns the GVariant int64 from the given Nix int value.
Type: # Type
mkInt64 :: Int -> gvariant
```
mkInt64 :: Int -> gvariant
```
*/ */
mkInt64 = mkPrimitive type.int64; mkInt64 = mkPrimitive type.int64;
/* Returns the GVariant uint64 from the given Nix int value. /**
Returns the GVariant uint64 from the given Nix int value.
Type: # Type
mkUint64 :: Int -> gvariant
```
mkUint64 :: Int -> gvariant
```
*/ */
mkUint64 = mkPrimitive type.uint64; mkUint64 = mkPrimitive type.uint64;
/* Returns the GVariant double from the given Nix float value. /**
Returns the GVariant double from the given Nix float value.
Type:
mkDouble :: Float -> gvariant # Inputs
`v`
: 1\. Function argument
# Type
```
mkDouble :: Float -> gvariant
```
*/ */
mkDouble = v: mkDouble = v:
mkPrimitive type.double v // { mkPrimitive type.double v // {

View file

@ -1,5 +1,7 @@
/* Some functions for manipulating meta attributes, as well as the /**
name attribute. */ Some functions for manipulating meta attributes, as well as the
name attribute.
*/
{ lib }: { lib }:
@ -11,90 +13,225 @@ in
rec { rec {
/* Add to or override the meta attributes of the given /**
derivation. Add to or override the meta attributes of the given
derivation.
Example: # Inputs
addMetaAttrs {description = "Bla blah";} somePkg
`newAttrs`
: 1\. Function argument
`drv`
: 2\. Function argument
# Examples
:::{.example}
## `lib.meta.addMetaAttrs` usage example
```nix
addMetaAttrs {description = "Bla blah";} somePkg
```
:::
*/ */
addMetaAttrs = newAttrs: drv: addMetaAttrs = newAttrs: drv:
drv // { meta = (drv.meta or {}) // newAttrs; }; drv // { meta = (drv.meta or {}) // newAttrs; };
/* Disable Hydra builds of given derivation. /**
Disable Hydra builds of given derivation.
# Inputs
`drv`
: 1\. Function argument
*/ */
dontDistribute = drv: addMetaAttrs { hydraPlatforms = []; } drv; dontDistribute = drv: addMetaAttrs { hydraPlatforms = []; } drv;
/* /**
Change the [symbolic name of a derivation](https://nixos.org/manual/nix/stable/language/derivations.html#attr-name). Change the [symbolic name of a derivation](https://nixos.org/manual/nix/stable/language/derivations.html#attr-name).
:::{.warning} :::{.warning}
Dependent derivations will be rebuilt when the symbolic name is changed. Dependent derivations will be rebuilt when the symbolic name is changed.
::: :::
# Inputs
`name`
: 1\. Function argument
`drv`
: 2\. Function argument
*/ */
setName = name: drv: drv // {inherit name;}; setName = name: drv: drv // {inherit name;};
/* Like `setName`, but takes the previous name as an argument. /**
Like `setName`, but takes the previous name as an argument.
Example: # Inputs
updateName (oldName: oldName + "-experimental") somePkg
`updater`
: 1\. Function argument
`drv`
: 2\. Function argument
# Examples
:::{.example}
## `lib.meta.updateName` usage example
```nix
updateName (oldName: oldName + "-experimental") somePkg
```
:::
*/ */
updateName = updater: drv: drv // {name = updater (drv.name);}; updateName = updater: drv: drv // {name = updater (drv.name);};
/* Append a suffix to the name of a package (before the version /**
part). */ Append a suffix to the name of a package (before the version
part).
# Inputs
`suffix`
: 1\. Function argument
*/
appendToName = suffix: updateName (name: appendToName = suffix: updateName (name:
let x = builtins.parseDrvName name; in "${x.name}-${suffix}-${x.version}"); let x = builtins.parseDrvName name; in "${x.name}-${suffix}-${x.version}");
/* Apply a function to each derivation and only to derivations in an attrset. /**
Apply a function to each derivation and only to derivations in an attrset.
# Inputs
`f`
: 1\. Function argument
`set`
: 2\. Function argument
*/ */
mapDerivationAttrset = f: set: lib.mapAttrs (name: pkg: if lib.isDerivation pkg then (f pkg) else pkg) set; mapDerivationAttrset = f: set: lib.mapAttrs (name: pkg: if lib.isDerivation pkg then (f pkg) else pkg) set;
/* Set the nix-env priority of the package. /**
Set the nix-env priority of the package.
# Inputs
`priority`
: 1\. Function argument
`drv`
: 2\. Function argument
*/ */
setPrio = priority: addMetaAttrs { inherit priority; }; setPrio = priority: addMetaAttrs { inherit priority; };
/* Decrease the nix-env priority of the package, i.e., other /**
versions/variants of the package will be preferred. Decrease the nix-env priority of the package, i.e., other
versions/variants of the package will be preferred.
# Inputs
`drv`
: 1\. Function argument
*/ */
lowPrio = setPrio 10; lowPrio = setPrio 10;
/* Apply lowPrio to an attrset with derivations /**
Apply lowPrio to an attrset with derivations
# Inputs
`set`
: 1\. Function argument
*/ */
lowPrioSet = set: mapDerivationAttrset lowPrio set; lowPrioSet = set: mapDerivationAttrset lowPrio set;
/* Increase the nix-env priority of the package, i.e., this /**
version/variant of the package will be preferred. Increase the nix-env priority of the package, i.e., this
version/variant of the package will be preferred.
# Inputs
`drv`
: 1\. Function argument
*/ */
hiPrio = setPrio (-10); hiPrio = setPrio (-10);
/* Apply hiPrio to an attrset with derivations /**
Apply hiPrio to an attrset with derivations
# Inputs
`set`
: 1\. Function argument
*/ */
hiPrioSet = set: mapDerivationAttrset hiPrio set; hiPrioSet = set: mapDerivationAttrset hiPrio set;
/* Check to see if a platform is matched by the given `meta.platforms` /**
element. Check to see if a platform is matched by the given `meta.platforms`
element.
A `meta.platform` pattern is either A `meta.platform` pattern is either
1. (legacy) a system string. 1. (legacy) a system string.
2. (modern) a pattern for the entire platform structure (see `lib.systems.inspect.platformPatterns`). 2. (modern) a pattern for the entire platform structure (see `lib.systems.inspect.platformPatterns`).
3. (modern) a pattern for the platform `parsed` field (see `lib.systems.inspect.patterns`). 3. (modern) a pattern for the platform `parsed` field (see `lib.systems.inspect.patterns`).
We can inject these into a pattern for the whole of a structured platform, We can inject these into a pattern for the whole of a structured platform,
and then match that. and then match that.
Example:
lib.meta.platformMatch { system = "aarch64-darwin"; } "aarch64-darwin" # Inputs
=> true
`platform`
: 1\. Function argument
`elem`
: 2\. Function argument
# Examples
:::{.example}
## `lib.meta.platformMatch` usage example
```nix
lib.meta.platformMatch { system = "aarch64-darwin"; } "aarch64-darwin"
=> true
```
:::
*/ */
platformMatch = platform: elem: ( platformMatch = platform: elem: (
# Check with simple string comparison if elem was a string. # Check with simple string comparison if elem was a string.
@ -112,39 +249,70 @@ rec {
) platform ) platform
); );
/* Check if a package is available on a given platform. /**
Check if a package is available on a given platform.
A package is available on a platform if both A package is available on a platform if both
1. One of `meta.platforms` pattern matches the given 1. One of `meta.platforms` pattern matches the given
platform, or `meta.platforms` is not present. platform, or `meta.platforms` is not present.
2. None of `meta.badPlatforms` pattern matches the given platform. 2. None of `meta.badPlatforms` pattern matches the given platform.
Example:
lib.meta.availableOn { system = "aarch64-darwin"; } pkg.zsh # Inputs
=> true
`platform`
: 1\. Function argument
`pkg`
: 2\. Function argument
# Examples
:::{.example}
## `lib.meta.availableOn` usage example
```nix
lib.meta.availableOn { system = "aarch64-darwin"; } pkg.zsh
=> true
```
:::
*/ */
availableOn = platform: pkg: availableOn = platform: pkg:
((!pkg?meta.platforms) || any (platformMatch platform) pkg.meta.platforms) && ((!pkg?meta.platforms) || any (platformMatch platform) pkg.meta.platforms) &&
all (elem: !platformMatch platform elem) (pkg.meta.badPlatforms or []); all (elem: !platformMatch platform elem) (pkg.meta.badPlatforms or []);
/* Get the corresponding attribute in lib.licenses /**
from the SPDX ID. Get the corresponding attribute in lib.licenses
For SPDX IDs, see from the SPDX ID.
https://spdx.org/licenses For SPDX IDs, see
https://spdx.org/licenses
Type: # Type
getLicenseFromSpdxId :: str -> AttrSet
Example: ```
lib.getLicenseFromSpdxId "MIT" == lib.licenses.mit getLicenseFromSpdxId :: str -> AttrSet
=> true ```
lib.getLicenseFromSpdxId "mIt" == lib.licenses.mit
=> true # Examples
lib.getLicenseFromSpdxId "MY LICENSE" :::{.example}
=> trace: warning: getLicenseFromSpdxId: No license matches the given SPDX ID: MY LICENSE ## `lib.meta.getLicenseFromSpdxId` usage example
=> { shortName = "MY LICENSE"; }
```nix
lib.getLicenseFromSpdxId "MIT" == lib.licenses.mit
=> true
lib.getLicenseFromSpdxId "mIt" == lib.licenses.mit
=> true
lib.getLicenseFromSpdxId "MY LICENSE"
=> trace: warning: getLicenseFromSpdxId: No license matches the given SPDX ID: MY LICENSE
=> { shortName = "MY LICENSE"; }
```
:::
*/ */
getLicenseFromSpdxId = getLicenseFromSpdxId =
let let
@ -156,15 +324,34 @@ rec {
{ shortName = licstr; } { shortName = licstr; }
); );
/* Get the path to the main program of a package based on meta.mainProgram /**
Get the path to the main program of a package based on meta.mainProgram
Type: getExe :: package -> string
Example: # Inputs
getExe pkgs.hello
=> "/nix/store/g124820p9hlv4lj8qplzxw1c44dxaw1k-hello-2.12/bin/hello" `x`
getExe pkgs.mustache-go
=> "/nix/store/am9ml4f4ywvivxnkiaqwr0hyxka1xjsf-mustache-go-1.3.0/bin/mustache" : 1\. Function argument
# Type
```
getExe :: package -> string
```
# Examples
:::{.example}
## `lib.meta.getExe` usage example
```nix
getExe pkgs.hello
=> "/nix/store/g124820p9hlv4lj8qplzxw1c44dxaw1k-hello-2.12/bin/hello"
getExe pkgs.mustache-go
=> "/nix/store/am9ml4f4ywvivxnkiaqwr0hyxka1xjsf-mustache-go-1.3.0/bin/mustache"
```
:::
*/ */
getExe = x: getExe' x (x.meta.mainProgram or ( getExe = x: getExe' x (x.meta.mainProgram or (
# This could be turned into an error when 23.05 is at end of life # This could be turned into an error when 23.05 is at end of life
@ -173,14 +360,38 @@ rec {
x x
)); ));
/* Get the path of a program of a derivation. /**
Get the path of a program of a derivation.
Type: getExe' :: derivation -> string -> string
Example: # Inputs
getExe' pkgs.hello "hello"
=> "/nix/store/g124820p9hlv4lj8qplzxw1c44dxaw1k-hello-2.12/bin/hello" `x`
getExe' pkgs.imagemagick "convert"
=> "/nix/store/5rs48jamq7k6sal98ymj9l4k2bnwq515-imagemagick-7.1.1-15/bin/convert" : 1\. Function argument
`y`
: 2\. Function argument
# Type
```
getExe' :: derivation -> string -> string
```
# Examples
:::{.example}
## `lib.meta.getExe'` usage example
```nix
getExe' pkgs.hello "hello"
=> "/nix/store/g124820p9hlv4lj8qplzxw1c44dxaw1k-hello-2.12/bin/hello"
getExe' pkgs.imagemagick "convert"
=> "/nix/store/5rs48jamq7k6sal98ymj9l4k2bnwq515-imagemagick-7.1.1-15/bin/convert"
```
:::
*/ */
getExe' = x: y: getExe' = x: y:
assert assertMsg (isDerivation x) assert assertMsg (isDerivation x)

View file

@ -220,10 +220,10 @@ rec {
(if isList example then "${pkgsText}." + concatStringsSep "." example else example); (if isList example then "${pkgsText}." + concatStringsSep "." example else example);
}); });
/* Alias of mkPackageOption. Previously used to create options with markdown /* Deprecated alias of mkPackageOption, to be removed in 25.05.
documentation, which is no longer required. Previously used to create options with markdown documentation, which is no longer required.
*/ */
mkPackageOptionMD = mkPackageOption; mkPackageOptionMD = lib.warn "mkPackageOptionMD is deprecated and will be removed in 25.05; please use mkPackageOption." mkPackageOption;
/* This option accepts anything, but it does not produce any result. /* This option accepts anything, but it does not produce any result.

View file

@ -84,20 +84,21 @@ let
useLLVM = final.isFreeBSD || final.isOpenBSD; useLLVM = final.isFreeBSD || final.isOpenBSD;
libc = libc =
/**/ if final.isDarwin then "libSystem" /**/ if final.isDarwin then "libSystem"
else if final.isMinGW then "msvcrt" else if final.isMinGW then "msvcrt"
else if final.isWasi then "wasilibc" else if final.isWasi then "wasilibc"
else if final.isRedox then "relibc" else if final.isWasm && !final.isWasi then null
else if final.isMusl then "musl" else if final.isRedox then "relibc"
else if final.isUClibc then "uclibc" else if final.isMusl then "musl"
else if final.isAndroid then "bionic" else if final.isUClibc then "uclibc"
else if final.isLinux /* default */ then "glibc" else if final.isAndroid then "bionic"
else if final.isFreeBSD then "fblibc" else if final.isLinux /* default */ then "glibc"
else if final.isOpenBSD then "oblibc" else if final.isFreeBSD then "fblibc"
else if final.isNetBSD then "nblibc" else if final.isOpenBSD then "oblibc"
else if final.isAvr then "avrlibc" else if final.isNetBSD then "nblibc"
else if final.isGhcjs then null else if final.isAvr then "avrlibc"
else if final.isNone then "newlib" else if final.isGhcjs then null
else if final.isNone then "newlib"
# TODO(@Ericson2314) think more about other operating systems # TODO(@Ericson2314) think more about other operating systems
else "native/impure"; else "native/impure";
# Choose what linker we wish to use by default. Someday we might also # Choose what linker we wish to use by default. Someday we might also
@ -179,6 +180,7 @@ let
(isAndroid || isGnu || isMusl # Linux (allows multiple libcs) (isAndroid || isGnu || isMusl # Linux (allows multiple libcs)
|| isDarwin || isSunOS || isOpenBSD || isFreeBSD || isNetBSD # BSDs || isDarwin || isSunOS || isOpenBSD || isFreeBSD || isNetBSD # BSDs
|| isCygwin || isMinGW # Windows || isCygwin || isMinGW # Windows
|| isWasm # WASM
) && !isStatic; ) && !isStatic;
# The difference between `isStatic` and `hasSharedLibraries` is mainly the # The difference between `isStatic` and `hasSharedLibraries` is mainly the
@ -187,7 +189,7 @@ let
# don't support dynamic linking, but don't get the `staticMarker`. # don't support dynamic linking, but don't get the `staticMarker`.
# `pkgsStatic` sets `isStatic=true`, so `pkgsStatic.hostPlatform` always # `pkgsStatic` sets `isStatic=true`, so `pkgsStatic.hostPlatform` always
# has the `staticMarker`. # has the `staticMarker`.
isStatic = final.isWasm || final.isRedox; isStatic = final.isWasi || final.isRedox;
# Just a guess, based on `system` # Just a guess, based on `system`
inherit inherit
@ -337,7 +339,8 @@ let
if isList f then f else [ f ] if isList f then f else [ f ]
) )
else optional final.isUnix "unix" else optional final.isUnix "unix"
++ optional final.isWindows "windows"; ++ optional final.isWindows "windows"
++ optional final.isWasm "wasm";
# https://doc.rust-lang.org/reference/conditional-compilation.html#target_vendor # https://doc.rust-lang.org/reference/conditional-compilation.html#target_vendor
vendor = let vendor = let

View file

@ -356,6 +356,12 @@ rec {
useLLVM = true; useLLVM = true;
}; };
wasm32-unknown-none = {
config = "wasm32-unknown-none";
rust.rustcTarget = "wasm32-unknown-unknown";
useLLVM = true;
};
# Ghcjs # Ghcjs
ghcjs = { ghcjs = {
# This triple is special to GHC/Cabal/GHCJS and not recognized by autotools # This triple is special to GHC/Cabal/GHCJS and not recognized by autotools

View file

@ -466,11 +466,12 @@ rec {
} }
# cpu-vendor-os # cpu-vendor-os
else if elemAt l 1 == "apple" || else if elemAt l 1 == "apple" ||
elem (elemAt l 2) [ "wasi" "redox" "mmixware" "ghcjs" "mingw32" ] || elem (elemAt l 2) [ "redox" "mmixware" "ghcjs" "mingw32" ] ||
hasPrefix "freebsd" (elemAt l 2) || hasPrefix "freebsd" (elemAt l 2) ||
hasPrefix "netbsd" (elemAt l 2) || hasPrefix "netbsd" (elemAt l 2) ||
hasPrefix "openbsd" (elemAt l 2) || hasPrefix "openbsd" (elemAt l 2) ||
hasPrefix "genode" (elemAt l 2) hasPrefix "genode" (elemAt l 2) ||
hasPrefix "wasm32" (elemAt l 0)
then { then {
cpu = elemAt l 0; cpu = elemAt l 0;
vendor = elemAt l 1; vendor = elemAt l 1;

View file

@ -379,7 +379,7 @@ in {
*/ */
oldestSupportedRelease = oldestSupportedRelease =
# Update on master only. Do not backport. # Update on master only. Do not backport.
2311; 2405;
/** /**
Whether a feature is supported in all supported releases (at the time of Whether a feature is supported in all supported releases (at the time of

View file

@ -97,6 +97,12 @@
githubId = 9675338; githubId = 9675338;
keys = [ { fingerprint = "F466 A548 AD3F C1F1 8C88 4576 8702 7528 B006 D66D"; } ]; keys = [ { fingerprint = "F466 A548 AD3F C1F1 8C88 4576 8702 7528 B006 D66D"; } ];
}; };
_0x5a4 = {
email = "bej86nug@hhu.de";
name = "0x5a4";
github = "0x5a4";
githubId = 54070204;
};
_0xB10C = { _0xB10C = {
email = "nixpkgs@b10c.me"; email = "nixpkgs@b10c.me";
name = "0xB10C"; name = "0xB10C";
@ -640,7 +646,7 @@
name = "Alexander Hirner"; name = "Alexander Hirner";
}; };
ahoneybun = { ahoneybun = {
email = "aaron@system76.com"; email = "aaronhoneycutt@proton.me";
github = "ahoneybun"; github = "ahoneybun";
githubId = 4884946; githubId = 4884946;
name = "Aaron Honeycutt"; name = "Aaron Honeycutt";
@ -1048,13 +1054,6 @@
githubId = 169249; githubId = 169249;
name = "Alex Brandt"; name = "Alex Brandt";
}; };
alva = {
email = "alva@skogen.is";
github = "illfygli";
githubId = 42881386;
name = "Alva";
keys = [ { fingerprint = "B422 CFB1 C9EF 73F7 E1E2 698D F53E 3233 42F7 A6D3A"; } ];
};
alxsimon = { alxsimon = {
email = "alexis.simon@normalesup.org"; email = "alexis.simon@normalesup.org";
github = "alxsimon"; github = "alxsimon";
@ -1160,6 +1159,11 @@
githubId = 858965; githubId = 858965;
name = "Andrew Morsillo"; name = "Andrew Morsillo";
}; };
amozeo = {
email = "wroclaw223@outlook.com";
githubId = 37040543;
name = "Wroclaw";
};
amyipdev = { amyipdev = {
email = "amy@amyip.net"; email = "amy@amyip.net";
github = "amyipdev"; github = "amyipdev";
@ -2665,6 +2669,12 @@
githubId = 37907; githubId = 37907;
name = "Julian Stecklina"; name = "Julian Stecklina";
}; };
bloeckchengrafik = {
email = "christian.bergschneider@gmx.de";
github = "Bloeckchengrafik";
githubId = 37768199;
name = "Christian Bergschneider";
};
bloveless = { bloveless = {
email = "brennon.loveless@gmail.com"; email = "brennon.loveless@gmail.com";
github = "bloveless"; github = "bloveless";
@ -4342,6 +4352,12 @@
githubId = 24708079; githubId = 24708079;
name = "Dan Eads"; name = "Dan Eads";
}; };
danielalvsaaker = {
email = "daniel.alvsaaker@proton.me";
github = "danielalvsaaker";
githubId = 30574112;
name = "Daniel Alvsåker";
};
danielbarter = { danielbarter = {
email = "danielbarter@gmail.com"; email = "danielbarter@gmail.com";
github = "danielbarter"; github = "danielbarter";
@ -5879,6 +5895,13 @@
githubId = 13485450; githubId = 13485450;
name = "Emmanuel Rosa"; name = "Emmanuel Rosa";
}; };
emneo = {
name = "emneo";
email = "emneo@kreog.com";
github = "emneo-dev";
githubId = 44233177;
keys = [ { fingerprint = "5FD0 400D 0E78 EAF9 8431 4880 8EBF C4B9 24C6 2D20"; } ];
};
emptyflask = { emptyflask = {
email = "jon@emptyflask.dev"; email = "jon@emptyflask.dev";
github = "emptyflask"; github = "emptyflask";
@ -6636,6 +6659,12 @@
githubId = 1109959; githubId = 1109959;
name = "Florian Jacob"; name = "Florian Jacob";
}; };
floriansanderscc = {
email = "florian.sanders+nixos@clever-cloud.com";
github = "florian-sanders-cc";
githubId = 100240294;
name = "Florian Sanders";
};
flosse = { flosse = {
email = "mail@markus-kohlhase.de"; email = "mail@markus-kohlhase.de";
github = "flosse"; github = "flosse";
@ -8395,6 +8424,12 @@
email = "astrid@astrid.tech"; email = "astrid@astrid.tech";
name = "ifd3f"; name = "ifd3f";
}; };
if-loop69420 = {
github = "if-loop69420";
githubId = 81078181;
email = "j.sztavi@pm.me";
name = "Jeremy Sztavinovszki";
};
iFreilicht = { iFreilicht = {
github = "iFreilicht"; github = "iFreilicht";
githubId = 9742635; githubId = 9742635;
@ -8740,12 +8775,6 @@
githubId = 650601; githubId = 650601;
name = "Ivan Tkatchev"; name = "Ivan Tkatchev";
}; };
ivar = {
email = "ivar.scholten@protonmail.com";
github = "IvarWithoutBones";
githubId = 41924494;
name = "Ivar";
};
ivarmedi = { ivarmedi = {
email = "ivar@larsson.me"; email = "ivar@larsson.me";
github = "ivarmedi"; github = "ivarmedi";
@ -8959,6 +8988,11 @@
githubId = 3874017; githubId = 3874017;
name = "Jappie Klooster"; name = "Jappie Klooster";
}; };
jaredmontoya = {
name = "Jared Montoya";
github = "jaredmontoya";
githubId = 49511278;
};
jasoncarr = { jasoncarr = {
email = "jcarr250@gmail.com"; email = "jcarr250@gmail.com";
github = "jasoncarr0"; github = "jasoncarr0";
@ -9757,13 +9791,6 @@
github = "jonochang"; github = "jonochang";
githubId = 13179; githubId = 13179;
}; };
jonringer = {
email = "jonringer117@gmail.com";
matrix = "@jonringer:matrix.org";
github = "jonringer";
githubId = 7673602;
name = "Jonathan Ringer";
};
jopejoe1 = { jopejoe1 = {
email = "johannes@joens.email"; email = "johannes@joens.email";
matrix = "@jopejoe1:matrix.org"; matrix = "@jopejoe1:matrix.org";
@ -10628,6 +10655,12 @@
github = "kkoniuszy"; github = "kkoniuszy";
githubId = 120419423; githubId = 120419423;
}; };
klchen0112 = {
name = "klchen0112";
email = "klchen0112@gmail.com";
github = "klchen0112";
githubId = 32459567;
};
klden = { klden = {
name = "Kenzyme Le"; name = "Kenzyme Le";
email = "kl@kenzymele.com"; email = "kl@kenzymele.com";
@ -11094,12 +11127,6 @@
githubId = 621759; githubId = 621759;
name = "Lassulus"; name = "Lassulus";
}; };
laurailway = {
email = "laurailway.git@posteo.net";
github = "LAURAilway";
githubId = 118690640;
name = "Laura";
};
laurent-f1z1 = { laurent-f1z1 = {
email = "laurent.nixpkgs@fainsin.bzh"; email = "laurent.nixpkgs@fainsin.bzh";
github = "Laurent2916"; github = "Laurent2916";
@ -11344,6 +11371,12 @@
githubId = 1769386; githubId = 1769386;
name = "Liam Diprose"; name = "Liam Diprose";
}; };
liarokapisv = {
email = "liarokapis.v@gmail.com";
github = "liarokapisv";
githubId = 19633626;
name = "Alexandros Liarokapis";
};
liassica = { liassica = {
email = "git-commit.jingle869@aleeas.com"; email = "git-commit.jingle869@aleeas.com";
github = "Liassica"; github = "Liassica";
@ -11441,6 +11474,12 @@
githubId = 36448130; githubId = 36448130;
name = "Michael Brantley"; name = "Michael Brantley";
}; };
linbreux = {
email = "linbreux@gmail.com";
github = "linbreux";
githubId = 29354411;
name = "linbreux";
};
linc01n = { linc01n = {
email = "git@lincoln.hk"; email = "git@lincoln.hk";
github = "linc01n"; github = "linc01n";
@ -12922,7 +12961,7 @@
name = "Merlin Humml"; name = "Merlin Humml";
}; };
mguentner = { mguentner = {
email = "code@klandest.in"; email = "code@mguentner.de";
github = "mguentner"; github = "mguentner";
githubId = 668926; githubId = 668926;
name = "Maximilian Güntner"; name = "Maximilian Güntner";
@ -12944,6 +12983,12 @@
githubId = 20536514; githubId = 20536514;
name = "Magdalena Haselsteiner"; name = "Magdalena Haselsteiner";
}; };
mi-ael = {
email = "miael.oss.1970@gmail.com";
name = "mi-ael";
github = "mi-ael";
githubId = 12199265;
};
miangraham = { miangraham = {
github = "miangraham"; github = "miangraham";
githubId = 704580; githubId = 704580;
@ -13327,6 +13372,12 @@
githubId = 5698461; githubId = 5698461;
name = "Maciej Kazulak"; name = "Maciej Kazulak";
}; };
mkez = {
email = "matias.zwinger+nix@protonmail.com";
github = "mk3z";
githubId = 52108954;
name = "Matias Zwinger";
};
mkf = { mkf = {
email = "m@mikf.pl"; email = "m@mikf.pl";
github = "mkf"; github = "mkf";
@ -14193,7 +14244,7 @@
networkexception = { networkexception = {
name = "networkException"; name = "networkException";
email = "nix@nwex.de"; email = "nix@nwex.de";
matrix = "@networkexception:chat.upi.li"; matrix = "@networkexception:nwex.de";
github = "networkException"; github = "networkException";
githubId = 42888162; githubId = 42888162;
keys = [ { fingerprint = "A0B9 48C5 A263 55C2 035F 8567 FBB7 2A94 52D9 1A72"; } ]; keys = [ { fingerprint = "A0B9 48C5 A263 55C2 035F 8567 FBB7 2A94 52D9 1A72"; } ];
@ -19932,6 +19983,13 @@
github = "thenonameguy"; github = "thenonameguy";
githubId = 2217181; githubId = 2217181;
}; };
theobori = {
name = "Théo Bori";
email = "theo1.bori@epitech.eu";
github = "theobori";
githubId = 71843723;
keys = [ { fingerprint = "EEFB CC3A C529 CFD1 943D A75C BDD5 7BE9 9D55 5965"; } ];
};
therealansh = { therealansh = {
email = "tyagiansh23@gmail.com"; email = "tyagiansh23@gmail.com";
github = "therealansh"; github = "therealansh";
@ -20316,6 +20374,12 @@
email = "tomaszierl@outlook.com"; email = "tomaszierl@outlook.com";
name = "Tomkoid"; name = "Tomkoid";
}; };
Tommimon = {
name = "Tommaso Montanari";
email = "sefymw7q8@mozmail.com";
github = "Tommimon";
githubId = 37435103;
};
tomodachi94 = { tomodachi94 = {
email = "tomodachi94@protonmail.com"; email = "tomodachi94@protonmail.com";
matrix = "@tomodachi94:matrix.org"; matrix = "@tomodachi94:matrix.org";
@ -21951,6 +22015,12 @@
githubId = 58453832; githubId = 58453832;
keys = [ { fingerprint = "FD0A C425 9EF5 4084 F99F 9B47 2ACC 9749 7C68 FAD4"; } ]; keys = [ { fingerprint = "FD0A C425 9EF5 4084 F99F 9B47 2ACC 9749 7C68 FAD4"; } ];
}; };
yelite = {
name = "Lite Ye";
email = "yelite958@gmail.com";
github = "yelite";
githubId = 3517225;
};
YellowOnion = { YellowOnion = {
name = "Daniel Hill"; name = "Daniel Hill";
email = "daniel@gluo.nz"; email = "daniel@gluo.nz";

View file

@ -47,6 +47,30 @@ target:
who can help you test the updated architecture and once reviewed tag who can help you test the updated architecture and once reviewed tag
`@lovesegfault` to upload the tarballs. `@lovesegfault` to upload the tarballs.
## How to add bootstrap files for a new target
The procedure to add a new target is very similar to the update
procedure. The only difference is that you need to set up a new job to
build the `bootstrapFiles`. To do that you will need the following:
1. Add your new target to `lib/systems/examples.nix`
This will populate `pkgsCross.$target` attribute set. If you are
dealing with `bootstrapFiles` upload you probably already have it.
2. Add your new target to
`pkgs/stdenv/linux/make-bootstrap-tools-cross.nix`. This will add a
new hydra job to `nixpkgs:cross-trunk` jobset.
3. Wait for a hydra to build your bootstrap tarballs.
4. Add your new target to
`maintainers/scripts/bootstrap-files/refresh-tarballs.bash` around
`CROSS_TARGETS=()`.
5. Add your new target to `pkgs/stdenv/linux/default.nix` and follow
standard bootstrap seed update procedure above.
## Bootstrap files job definitions ## Bootstrap files job definitions
There are two types of bootstrap files: There are two types of bootstrap files:

View file

@ -136,7 +136,6 @@ telescope.nvim,,,,,5.1,
telescope-manix,,,,,, telescope-manix,,,,,,
tiktoken_core,,,,,,natsukium tiktoken_core,,,,,,natsukium
tl,,,,,,mephistophiles tl,,,,,,mephistophiles
toml,,,,,,mrcjkb
toml-edit,,,,,5.1,mrcjkb toml-edit,,,,,5.1,mrcjkb
tree-sitter-norg,,,,,5.1,mrcjkb tree-sitter-norg,,,,,5.1,mrcjkb
vstruct,,,,,, vstruct,,,,,,

1 name rockspec ref server version luaversion maintainers
136 telescope-manix
137 tiktoken_core natsukium
138 tl mephistophiles
toml mrcjkb
139 toml-edit 5.1 mrcjkb
140 tree-sitter-norg 5.1 mrcjkb
141 vstruct

View file

@ -141,6 +141,13 @@ with lib.maintainers;
enableFeatureFreezePing = true; enableFeatureFreezePing = true;
}; };
clevercloud = {
members = [ floriansanderscc ];
scope = "Maintain Clever Cloud related packages.";
shortName = "CleverCloud";
githubTeams = [ "CleverCloud" ];
};
cloudposse = { cloudposse = {
members = [ dudymas ]; members = [ dudymas ];
scope = "Maintain atmos and applications made by the Cloud Posse team."; scope = "Maintain atmos and applications made by the Cloud Posse team.";
@ -192,7 +199,6 @@ with lib.maintainers;
dotnet = { dotnet = {
members = [ members = [
ivar
mdarocha mdarocha
corngood corngood
ggg ggg
@ -380,6 +386,7 @@ with lib.maintainers;
golang = { golang = {
members = [ members = [
kalbasit kalbasit
katexochen
mic92 mic92
zowoq zowoq
qbit qbit
@ -460,7 +467,6 @@ with lib.maintainers;
members = [ members = [
cleverca22 cleverca22
disassembler disassembler
jonringer
manveru manveru
nrdxp nrdxp
]; ];
@ -794,7 +800,6 @@ with lib.maintainers;
python = { python = {
members = [ members = [
hexa hexa
jonringer
natsukium natsukium
]; ];
scope = "Maintain the Python interpreter and related packages."; scope = "Maintain the Python interpreter and related packages.";
@ -913,7 +918,6 @@ with lib.maintainers;
members = [ members = [
atemu atemu
eclairevoyant eclairevoyant
jonringer
k900 k900
mkg20001 mkg20001
]; ];
@ -945,7 +949,6 @@ with lib.maintainers;
vim = { vim = {
members = [ members = [
figsoda figsoda
jonringer
softinio softinio
teto teto
]; ];

View file

@ -21,6 +21,10 @@
- [Renovate](https://github.com/renovatebot/renovate), a dependency updating tool for various git forges and language ecosystems. Available as [services.renovate](#opt-services.renovate.enable). - [Renovate](https://github.com/renovatebot/renovate), a dependency updating tool for various git forges and language ecosystems. Available as [services.renovate](#opt-services.renovate.enable).
- [wg-access-server](https://github.com/freifunkMUC/wg-access-server/), an all-in-one WireGuard VPN solution with a web ui for connecting devices. Available at [services.wg-access-server](#opt-services.wg-access-server.enable).
- [Playerctld](https://github.com/altdesktop/playerctl), a daemon to track media player activity. Available as [services.playerctld](option.html#opt-services.playerctld).
## Backward Incompatibilities {#sec-release-24.11-incompatibilities} ## Backward Incompatibilities {#sec-release-24.11-incompatibilities}
- `transmission` package has been aliased with a `trace` warning to `transmission_3`. Since [Transmission 4 has been released last year](https://github.com/transmission/transmission/releases/tag/4.0.0), and Transmission 3 will eventually go away, it was decided perform this warning alias to make people aware of the new version. The `services.transmission.package` defaults to `transmission_3` as well because the upgrade can cause data loss in certain specific usage patterns (examples: [#5153](https://github.com/transmission/transmission/issues/5153), [#6796](https://github.com/transmission/transmission/issues/6796)). Please make sure to back up to your data directory per your usage: - `transmission` package has been aliased with a `trace` warning to `transmission_3`. Since [Transmission 4 has been released last year](https://github.com/transmission/transmission/releases/tag/4.0.0), and Transmission 3 will eventually go away, it was decided perform this warning alias to make people aware of the new version. The `services.transmission.package` defaults to `transmission_3` as well because the upgrade can cause data loss in certain specific usage patterns (examples: [#5153](https://github.com/transmission/transmission/issues/5153), [#6796](https://github.com/transmission/transmission/issues/6796)). Please make sure to back up to your data directory per your usage:
@ -43,6 +47,8 @@
- For convenience, the top-level `clang-tools` attribute remains and is now bound to `llvmPackages.clang-tools`. - For convenience, the top-level `clang-tools` attribute remains and is now bound to `llvmPackages.clang-tools`.
- Top-level `clang_tools_<version>` attributes are now aliases; these will be removed in a future release. - Top-level `clang_tools_<version>` attributes are now aliases; these will be removed in a future release.
- `buildbot` was updated to 4.0, the AngularJS frontend has been replaced by a React frontend, see the [upstream release notes](https://docs.buildbot.net/current/manual/upgrading/4.0-upgrade.html).
- `nginx` package no longer includes `gd` and `geoip` dependencies. For enabling it, override `nginx` package with the optionals `withImageFilter` and `withGeoIP`. - `nginx` package no longer includes `gd` and `geoip` dependencies. For enabling it, override `nginx` package with the optionals `withImageFilter` and `withGeoIP`.
- `openssh` and `openssh_hpn` are now compiled without Kerberos 5 / GSSAPI support in an effort to reduce the attack surface of the components for the majority of users. Users needing this support can - `openssh` and `openssh_hpn` are now compiled without Kerberos 5 / GSSAPI support in an effort to reduce the attack surface of the components for the majority of users. Users needing this support can
@ -56,6 +62,8 @@
nvimpager settings: user commands in `-c` and `--cmd` now override the nvimpager settings: user commands in `-c` and `--cmd` now override the
respective default settings because they are executed later. respective default settings because they are executed later.
- `pkgs.nextcloud27` has been removed since it's EOL.
- `services.forgejo.mailerPasswordFile` has been deprecated by the drop-in replacement `services.forgejo.secrets.mailer.PASSWD`, - `services.forgejo.mailerPasswordFile` has been deprecated by the drop-in replacement `services.forgejo.secrets.mailer.PASSWD`,
which is part of the new free-form `services.forgejo.secrets` option. which is part of the new free-form `services.forgejo.secrets` option.
`services.forgejo.secrets` is a small wrapper over systemd's `LoadCredential=`. It has the same structure (sections/keys) as `services.forgejo.secrets` is a small wrapper over systemd's `LoadCredential=`. It has the same structure (sections/keys) as
@ -98,8 +106,24 @@
for `stateVersion` ≥ 24.11. (It was previously using SQLite for structured for `stateVersion` ≥ 24.11. (It was previously using SQLite for structured
data and the filesystem for blobs). data and the filesystem for blobs).
- The `shiori` service now requires an HTTP secret value `SHIORI_HTTP_SECRET_KEY` to be provided via environment variable. The nixos module therefore, now provides an environmentFile option:
```
# This is how a environment file can be generated:
# $ printf "SHIORI_HTTP_SECRET_KEY=%s\n" "$(openssl rand -hex 16)" > /path/to/env-file
services.shiori.environmentFile = "/path/to/env-file";
```
- `libe57format` has been updated to `>= 3.0.0`, which contains some backward-incompatible API changes. See the [release note](https://github.com/asmaloney/libE57Format/releases/tag/v3.0.0) for more details. - `libe57format` has been updated to `>= 3.0.0`, which contains some backward-incompatible API changes. See the [release note](https://github.com/asmaloney/libE57Format/releases/tag/v3.0.0) for more details.
- `gitlab` deprecated support for *runner registration tokens* in GitLab 16.0, disabled their support in GitLab 17.0 and will
ultimately remove it in GitLab 18.0, as outlined in the
[documentation](https://docs.gitlab.com/17.0/ee/ci/runners/new_creation_workflow.html#estimated-time-frame-for-planned-changes).
After upgrading to GitLab >= 17.0, it is possible to re-enable support for registration tokens in the UI until GitLab 18.0.
Refer to the manual on [using registration tokens after GitLab 17.0](https://docs.gitlab.com/17.0/ee/ci/runners/new_creation_workflow.html#using-registration-tokens-after-gitlab-170).
GitLab administrators should migrate to the [new runner registration workflow](https://docs.gitlab.com/17.0/ee/ci/runners/new_creation_workflow.html#using-registration-tokens-after-gitlab-170)
with *runner authentication tokens* until the release of GitLab 18.0.
- `zx` was updated to v8, which introduces several breaking changes. - `zx` was updated to v8, which introduces several breaking changes.
See the [v8 changelog](https://github.com/google/zx/releases/tag/8.0.0) for more information. See the [v8 changelog](https://github.com/google/zx/releases/tag/8.0.0) for more information.
@ -112,6 +136,10 @@
services.portunus.ldap.package = pkgs.openldap.override { libxcrypt = pkgs.libxcrypt-legacy; }; services.portunus.ldap.package = pkgs.openldap.override { libxcrypt = pkgs.libxcrypt-legacy; };
``` ```
- The default value of `services.kubernetes.kubelet.hostname` is now lowercased.
Explicitly set `kubelet.hostname` to `networking.fqdnOrHostName` to get back
the old default behavior.
- `keycloak` was updated to version 25, which introduces new hostname related options. - `keycloak` was updated to version 25, which introduces new hostname related options.
See [Upgrading Guide](https://www.keycloak.org/docs/25.0.1/upgrading/#migrating-to-25-0-0) for instructions. See [Upgrading Guide](https://www.keycloak.org/docs/25.0.1/upgrading/#migrating-to-25-0-0) for instructions.
@ -119,6 +147,9 @@
support, which is the intended default behavior by Tracy maintainers. support, which is the intended default behavior by Tracy maintainers.
X11 users have to switch to the new package `tracy-x11`. X11 users have to switch to the new package `tracy-x11`.
- The `services.prometheus.exporters.minio` option has been removed, as it's upstream implementation was broken and unmaintained.
Minio now has built-in [Prometheus metrics exposure](https://min.io/docs/minio/linux/operations/monitoring/collect-minio-metrics-using-prometheus.html), which can be used instead.
## Other Notable Changes {#sec-release-24.11-notable-changes} ## Other Notable Changes {#sec-release-24.11-notable-changes}
<!-- To avoid merge conflicts, consider adding your item at an arbitrary place in the list instead. --> <!-- To avoid merge conflicts, consider adding your item at an arbitrary place in the list instead. -->
@ -127,6 +158,19 @@
not the `hare` package, should be added to `nativeBuildInputs` when building not the `hare` package, should be added to `nativeBuildInputs` when building
Hare programs. Hare programs.
- [`lib.options.mkPackageOptionMD`](https://nixos.org/manual/nixpkgs/unstable#function-library-lib.options.mkPackageOptionMD) is now obsolete; use the identical [`lib.options.mkPackageOption`](https://nixos.org/manual/nixpkgs/unstable#function-library-lib.options.mkPackageOption) instead.
- To facilitate dependency injection, the `imgui` package now builds a static archive using vcpkg' CMake rules. - To facilitate dependency injection, the `imgui` package now builds a static archive using vcpkg' CMake rules.
The derivation now installs "impl" headers selectively instead of by a wildcard. The derivation now installs "impl" headers selectively instead of by a wildcard.
Use `imgui.src` if you just want to access the unpacked sources. Use `imgui.src` if you just want to access the unpacked sources.
- Cinnamon has been updated to 6.2.
- Following Mint 22 defaults, the Cinnamon module no longer ships geary and hexchat by default.
- Nemo is now built with gtk-layer-shell support, note that for now it will be expected to see nemo-desktop
listed as a regular entry in Cinnamon Wayland session's window list applet.
- Support for *runner registration tokens* has been [deprecated](https://gitlab.com/gitlab-org/gitlab/-/issues/380872)
in `gitlab-runner` 15.6 and is expected to be removed in `gitlab-runner` 18.0. Configuration of existing runners
should be changed to using *runner authentication tokens* by configuring
{option}`services.gitlab-runner.services.<name>.authenticationTokenConfigFile` instead of the former
{option}`services.gitlab-runner.services.<name>.registrationConfigFile` option.

View file

@ -46,8 +46,6 @@ in
TRUNK_LINK_FAILURE_MODE = 0; TRUNK_LINK_FAILURE_MODE = 0;
NVSWITCH_FAILURE_MODE = 0; NVSWITCH_FAILURE_MODE = 0;
ABORT_CUDA_JOBS_ON_FM_EXIT = 1; ABORT_CUDA_JOBS_ON_FM_EXIT = 1;
TOPOLOGY_FILE_PATH = "${nvidia_x11.fabricmanager}/share/nvidia-fabricmanager/nvidia/nvswitch";
DATABASE_PATH = "${nvidia_x11.fabricmanager}/share/nvidia-fabricmanager/nvidia/nvswitch";
}; };
defaultText = lib.literalExpression '' defaultText = lib.literalExpression ''
{ {
@ -69,8 +67,6 @@ in
TRUNK_LINK_FAILURE_MODE=0; TRUNK_LINK_FAILURE_MODE=0;
NVSWITCH_FAILURE_MODE=0; NVSWITCH_FAILURE_MODE=0;
ABORT_CUDA_JOBS_ON_FM_EXIT=1; ABORT_CUDA_JOBS_ON_FM_EXIT=1;
TOPOLOGY_FILE_PATH="''${nvidia_x11.fabricmanager}/share/nvidia-fabricmanager/nvidia/nvswitch";
DATABASE_PATH="''${nvidia_x11.fabricmanager}/share/nvidia-fabricmanager/nvidia/nvswitch";
} }
''; '';
description = '' description = ''
@ -628,7 +624,14 @@ in
TimeoutStartSec = 240; TimeoutStartSec = 240;
ExecStart = ExecStart =
let let
nv-fab-conf = settingsFormat.generate "fabricmanager.conf" cfg.datacenter.settings; # Since these rely on the `nvidia_x11.fabricmanager` derivation, they're
# unsuitable to be mentioned in the configuration defaults, but they _can_
# be overridden in `cfg.datacenter.settings` if needed.
fabricManagerConfDefaults = {
TOPOLOGY_FILE_PATH = "${nvidia_x11.fabricmanager}/share/nvidia-fabricmanager/nvidia/nvswitch";
DATABASE_PATH = "${nvidia_x11.fabricmanager}/share/nvidia-fabricmanager/nvidia/nvswitch";
};
nv-fab-conf = settingsFormat.generate "fabricmanager.conf" (fabricManagerConfDefaults // cfg.datacenter.settings);
in in
"${lib.getExe nvidia_x11.fabricmanager} -c ${nv-fab-conf}"; "${lib.getExe nvidia_x11.fabricmanager} -c ${nv-fab-conf}";
LimitCORE = "infinity"; LimitCORE = "infinity";

View file

@ -90,8 +90,8 @@ let
}."${compression.algorithm}"; }."${compression.algorithm}";
compressionCommand = { compressionCommand = {
"zstd" = "zstd --no-progress --threads=0 -${toString compression.level}"; "zstd" = "zstd --no-progress --threads=$NIX_BUILD_CORES -${toString compression.level}";
"xz" = "xz --keep --verbose --threads=0 -${toString compression.level}"; "xz" = "xz --keep --verbose --threads=$NIX_BUILD_CORES -${toString compression.level}";
}."${compression.algorithm}"; }."${compression.algorithm}";
in in
stdenvNoCC.mkDerivation (finalAttrs: stdenvNoCC.mkDerivation (finalAttrs:

View file

@ -1,7 +1,7 @@
{ {
x86_64-linux = "/nix/store/yrsmzlw2lgbknzwic1gy1gmv3l2w1ax8-nix-2.18.3"; x86_64-linux = "/nix/store/1w4b47zhp33md29wjhgg549pc281vv02-nix-2.18.4";
i686-linux = "/nix/store/ds9381l9mlwfaclvqnkzn3jl4qb8m3y1-nix-2.18.3"; i686-linux = "/nix/store/hz02kn0ffn3wdi2xs7lndpr88v4v4fp2-nix-2.18.4";
aarch64-linux = "/nix/store/hw1zny3f8520zyskmp1qaybv1ir5ilxh-nix-2.18.3"; aarch64-linux = "/nix/store/90zwqa9z2fgldc7ki1p5gfvglchjh9r6-nix-2.18.4";
x86_64-darwin = "/nix/store/z08yc4sl1fr65q53wz6pw30h67qafaln-nix-2.18.3"; x86_64-darwin = "/nix/store/bd1ix5mj9lj2yh7bqnmdjc24zlg5jivk-nix-2.18.4";
aarch64-darwin = "/nix/store/p57m7m0wrz8sqxiwinzpwzqzak82zn75-nix-2.18.3"; aarch64-darwin = "/nix/store/5hvsmklhqiay5i4q5vdkg60p8qpc69rz-nix-2.18.4";
} }

View file

@ -96,12 +96,17 @@ in
{option}`documentation.man.mandoc.manPath` to an empty list (`[]`). {option}`documentation.man.mandoc.manPath` to an empty list (`[]`).
''; '';
}; };
output.fragment = lib.mkEnableOption '' output.fragment = lib.mkOption {
Omit the <!DOCTYPE> declaration and the <html>, <head>, and <body> type = lib.types.bool;
elements and only emit the subtree below the <body> element in HTML default = false;
output of {manpage}`mandoc(1)`. The style argument will be ignored. example = true;
This is useful when embedding manual content within existing documents. description = ''
''; Whether to omit the <!DOCTYPE> declaration and the <html>, <head>, and <body>
elements and only emit the subtree below the <body> element in HTML
output of {manpage}`mandoc(1)`. The style argument will be ignored.
This is useful when embedding manual content within existing documents.
'';
};
output.includes = lib.mkOption { output.includes = lib.mkOption {
type = with lib.types; nullOr str; type = with lib.types; nullOr str;
default = null; default = null;
@ -160,9 +165,9 @@ in
''; '';
}; };
output.toc = lib.mkEnableOption '' output.toc = lib.mkEnableOption ''
In HTML output of {manpage}`mandoc(1)`, If an input file contains printing a table of contents near the beginning of the HTML output
at least two non-standard sections, print a table of contents near of {manpage}`mandoc(1)` if an input file contains at least two
the beginning of the output. non-standard sections
''; '';
output.width = lib.mkOption { output.width = lib.mkOption {
type = with lib.types; nullOr int; type = with lib.types; nullOr int;

View file

@ -243,6 +243,7 @@
./programs/nh.nix ./programs/nh.nix
./programs/nix-index.nix ./programs/nix-index.nix
./programs/nix-ld.nix ./programs/nix-ld.nix
./programs/nix-required-mounts.nix
./programs/nm-applet.nix ./programs/nm-applet.nix
./programs/nncp.nix ./programs/nncp.nix
./programs/noisetorch.nix ./programs/noisetorch.nix
@ -477,6 +478,7 @@
./services/desktops/bamf.nix ./services/desktops/bamf.nix
./services/desktops/blueman.nix ./services/desktops/blueman.nix
./services/desktops/cpupower-gui.nix ./services/desktops/cpupower-gui.nix
./services/desktops/deepin/deepin-anything.nix
./services/desktops/deepin/dde-api.nix ./services/desktops/deepin/dde-api.nix
./services/desktops/deepin/app-services.nix ./services/desktops/deepin/app-services.nix
./services/desktops/deepin/dde-daemon.nix ./services/desktops/deepin/dde-daemon.nix
@ -485,6 +487,7 @@
./services/desktops/espanso.nix ./services/desktops/espanso.nix
./services/desktops/flatpak.nix ./services/desktops/flatpak.nix
./services/desktops/geoclue2.nix ./services/desktops/geoclue2.nix
./services/desktops/playerctld.nix
./services/desktops/gnome/at-spi2-core.nix ./services/desktops/gnome/at-spi2-core.nix
./services/desktops/gnome/evolution-data-server.nix ./services/desktops/gnome/evolution-data-server.nix
./services/desktops/gnome/glib-networking.nix ./services/desktops/gnome/glib-networking.nix
@ -1224,6 +1227,7 @@
./services/networking/vsftpd.nix ./services/networking/vsftpd.nix
./services/networking/wasabibackend.nix ./services/networking/wasabibackend.nix
./services/networking/websockify.nix ./services/networking/websockify.nix
./services/networking/wg-access-server.nix
./services/networking/wg-netmanager.nix ./services/networking/wg-netmanager.nix
./services/networking/webhook.nix ./services/networking/webhook.nix
./services/networking/wg-quick.nix ./services/networking/wg-quick.nix

View file

@ -8,9 +8,7 @@ in {
options = { options = {
programs.dublin-traceroute = { programs.dublin-traceroute = {
enable = lib.mkEnableOption '' enable = lib.mkEnableOption "dublin-traceroute (including setcap wrapper)";
dublin-traceroute, add it to the global environment and configure a setcap wrapper for it.
'';
package = lib.mkPackageOption pkgs "dublin-traceroute" { }; package = lib.mkPackageOption pkgs "dublin-traceroute" { };
}; };

View file

@ -1,7 +1,7 @@
{ lib, pkgs, config, ... }: { lib, pkgs, config, ... }:
{ {
options.programs.joycond-cemuhook = { options.programs.joycond-cemuhook = {
enable = lib.mkEnableOption "joycond-cemuhook, a program to enable support for cemuhook's UDP protocol for joycond devices."; enable = lib.mkEnableOption "joycond-cemuhook, a program to enable support for cemuhook's UDP protocol for joycond devices";
}; };
config = lib.mkIf config.programs.joycond-cemuhook.enable { config = lib.mkIf config.programs.joycond-cemuhook.enable {

View file

@ -6,7 +6,7 @@ in
{ {
options.programs.mouse-actions = { options.programs.mouse-actions = {
enable = lib.mkEnableOption '' enable = lib.mkEnableOption ''
mouse-actions udev rules. This is a prerequisite for using mouse-actions without being root. mouse-actions udev rules. This is a prerequisite for using mouse-actions without being root
''; '';
}; };
config = lib.mkIf cfg.enable { config = lib.mkIf cfg.enable {

View file

@ -0,0 +1,118 @@
{
config,
lib,
pkgs,
...
}:
let
cfg = config.programs.nix-required-mounts;
package = pkgs.nix-required-mounts;
Mount =
with lib;
types.submodule {
options.host = mkOption {
type = types.str;
description = "Host path to mount";
};
options.guest = mkOption {
type = types.str;
description = "Location in the sandbox to mount the host path at";
};
};
Pattern =
with lib.types;
types.submodule (
{ config, name, ... }:
{
options.onFeatures = lib.mkOption {
type = listOf types.str;
description = "Which requiredSystemFeatures should trigger relaxation of the sandbox";
default = [ name ];
};
options.paths = lib.mkOption {
type = listOf (oneOf [
path
Mount
]);
description = "A list of glob patterns, indicating which paths to expose to the sandbox";
};
options.unsafeFollowSymlinks = lib.mkEnableOption ''
Instructs the hook to mount the symlink targets as well, when any of
the `paths` contain symlinks. This may not work correctly with glob
patterns.
'';
}
);
driverPaths = [
pkgs.addOpenGLRunpath.driverLink
# mesa:
config.hardware.opengl.package
# nvidia_x11, etc:
] ++ config.hardware.opengl.extraPackages; # nvidia_x11
defaults = {
nvidia-gpu.onFeatures = package.allowedPatterns.nvidia-gpu.onFeatures;
nvidia-gpu.paths = package.allowedPatterns.nvidia-gpu.paths ++ driverPaths;
nvidia-gpu.unsafeFollowSymlinks = false;
};
in
{
meta.maintainers = with lib.maintainers; [ SomeoneSerge ];
options.programs.nix-required-mounts = {
enable = lib.mkEnableOption "Expose extra paths to the sandbox depending on derivations' requiredSystemFeatures";
presets.nvidia-gpu.enable = lib.mkEnableOption ''
Declare the support for derivations that require an Nvidia GPU to be
available, e.g. derivations with `requiredSystemFeatures = [ "cuda" ]`.
This mounts the corresponding userspace drivers and device nodes in the
sandbox, but only for derivations that request these special features.
You may extend or override the exposed paths via the
`programs.nix-required-mounts.allowedPatterns.nvidia-gpu.paths` option.
'';
allowedPatterns =
with lib.types;
lib.mkOption rec {
type = attrsOf Pattern;
description = "The hook config, describing which paths to mount for which system features";
default = { };
defaultText = lib.literalExpression ''
{
opengl.paths = config.hardware.opengl.extraPackages ++ [
config.hardware.opengl.package
pkgs.addOpenGLRunpath.driverLink
"/dev/dri"
];
}
'';
example.require-ipfs.paths = [ "/ipfs" ];
example.require-ipfs.onFeatures = [ "ifps" ];
};
extraWrapperArgs = lib.mkOption {
type = with lib.types; listOf str;
default = [ ];
description = "List of extra arguments (such as `--add-flags -v`) to pass to the hook's wrapper";
};
package = lib.mkOption {
type = lib.types.package;
default = package.override { inherit (cfg) allowedPatterns extraWrapperArgs; };
description = "The final package with the final config applied";
internal = true;
};
};
config = lib.mkIf cfg.enable (
lib.mkMerge [
{ nix.settings.pre-build-hook = lib.getExe cfg.package; }
(lib.mkIf cfg.presets.nvidia-gpu.enable {
nix.settings.system-features = cfg.allowedPatterns.nvidia-gpu.onFeatures;
programs.nix-required-mounts.allowedPatterns = {
inherit (defaults) nvidia-gpu;
};
})
]
);
}

View file

@ -9,7 +9,7 @@ in
programs.screen = { programs.screen = {
enable = lib.mkEnableOption "screen, a basic terminal multiplexer"; enable = lib.mkEnableOption "screen, a basic terminal multiplexer";
package = lib.mkPackageOptionMD pkgs "screen" { }; package = lib.mkPackageOption pkgs "screen" { };
screenrc = lib.mkOption { screenrc = lib.mkOption {
type = lib.types.lines; type = lib.types.lines;

View file

@ -38,12 +38,13 @@ in
xwayland.enable = lib.mkEnableOption "XWayland" // { default = true; }; xwayland.enable = lib.mkEnableOption "XWayland" // { default = true; };
systemd.setPath.enable = lib.mkEnableOption null // { systemd.setPath.enable = lib.mkEnableOption null // {
default = true; default = lib.versionOlder cfg.package.version "0.41.2";
defaultText = lib.literalExpression ''lib.versionOlder cfg.package.version "0.41.2"'';
example = false; example = false;
description = '' description = ''
Set environment path of systemd to include the current system's bin directory. Set environment path of systemd to include the current system's bin directory.
This is needed in Hyprland setups, where opening links in applications do not work. This is needed in Hyprland setups, where opening links in applications do not work.
Enabled by default. Enabled by default for Hyprland versions older than 0.41.2.
''; '';
}; };
}; };

View file

@ -26,13 +26,13 @@ in
security.pki.useCompatibleBundle = mkEnableOption ''usage of a compatibility bundle. security.pki.useCompatibleBundle = mkEnableOption ''usage of a compatibility bundle.
Such a bundle consist exclusively of `BEGIN CERTIFICATE` and no `BEGIN TRUSTED CERTIFICATE`, Such a bundle consists exclusively of `BEGIN CERTIFICATE` and no `BEGIN TRUSTED CERTIFICATE`,
which is a OpenSSL specific PEM format. which is an OpenSSL specific PEM format.
It is known to be incompatible with certain software stacks. It is known to be incompatible with certain software stacks.
Nevertheless, enabling this will strip all additional trust rules provided by the Nevertheless, enabling this will strip all additional trust rules provided by the
certificates themselves, this can have security consequences depending on your usecases. certificates themselves. This can have security consequences depending on your usecases
''; '';
security.pki.certificateFiles = mkOption { security.pki.certificateFiles = mkOption {

View file

@ -1055,7 +1055,7 @@ in
the dp9ik pam module provided by tlsclient. the dp9ik pam module provided by tlsclient.
If set, users can be authenticated against the 9front If set, users can be authenticated against the 9front
authentication server given in {option}`security.pam.dp9ik.authserver`. authentication server given in {option}`security.pam.dp9ik.authserver`
''; '';
control = mkOption { control = mkOption {
default = "sufficient"; default = "sufficient";

View file

@ -14,6 +14,8 @@ in
security.polkit.enable = mkEnableOption "polkit"; security.polkit.enable = mkEnableOption "polkit";
security.polkit.package = mkPackageOption pkgs "polkit" { };
security.polkit.debug = mkEnableOption "debug logs from polkit. This is required in order to see log messages from rule definitions"; security.polkit.debug = mkEnableOption "debug logs from polkit. This is required in order to see log messages from rule definitions";
security.polkit.extraConfig = mkOption { security.polkit.extraConfig = mkOption {
@ -57,13 +59,13 @@ in
config = mkIf cfg.enable { config = mkIf cfg.enable {
environment.systemPackages = [ pkgs.polkit.bin pkgs.polkit.out ]; environment.systemPackages = [ cfg.package.bin cfg.package.out ];
systemd.packages = [ pkgs.polkit.out ]; systemd.packages = [ cfg.package.out ];
systemd.services.polkit.serviceConfig.ExecStart = [ systemd.services.polkit.serviceConfig.ExecStart = [
"" ""
"${pkgs.polkit.out}/lib/polkit-1/polkitd ${optionalString (!cfg.debug) "--no-debug"}" "${cfg.package.out}/lib/polkit-1/polkitd ${optionalString (!cfg.debug) "--no-debug"}"
]; ];
systemd.services.polkit.restartTriggers = [ config.system.path ]; systemd.services.polkit.restartTriggers = [ config.system.path ];
@ -82,7 +84,7 @@ in
${cfg.extraConfig} ${cfg.extraConfig}
''; #TODO: validation on compilation (at least against typos) ''; #TODO: validation on compilation (at least against typos)
services.dbus.packages = [ pkgs.polkit.out ]; services.dbus.packages = [ cfg.package.out ];
security.pam.services.polkit-1 = {}; security.pam.services.polkit-1 = {};
@ -91,13 +93,13 @@ in
{ setuid = true; { setuid = true;
owner = "root"; owner = "root";
group = "root"; group = "root";
source = "${pkgs.polkit.bin}/bin/pkexec"; source = "${cfg.package.bin}/bin/pkexec";
}; };
polkit-agent-helper-1 = polkit-agent-helper-1 =
{ setuid = true; { setuid = true;
owner = "root"; owner = "root";
group = "root"; group = "root";
source = "${pkgs.polkit.out}/lib/polkit-1/polkit-agent-helper-1"; source = "${cfg.package.out}/lib/polkit-1/polkit-agent-helper-1";
}; };
}; };

View file

@ -41,7 +41,7 @@ in
enable = mkEnableOption '' enable = mkEnableOption ''
a memory-safe implementation of the {command}`sudo` command, a memory-safe implementation of the {command}`sudo` command,
which allows non-root users to execute commands as root. which allows non-root users to execute commands as root
''; '';
package = mkPackageOption pkgs "sudo-rs" { }; package = mkPackageOption pkgs "sudo-rs" { };

View file

@ -35,7 +35,7 @@ in
default = 5050; default = 5050;
}; };
package = mkPackageOptionMD pkgs "pgadmin4" { }; package = mkPackageOption pkgs "pgadmin4" { };
initialEmail = mkOption { initialEmail = mkOption {
description = "Initial email for the pgAdmin account"; description = "Initial email for the pgAdmin account";

View file

@ -356,7 +356,7 @@ in
boot.kernelModules = ["br_netfilter" "overlay"]; boot.kernelModules = ["br_netfilter" "overlay"];
services.kubernetes.kubelet.hostname = services.kubernetes.kubelet.hostname =
mkDefault config.networking.fqdnOrHostName; mkDefault (lib.toLower config.networking.fqdnOrHostName);
services.kubernetes.pki.certs = with top.lib; { services.kubernetes.pki.certs = with top.lib; {
kubelet = mkCert { kubelet = mkCert {

View file

@ -1,7 +1,43 @@
{ config, lib, pkgs, ... }: { config, lib, pkgs, ... }:
with builtins;
with lib;
let let
inherit (builtins)
hashString
map
substring
toJSON
toString
unsafeDiscardStringContext
;
inherit (lib)
any
assertMsg
attrValues
concatStringsSep
escapeShellArg
filterAttrs
hasPrefix
isStorePath
literalExpression
mapAttrs'
mapAttrsToList
mkDefault
mkEnableOption
mkIf
mkOption
mkPackageOption
mkRemovedOptionModule
mkRenamedOptionModule
nameValuePair
optional
optionalAttrs
optionals
teams
toShellVar
types
;
cfg = config.services.gitlab-runner; cfg = config.services.gitlab-runner;
hasDocker = config.virtualisation.docker.enable; hasDocker = config.virtualisation.docker.enable;
@ -20,17 +56,16 @@ let
configPath = ''"$HOME"/.gitlab-runner/config.toml''; configPath = ''"$HOME"/.gitlab-runner/config.toml'';
configureScript = pkgs.writeShellApplication { configureScript = pkgs.writeShellApplication {
name = "gitlab-runner-configure"; name = "gitlab-runner-configure";
runtimeInputs = with pkgs; [ runtimeInputs = [ cfg.package ] ++ (with pkgs; [
bash bash
gawk gawk
jq jq
moreutils moreutils
remarshal remarshal
util-linux util-linux
cfg.package
perl perl
python3 python3
]; ]);
text = if (cfg.configFile != null) then '' text = if (cfg.configFile != null) then ''
cp ${cfg.configFile} ${configPath} cp ${cfg.configFile} ${configPath}
# make config file readable by service # make config file readable by service
@ -84,15 +119,20 @@ let
# TODO so here we should mention NEW_SERVICES # TODO so here we should mention NEW_SERVICES
if [ -v 'NEW_SERVICES["${name}"]' ] ; then if [ -v 'NEW_SERVICES["${name}"]' ] ; then
bash -c ${escapeShellArg (concatStringsSep " \\\n " ([ bash -c ${escapeShellArg (concatStringsSep " \\\n " ([
"set -a && source ${service.registrationConfigFile} &&" "set -a && source ${
if service.registrationConfigFile != null
then service.registrationConfigFile
else service.authenticationTokenConfigFile} &&"
"gitlab-runner register" "gitlab-runner register"
"--non-interactive" "--non-interactive"
"--name '${name}'" "--name '${name}'"
"--executor ${service.executor}" "--executor ${service.executor}"
"--limit ${toString service.limit}" "--limit ${toString service.limit}"
"--request-concurrency ${toString service.requestConcurrency}" "--request-concurrency ${toString service.requestConcurrency}"
]
++ optional (service.authenticationTokenConfigFile == null)
"--maximum-timeout ${toString service.maximumTimeout}" "--maximum-timeout ${toString service.maximumTimeout}"
] ++ service.registrationFlags ++ service.registrationFlags
++ optional (service.buildsDir != null) ++ optional (service.buildsDir != null)
"--builds-dir ${service.buildsDir}" "--builds-dir ${service.buildsDir}"
++ optional (service.cloneUrl != null) ++ optional (service.cloneUrl != null)
@ -103,11 +143,11 @@ let
"--pre-build-script ${service.preBuildScript}" "--pre-build-script ${service.preBuildScript}"
++ optional (service.postBuildScript != null) ++ optional (service.postBuildScript != null)
"--post-build-script ${service.postBuildScript}" "--post-build-script ${service.postBuildScript}"
++ optional (service.tagList != [ ]) ++ optional (service.authenticationTokenConfigFile == null && service.tagList != [ ])
"--tag-list ${concatStringsSep "," service.tagList}" "--tag-list ${concatStringsSep "," service.tagList}"
++ optional service.runUntagged ++ optional (service.authenticationTokenConfigFile == null && service.runUntagged)
"--run-untagged" "--run-untagged"
++ optional service.protected ++ optional (service.authenticationTokenConfigFile == null && service.protected)
"--access-level ref_protected" "--access-level ref_protected"
++ optional service.debugTraceDisabled ++ optional service.debugTraceDisabled
"--debug-trace-disabled" "--debug-trace-disabled"
@ -214,9 +254,14 @@ in {
# nix store will be readable in runner, might be insecure # nix store will be readable in runner, might be insecure
nix = { nix = {
# File should contain at least these two variables: # File should contain at least these two variables:
# `CI_SERVER_URL` # - `CI_SERVER_URL`
# `REGISTRATION_TOKEN` # - `REGISTRATION_TOKEN`
#
# NOTE: Support for runner registration tokens will be removed in GitLab 18.0.
# Please migrate to runner authentication tokens soon. For reference, the example
# runners below this one are configured with authentication tokens instead.
registrationConfigFile = "/run/secrets/gitlab-runner-registration"; registrationConfigFile = "/run/secrets/gitlab-runner-registration";
dockerImage = "alpine"; dockerImage = "alpine";
dockerVolumes = [ dockerVolumes = [
"/nix/store:/nix/store:ro" "/nix/store:/nix/store:ro"
@ -255,8 +300,9 @@ in {
docker-images = { docker-images = {
# File should contain at least these two variables: # File should contain at least these two variables:
# `CI_SERVER_URL` # `CI_SERVER_URL`
# `REGISTRATION_TOKEN` # `CI_SERVER_TOKEN`
registrationConfigFile = "/run/secrets/gitlab-runner-registration"; authenticationTokenConfigFile = "/run/secrets/gitlab-runner-docker-images-token-env";
dockerImage = "docker:stable"; dockerImage = "docker:stable";
dockerVolumes = [ dockerVolumes = [
"/var/run/docker.sock:/var/run/docker.sock" "/var/run/docker.sock:/var/run/docker.sock"
@ -269,8 +315,9 @@ in {
shell = { shell = {
# File should contain at least these two variables: # File should contain at least these two variables:
# `CI_SERVER_URL` # `CI_SERVER_URL`
# `REGISTRATION_TOKEN` # `CI_SERVER_TOKEN`
registrationConfigFile = "/run/secrets/gitlab-runner-registration"; authenticationTokenConfigFile = "/run/secrets/gitlab-runner-shell-token-env";
executor = "shell"; executor = "shell";
tagList = [ "shell" ]; tagList = [ "shell" ];
}; };
@ -278,30 +325,67 @@ in {
default = { default = {
# File should contain at least these two variables: # File should contain at least these two variables:
# `CI_SERVER_URL` # `CI_SERVER_URL`
# `REGISTRATION_TOKEN` # `CI_SERVER_TOKEN`
registrationConfigFile = "/run/secrets/gitlab-runner-registration"; authenticationTokenConfigFile = "/run/secrets/gitlab-runner-default-token-env";
dockerImage = "debian:stable"; dockerImage = "debian:stable";
}; };
} }
''; '';
type = types.attrsOf (types.submodule { type = types.attrsOf (types.submodule {
options = { options = {
authenticationTokenConfigFile = mkOption {
type = with types; nullOr path;
default = null;
description = ''
Absolute path to a file containing environment variables used for
gitlab-runner registrations with *runner authentication tokens*.
They replace the deprecated *runner registration tokens*, as
outlined in the [GitLab documentation].
A list of all supported environment variables can be found with
`gitlab-runner register --help`.
The ones you probably want to set are:
- `CI_SERVER_URL=<CI server URL>`
- `CI_SERVER_TOKEN=<runner authentication token secret>`
::: {.warning}
Make sure to use a quoted absolute path,
or it is going to be copied to Nix Store.
:::
[GitLab documentation]: https://docs.gitlab.com/17.0/ee/ci/runners/new_creation_workflow.html#estimated-time-frame-for-planned-changes
'';
};
registrationConfigFile = mkOption { registrationConfigFile = mkOption {
type = types.path; type = with types; nullOr path;
default = null;
description = '' description = ''
Absolute path to a file with environment variables Absolute path to a file with environment variables
used for gitlab-runner registration. used for gitlab-runner registration with *runner registration
tokens*.
A list of all supported environment variables can be found in A list of all supported environment variables can be found in
`gitlab-runner register --help`. `gitlab-runner register --help`.
Ones that you probably want to set is The ones you probably want to set are:
- `CI_SERVER_URL=<CI server URL>`
- `REGISTRATION_TOKEN=<registration secret>`
`CI_SERVER_URL=<CI server URL>` Support for *runner registration tokens* is deprecated since
GitLab 16.0, has been disabled by default in GitLab 17.0 and
will be removed in GitLab 18.0, as outlined in the
[GitLab documentation]. Please consider migrating to
[runner authentication tokens] and check the documentation on
{option}`services.gitlab-runner.services.<name>.authenticationTokenConfigFile`.
`REGISTRATION_TOKEN=<registration secret>` ::: {.warning}
Make sure to use a quoted absolute path,
WARNING: make sure to use quoted absolute path,
or it is going to be copied to Nix Store. or it is going to be copied to Nix Store.
:::
[GitLab documentation]: https://docs.gitlab.com/17.0/ee/ci/runners/new_creation_workflow.html#estimated-time-frame-for-planned-changes
[runner authentication tokens]: https://docs.gitlab.com/17.0/ee/ci/runners/new_creation_workflow.html#the-new-runner-registration-workflow
''; '';
}; };
registrationFlags = mkOption { registrationFlags = mkOption {
@ -439,6 +523,9 @@ in {
default = [ ]; default = [ ];
description = '' description = ''
Tag list. Tag list.
This option has no effect for runners registered with an runner
authentication tokens and will be ignored.
''; '';
}; };
runUntagged = mkOption { runUntagged = mkOption {
@ -447,6 +534,9 @@ in {
description = '' description = ''
Register to run untagged builds; defaults to Register to run untagged builds; defaults to
`true` when {option}`tagList` is empty. `true` when {option}`tagList` is empty.
This option has no effect for runners registered with an runner
authentication tokens and will be ignored.
''; '';
}; };
limit = mkOption { limit = mkOption {
@ -470,6 +560,9 @@ in {
description = '' description = ''
What is the maximum timeout (in seconds) that will be set for What is the maximum timeout (in seconds) that will be set for
job when using this Runner. 0 (default) simply means don't limit. job when using this Runner. 0 (default) simply means don't limit.
This option has no effect for runners registered with an runner
authentication tokens and will be ignored.
''; '';
}; };
protected = mkOption { protected = mkOption {
@ -478,6 +571,9 @@ in {
description = '' description = ''
When set to true Runner will only run on pipelines When set to true Runner will only run on pipelines
triggered on protected branches. triggered on protected branches.
This option has no effect for runners registered with an runner
authentication tokens and will be ignored.
''; '';
}; };
debugTraceDisabled = mkOption { debugTraceDisabled = mkOption {
@ -530,9 +626,67 @@ in {
}; };
}; };
config = mkIf cfg.enable { config = mkIf cfg.enable {
warnings = mapAttrsToList assertions =
(n: v: "services.gitlab-runner.services.${n}.`registrationConfigFile` points to a file in Nix Store. You should use quoted absolute path to prevent this.") mapAttrsToList (name: serviceConfig: {
(filterAttrs (n: v: isStorePath v.registrationConfigFile) cfg.services); assertion = serviceConfig.registrationConfigFile == null || serviceConfig.authenticationTokenConfigFile == null;
message = "`services.gitlab-runner.${name}.registrationConfigFile` and `services.gitlab-runner.services.${name}.authenticationTokenConfigFile` are mutually exclusive.";
}) cfg.services;
warnings =
mapAttrsToList
(name: serviceConfig: "services.gitlab-runner.services.${name}.`registrationConfigFile` points to a file in Nix Store. You should use quoted absolute path to prevent this.")
(filterAttrs (name: serviceConfig: isStorePath serviceConfig.registrationConfigFile) cfg.services)
++ mapAttrsToList
(name: serviceConfig: "services.gitlab-runner.services.${name}.`authenticationTokenConfigFile` points to a file in Nix Store. You should use quoted absolute path to prevent this.")
(filterAttrs (name: serviceConfig: isStorePath serviceConfig.authenticationTokenConfigFile) cfg.services)
++ mapAttrsToList
(name: serviceConfig: ''
Runner registration tokens have been deprecated and disabled by default in GitLab >= 17.0.
Consider migrating to runner authentication tokens by setting `services.gitlab-runner.services.${name}.authenticationTokenConfigFile`.
https://docs.gitlab.com/17.0/ee/ci/runners/new_creation_workflow.html''
)
(
filterAttrs (name: serviceConfig:
serviceConfig.authenticationTokenConfigFile == null
) cfg.services
)
++ mapAttrsToList
(name: serviceConfig: ''
`services.gitlab-runner.services.${name}.protected` with runner authentication tokens has no effect and will be ignored. Please remove it from your configuration.''
)
(
filterAttrs (name: serviceConfig:
serviceConfig.authenticationTokenConfigFile != null && serviceConfig.protected == true
) cfg.services
)
++ mapAttrsToList
(name: serviceConfig: ''
`services.gitlab-runner.services.${name}.runUntagged` with runner authentication tokens has no effect and will be ignored. Please remove it from your configuration.''
)
(
filterAttrs (name: serviceConfig:
serviceConfig.authenticationTokenConfigFile != null && serviceConfig.runUntagged == true
) cfg.services
)
++ mapAttrsToList
(name: v: ''
`services.gitlab-runner.services.${name}.maximumTimeout` with runner authentication tokens has no effect and will be ignored. Please remove it from your configuration.''
)
(
filterAttrs (name: serviceConfig:
serviceConfig.authenticationTokenConfigFile != null && serviceConfig.maximumTimeout != 0
) cfg.services
)
++ mapAttrsToList
(name: v: ''
`services.gitlab-runner.services.${name}.tagList` with runner authentication tokens has no effect and will be ignored. Please remove it from your configuration.''
)
(
filterAttrs (serviceName: serviceConfig:
serviceConfig.authenticationTokenConfigFile != null && serviceConfig.tagList != [ ]
) cfg.services
)
;
environment.systemPackages = [ cfg.package ]; environment.systemPackages = [ cfg.package ];
systemd.services.gitlab-runner = { systemd.services.gitlab-runner = {
@ -545,15 +699,19 @@ in {
environment = config.networking.proxy.envVars // { environment = config.networking.proxy.envVars // {
HOME = "/var/lib/gitlab-runner"; HOME = "/var/lib/gitlab-runner";
}; };
path = with pkgs; [
bash path =
gawk (with pkgs; [
jq bash
moreutils gawk
remarshal jq
util-linux moreutils
cfg.package remarshal
] ++ cfg.extraPackages; util-linux
])
++ [ cfg.package ]
++ cfg.extraPackages;
reloadIfChanged = true; reloadIfChanged = true;
serviceConfig = { serviceConfig = {
# Set `DynamicUser` under `systemd.services.gitlab-runner.serviceConfig` # Set `DynamicUser` under `systemd.services.gitlab-runner.serviceConfig`

View file

@ -37,7 +37,7 @@ in
description = "The port to bind to."; description = "The port to bind to.";
}; };
enableUnixSocket = mkEnableOption "Unix Domain Socket at /run/memcached/memcached.sock instead of listening on an IP address and port. The `listen` and `port` options are ignored."; enableUnixSocket = mkEnableOption "Unix Domain Socket at /run/memcached/memcached.sock instead of listening on an IP address and port. The `listen` and `port` options are ignored";
maxMemory = mkOption { maxMemory = mkOption {
type = types.ints.unsigned; type = types.ints.unsigned;

View file

@ -620,6 +620,6 @@ in {
}; };
meta = { meta = {
maintainers = with lib.maintainers; [ patternspandemic jonringer ]; maintainers = with lib.maintainers; [ patternspandemic ];
}; };
} }

View file

@ -8,7 +8,7 @@
cfg = config.services.desktopManager.plasma6; cfg = config.services.desktopManager.plasma6;
inherit (pkgs) kdePackages; inherit (pkgs) kdePackages;
inherit (lib) literalExpression mkDefault mkIf mkOption mkPackageOptionMD types; inherit (lib) literalExpression mkDefault mkIf mkOption mkPackageOption types;
activationScript = '' activationScript = ''
# will be rebuilt automatically # will be rebuilt automatically
@ -29,7 +29,7 @@ in {
description = "Enable Qt 5 integration (theming, etc). Disable for a pure Qt 6 system."; description = "Enable Qt 5 integration (theming, etc). Disable for a pure Qt 6 system.";
}; };
notoPackage = mkPackageOptionMD pkgs "Noto fonts - used for UI by default" { notoPackage = mkPackageOption pkgs "Noto fonts - used for UI by default" {
default = ["noto-fonts"]; default = ["noto-fonts"];
example = "noto-fonts-lgc-plus"; example = "noto-fonts-lgc-plus";
}; };

View file

@ -0,0 +1,38 @@
{ config, pkgs, lib, ... }:
{
meta = {
maintainers = lib.teams.deepin.members;
};
options = {
services.deepin.deepin-anything = {
enable = lib.mkEnableOption "deepin anything file search tool";
};
};
config = lib.mkIf config.services.deepin.dde-api.enable {
environment.systemPackages = [ pkgs.deepin.deepin-anything ];
services.dbus.packages = [ pkgs.deepin.deepin-anything ];
users.groups.deepin-anything = { };
users.users.deepin-anything = {
description = "Deepin Anything Server";
home = "/var/lib/deepin-anything";
createHome = true;
group = "deepin-anything";
isSystemUser = true;
};
boot.extraModulePackages = [ config.boot.kernelPackages.deepin-anything-module ];
boot.kernelModules = [ "vfs_monitor" ];
};
}

View file

@ -0,0 +1,32 @@
{
config,
lib,
pkgs,
...
}:
let
cfg = config.services.playerctld;
in
{
options.services.playerctld = {
enable = lib.mkEnableOption "the playerctld daemon";
package = lib.mkPackageOption pkgs "playerctl" { };
};
config = lib.mkIf cfg.enable {
environment.systemPackages = [ cfg.package ];
systemd.user.services.playerctld = {
description = "Playerctld daemon to track media player activity";
wantedBy = [ "default.target" ];
serviceConfig = {
Type = "exec";
ExecStart = "${cfg.package}/bin/playerctld";
};
};
};
meta.maintainers = with lib.maintainers; [ aacebedo ];
}

View file

@ -36,7 +36,7 @@ in
options = { options = {
enable = mkEnableOption "armagetronad"; enable = mkEnableOption "armagetronad";
package = lib.mkPackageOptionMD pkgs "armagetronad-dedicated" { package = lib.mkPackageOption pkgs "armagetronad-dedicated" {
example = '' example = ''
pkgs.armagetronad."0.2.9-sty+ct+ap".dedicated pkgs.armagetronad."0.2.9-sty+ct+ap".dedicated
''; '';

View file

@ -95,7 +95,7 @@ in
services.teeworlds = { services.teeworlds = {
enable = mkEnableOption "Teeworlds Server"; enable = mkEnableOption "Teeworlds Server";
package = mkPackageOptionMD pkgs "teeworlds-server" { }; package = mkPackageOption pkgs "teeworlds-server" { };
openPorts = mkOption { openPorts = mkOption {
type = types.bool; type = types.bool;

View file

@ -10,7 +10,7 @@ in {
services.auto-epp = { services.auto-epp = {
enable = lib.mkEnableOption "auto-epp for amd active pstate"; enable = lib.mkEnableOption "auto-epp for amd active pstate";
package = lib.mkPackageOptionMD pkgs "auto-epp" {}; package = lib.mkPackageOption pkgs "auto-epp" {};
settings = mkOption { settings = mkOption {
type = types.submodule { type = types.submodule {

View file

@ -51,5 +51,5 @@ in {
}; };
}; };
meta.maintainers = with lib.maintainers; [ jonringer ]; meta.maintainers = with lib.maintainers; [ ];
} }

View file

@ -11,7 +11,7 @@ in
options.services.ebusd = { options.services.ebusd = {
enable = mkEnableOption "ebusd, a daemon for communication with eBUS heating systems"; enable = mkEnableOption "ebusd, a daemon for communication with eBUS heating systems";
package = mkPackageOptionMD pkgs "ebusd" { }; package = mkPackageOption pkgs "ebusd" { };
device = mkOption { device = mkOption {
type = types.str; type = types.str;

View file

@ -19,7 +19,7 @@ in
options.services.matter-server = with types; { options.services.matter-server = with types; {
enable = mkEnableOption "Matter-server"; enable = mkEnableOption "Matter-server";
package = mkPackageOptionMD pkgs "python-matter-server" { }; package = mkPackageOption pkgs "python-matter-server" { };
port = mkOption { port = mkOption {
type = types.port; type = types.port;

View file

@ -52,7 +52,7 @@ let
in in
{ {
options.services.mautrix-signal = { options.services.mautrix-signal = {
enable = lib.mkEnableOption "mautrix-signal, a Matrix-Signal puppeting bridge."; enable = lib.mkEnableOption "mautrix-signal, a Matrix-Signal puppeting bridge";
settings = lib.mkOption { settings = lib.mkOption {
apply = lib.recursiveUpdate defaultConfig; apply = lib.recursiveUpdate defaultConfig;

View file

@ -47,7 +47,7 @@
in { in {
options.services.mautrix-whatsapp = { options.services.mautrix-whatsapp = {
enable = lib.mkEnableOption "mautrix-whatsapp, a puppeting/relaybot bridge between Matrix and WhatsApp."; enable = lib.mkEnableOption "mautrix-whatsapp, a puppeting/relaybot bridge between Matrix and WhatsApp";
settings = lib.mkOption { settings = lib.mkOption {
type = settingsFormat.type; type = settingsFormat.type;

View file

@ -124,7 +124,7 @@ let
in { in {
options = { options = {
services.mqtt2influxdb = { services.mqtt2influxdb = {
enable = mkEnableOption "BigClown MQTT to InfluxDB bridge."; enable = mkEnableOption "BigClown MQTT to InfluxDB bridge";
package = mkPackageOption pkgs ["python3Packages" "mqtt2influxdb"] {}; package = mkPackageOption pkgs ["python3Packages" "mqtt2influxdb"] {};
environmentFiles = mkOption { environmentFiles = mkOption {
type = types.listOf types.path; type = types.listOf types.path;

View file

@ -1,13 +1,10 @@
{ config, lib, pkgs, ... }: { config, lib, pkgs, ... }:
let let
inherit (lib) types; inherit (lib) types mkBefore;
cfg = config.services.ollama; cfg = config.services.ollama;
ollamaPackage = cfg.package.override { ollamaPackage = cfg.package.override {
inherit (cfg) acceleration; inherit (cfg) acceleration;
linuxPackages = config.boot.kernelPackages // {
nvidia_x11 = config.hardware.nvidia.package;
};
}; };
in in
{ {
@ -132,6 +129,14 @@ in
Since `ollama run` is mostly a shell around the ollama server, this is usually sufficient. Since `ollama run` is mostly a shell around the ollama server, this is usually sufficient.
''; '';
}; };
loadModels = lib.mkOption {
type = types.listOf types.str;
default = [ ];
description = ''
The models to download as soon as the service starts.
Search for models of your choice from: https://ollama.com/library
'';
};
openFirewall = lib.mkOption { openFirewall = lib.mkOption {
type = types.bool; type = types.bool;
default = false; default = false;
@ -161,6 +166,14 @@ in
DynamicUser = cfg.sandbox; DynamicUser = cfg.sandbox;
ReadWritePaths = cfg.writablePaths; ReadWritePaths = cfg.writablePaths;
}; };
postStart = mkBefore ''
set -x
export OLLAMA_HOST=${lib.escapeShellArg cfg.host}:${builtins.toString cfg.port}
for model in ${lib.escapeShellArgs cfg.loadModels}
do
${lib.escapeShellArg (lib.getExe ollamaPackage)} pull "$model"
done
'';
}; };
networking.firewall = lib.mkIf cfg.openFirewall { allowedTCPPorts = [ cfg.port ]; }; networking.firewall = lib.mkIf cfg.openFirewall { allowedTCPPorts = [ cfg.port ]; };

View file

@ -225,7 +225,7 @@ in
effectively never complete due to running into timeouts. effectively never complete due to running into timeouts.
This sets `OMP_NUM_THREADS` to `1` in order to mitigate the issue. See This sets `OMP_NUM_THREADS` to `1` in order to mitigate the issue. See
https://github.com/NixOS/nixpkgs/issues/240591 for more information. https://github.com/NixOS/nixpkgs/issues/240591 for more information
'' // mkOption { default = true; }; '' // mkOption { default = true; };
}; };

View file

@ -70,7 +70,7 @@ in
To activate dex, first a search user must be created in the Portunus web ui To activate dex, first a search user must be created in the Portunus web ui
and then the password must to be set as the `DEX_SEARCH_USER_PASSWORD` environment variable and then the password must to be set as the `DEX_SEARCH_USER_PASSWORD` environment variable
in the [](#opt-services.dex.environmentFile) setting. in the [](#opt-services.dex.environmentFile) setting
''; '';
oidcClients = mkOption { oidcClients = mkOption {

View file

@ -6,7 +6,7 @@ in
{ {
options = { options = {
services.spice-autorandr = { services.spice-autorandr = {
enable = lib.mkEnableOption "spice-autorandr service that will automatically resize display to match SPICE client window size."; enable = lib.mkEnableOption "spice-autorandr service that will automatically resize display to match SPICE client window size";
package = lib.mkPackageOption pkgs "spice-autorandr" { }; package = lib.mkPackageOption pkgs "spice-autorandr" { };
}; };
}; };

View file

@ -24,6 +24,13 @@ in
Enable SSL/TLS encryption. Enable SSL/TLS encryption.
''; '';
}; };
gpu = lib.mkOption {
type = lib.types.bool;
default = true;
description = ''
Enable GPU monitoring.
'';
};
disableCommandExecute = lib.mkOption { disableCommandExecute = lib.mkOption {
type = lib.types.bool; type = lib.types.bool;
default = true; default = true;
@ -46,7 +53,12 @@ in
''; '';
}; };
reportDelay = lib.mkOption { reportDelay = lib.mkOption {
type = lib.types.enum [ 1 2 3 4 ]; type = lib.types.enum [
1
2
3
4
];
default = 1; default = 1;
description = '' description = ''
The interval between system status reportings. The interval between system status reportings.
@ -96,6 +108,7 @@ in
++ lib.optional cfg.skipConnection "--skip-conn" ++ lib.optional cfg.skipConnection "--skip-conn"
++ lib.optional cfg.skipProcess "--skip-procs" ++ lib.optional cfg.skipProcess "--skip-procs"
++ lib.optional cfg.tls "--tls" ++ lib.optional cfg.tls "--tls"
++ lib.optional cfg.gpu "--gpu"
); );
wantedBy = [ "multi-user.target" ]; wantedBy = [ "multi-user.target" ];
}; };

View file

@ -52,7 +52,6 @@ let
"lnd" "lnd"
"mail" "mail"
"mikrotik" "mikrotik"
"minio"
"modemmanager" "modemmanager"
"mongodb" "mongodb"
"mysqld" "mysqld"
@ -279,20 +278,16 @@ let
in in
{ {
imports = (lib.forEach [ "blackboxExporter" "collectdExporter" "fritzboxExporter"
"jsonExporter" "minioExporter" "nginxExporter" "nodeExporter"
"snmpExporter" "unifiExporter" "varnishExporter" ]
(opt: lib.mkRemovedOptionModule [ "services" "prometheus" "${opt}" ] ''
The prometheus exporters are now configured using `services.prometheus.exporters'.
See the 18.03 release notes for more information.
'' ));
options.services.prometheus.exporters = mkOption { options.services.prometheus.exporters = mkOption {
type = types.submodule { type = types.submodule {
options = (mkSubModules); options = (mkSubModules);
imports = [ imports = [
../../../misc/assertions.nix ../../../misc/assertions.nix
(lib.mkRenamedOptionModule [ "unifi-poller" ] [ "unpoller" ]) (lib.mkRenamedOptionModule [ "unifi-poller" ] [ "unpoller" ])
(lib.mkRemovedOptionModule [ "minio" ] ''
The Minio exporter has been removed, as it was broken and unmaintained.
See the 24.11 release notes for more information.
'')
]; ];
}; };
description = "Prometheus exporter configuration"; description = "Prometheus exporter configuration";
@ -438,11 +433,7 @@ in
'' ''
) )
] ++ config.services.prometheus.exporters.warnings; ] ++ config.services.prometheus.exporters.warnings;
}] ++ [(mkIf config.services.minio.enable { }] ++ [(mkIf config.services.prometheus.exporters.rtl_433.enable {
services.prometheus.exporters.minio.minioAddress = mkDefault "http://localhost:9000";
services.prometheus.exporters.minio.minioAccessKey = mkDefault config.services.minio.accessKey;
services.prometheus.exporters.minio.minioAccessSecret = mkDefault config.services.minio.secretKey;
})] ++ [(mkIf config.services.prometheus.exporters.rtl_433.enable {
hardware.rtl-sdr.enable = mkDefault true; hardware.rtl-sdr.enable = mkDefault true;
})] ++ [(mkIf config.services.postfix.enable { })] ++ [(mkIf config.services.postfix.enable {
services.prometheus.exporters.postfix.group = mkDefault config.services.postfix.setgidGroup; services.prometheus.exporters.postfix.group = mkDefault config.services.postfix.setgidGroup;

View file

@ -1,69 +0,0 @@
{ config, lib, pkgs, options, ... }:
let
cfg = config.services.prometheus.exporters.minio;
inherit (lib)
mkOption
types
optionalString
concatStringsSep
escapeShellArg
;
in
{
port = 9290;
extraOpts = {
minioAddress = mkOption {
type = types.str;
example = "https://10.0.0.1:9000";
description = ''
The URL of the minio server.
Use HTTPS if Minio accepts secure connections only.
By default this connects to the local minio server if enabled.
'';
};
minioAccessKey = mkOption {
type = types.str;
example = "yourMinioAccessKey";
description = ''
The value of the Minio access key.
It is required in order to connect to the server.
By default this uses the one from the local minio server if enabled
and `config.services.minio.accessKey`.
'';
};
minioAccessSecret = mkOption {
type = types.str;
description = ''
The value of the Minio access secret.
It is required in order to connect to the server.
By default this uses the one from the local minio server if enabled
and `config.services.minio.secretKey`.
'';
};
minioBucketStats = mkOption {
type = types.bool;
default = false;
description = ''
Collect statistics about the buckets and files in buckets.
It requires more computation, use it carefully in case of large buckets..
'';
};
};
serviceOpts = {
serviceConfig = {
ExecStart = ''
${pkgs.prometheus-minio-exporter}/bin/minio-exporter \
-web.listen-address ${cfg.listenAddress}:${toString cfg.port} \
-minio.server ${cfg.minioAddress} \
-minio.access-key ${escapeShellArg cfg.minioAccessKey} \
-minio.access-secret ${escapeShellArg cfg.minioAccessSecret} \
${optionalString cfg.minioBucketStats "-minio.bucket-stats"} \
${concatStringsSep " \\\n " cfg.extraFlags}
'';
};
};
}

View file

@ -4,7 +4,7 @@ let
UDPPorts = [21116]; UDPPorts = [21116];
in { in {
options.services.rustdesk-server = with lib; with types; { options.services.rustdesk-server = with lib; with types; {
enable = mkEnableOption "RustDesk, a remote access and remote control software, allowing maintenance of computers and other devices."; enable = mkEnableOption "RustDesk, a remote access and remote control software, allowing maintenance of computers and other devices";
package = mkPackageOption pkgs "rustdesk-server" {}; package = mkPackageOption pkgs "rustdesk-server" {};

View file

@ -10,6 +10,7 @@ let
opt = options.services.smartd; opt = options.services.smartd;
nm = cfg.notifications.mail; nm = cfg.notifications.mail;
ns = cfg.notifications.systembus-notify;
nw = cfg.notifications.wall; nw = cfg.notifications.wall;
nx = cfg.notifications.x11; nx = cfg.notifications.x11;
@ -28,6 +29,12 @@ let
${pkgs.smartmontools}/sbin/smartctl -a -d "$SMARTD_DEVICETYPE" "$SMARTD_DEVICE" ${pkgs.smartmontools}/sbin/smartctl -a -d "$SMARTD_DEVICETYPE" "$SMARTD_DEVICE"
} | ${nm.mailer} -i "${nm.recipient}" } | ${nm.mailer} -i "${nm.recipient}"
''} ''}
${optionalString ns.enable ''
${pkgs.dbus}/bin/dbus-send --system \
/ net.nuetzlich.SystemNotifications.Notify \
"string:Problem detected with disk: $SMARTD_DEVICESTRING" \
"string:Warning message from smartd is: $SMARTD_MESSAGE"
''}
${optionalString nw.enable '' ${optionalString nw.enable ''
{ {
${pkgs.coreutils}/bin/cat << EOF ${pkgs.coreutils}/bin/cat << EOF
@ -159,6 +166,24 @@ in
}; };
}; };
systembus-notify = {
enable = mkOption {
default = false;
type = types.bool;
description = ''
Whenever to send systembus-notify notifications.
WARNING: enabling this option (while convenient) should *not* be done on a
machine where you do not trust the other users as it allows any other
local user to DoS your session by spamming notifications.
To actually see the notifications in your GUI session, you need to have
`systembus-notify` running as your user, which this
option handles by enabling {option}`services.systembus-notify`.
'';
};
};
wall = { wall = {
enable = mkOption { enable = mkOption {
default = true; default = true;
@ -247,6 +272,8 @@ in
serviceConfig.ExecStart = "${pkgs.smartmontools}/sbin/smartd ${lib.concatStringsSep " " cfg.extraOptions} --no-fork --configfile=${smartdConf}"; serviceConfig.ExecStart = "${pkgs.smartmontools}/sbin/smartd ${lib.concatStringsSep " " cfg.extraOptions} --no-fork --configfile=${smartdConf}";
}; };
services.systembus-notify.enable = mkDefault ns.enable;
}; };
} }

View file

@ -696,7 +696,7 @@ in {
}; };
store = paramsToOptions params.store // { store = paramsToOptions params.store // {
enable = mkEnableOption "the Thanos store node giving access to blocks in a bucket provider."; enable = mkEnableOption "the Thanos store node giving access to blocks in a bucket provider";
arguments = mkArgumentsOption "store"; arguments = mkArgumentsOption "store";
}; };

View file

@ -385,8 +385,8 @@ in
power.ups = { power.ups = {
enable = mkEnableOption '' enable = mkEnableOption ''
Enables support for Power Devices, such as Uninterruptible Power support for Power Devices, such as Uninterruptible Power
Supplies, Power Distribution Units and Solar Controllers. Supplies, Power Distribution Units and Solar Controllers
''; '';
mode = mkOption { mode = mkOption {

View file

@ -183,7 +183,7 @@ in {
enableFabs = mkEnableOption '' enableFabs = mkEnableOption ''
FABS, the flexible AFS backup system. It stores volumes as dump files, relying on other FABS, the flexible AFS backup system. It stores volumes as dump files, relying on other
pre-existing backup solutions for handling them. pre-existing backup solutions for handling them
''; '';
buserverArgs = mkOption { buserverArgs = mkOption {

View file

@ -10,7 +10,7 @@ in {
services.samba-wsdd = { services.samba-wsdd = {
enable = mkEnableOption '' enable = mkEnableOption ''
Web Services Dynamic Discovery host daemon. This enables (Samba) hosts, like your local NAS device, Web Services Dynamic Discovery host daemon. This enables (Samba) hosts, like your local NAS device,
to be found by Web Service Discovery Clients like Windows. to be found by Web Service Discovery Clients like Windows
''; '';
interface = mkOption { interface = mkOption {
type = types.nullOr types.str; type = types.nullOr types.str;

View file

@ -16,7 +16,7 @@ in {
services.gns3-server = { services.gns3-server = {
enable = lib.mkEnableOption "GNS3 Server daemon"; enable = lib.mkEnableOption "GNS3 Server daemon";
package = lib.mkPackageOptionMD pkgs "gns3-server" { }; package = lib.mkPackageOption pkgs "gns3-server" { };
auth = { auth = {
enable = lib.mkEnableOption "password based HTTP authentication to access the GNS3 Server"; enable = lib.mkEnableOption "password based HTTP authentication to access the GNS3 Server";
@ -87,18 +87,18 @@ in {
}; };
dynamips = { dynamips = {
enable = lib.mkEnableOption ''Whether to enable Dynamips support.''; enable = lib.mkEnableOption ''Dynamips support'';
package = lib.mkPackageOptionMD pkgs "dynamips" { }; package = lib.mkPackageOption pkgs "dynamips" { };
}; };
ubridge = { ubridge = {
enable = lib.mkEnableOption ''Whether to enable uBridge support.''; enable = lib.mkEnableOption ''uBridge support'';
package = lib.mkPackageOptionMD pkgs "ubridge" { }; package = lib.mkPackageOption pkgs "ubridge" { };
}; };
vpcs = { vpcs = {
enable = lib.mkEnableOption ''Whether to enable VPCS support.''; enable = lib.mkEnableOption ''VPCS support'';
package = lib.mkPackageOptionMD pkgs "vpcs" { }; package = lib.mkPackageOption pkgs "vpcs" { };
}; };
}; };
}; };

View file

@ -17,7 +17,7 @@ with lib;
options = { options = {
services.haproxy = { services.haproxy = {
enable = mkEnableOption "HAProxy, the reliable, high performance TCP/HTTP load balancer."; enable = mkEnableOption "HAProxy, the reliable, high performance TCP/HTTP load balancer";
package = mkPackageOption pkgs "haproxy" { }; package = mkPackageOption pkgs "haproxy" { };

View file

@ -312,9 +312,9 @@ in
}; };
faxqclean.enable.spoolInit = mkEnableOption '' faxqclean.enable.spoolInit = mkEnableOption ''
Purge old files from the spooling area with purging old files from the spooling area with
{file}`faxqclean` {file}`faxqclean`
each time the spooling area is initialized. each time the spooling area is initialized
''; '';
faxqclean.enable.frequency = mkOption { faxqclean.enable.frequency = mkOption {
type = nullOr nonEmptyStr; type = nullOr nonEmptyStr;

View file

@ -39,7 +39,7 @@ in
package = mkPackageOption pkgs "netbird-dashboard" { }; package = mkPackageOption pkgs "netbird-dashboard" { };
enableNginx = mkEnableOption "Nginx reverse-proxy to serve the dashboard."; enableNginx = mkEnableOption "Nginx reverse-proxy to serve the dashboard";
domain = mkOption { domain = mkOption {
type = str; type = str;

View file

@ -137,7 +137,7 @@ in
{ {
options.services.netbird.server.management = { options.services.netbird.server.management = {
enable = mkEnableOption "Netbird Management Service."; enable = mkEnableOption "Netbird Management Service";
package = mkPackageOption pkgs "netbird" { }; package = mkPackageOption pkgs "netbird" { };
@ -335,7 +335,7 @@ in
description = "Log level of the netbird services."; description = "Log level of the netbird services.";
}; };
enableNginx = mkEnableOption "Nginx reverse-proxy for the netbird management service."; enableNginx = mkEnableOption "Nginx reverse-proxy for the netbird management service";
}; };
config = mkIf cfg.enable { config = mkIf cfg.enable {

View file

@ -31,7 +31,7 @@ in
options.services.netbird.server = { options.services.netbird.server = {
enable = mkEnableOption "Netbird Server stack, comprising the dashboard, management API and signal service"; enable = mkEnableOption "Netbird Server stack, comprising the dashboard, management API and signal service";
enableNginx = mkEnableOption "Nginx reverse-proxy for the netbird server services."; enableNginx = mkEnableOption "Nginx reverse-proxy for the netbird server services";
domain = mkOption { domain = mkOption {
type = str; type = str;

View file

@ -28,7 +28,7 @@ in
package = mkPackageOption pkgs "netbird" { }; package = mkPackageOption pkgs "netbird" { };
enableNginx = mkEnableOption "Nginx reverse-proxy for the netbird signal service."; enableNginx = mkEnableOption "Nginx reverse-proxy for the netbird signal service";
domain = mkOption { domain = mkOption {
type = str; type = str;

View file

@ -14,7 +14,7 @@ in {
enable = mkEnableOption '' enable = mkEnableOption ''
Networkd-dispatcher service for systemd-networkd connection status Networkd-dispatcher service for systemd-networkd connection status
change. See [https://gitlab.com/craftyguy/networkd-dispatcher](upstream instructions) change. See [https://gitlab.com/craftyguy/networkd-dispatcher](upstream instructions)
for usage. for usage
''; '';
rules = mkOption { rules = mkOption {

View file

@ -34,9 +34,7 @@ in {
[](#opt-programs.nncp.settings) [](#opt-programs.nncp.settings)
''; '';
socketActivation = { socketActivation = {
enable = mkEnableOption '' enable = mkEnableOption "socket activation for nncp-daemon";
Whether to run nncp-daemon persistently or socket-activated.
'';
listenStreams = mkOption { listenStreams = mkOption {
type = with types; listOf str; type = with types; listOf str;
description = '' description = ''

View file

@ -77,6 +77,7 @@ in
config = mkIf cfg.enable { config = mkIf cfg.enable {
systemd.services.oink = { systemd.services.oink = {
description = "Dynamic DNS client for Porkbun"; description = "Dynamic DNS client for Porkbun";
after = [ "network.target" ];
wantedBy = [ "multi-user.target" ]; wantedBy = [ "multi-user.target" ];
script = "${cfg.package}/bin/oink -c ${oinkConfig}"; script = "${cfg.package}/bin/oink -c ${oinkConfig}";
}; };

View file

@ -12,19 +12,19 @@ let
reconnect_to_dispatcher = true; reconnect_to_dispatcher = true;
}; };
beacon_db = { beacon_db = {
connection = "/var/lib/scion-control/control.beacon.db"; connection = "/run/scion-control/control.beacon.db";
}; };
path_db = { path_db = {
connection = "/var/lib/scion-control/control.path.db"; connection = "/run/scion-control/control.path.db";
}; };
trust_db = { trust_db = {
connection = "/var/lib/scion-control/control.trust.db"; connection = "/run/scion-control/control.trust.db";
}; };
log.console = { log.console = {
level = "info"; level = "info";
}; };
}; };
configFile = toml.generate "scion-control.toml" (defaultConfig // cfg.settings); configFile = toml.generate "scion-control.toml" (recursiveUpdate defaultConfig cfg.settings);
in in
{ {
options.services.scion.scion-control = { options.services.scion.scion-control = {
@ -35,7 +35,7 @@ in
example = literalExpression '' example = literalExpression ''
{ {
path_db = { path_db = {
connection = "/var/lib/scion-control/control.path.db"; connection = "/run/scion-control/control.path.db";
}; };
log.console = { log.console = {
level = "info"; level = "info";
@ -62,7 +62,7 @@ in
DynamicUser = true; DynamicUser = true;
Restart = "on-failure"; Restart = "on-failure";
BindPaths = [ "/dev/shm:/run/shm" ]; BindPaths = [ "/dev/shm:/run/shm" ];
StateDirectory = "scion-control"; RuntimeDirectory = "scion-control";
}; };
}; };
}; };

View file

@ -12,16 +12,16 @@ let
reconnect_to_dispatcher = true; reconnect_to_dispatcher = true;
}; };
path_db = { path_db = {
connection = "/var/lib/scion-daemon/sd.path.db"; connection = "/run/scion-daemon/sd.path.db";
}; };
trust_db = { trust_db = {
connection = "/var/lib/scion-daemon/sd.trust.db"; connection = "/run/scion-daemon/sd.trust.db";
}; };
log.console = { log.console = {
level = "info"; level = "info";
}; };
}; };
configFile = toml.generate "scion-daemon.toml" (defaultConfig // cfg.settings); configFile = toml.generate "scion-daemon.toml" (recursiveUpdate defaultConfig cfg.settings);
in in
{ {
options.services.scion.scion-daemon = { options.services.scion.scion-daemon = {
@ -32,7 +32,7 @@ in
example = literalExpression '' example = literalExpression ''
{ {
path_db = { path_db = {
connection = "/var/lib/scion-daemon/sd.path.db"; connection = "/run/scion-daemon/sd.path.db";
}; };
log.console = { log.console = {
level = "info"; level = "info";
@ -57,7 +57,7 @@ in
ExecStart = "${pkgs.scion}/bin/scion-daemon --config ${configFile}"; ExecStart = "${pkgs.scion}/bin/scion-daemon --config ${configFile}";
Restart = "on-failure"; Restart = "on-failure";
DynamicUser = true; DynamicUser = true;
StateDirectory = "scion-daemon"; RuntimeDirectory = "scion-daemon";
}; };
}; };
}; };

View file

@ -15,7 +15,7 @@ let
level = "info"; level = "info";
}; };
}; };
configFile = toml.generate "scion-dispatcher.toml" (defaultConfig // cfg.settings); configFile = toml.generate "scion-dispatcher.toml" (recursiveUpdate defaultConfig cfg.settings);
in in
{ {
options.services.scion.scion-dispatcher = { options.services.scion.scion-dispatcher = {
@ -66,7 +66,7 @@ in
ExecStartPre = "${pkgs.coreutils}/bin/rm -rf /run/shm/dispatcher"; ExecStartPre = "${pkgs.coreutils}/bin/rm -rf /run/shm/dispatcher";
ExecStart = "${pkgs.scion}/bin/scion-dispatcher --config ${configFile}"; ExecStart = "${pkgs.scion}/bin/scion-dispatcher --config ${configFile}";
Restart = "on-failure"; Restart = "on-failure";
StateDirectory = "scion-dispatcher"; RuntimeDirectory = "scion-dispatcher";
}; };
}; };
}; };

Some files were not shown because too many files have changed in this diff Show more