Merge ee11c0fef4 into haskell-updates

This commit is contained in:
nixpkgs-ci[bot]
2025-08-15 00:23:03 +00:00
committed by GitHub
522 changed files with 6571 additions and 4232 deletions

View File

@@ -61,3 +61,17 @@ This results in a key with the following semantics:
```
<running-workflow>-<triggering-workflow>-<triggered-event>-<pull-request/fallback>
```
## Required Status Checks
The "Required Status Checks" branch ruleset is implemented in two top-level workflows: `pr.yml` and `merge-group.yml`.
The PR workflow defines all checks that need to succeed to add a Pull Request to the Merge Queue.
If no Merge Queue is set up for a branch, the PR workflow defines the checks required to merge into the target branch.
The Merge Group workflow defines all checks that are run as part of the Merge Queue.
Only when these pass, a Pull Request is finally merged into the target branch.
They don't apply when no Merge Queue is set up.
Both workflows work with the same `no PR failures` status check.
This name can never be changed, because it's used in the branch ruleset for these rules.

View File

@@ -38,13 +38,13 @@ jobs:
permissions:
pull-requests: write
runs-on: ubuntu-24.04-arm
timeout-minutes: 10
timeout-minutes: 3
steps:
- uses: actions/checkout@08c6903cd8c0fde910a37f88322edcfb5dd907a8 # v5.0.0
with:
fetch-depth: 0
filter: tree:0
path: trusted
sparse-checkout: |
ci/github-script
- name: Install dependencies
run: npm install bottleneck

31
.github/workflows/merge-group.yml vendored Normal file
View File

@@ -0,0 +1,31 @@
name: Merge Group
on:
merge_group:
permissions: {}
jobs:
lint:
name: Lint
uses: ./.github/workflows/lint.yml
with:
mergedSha: ${{ github.event.merge_group.head_sha }}
targetSha: ${{ github.event.merge_group.base_sha }}
# This job's only purpose is to serve as a target for the "Required Status Checks" branch ruleset.
# It "needs" all the jobs that should block the Merge Queue.
# If they pass, it is skipped — which counts as "success" for purposes of the branch ruleset.
# However, if any of them fail, this job will also fail — thus blocking the branch ruleset.
no-pr-failures:
# Modify this list to add or remove jobs from required status checks.
needs:
- lint
# WARNING:
# Do NOT change the name of this job, otherwise the rule will not catch it anymore.
# This would prevent all PRs from passing the merge queue.
name: no PR failures
if: ${{ failure() }}
runs-on: ubuntu-24.04-arm
steps:
- run: exit 1

View File

@@ -79,7 +79,7 @@ You can donate to the NixOS foundation through [SEPA bank transfers](https://nix
Nixpkgs is licensed under the [MIT License](COPYING).
Note:
MIT license does not apply to the packages built by Nixpkgs, merely to the files in this repository (the Nix expressions, build scripts, NixOS modules, etc.).
> [!Note]
> MIT license does not apply to the packages built by Nixpkgs, merely to the files in this repository (the Nix expressions, build scripts, NixOS modules, etc.).
It also might not apply to patches included in Nixpkgs, which may be derivative works of the packages to which they apply.
The aforementioned artifacts are all covered by the licenses of the respective packages.

View File

@@ -1,10 +0,0 @@
This report is automatically generated by the `PR / Check / cherry-pick` CI workflow.
Some of the commits in this PR require the author's and reviewer's attention.
Please follow the [backporting guidelines](https://github.com/NixOS/nixpkgs/blob/master/CONTRIBUTING.md#how-to-backport-pull-requests) and cherry-pick with the `-x` flag.
This requires changes to the unstable `master` and `staging` branches first, before backporting them.
Occasionally, it is not possible to cherry-pick exactly the same patch.
This most frequently happens when resolving merge conflicts or when updating minor versions of packages which have already advanced to the next major on unstable.
If you need to merge this PR despite the warnings, please [dismiss](https://docs.github.com/en/pull-requests/collaborating-with-pull-requests/reviewing-changes-in-pull-requests/dismissing-a-pull-request-review) this review shortly before merging.

View File

@@ -22,22 +22,36 @@ module.exports = async function ({ github, context, core, dry }) {
'?pr=' +
pull_number
async function handle({ sha, commit }) {
async function extract({ sha, commit }) {
const noCherryPick = Array.from(
commit.message.matchAll(/^Not-cherry-picked-because: (.*)$/g)
).at(0)
if (noCherryPick)
return {
sha,
commit,
severity: 'important',
message: `${sha} is not a cherry-pick, because: ${noCherryPick[1]}. Please review this commit manually.`,
type: 'no-cherry-pick',
}
// Using the last line with "cherry" + hash, because a chained backport
// can result in multiple of those lines. Only the last one counts.
const match = Array.from(
const cherry = Array.from(
commit.message.matchAll(/cherry.*([0-9a-f]{40})/g),
).at(-1)
if (!match)
if (!cherry)
return {
sha,
commit,
severity: 'warning',
message: `Couldn't locate original commit hash in message of ${sha}.`,
type: 'no-commit-hash',
}
const original_sha = match[1]
const original_sha = cherry[1]
let branches
try {
@@ -68,6 +82,14 @@ module.exports = async function ({ github, context, core, dry }) {
message: `${original_sha} given in ${sha} not found in any pickable branch.`,
}
return {
sha,
commit,
original_sha,
}
}
function diff({ sha, commit, original_sha }) {
const diff = execFileSync('git', [
'-C',
__dirname,
@@ -113,6 +135,7 @@ module.exports = async function ({ github, context, core, dry }) {
colored_diff,
severity: 'warning',
message: `Difference between ${sha} and original ${original_sha} may warrant inspection.`,
type: 'diff',
}
}
@@ -121,7 +144,26 @@ module.exports = async function ({ github, context, core, dry }) {
pull_number,
})
const results = await Promise.all(commits.map(handle))
const extracted = await Promise.all(commits.map(extract))
const fetch = extracted
.filter(({ severity }) => !severity)
.map(({ sha, original_sha }) => [ sha, original_sha ])
.flat()
if (fetch.length > 0) {
// Fetching all commits we need for diff at once is much faster than any other method.
execFileSync('git', [
'-C',
__dirname,
'fetch',
'--depth=2',
'origin',
...fetch,
])
}
const results = extracted.map(result => result.severity ? result : diff(result))
// Log all results without truncation, with better highlighting and all whitespace changes to the job log.
results.forEach(({ sha, commit, severity, message, colored_diff }) => {
@@ -175,10 +217,29 @@ module.exports = async function ({ github, context, core, dry }) {
if (results.some(({ severity }) => severity == 'error'))
process.exitCode = 1
core.summary.addRaw(
await readFile(join(__dirname, 'check-cherry-picks.md'), 'utf-8'),
true,
)
core.summary.addRaw('This report is automatically generated by the `PR / Check / cherry-pick` CI workflow.', true)
core.summary.addEOL()
core.summary.addRaw("Some of the commits in this PR require the author's and reviewer's attention.", true)
core.summary.addEOL()
if (results.some(({ type }) => type === 'no-commit-hash')) {
core.summary.addRaw('Please follow the [backporting guidelines](https://github.com/NixOS/nixpkgs/blob/master/CONTRIBUTING.md#how-to-backport-pull-requests) and cherry-pick with the `-x` flag.', true)
core.summary.addRaw('This requires changes to the unstable `master` and `staging` branches first, before backporting them.', true)
core.summary.addEOL()
core.summary.addRaw('Occasionally, commits are not cherry-picked at all, for example when updating minor versions of packages which have already advanced to the next major on unstable.', true)
core.summary.addRaw('These commits can optionally be marked with a `Not-cherry-picked-because: <reason>` footer.', true)
core.summary.addEOL()
}
if (results.some(({ type }) => type === 'diff')) {
core.summary.addRaw('Sometimes it is not possible to cherry-pick exactly the same patch.', true)
core.summary.addRaw('This most frequently happens when resolving merge conflicts.', true)
core.summary.addRaw('The range-diff will help to review the resolution of conflicts.', true)
core.summary.addEOL()
}
core.summary.addRaw('If you need to merge this PR despite the warnings, please [dismiss](https://docs.github.com/en/pull-requests/collaborating-with-pull-requests/reviewing-changes-in-pull-requests/dismissing-a-pull-request-review) this review shortly before merging.', true)
results.forEach(({ severity, message, diff }) => {
if (severity == 'info') return
@@ -195,7 +256,7 @@ module.exports = async function ({ github, context, core, dry }) {
// Whether this is intended or just an implementation detail is unclear.
core.summary.addRaw('<blockquote>')
core.summary.addRaw(
`\n\n[!${severity == 'warning' ? 'WARNING' : 'CAUTION'}]`,
`\n\n[!${({ important: 'IMPORTANT', warning: 'WARNING', error: 'CAUTION' })[severity]}]`,
true,
)
core.summary.addRaw(`${message}`, true)

View File

@@ -2123,12 +2123,8 @@ The following rules are desired to be respected:
It does not need to be set explicitly unless the package requires a specific platform.
* The file is formatted with `nixfmt-rfc-style`.
* Commit names of Python libraries must reflect that they are Python
libraries (e.g. `python313Packages.numpy: 1.11 -> 1.12` rather than `numpy: 1.11 -> 1.12`).
* The current default version of python should be included
in commit messages to enable automatic builds by ofborg.
For example `python313Packages.numpy: 1.11 -> 1.12` should be used rather
than `python3Packages.numpy: 1.11 -> 1.12`.
Note that `pythonPackages` is an alias for `python27Packages`.
libraries (e.g. `python3Packages.numpy: 1.11 -> 1.12` rather than `numpy: 1.11 -> 1.12`).
See also [`pkgs/README.md`](https://github.com/NixOS/nixpkgs/blob/master/pkgs/README.md#commit-conventions).
* Attribute names in `python-packages.nix` as well as `pname`s should match the
library's name on PyPI, but be normalized according to [PEP
0503](https://www.python.org/dev/peps/pep-0503/#normalized-names). This means

View File

@@ -115,6 +115,10 @@
- `fetchgit`: Add `rootDir` argument to limit the resulting source to one subdirectory of the whole Git repository. Corresponding `--root-dir` option added to `nix-prefetch-git`.
- The `clickhouse` package now track the stable upstream version per [upstream's
recommendation](https://clickhouse.com/docs/faq/operations/production). Users
can continue to use the `clickhouse-lts` package if desired.
## Nixpkgs Library {#sec-nixpkgs-release-25.11-lib}
<!-- To avoid merge conflicts, consider adding your item at an arbitrary place in the list instead. -->

View File

@@ -1,10 +0,0 @@
# Throws an error if any of our lib tests fail.
let
tests = [
"misc"
"systems"
];
all = builtins.concatLists (map (f: import (./. + "/${f}.nix")) tests);
in
if all == [ ] then null else throw (builtins.toJSON all)

View File

@@ -145,6 +145,11 @@ let
inherit expected;
};
dummyDerivation = derivation {
name = "name";
builder = "builder";
system = "system";
};
in
runTests {
@@ -757,18 +762,8 @@ runTests {
};
testSplitStringsDerivation = {
expr = take 3 (
strings.splitString "/" (derivation {
name = "name";
builder = "builder";
system = "system";
})
);
expected = [
""
"nix"
"store"
];
expr = lib.dropEnd 1 (strings.splitString "/" dummyDerivation);
expected = strings.splitString "/" builtins.storeDir;
};
testSplitVersionSingle = {
@@ -816,7 +811,7 @@ runTests {
in
{
storePath = isStorePath goodPath;
storePathDerivation = isStorePath (import ../.. { system = "x86_64-linux"; }).hello;
storePathDerivation = isStorePath dummyDerivation;
storePathAppendix = isStorePath "${goodPath}/bin/python";
nonAbsolute = isStorePath (concatStrings (tail (stringToCharacters goodPath)));
asPath = isStorePath (/. + goodPath);
@@ -901,7 +896,7 @@ runTests {
};
testHasInfixDerivation = {
expr = hasInfix "hello" (import ../.. { system = "x86_64-linux"; }).hello;
expr = hasInfix "name" dummyDerivation;
expected = true;
};

View File

@@ -18,8 +18,6 @@
pkgs.runCommand "nixpkgs-lib-tests-nix-${nix.version}"
{
buildInputs = [
(import ./check-eval.nix)
(import ./fetchers.nix)
(import ../path/tests {
inherit pkgs;
})
@@ -71,6 +69,12 @@ pkgs.runCommand "nixpkgs-lib-tests-nix-${nix.version}"
echo "Running lib/tests/systems.nix"
[[ $(nix-instantiate --eval --strict lib/tests/systems.nix | tee /dev/stderr) == '[ ]' ]];
echo "Running lib/tests/misc.nix"
[[ $(nix-instantiate --eval --strict lib/tests/misc.nix | tee /dev/stderr) == '[ ]' ]];
echo "Running lib/tests/fetchers.nix"
[[ $(nix-instantiate --eval --strict lib/tests/fetchers.nix | tee /dev/stderr) == '[ ]' ]];
mkdir $out
echo success > $out/${nix.version}
''

View File

@@ -2737,6 +2737,12 @@
githubId = 31864305;
name = "William Hai";
};
bahrom04 = {
name = "Baxrom Raxmatov";
email = "magdiyevbahrom@gmail.com";
github = "bahrom04";
githubId = 116780481;
};
baileylu = {
name = "Luke Bailey";
email = "baileylu@tcd.ie";
@@ -3034,6 +3040,12 @@
githubId = 32039602;
keys = [ { fingerprint = "2B46 58FF 887A 8366 F88B BE92 CF83 0BB3 B973 9A6A"; } ];
};
bemeritus = {
name = "Shohrux Rasulov";
email = "bemerituss@gmail.com";
github = "bemeritus";
githubId = 175357618;
};
ben9986 = {
name = "Ben Carmichael";
email = "ben9986.unvmn@passinbox.com";
@@ -6258,13 +6270,6 @@
githubId = 17111639;
name = "Devin Singh";
};
devpikachu = {
email = "andrei.hava@proton.me";
matrix = "@andrei:matrix.detpikachu.dev";
github = "devpikachu";
githubId = 30475873;
name = "Andrei Hava";
};
devplayer0 = {
email = "dev@nul.ie";
github = "devplayer0";
@@ -26189,6 +26194,11 @@
githubId = 1215104;
keys = [ { fingerprint = "B1FD 4E2A 84B2 2379 F4BF 2EF5 FE33 A228 2371 E831"; } ];
};
txkyel = {
github = "txkyel";
githubId = 56144092;
name = "Kyle Xiao";
};
tyberius-prime = {
name = "Tyberius Prime";
github = "TyberiusPrime";

View File

@@ -1252,6 +1252,16 @@ with lib.maintainers;
shortName = "coqui-ai TTS";
};
uzinfocom = {
members = [
orzklv
bahrom04
bemeritus
];
scope = "Maintain Uzbek Linux state & community packages and modules.";
shortName = "Uzinfocom Open Source";
};
windows = {
members = [
RossSmyth

View File

@@ -1468,6 +1468,9 @@
"module-security-acme-fix-jws": [
"index.html#module-security-acme-fix-jws"
],
"module-security-acme-reload-dependencies": [
"index.html#module-security-acme-reload-dependencies"
],
"module-programs-zsh-ohmyzsh": [
"index.html#module-programs-zsh-ohmyzsh"
],

View File

@@ -171,6 +171,21 @@
- `services.gitea` supports sending notifications with sendmail again. To do this, activate the parameter `services.gitea.mailerUseSendmail` and configure SMTP server.
- Revamp of the ACME certificate acquisication and renewal process to help scale systems with lots (100+) of certificates.
Units and targets have been reshaped to better support more specific dependency propagation and avoid
superfluously triggering unchanged units:
If a service requires a syntactically valid certificate to start it should now depend on the `acme-{certname}.service` unit.
We now always generate initial self-signed certificates as this drastically simplifies the dependency structure. As a result, the option `security.acme.preliminarySelfsigned` has been removed.
Instead of the previous `acme-finished-{certname}.target`s there are now `acme-order-renew-{certname}.service`s that will be activated
in a delayed fashion to ensure that bootstrapping with servers like nginx that take part in the acquisition/renewal process works
smoothly. Dependencies on `acme-finished` units should move to `acme-order-renew`.
Note that system activation will complete before all certificates may have been renewed or acquired.
- `libvirt` now supports using `nftables` backend.
- The `virtualisation.libvirtd.firewallBackend` option can be used to configure the firewall backend used by libvirtd.

View File

@@ -26,7 +26,7 @@ let
inherit (config.sdImage) storePaths;
compressImage = config.sdImage.compressImage;
populateImageCommands = config.sdImage.populateRootCommands;
volumeLabel = "NIXOS_SD";
volumeLabel = config.sdImage.rootVolumeLabel;
}
// optionalAttrs (config.sdImage.rootPartitionUUID != null) {
uuid = config.sdImage.rootPartitionUUID;
@@ -117,6 +117,17 @@ in
'';
};
rootVolumeLabel = mkOption {
type = types.str;
default = "NIXOS_SD";
example = "NIXOS_PENDRIVE";
description = ''
Label for the NixOS root volume.
Usually used when creating a recovery NixOS media installation
that avoids conflicting with previous instalation label.
'';
};
firmwareSize = mkOption {
type = types.int;
# As of 2019-08-18 the Raspberry pi firmware + u-boot takes ~18MiB
@@ -197,7 +208,7 @@ in
];
};
"/" = {
device = "/dev/disk/by-label/NIXOS_SD";
device = "/dev/disk/by-label/${config.sdImage.rootVolumeLabel}";
fsType = "ext4";
};
};

View File

@@ -318,7 +318,7 @@ can be applied to any service.
# Now you must augment OpenSMTPD's systemd service to load
# the certificate files.
systemd.services.opensmtpd.requires = [ "acme-finished-mail.example.com.target" ];
systemd.services.opensmtpd.requires = [ "acme-mail.example.com.service" ];
systemd.services.opensmtpd.serviceConfig.LoadCredential =
let
certDir = config.security.acme.certs."mail.example.com".directory;
@@ -376,3 +376,11 @@ systemd-tmpfiles --create
# Note: Do this for all certs that share the same account email address
systemctl start acme-example.com.service
```
## Ensuring dependencies for services that need to be reloaded when a certificate challenges {#module-security-acme-reload-dependencies}
Services that depend on ACME certificates and need to be reloaded can use one of two approaches to reload upon successfull certificate acquisition or renewal:
1. **Using the `security.acme.certs.<name>.reloadServices` option**: This will cause `systemctl try-reload-or-restart` to be run for the listed services.
2. **Using a separate reload unit**: if you need perform more complex actions you can implement a separate reload unit but need to ensure that it lists the `acme-renew-<name>.service` unit both as `wantedBy` AND `after`. See the nginx module implementation with its `nginx-config-reload` service.

View File

@@ -24,56 +24,32 @@ let
# Since that service is a oneshot with RemainAfterExit,
# the folder will exist during all renewal services.
lockdir = "/run/acme/";
concurrencyLockfiles = map (n: "${toString n}.lock") (lib.range 1 cfg.maxConcurrentRenewals);
# Assign elements of `baseList` to each element of `needAssignmentList`, until the latter is exhausted.
# returns: [{fst = "element of baseList"; snd = "element of needAssignmentList"}]
roundRobinAssign =
baseList: needAssignmentList:
if baseList == [ ] then [ ] else _rrCycler baseList baseList needAssignmentList;
_rrCycler =
with builtins;
origBaseList: workingBaseList: needAssignmentList:
if (workingBaseList == [ ] || needAssignmentList == [ ]) then
[ ]
else
[
{
fst = head workingBaseList;
snd = head needAssignmentList;
}
]
++ _rrCycler origBaseList (
if (tail workingBaseList == [ ]) then origBaseList else tail workingBaseList
) (tail needAssignmentList);
attrsToList = lib.mapAttrsToList (
attrname: attrval: {
name = attrname;
value = attrval;
}
);
# for an AttrSet `funcsAttrs` having functions as values, apply single arguments from
# `argsList` to them in a round-robin manner.
# Returns an attribute set with the applied functions as values.
roundRobinApplyAttrs =
funcsAttrs: argsList:
lib.listToAttrs (
map (x: {
inherit (x.snd) name;
value = x.snd.value x.fst;
}) (roundRobinAssign argsList (attrsToList funcsAttrs))
);
wrapInFlock =
lockfilePath: script:
script:
# explainer: https://stackoverflow.com/a/60896531
''
exec {LOCKFD}> ${lockfilePath}
echo "Waiting to acquire lock ${lockfilePath}"
${pkgs.flock}/bin/flock ''${LOCKFD} || exit 1
echo "Acquired lock ${lockfilePath}"
maxConcurrentRenewals=${toString cfg.maxConcurrentRenewals}
acquireLock() {
echo "Waiting to acquire lock in ${lockdir}"
while true; do
for i in $(seq 1 $maxConcurrentRenewals); do
exec {LOCKFD}> "${lockdir}/$i.lock"
if ${pkgs.flock}/bin/flock -n ''${LOCKFD}; then
return 0
fi
exec {LOCKFD}>&-
done
sleep 1;
done
}
if [ "$maxConcurrentRenewals" -gt "0" ]; then
acquireLock
fi
''
+ script
+ "\n"
+ ''echo "Releasing lock ${lockfilePath}" # only released after process exit'';
+ script;
# There are many services required to make cert renewals work.
# They all follow a common structure:
@@ -160,58 +136,49 @@ let
);
# This is defined with lib.mkMerge so that we can separate the config per function.
setupService = lib.mkMerge [
{
description = "Set up the ACME certificate renewal infrastructure";
script = lib.mkBefore ''
${lib.optionalString cfg.defaults.enableDebugLogs "set -x"}
set -euo pipefail
'';
serviceConfig = commonServiceConfig // {
# This script runs with elevated privileges, denoted by the +
# ExecStartPre is used instead of ExecStart so that the `script` continues to work.
ExecStartPre = "+${lib.getExe privilegedSetupScript}";
setupService = {
description = "Set up the ACME certificate renewal infrastructure";
path = [ pkgs.minica ];
# We don't want this to run every time a renewal happens
RemainAfterExit = true;
script = lib.mkBefore ''
${lib.optionalString cfg.defaults.enableDebugLogs "set -x"}
set -euo pipefail
test -e ca/key.pem || minica \
--ca-key ca/key.pem \
--ca-cert ca/cert.pem \
--domains selfsigned.local
'';
# StateDirectory entries are a cleaner, service-level mechanism
# for dealing with persistent service data
StateDirectory = [
"acme"
"acme/.lego"
"acme/.lego/accounts"
];
StateDirectoryMode = "0755";
serviceConfig = commonServiceConfig // {
# This script runs with elevated privileges, denoted by the +
# ExecStartPre is used instead of ExecStart so that the `script` continues to work.
ExecStartPre = "+${lib.getExe privilegedSetupScript}";
# Creates ${lockdir}. Earlier RemainAfterExit=true means
# it does not get deleted immediately.
RuntimeDirectory = "acme";
RuntimeDirectoryMode = "0700";
# We don't want this to run every time a renewal happens
RemainAfterExit = true;
# Generally, we don't write anything that should be group accessible.
# Group varies for most ACME units, and setup files are only used
# under the acme user.
UMask = "0077";
};
}
# StateDirectory entries are a cleaner, service-level mechanism
# for dealing with persistent service data
StateDirectory = [
"acme"
"acme/.lego"
"acme/.lego/accounts"
"acme/.minica"
];
BindPaths = "/var/lib/acme/.minica:/tmp/ca";
StateDirectoryMode = "0755";
# Avoid race conditions creating the CA for selfsigned certs
(lib.mkIf cfg.preliminarySelfsigned {
path = [ pkgs.minica ];
# Working directory will be /tmp
script = ''
test -e ca/key.pem || minica \
--ca-key ca/key.pem \
--ca-cert ca/cert.pem \
--domains selfsigned.local
'';
serviceConfig = {
StateDirectory = [ "acme/.minica" ];
BindPaths = "/var/lib/acme/.minica:/tmp/ca";
};
})
];
# Creates ${lockdir}. Earlier RemainAfterExit=true means
# it does not get deleted immediately.
RuntimeDirectory = "acme";
RuntimeDirectoryMode = "0700";
# Generally, we don't write anything that should be group accessible.
# Group varies for most ACME units, and setup files are only used
# under the acme user.
UMask = "0077";
};
};
certToConfig =
cert: data:
@@ -219,7 +186,6 @@ let
acmeServer = data.server;
useDns = data.dnsProvider != null;
destPath = "/var/lib/acme/${cert}";
selfsignedDeps = lib.optionals (cfg.preliminarySelfsigned) [ "acme-selfsigned-${cert}.service" ];
# Minica and lego have a "feature" which replaces * with _. We need
# to make this substitution to reference the output files from both programs.
@@ -339,16 +305,18 @@ let
certificateKey = if data.csrKey != null then "${data.csrKey}" else "certificates/${keyName}.key";
in
{
inherit accountHash cert selfsignedDeps;
inherit accountHash cert;
group = data.group;
renewTimer = {
description = "Renew ACME Certificate for ${cert}";
wantedBy = [ "timers.target" ];
# Avoid triggering certificate renewals accidentally when running s-t-c.
unitConfig."X-OnlyManualStart" = true;
timerConfig = {
OnCalendar = data.renewInterval;
Unit = "acme-${cert}.service";
Unit = "acme-order-renew-${cert}.service";
Persistent = "yes";
# Allow systemd to pick a convenient time within the day
@@ -364,15 +332,29 @@ let
};
};
selfsignService = lockfileName: {
description = "Generate self-signed certificate for ${cert}";
baseService = {
description = "Ensure certificate for ${cert}";
wantedBy = [ "multi-user.target" ];
after = [ "acme-setup.service" ];
requires = [ "acme-setup.service" ];
# Whenever this service starts (on boot, through dependencies, through
# changes) we trigger the acme-order-renew service to give it a chance
# to catch up with the potentially changed config.
wants = [
"acme-setup.service"
"acme-order-renew-${cert}.service"
];
before = [ "acme-order-renew-${cert}.service" ];
restartTriggers = [
config.systemd.services."acme-order-renew-${cert}".script
];
path = [ pkgs.minica ];
unitConfig = {
ConditionPathExists = "!/var/lib/acme/${cert}/key.pem";
StartLimitIntervalSec = 0;
};
@@ -380,52 +362,83 @@ let
Group = data.group;
UMask = "0027";
RemainAfterExit = true;
StateDirectory = "acme/${cert}";
BindPaths = [
"/var/lib/acme/.minica:/tmp/ca"
"/var/lib/acme/${cert}:/tmp/${keyName}"
"/var/lib/acme/${cert}:/tmp/out"
];
};
# Working directory will be /tmp
# minica will output to a folder sharing the name of the first domain
# in the list, which will be ${data.domain}
script = (if (lockfileName == null) then lib.id else wrapInFlock "${lockdir}${lockfileName}") ''
script = wrapInFlock ''
set -ex
# Regenerate self-signed certificates (in case the SANs change) until we
# have seen a succesfull ACME certificate at least once.
if [ -e out/acme-success ]; then
exit 0
fi
minica \
--ca-key ca/key.pem \
--ca-cert ca/cert.pem \
--domains ${lib.escapeShellArg (builtins.concatStringsSep "," ([ data.domain ] ++ extraDomains))}
# Create files to match directory layout for real certificates
cd '${keyName}'
cp ../ca/cert.pem chain.pem
cat cert.pem chain.pem > fullchain.pem
cat key.pem fullchain.pem > full.pem
(
cd '${keyName}'
cp -vp cert.pem ../out/cert.pem
cp -vp key.pem ../out/key.pem
)
cat out/cert.pem ca/cert.pem > out/fullchain.pem
cp ca/cert.pem out/chain.pem
cat out/key.pem out/fullchain.pem > out/full.pem
# Group might change between runs, re-apply it
chown '${user}:${data.group}' -- *
# Fix up the output files to adhere to the group and
# have consistent permissions. This needs to be kept
# consistent with the acme-setup script above.
for fixpath in out certificates; do
if [ -d "$fixpath" ]; then
chmod -R u=rwX,g=rX,o= "$fixpath"
chown -R ${user}:${data.group} "$fixpath"
fi
done
# Default permissions make the files unreadable by group + anon
# Need to be readable by group
chmod 640 -- *
${lib.optionalString (data.webroot != null) ''
# Ensure the webroot exists. Fixing group is required in case configuration was changed between runs.
# Lego will fail if the webroot does not exist at all.
(
mkdir -p '${data.webroot}/.well-known/acme-challenge' \
&& chgrp '${data.group}' ${data.webroot}/.well-known/acme-challenge
) || (
echo 'Please ensure ${data.webroot}/.well-known/acme-challenge exists and is writable by acme:${data.group}' \
&& exit 1
)
''}
'';
};
renewService = lockfileName: {
description = "Renew ACME certificate for ${cert}";
orderRenewService = {
description = "Order (and renew) ACME certificate for ${cert}";
after = [
"network.target"
"network-online.target"
"acme-setup.service"
"nss-lookup.target"
]
++ selfsignedDeps;
wants = [ "network-online.target" ] ++ selfsignedDeps;
requires = [ "acme-setup.service" ];
# https://github.com/NixOS/nixpkgs/pull/81371#issuecomment-605526099
wantedBy = lib.optionals (!config.boot.isContainer) [ "multi-user.target" ];
"acme-${cert}.service"
];
wants = [
"network-online.target"
"acme-setup.service"
"acme-${cert}.service"
];
# Ensure that certificates are generated if people use `security.acme.certs`
# without having/declaring other systemd units that depend on the cert.
path = with pkgs; [
lego
@@ -491,7 +504,7 @@ let
};
# Working directory will be /tmp
script = (if (lockfileName == null) then lib.id else wrapInFlock "${lockdir}${lockfileName}") ''
script = wrapInFlock ''
${lib.optionalString data.enableDebugLogs "set -x"}
set -euo pipefail
@@ -523,25 +536,12 @@ let
[[ $expiration_days -gt ${toString data.validMinDays} ]]
}
${lib.optionalString (data.webroot != null) ''
# Ensure the webroot exists. Fixing group is required in case configuration was changed between runs.
# Lego will fail if the webroot does not exist at all.
(
mkdir -p '${data.webroot}/.well-known/acme-challenge' \
&& chgrp '${data.group}' ${data.webroot}/.well-known/acme-challenge
) || (
echo 'Please ensure ${data.webroot}/.well-known/acme-challenge exists and is writable by acme:${data.group}' \
&& exit 1
)
''}
echo '${domainHash}' > domainhash.txt
# Check if we can renew.
# Check if a new order is needed
# We can only renew if the list of domains has not changed.
# We also need an account key. Avoids #190493
if cmp -s domainhash.txt certificates/domainhash.txt && [ -e '${certificateKey}' ] && [ -e 'certificates/${keyName}.crt' ] && [ -n "$(find accounts -name '${data.email}.key')" ]; then
# Even if a cert is not expired, it may be revoked by the CA.
# Try to renew, and silently fail if the cert is not expired.
# Avoids #85794 and resolves #129838
@@ -553,13 +553,12 @@ let
exit 11
fi
fi
# Otherwise do a full run
# Do a full run
elif ! lego ${runOpts}; then
# Produce a nice error for those doing their first nixos-rebuild with these certs
echo Failed to fetch certificates. \
This may mean your DNS records are set up incorrectly. \
${lib.optionalString (cfg.preliminarySelfsigned) "Selfsigned certs are in place and dependant services will still start."}
Self-signed certs are in place and dependant services will still start.
# Exit 10 so that users can potentially amend SuccessExitStatus to ignore this error.
# High number to avoid Systemd reserved codes.
exit 10
@@ -567,10 +566,12 @@ let
mv domainhash.txt certificates/
# Group might change between runs, re-apply it
chown '${user}:${data.group}' certificates/*
touch out/acme-success
# Copy all certs to the "real" certs directory
# lego has only an interesting subset of files available,
# construct reasonably compatible files that clients can consume
# as expected.
if ! cmp -s 'certificates/${keyName}.crt' out/fullchain.pem; then
touch out/renewed
echo Installing new certificate
@@ -581,10 +582,13 @@ let
cat out/key.pem out/fullchain.pem > out/full.pem
fi
# By default group will have no access to the cert files.
# This chmod will fix that.
chmod 640 out/*
# Keep permissions consistent. Needs to be in sync with the other scripts.
for fixpath in out certificates; do
if [ -d "$fixpath" ]; then
chmod -R u=rwX,g=rX,o= "$fixpath"
chown -R ${user}:${data.group} "$fixpath"
fi
done
# Also ensure safer permissions on the account directory.
chmod -R u=rwX,g=,o= accounts/.
'';
@@ -905,19 +909,6 @@ in
options = {
security.acme = {
preliminarySelfsigned = lib.mkOption {
type = lib.types.bool;
default = true;
description = ''
Whether a preliminary self-signed certificate should be generated before
doing ACME requests. This can be useful when certificates are required in
a webserver, but ACME needs the webserver to make its requests.
With preliminary self-signed certificate the webserver can be started and
can later reload the correct ACME certificates.
'';
};
acceptTerms = lib.mkOption {
type = lib.types.bool;
default = false;
@@ -1003,10 +994,13 @@ in
"ACME Directory is now hardcoded to /var/lib/acme and its permissions are managed by systemd. See https://github.com/NixOS/nixpkgs/issues/53852 for more info."
)
(lib.mkRemovedOptionModule [ "security" "acme" "preDelay" ]
"This option has been removed. If you want to make sure that something executes before certificates are provisioned, add a RequiredBy=acme-\${cert}.service to the service you want to execute before the cert renewal"
"This option has been removed. If you want to make sure that something executes before certificates are provisioned, add a RequiredBy=acme-\${cert}.service and Before=acme-\${cert}.service to the service you want to execute before the cert renewal"
)
(lib.mkRemovedOptionModule [ "security" "acme" "activationDelay" ]
"This option has been removed. If you want to make sure that something executes before certificates are provisioned, add a RequiredBy=acme-\${cert}.service to the service you want to execute before the cert renewal"
"This option has been removed. If you want to make sure that something executes before certificates are provisioned, add a RequiredBy=acme-\${cert}.service and Before=acme-\${cert}.service to the service you want to execute before the cert renewal"
)
(lib.mkRemovedOptionModule [ "security" "acme" "preliminarySelfsigned" ]
"This option has been removed. Preliminary self-signed certificates are now always generated to simplify the dependency structure."
)
(lib.mkChangedOptionModule
[ "security" "acme" "validMin" ]
@@ -1161,45 +1155,25 @@ in
systemd.services =
let
renewServiceFunctions = lib.mapAttrs' (
cert: conf: lib.nameValuePair "acme-${cert}" conf.renewService
orderRenewServices = lib.mapAttrs' (
cert: conf: lib.nameValuePair "acme-order-renew-${cert}" conf.orderRenewService
) certConfigs;
renewServices =
if cfg.maxConcurrentRenewals > 0 then
roundRobinApplyAttrs renewServiceFunctions concurrencyLockfiles
else
lib.mapAttrs (_: f: f null) renewServiceFunctions;
selfsignServiceFunctions = lib.mapAttrs' (
cert: conf: lib.nameValuePair "acme-selfsigned-${cert}" conf.selfsignService
baseServices = lib.mapAttrs' (
cert: conf: lib.nameValuePair "acme-${cert}" conf.baseService
) certConfigs;
selfsignServices =
if cfg.maxConcurrentRenewals > 0 then
roundRobinApplyAttrs selfsignServiceFunctions concurrencyLockfiles
else
lib.mapAttrs (_: f: f null) selfsignServiceFunctions;
in
{
acme-setup = setupService;
}
// renewServices
// lib.optionalAttrs cfg.preliminarySelfsigned selfsignServices;
// baseServices
// orderRenewServices;
systemd.timers = lib.mapAttrs' (
cert: conf: lib.nameValuePair "acme-${cert}" conf.renewTimer
cert: conf: lib.nameValuePair "acme-renew-${cert}" conf.renewTimer
) certConfigs;
systemd.targets =
let
# Create some targets which can be depended on to be "active" after cert renewals
finishedTargets = lib.mapAttrs' (
cert: conf:
lib.nameValuePair "acme-finished-${cert}" {
wantedBy = [ "default.target" ];
requires = [ "acme-${cert}.service" ];
after = [ "acme-${cert}.service" ];
}
) certConfigs;
# Create targets to limit the number of simultaneous account creations
# How it works:
# - Pick a "leader" cert service, which will be in charge of creating the account,
@@ -1214,8 +1188,8 @@ in
let
dnsConfs = builtins.filter (conf: cfg.certs.${conf.cert}.dnsProvider != null) confs;
leaderConf = if dnsConfs != [ ] then builtins.head dnsConfs else builtins.head confs;
leader = "acme-${leaderConf.cert}.service";
followers = map (conf: "acme-${conf.cert}.service") (
leader = "acme-order-renew-${leaderConf.cert}.service";
followers = map (conf: "acme-order-renew-${conf.cert}.service") (
builtins.filter (conf: conf != leaderConf) confs
);
in
@@ -1224,10 +1198,11 @@ in
before = followers;
requires = [ leader ];
after = [ leader ];
unitConfig.RefuseManualStart = true;
}
) (lib.groupBy (conf: conf.accountHash) (lib.attrValues certConfigs));
in
finishedTargets // accountTargets;
accountTargets;
})
];

View File

@@ -156,7 +156,7 @@ in
"network.target"
]
++ lib.optional (cfg.useACMEHost != null) "acme-${cfg.useACMEHost}.service";
wants = lib.optional (cfg.useACMEHost != null) "acme-finished-${cfg.useACMEHost}.target";
wants = lib.optional (cfg.useACMEHost != null) "acme-${cfg.useACMEHost}.service";
wantedBy = [ "multi-user.target" ];
serviceConfig = {
AmbientCapabilities = "CAP_NET_BIND_SERVICE";

View File

@@ -87,9 +87,8 @@ with lib;
ppp-pptpd-wrapped = pkgs.stdenv.mkDerivation {
name = "ppp-pptpd-wrapped";
phases = [ "installPhase" ];
nativeBuildInputs = with pkgs; [ makeWrapper ];
installPhase = ''
buildCommand = ''
mkdir -p $out/bin
makeWrapper ${pkgs.ppp}/bin/pppd $out/bin/pppd \
--set LD_PRELOAD "${pkgs.libredirect}/lib/libredirect.so" \

View File

@@ -89,9 +89,8 @@ with lib;
xl2tpd-ppp-wrapped = pkgs.stdenv.mkDerivation {
name = "xl2tpd-ppp-wrapped";
phases = [ "installPhase" ];
nativeBuildInputs = with pkgs; [ makeWrapper ];
installPhase = ''
buildCommand = ''
mkdir -p $out/bin
makeWrapper ${pkgs.ppp}/sbin/pppd $out/bin/pppd \

View File

@@ -46,5 +46,5 @@ in
};
};
meta.maintainers = with lib.maintainers; [ orzklv ];
meta.maintainers = lib.teams.uzinfocom.members;
}

View File

@@ -201,7 +201,7 @@ let
echo "Tried for at least 30 seconds, giving up..."
exit 1
fi
count=$((count++))
count=$((++count))
done
${recoverIdmAdmin}

View File

@@ -23,7 +23,7 @@ in
};
openFirewall = lib.mkEnableOption "" // {
description = "Open ports in the firewall for the Radarr web interface.";
description = "Open ports in the firewall for LANraragi's web interface.";
};
passwordFile = lib.mkOption {

View File

@@ -145,7 +145,7 @@ in
'';
"~* ^(\\/cache\\/files.*)(\\/.*)".extraConfig = ''
alias /var/lib/onlyoffice/documentserver/App_Data$1;
add_header Content-Disposition "attachment; filename*=UTF-8''$arg_filename";
more_set_headers Content-Disposition "attachment; filename*=UTF-8''$arg_filename";
set $secure_link_secret verysecretstring;
secure_link $arg_md5,$arg_expires;

View File

@@ -294,6 +294,45 @@ in
);
};
discordAuthentication = lib.mkOption {
description = ''
To configure Discord auth, you'll need to create an application at
https://discord.com/developers/applications/
See https://docs.getoutline.com/s/hosting/doc/discord-g4JdWFFub6
for details on setting up your Discord app.
'';
default = null;
type = lib.types.nullOr (
lib.types.submodule {
options = {
clientId = lib.mkOption {
type = lib.types.str;
description = "Authentication client identifier.";
};
clientSecretFile = lib.mkOption {
type = lib.types.str;
description = "File path containing the authentication secret.";
};
serverId = lib.mkOption {
type = lib.types.str;
default = "";
description = ''
Restrict logins to a specific server (optional, but recommended).
You can find a Discord server's ID by right-clicking the server icon,
and select Copy Server ID.
'';
};
serverRoles = lib.mkOption {
type = lib.types.commas;
default = "";
description = "Optionally restrict logins to a comma-separated list of role IDs";
};
};
}
);
};
oidcAuthentication = lib.mkOption {
description = ''
To configure generic OIDC auth, you'll need some kind of identity
@@ -721,6 +760,12 @@ in
SLACK_MESSAGE_ACTIONS = builtins.toString cfg.slackIntegration.messageActions;
})
(lib.mkIf (cfg.discordAuthentication != null) {
DISCORD_CLIENT_ID = cfg.discordAuthentication.clientId;
DISCORD_SERVER_ID = cfg.discordAuthentication.serverId;
DISCORD_SERVER_ROLES = cfg.discordAuthentication.serverRoles;
})
(lib.mkIf (cfg.smtp != null) {
SMTP_HOST = cfg.smtp.host;
SMTP_PORT = builtins.toString cfg.smtp.port;
@@ -760,6 +805,9 @@ in
${lib.optionalString (cfg.oidcAuthentication != null) ''
export OIDC_CLIENT_SECRET="$(head -n1 ${lib.escapeShellArg cfg.oidcAuthentication.clientSecretFile})"
''}
${lib.optionalString (cfg.discordAuthentication != null) ''
export DISCORD_CLIENT_SECRET="$(head -n1 ${lib.escapeShellArg cfg.discordAuthentication.clientSecretFile})"
''}
${lib.optionalString (cfg.sslKeyFile != null) ''
export SSL_KEY="$(head -n1 ${lib.escapeShellArg cfg.sslKeyFile})"
''}

View File

@@ -48,8 +48,6 @@ let
) (filter (hostOpts: hostOpts.enableACME || hostOpts.useACMEHost != null) vhosts);
vhostCertNames = unique (map (hostOpts: hostOpts.certName) acmeEnabledVhosts);
dependentCertNames = filter (cert: certs.${cert}.dnsProvider == null) vhostCertNames; # those that might depend on the HTTP server
independentCertNames = filter (cert: certs.${cert}.dnsProvider != null) vhostCertNames; # those that don't depend on the HTTP server
mkListenInfo =
hostOpts:
@@ -914,13 +912,14 @@ in
systemd.services.httpd = {
description = "Apache HTTPD";
wantedBy = [ "multi-user.target" ];
wants = concatLists (map (certName: [ "acme-finished-${certName}.target" ]) vhostCertNames);
wants = concatLists (map (certName: [ "acme-${certName}.service" ]) vhostCertNames);
after = [
"network.target"
]
++ map (certName: "acme-selfsigned-${certName}.service") vhostCertNames
++ map (certName: "acme-${certName}.service") independentCertNames; # avoid loading self-signed key w/ real cert, or vice-versa
before = map (certName: "acme-${certName}.service") dependentCertNames;
# Ensure httpd runs with baseline certificates in place.
++ map (certName: "acme-${certName}.service") vhostCertNames;
# Ensure httpd runs (with current config) before the actual ACME jobs run
before = map (certName: "acme-order-renew-${certName}.service") vhostCertNames;
restartTriggers = [ cfg.configFile ];
path = [
@@ -960,19 +959,17 @@ in
# postRun hooks on cert renew can't be used to restart Apache since renewal
# runs as the unprivileged acme user. sslTargets are added to wantedBy + before
# which allows the acme-finished-$cert.target to signify the successful updating
# which allows the acme-order-renew-$cert.service to signify the successful updating
# of certs end-to-end.
systemd.services.httpd-config-reload =
let
sslServices = map (certName: "acme-${certName}.service") vhostCertNames;
sslTargets = map (certName: "acme-finished-${certName}.target") vhostCertNames;
sslServices = map (certName: "acme-order-renew-${certName}.service") vhostCertNames;
in
mkIf (vhostCertNames != [ ]) {
wantedBy = sslServices ++ [ "multi-user.target" ];
# Before the finished targets, after the renew services.
# This service might be needed for HTTP-01 challenges, but we only want to confirm
# certs are updated _after_ config has been reloaded.
before = sslTargets;
after = sslServices;
restartTriggers = [ cfg.configFile ];
# Block reloading if not all certs exist yet.

View File

@@ -14,13 +14,11 @@ let
virtualHosts = attrValues cfg.virtualHosts;
acmeEnabledVhosts = filter (hostOpts: hostOpts.useACMEHost != null) virtualHosts;
vhostCertNames = unique (map (hostOpts: hostOpts.useACMEHost) acmeEnabledVhosts);
dependentCertNames = filter (cert: certs.${cert}.dnsProvider == null) vhostCertNames; # those that might depend on the HTTP server
independentCertNames = filter (cert: certs.${cert}.dnsProvider != null) vhostCertNames; # those that don't depend on the HTTP server
mkVHostConf =
hostOpts:
let
sslCertDir = config.security.acme.certs.${hostOpts.useACMEHost}.directory;
sslCertDir = certs.${hostOpts.useACMEHost}.directory;
in
''
${hostOpts.hostName} ${concatStringsSep " " hostOpts.serverAliases} {
@@ -392,7 +390,7 @@ in
++ map (
name:
mkCertOwnershipAssertion {
cert = config.security.acme.certs.${name};
cert = certs.${name};
groups = config.users.groups;
services = [ config.systemd.services.caddy ];
}
@@ -412,11 +410,8 @@ in
systemd.packages = [ cfg.package ];
systemd.services.caddy = {
wants = map (certName: "acme-finished-${certName}.target") vhostCertNames;
after =
map (certName: "acme-selfsigned-${certName}.service") vhostCertNames
++ map (certName: "acme-${certName}.service") independentCertNames; # avoid loading self-signed key w/ real cert, or vice-versa
before = map (certName: "acme-${certName}.service") dependentCertNames;
wants = map (certName: "acme-${certName}.service") vhostCertNames;
after = map (certName: "acme-${certName}.service") vhostCertNames;
wantedBy = [ "multi-user.target" ];
startLimitIntervalSec = 14400;

View File

@@ -434,14 +434,13 @@ in
systemd.services.h2o = {
description = "H2O HTTP server";
wantedBy = [ "multi-user.target" ];
wants = lib.concatLists (map (certName: [ "acme-finished-${certName}.target" ]) acmeCertNames.all);
wants = lib.concatLists (map (certName: [ "acme-${certName}.service" ]) acmeCertNames.all);
# Since H2O will be hosting the challenges, H2O must be started
before = builtins.map (certName: "acme-${certName}.service") acmeCertNames.dependent;
before = builtins.map (certName: "acme-order-renew-${certName}.service") acmeCertNames.all;
after = [
"network.target"
]
++ builtins.map (certName: "acme-selfsigned-${certName}.service") acmeCertNames.all
++ builtins.map (certName: "acme-${certName}.service") acmeCertNames.independent; # avoid loading self-signed key w/ real cert, or vice-versa
++ builtins.map (certName: "acme-${certName}.service") acmeCertNames.all;
serviceConfig = {
ExecStart = "${h2oExe} --mode 'master'";
@@ -490,16 +489,14 @@ in
# This service waits for all certificates to be available before reloading
# H2O configuration. `tlsTargets` are added to `wantedBy` + `before` which
# allows the `acme-finished-$cert.target` to signify the successful updating
# allows the `acme-order-renew-$cert.service` to signify the successful updating
# of certs end-to-end.
systemd.services.h2o-config-reload =
let
tlsTargets = map (certName: "acme-${certName}.target") acmeCertNames.all;
tlsServices = map (certName: "acme-${certName}.service") acmeCertNames.all;
tlsServices = map (certName: "acme-order-renew-${certName}.service") acmeCertNames.all;
in
mkIf (acmeCertNames.all != [ ]) {
wantedBy = tlsServices ++ [ "multi-user.target" ];
before = tlsTargets;
after = tlsServices;
unitConfig = {
ConditionPathExists = map (

View File

@@ -15,8 +15,6 @@ let
vhostConfig: vhostConfig.enableACME || vhostConfig.useACMEHost != null
) vhostsConfigs;
vhostCertNames = unique (map (hostOpts: hostOpts.certName) acmeEnabledVhosts);
dependentCertNames = filter (cert: certs.${cert}.dnsProvider == null) vhostCertNames; # those that might depend on the HTTP server
independentCertNames = filter (cert: certs.${cert}.dnsProvider != null) vhostCertNames; # those that don't depend on the HTTP server
virtualHosts = mapAttrs (
vhostName: vhostConfig:
let
@@ -442,6 +440,7 @@ let
auth_basic off;
auth_request off;
proxy_pass http://${vhost.acmeFallbackHost};
proxy_set_header Host $host;
}
''}
'';
@@ -1481,16 +1480,14 @@ in
systemd.services.nginx = {
description = "Nginx Web Server";
wantedBy = [ "multi-user.target" ];
wants = concatLists (map (certName: [ "acme-finished-${certName}.target" ]) vhostCertNames);
wants = concatLists (map (certName: [ "acme-${certName}.service" ]) vhostCertNames);
after = [
"network.target"
]
++ map (certName: "acme-selfsigned-${certName}.service") vhostCertNames
++ map (certName: "acme-${certName}.service") independentCertNames; # avoid loading self-signed key w/ real cert, or vice-versa
# Nginx needs to be started in order to be able to request certificates
# (it's hosting the acme challenge after all)
# This fixes https://github.com/NixOS/nixpkgs/issues/81842
before = map (certName: "acme-${certName}.service") dependentCertNames;
# Ensure nginx runs with baseline certificates in place.
++ map (certName: "acme-${certName}.service") vhostCertNames;
# Ensure nginx runs (with current config) before the actual ACME jobs run
before = map (certName: "acme-order-renew-${certName}.service") vhostCertNames;
stopIfChanged = false;
preStart = ''
${cfg.preStart}
@@ -1585,26 +1582,24 @@ in
# This service waits for all certificates to be available
# before reloading nginx configuration.
# sslTargets are added to wantedBy + before
# which allows the acme-finished-$cert.target to signify the successful updating
# which allows the acme-order-renew-$cert.service to signify the successful updating
# of certs end-to-end.
systemd.services.nginx-config-reload =
let
sslServices = map (certName: "acme-${certName}.service") vhostCertNames;
sslTargets = map (certName: "acme-finished-${certName}.target") vhostCertNames;
sslOrderRenewServices = map (certName: "acme-order-renew-${certName}.service") vhostCertNames;
in
mkIf (cfg.enableReload || vhostCertNames != [ ]) {
wants = optionals cfg.enableReload [ "nginx.service" ];
wantedBy = sslServices ++ [ "multi-user.target" ];
# Before the finished targets, after the renew services.
wantedBy = sslOrderRenewServices ++ [ "multi-user.target" ];
# XXX Before the finished targets, after the renew services.
# This service might be needed for HTTP-01 challenges, but we only want to confirm
# certs are updated _after_ config has been reloaded.
before = sslTargets;
after = sslServices;
after = sslOrderRenewServices;
restartTriggers = optionals cfg.enableReload [ configFile ];
# Block reloading if not all certs exist yet.
# Happens when config changes add new vhosts/certs.
unitConfig = {
ConditionPathExists = optionals (sslServices != [ ]) (
ConditionPathExists = optionals (vhostCertNames != [ ]) (
map (certName: certs.${certName}.directory + "/fullchain.pem") vhostCertNames
);
# Disable rate limiting for this, because it may be triggered quickly a bunch of times

View File

@@ -72,11 +72,11 @@ in
wants = [
"network.target"
]
++ (optional (cfg.useACMEHost != null) "acme-finished-${cfg.useACMEHost}.target");
++ (optional (cfg.useACMEHost != null) "acme-${cfg.useACMEHost}.service");
after = [
"network.target"
]
++ (optional (cfg.useACMEHost != null) "acme-finished-${cfg.useACMEHost}.target");
++ (optional (cfg.useACMEHost != null) "acme-${cfg.useACMEHost}.service");
wantedBy = [ "multi-user.target" ];
environment = optionalAttrs (cfg.useACMEHost != null) {
CERTIFICATE_FILE = "fullchain.pem";
@@ -127,18 +127,16 @@ in
# postRun hooks on cert renew can't be used to restart Nginx since renewal
# runs as the unprivileged acme user. sslTargets are added to wantedBy + before
# which allows the acme-finished-$cert.target to signify the successful updating
# which allows the acme-order-renew-$cert.target to signify the successful updating
# of certs end-to-end.
systemd.services.pomerium-config-reload = mkIf (cfg.useACMEHost != null) {
# TODO(lukegb): figure out how to make config reloading work with credentials.
wantedBy = [
"acme-finished-${cfg.useACMEHost}.target"
"acme-order-renew-${cfg.useACMEHost}.service"
"multi-user.target"
];
# Before the finished targets, after the renew services.
before = [ "acme-finished-${cfg.useACMEHost}.target" ];
after = [ "acme-${cfg.useACMEHost}.service" ];
after = [ "acme-order-renew-${cfg.useACMEHost}.service" ];
# Block reloading if not all certs exist yet.
unitConfig.ConditionPathExists = [
"${config.security.acme.certs.${cfg.useACMEHost}.directory}/fullchain.pem"

View File

@@ -1,7 +1,8 @@
{
config,
pkgs,
lib,
pkgs,
utils,
...
}:
@@ -12,6 +13,7 @@ let
e = pkgs.enlightenment;
xcfg = config.services.xserver;
cfg = xcfg.desktopManager.enlightenment;
GST_PLUGIN_PATH = lib.makeSearchPathOutput "lib" "lib/gstreamer-1.0" [
pkgs.gst_all_1.gst-plugins-base
pkgs.gst_all_1.gst-plugins-good
@@ -41,11 +43,17 @@ in
description = "Enable the Enlightenment desktop environment.";
};
environment.enlightenment.excludePackages = mkOption {
default = [ ];
example = literalExpression "[ pkgs.enlightenment.ephoto ]";
type = types.listOf types.package;
description = "Which packages Enlightenment should exclude from the default environment";
};
};
config = mkIf cfg.enable {
environment.systemPackages = with pkgs; [
environment.systemPackages = utils.removePackagesByName (with pkgs; [
enlightenment.econnman
enlightenment.efl
enlightenment.enlightenment
@@ -54,7 +62,7 @@ in
enlightenment.rage
enlightenment.terminology
xorg.xcursorthemes
];
]) config.environment.enlightenment.excludePackages;
environment.pathsToLink = [
"/etc/enlightenment"

View File

@@ -85,33 +85,24 @@ in
ca_domain = "${nodes.acme.test-support.acme.caDomain}"
fqdn = "${nodes.caddy.networking.fqdn}"
with subtest("Boot and start with selfsigned certificates"):
caddy.start()
caddy.wait_for_unit("caddy.service")
check_issuer(caddy, fqdn, "minica")
# Check that the web server has picked up the selfsigned cert
check_connection(caddy, fqdn, minica=True)
acme.start()
wait_for_running(acme)
acme.wait_for_open_port(443)
with subtest("Boot and acquire a new cert"):
caddy.start()
wait_for_running(caddy)
with subtest("Acquire a new cert"):
caddy.succeed(f"systemctl restart acme-{fqdn}.service")
check_issuer(caddy, fqdn, "pebble")
check_domain(caddy, fqdn, fqdn)
download_ca_certs(caddy, ca_domain)
check_connection(caddy, fqdn)
with subtest("Can run on selfsigned certificates"):
# Switch to selfsigned first
caddy.succeed(f"systemctl clean acme-{fqdn}.service --what=state")
caddy.succeed(f"systemctl start acme-selfsigned-{fqdn}.service")
check_issuer(caddy, fqdn, "minica")
caddy.succeed("systemctl restart caddy.service")
# Check that the web server has picked up the selfsigned cert
check_connection(caddy, fqdn, minica=True)
caddy.succeed(f"systemctl start acme-{fqdn}.service")
# This may fail a couple of times before caddy is restarted
check_issuer(caddy, fqdn, "pebble")
check_connection(caddy, fqdn)
with subtest("security.acme changes reflect on caddy"):
check_connection(caddy, f"caddy-alt.{domain}", fail=True)
switch_to(caddy, "add_domain")

View File

@@ -1,10 +1,14 @@
{ runTest }:
let
domain = "example.test";
in
{
http01-builtin = runTest ./http01-builtin.nix;
dns01 = runTest ./dns01.nix;
caddy = runTest ./caddy.nix;
nginx = runTest (
import ./webserver.nix {
inherit domain;
serverName = "nginx";
group = "nginx";
baseModule = {
@@ -22,17 +26,17 @@
addSSL = true;
useACMEHost = "proxied.example.test";
acmeFallbackHost = "localhost:8080";
# lego will refuse the request if the host header is not correct
extraConfig = ''
proxy_set_header Host $host;
'';
};
};
specialisation.nullroot.configuration = {
services.nginx.virtualHosts."nullroot.${domain}".acmeFallbackHost = "localhost:8081";
};
};
}
);
httpd = runTest (
import ./webserver.nix {
inherit domain;
serverName = "httpd";
group = "wwwrun";
baseModule = {
@@ -50,6 +54,16 @@
};
};
};
specialisation.nullroot.configuration = {
services.httpd.virtualHosts."nullroot.${domain}" = {
locations."/.well-known/acme-challenge" = {
proxyPass = "http://localhost:8081/.well-known/acme-challenge";
extraConfig = ''
ProxyPreserveHost On
'';
};
};
};
};
}
);

View File

@@ -37,6 +37,12 @@ in
listenHTTP = ":80";
};
systemd.targets."renew-triggered" = {
wantedBy = [ "acme-order-renew-${config.networking.fqdn}.service" ];
after = [ "acme-order-renew-${config.networking.fqdn}.service" ];
unitConfig.RefuseManualStart = true;
};
specialisation = {
renew.configuration = {
# Pebble provides 5 year long certs,
@@ -177,17 +183,29 @@ in
# old_hash will be used in the preservation tests later
old_hash = hash
builtin.succeed(f"systemctl start acme-{cert}.service")
builtin.succeed(f"systemctl start acme-order-renew-{cert}.service")
builtin.wait_for_unit("renew-triggered.target")
hash_after = builtin.succeed(f"sha256sum /var/lib/acme/{cert}/cert.pem")
assert hash == hash_after, "Certificate was unexpectedly changed"
builtin.succeed("systemctl stop renew-triggered.target")
switch_to(builtin, "renew")
builtin.wait_for_unit("renew-triggered.target")
check_issuer(builtin, cert, "pebble")
hash_after = builtin.succeed(f"sha256sum /var/lib/acme/{cert}/cert.pem | tee /dev/stderr")
assert hash != hash_after, "Certificate was not renewed"
check_permissions(builtin, cert, "acme")
with subtest("Handles email change correctly"):
hash = builtin.succeed(f"sha256sum /var/lib/acme/{cert}/cert.pem")
builtin.succeed("systemctl stop renew-triggered.target")
switch_to(builtin, "accountchange")
builtin.wait_for_unit("renew-triggered.target")
check_issuer(builtin, cert, "pebble")
# Check that there are now 2 account directories
builtin.succeed("test $(ls -1 /var/lib/acme/.lego/accounts | tee /dev/stderr | wc -l) -eq 2")
@@ -202,58 +220,101 @@ in
# old_hash will be used in the preservation tests later
old_hash = hash_after
check_permissions(builtin, cert, "acme")
with subtest("Correctly implements OCSP stapling"):
check_stapling(builtin, cert, "${caDomain}", fail=True)
builtin.succeed("systemctl stop renew-triggered.target")
switch_to(builtin, "ocsp_stapling")
builtin.wait_for_unit("renew-triggered.target")
check_stapling(builtin, cert, "${caDomain}")
check_permissions(builtin, cert, "acme")
with subtest("Handles keyType change correctly"):
check_key_bits(builtin, cert, 256)
builtin.succeed("systemctl stop renew-triggered.target")
switch_to(builtin, "keytype")
builtin.wait_for_unit("renew-triggered.target")
check_key_bits(builtin, cert, 384)
# keyType is part of the accountHash, thus a new account will be created
builtin.succeed("test $(ls -1 /var/lib/acme/.lego/accounts | tee /dev/stderr | wc -l) -eq 2")
check_permissions(builtin, cert, "acme")
with subtest("Reuses generated, valid certs from previous configurations"):
# Right now, the hash should not match due to the previous test
hash = builtin.succeed(f"sha256sum /var/lib/acme/{cert}/cert.pem | tee /dev/stderr")
assert hash != old_hash, "Expected certificate to differ"
builtin.succeed("systemctl stop renew-triggered.target")
switch_to(builtin, "preservation")
builtin.wait_for_unit("renew-triggered.target")
hash = builtin.succeed(f"sha256sum /var/lib/acme/{cert}/cert.pem | tee /dev/stderr")
assert hash == old_hash, "Expected certificate to match from older configuration"
check_permissions(builtin, cert, "acme")
with subtest("Add a new cert, extend existing cert domains"):
check_domain(builtin, cert, f"builtin-alt.{domain}", fail=True)
builtin.succeed("systemctl stop renew-triggered.target")
switch_to(builtin, "add_cert_and_domain")
builtin.wait_for_unit("renew-triggered.target")
check_issuer(builtin, cert, "pebble")
check_domain(builtin, cert, f"builtin-alt.{domain}")
check_issuer(builtin, cert2, "pebble")
check_domain(builtin, cert2, cert2)
# There should not be a new account folder created
builtin.succeed("test $(ls -1 /var/lib/acme/.lego/accounts | tee /dev/stderr | wc -l) -eq 2")
check_permissions(builtin, cert, "acme")
check_permissions(builtin, cert2, "acme")
with subtest("Check account hashing compatibility with pre-24.05 settings"):
switch_to(builtin, "legacy_account_hash", fail=True)
builtin.succeed(f"stat {legacy_account_dir} > /dev/stderr && rm -rf {legacy_account_dir}")
builtin.succeed("systemctl stop renew-triggered.target")
switch_to(builtin, "legacy_account_hash"
)
builtin.wait_for_unit("renew-triggered.target")
with subtest("Ensure Concurrency limits work"):
builtin.succeed(f"stat {legacy_account_dir} > /dev/stderr && rm -rf {legacy_account_dir}")
check_permissions(builtin, cert, "acme")
with subtest("Ensure concurrency limits work"):
builtin.succeed("systemctl stop renew-triggered.target")
switch_to(builtin, "concurrency")
builtin.wait_for_unit("renew-triggered.target")
check_issuer(builtin, cert3, "pebble")
check_domain(builtin, cert3, cert3)
check_permissions(builtin, cert, "acme")
with subtest("Can renew using a CSR"):
builtin.succeed(f"systemctl stop acme-{cert}.service")
builtin.succeed(f"systemctl clean acme-{cert}.service --what=state")
builtin.succeed("systemctl stop renew-triggered.target")
switch_to(builtin, "csr")
builtin.wait_for_unit("renew-triggered.target")
check_issuer(builtin, cert, "pebble")
with subtest("Generate self-signed certs"):
acme.shutdown()
check_issuer(builtin, cert, "pebble")
builtin.succeed(f"systemctl stop acme-{cert}.service")
builtin.succeed(f"systemctl clean acme-{cert}.service --what=state")
builtin.succeed(f"systemctl start acme-selfsigned-{cert}.service")
builtin.succeed(f"systemctl start acme-{cert}.service")
check_issuer(builtin, cert, "minica")
check_domain(builtin, cert, cert)
with subtest("Validate permissions (self-signed)"):
check_permissions(builtin, cert, "acme")
with subtest("Can renew using a CSR"):
builtin.succeed(f"systemctl clean acme-{cert}.service --what=state")
switch_to(builtin, "csr")
check_issuer(builtin, cert, "pebble")
'';
}

View File

@@ -3,6 +3,36 @@ import time
TOTAL_RETRIES = 20
# BackoffTracker provides a robust system for handling test retries
class BackoffTracker:
delay = 1
increment = 1
def handle_fail(self, retries, message) -> int:
assert retries < TOTAL_RETRIES, message
print(f"Retrying in {self.delay}s, {retries + 1}/{TOTAL_RETRIES}")
time.sleep(self.delay)
# Only increment after the first try
if retries == 0:
self.delay += self.increment
self.increment *= 2
return retries + 1
def protect(self, func):
def wrapper(*args, retries: int = 0, **kwargs):
try:
return func(*args, **kwargs)
except Exception as err:
retries = self.handle_fail(retries, err.args)
return wrapper(*args, retries=retries, **kwargs)
return wrapper
backoff = BackoffTracker()
def run(node, cmd, fail=False):
if fail:
@@ -39,6 +69,7 @@ def switch_to(node, name, fail=False) -> None:
# and matches the issuer we expect it to be.
# It's a good validation to ensure the cert.pem and fullchain.pem
# are not still selfsigned after verification
@backoff.protect
def check_issuer(node, cert_name, issuer) -> None:
for fname in ("cert.pem", "fullchain.pem"):
actual_issuer = node.succeed(
@@ -102,9 +133,10 @@ def check_permissions(node, cert_name, group):
f"test $({stat} /var/lib/acme/{cert_name}/*.pem"
f" | tee /dev/stderr | grep -v '640 acme {group}' | wc -l) -eq 0"
)
node.execute(f"ls -lahR /var/lib/acme/.lego/{cert_name}/* > /dev/stderr")
node.succeed(
f"test $({stat} /var/lib/acme/.lego/{cert_name}/*/{cert_name}*"
f" | tee /dev/stderr | grep -v '600 acme {group}' | wc -l) -eq 0"
f" | tee /dev/stderr | grep -v '640 acme {group}' | wc -l) -eq 0"
)
node.succeed(
f"test $({stat} /var/lib/acme/{cert_name}"
@@ -115,37 +147,6 @@ def check_permissions(node, cert_name, group):
f" | tee /dev/stderr | grep -v '600 acme {group}' | wc -l) -eq 0"
)
# BackoffTracker provides a robust system for handling test retries
class BackoffTracker:
delay = 1
increment = 1
def handle_fail(self, retries, message) -> int:
assert retries < TOTAL_RETRIES, message
print(f"Retrying in {self.delay}s, {retries + 1}/{TOTAL_RETRIES}")
time.sleep(self.delay)
# Only increment after the first try
if retries == 0:
self.delay += self.increment
self.increment *= 2
return retries + 1
def protect(self, func):
def wrapper(*args, retries: int = 0, **kwargs):
try:
return func(*args, **kwargs)
except Exception as err:
retries = self.handle_fail(retries, err.args)
return wrapper(*args, retries=retries, **kwargs)
return wrapper
backoff = BackoffTracker()
@backoff.protect
def download_ca_certs(node, ca_domain):

View File

@@ -2,7 +2,7 @@
serverName,
group,
baseModule,
domain ? "example.test",
domain,
}:
{
config,
@@ -18,6 +18,8 @@
timeout = 300;
};
interactive.sshBackdoor.enable = true;
nodes = {
# The fake ACME server which will respond to client requests
acme =
@@ -45,6 +47,7 @@
"certchange.${domain}"
"zeroconf.${domain}"
"zeroconf2.${domain}"
"zeroconf3.${domain}"
"nullroot.${domain}"
];
@@ -57,6 +60,7 @@
systemd.targets."renew-triggered" = {
wantedBy = [ "${serverName}-config-reload.service" ];
after = [ "${serverName}-config-reload.service" ];
unitConfig.RefuseManualStart = true;
};
security.acme.certs."proxied.${domain}" = {
@@ -101,13 +105,42 @@
# Test that "acmeRoot = null" still results in
# valid cert generation by inheriting defaults.
nullroot.configuration = {
security.acme.defaults.listenHTTP = ":8080";
# The default.nix has the server-type dependent config statements
# to properly set up the proxying. We need a separate port here to
# avoid hostname issues with the proxy already running on :8080
security.acme.defaults.listenHTTP = ":8081";
services.${serverName}.virtualHosts."nullroot.${domain}" = {
onlySSL = true;
addSSL = true;
enableACME = true;
acmeRoot = null;
};
};
# Test that a adding a second virtual host will not trigger
# other units (account and renewal service for first)
zeroconf3.configuration = {
services.${serverName}.virtualHosts = {
"zeroconf.${domain}" = {
addSSL = true;
enableACME = true;
serverAliases = [ "zeroconf2.${domain}" ];
};
"zeroconf3.${domain}" = {
addSSL = true;
enableACME = true;
};
};
# We're doing something risky with the combination of the service unit being persistent
# that could end up that the timers do not trigger properly. Show that timers have the
# desired effect.
systemd.timers."acme-renew-zeroconf3.${domain}".timerConfig = {
OnCalendar = lib.mkForce "*-*-* *:*:0/5";
AccuracySec = lib.mkForce 0;
# Skew randomly within the day, per https://letsencrypt.org/docs/integration-guide/.
RandomizedDelaySec = lib.mkForce 0;
FixedRandomDelay = lib.mkForce 0;
};
};
};
};
};
@@ -121,30 +154,24 @@
ca_domain = "${nodes.acme.test-support.acme.caDomain}"
fqdn = f"proxied.{domain}"
webserver.start()
webserver.wait_for_unit("${serverName}.service")
with subtest("Can run on self-signed certificates"):
check_issuer(webserver, fqdn, "minica")
# Check that the web server has picked up the selfsigned cert
check_connection(webserver, fqdn, minica=True)
acme.start()
wait_for_running(acme)
acme.wait_for_open_port(443)
with subtest("Acquire a cert through a proxied lego"):
webserver.start()
webserver.succeed("systemctl is-system-running --wait")
wait_for_running(webserver)
download_ca_certs(webserver, ca_domain)
check_connection(webserver, fqdn)
with subtest("Can run on selfsigned certificates"):
# Switch to selfsigned first
webserver.succeed(f"systemctl clean acme-{fqdn}.service --what=state")
webserver.succeed(f"systemctl start acme-selfsigned-{fqdn}.service")
check_issuer(webserver, fqdn, "minica")
webserver.succeed("systemctl restart ${serverName}-config-reload.service")
# Check that the web server has picked up the selfsigned cert
check_connection(webserver, fqdn, minica=True)
webserver.succeed("systemctl stop renew-triggered.target")
webserver.succeed(f"systemctl start acme-{fqdn}.service")
webserver.wait_for_unit("renew-triggered.target")
check_issuer(webserver, fqdn, "pebble")
check_connection(webserver, fqdn)
webserver.succeed(f"systemctl start acme-order-renew-{fqdn}.service")
webserver.wait_for_unit("renew-triggered.target")
download_ca_certs(webserver, ca_domain)
check_issuer(webserver, fqdn, "pebble")
check_connection(webserver, fqdn)
with subtest("security.acme changes reflect on web server part 1"):
check_connection(webserver, f"certchange.{domain}", fail=True)
@@ -181,5 +208,23 @@
switch_to(webserver, "nullroot")
webserver.wait_for_unit("renew-triggered.target")
check_connection(webserver, f"nullroot.{domain}")
with subtest("Ensure that adding a second vhost does not trigger first vhost acme units"):
switch_to(webserver, "zeroconf")
webserver.wait_for_unit("renew-triggered.target")
webserver.succeed("journalctl --cursor-file=/tmp/cursor | grep acme")
switch_to(webserver, "zeroconf3")
webserver.wait_for_unit("renew-triggered.target")
output = webserver.succeed("journalctl --cursor-file=/tmp/cursor | grep acme")
# The new certificate unit gets triggered:
t.assertIn(f"acme-zeroconf3.{domain}-start", output)
# The account generation should not be triggered again:
t.assertNotIn("acme-account-d590213ed52603e9128d.target", output)
# The other certificates should also not be triggered:
t.assertNotIn(f"acme-zeroconf.{domain}-start", output)
t.assertNotIn(f"acme-proxied.{domain}-start", output)
# Ensure the timer works, due to our shenanigans with
# RemainAfterExit=true
webserver.wait_until_succeeds(f"journalctl --cursor-file=/tmp/cursor | grep 'Starting Order (and renew) ACME certificate for zeroconf3.{domain}...'")
'';
}

View File

@@ -333,7 +333,14 @@ in
cinnamon-wayland = runTest ./cinnamon-wayland.nix;
cjdns = runTest ./cjdns.nix;
clatd = runTest ./clatd.nix;
clickhouse = import ./clickhouse { inherit runTest; };
clickhouse = import ./clickhouse {
inherit runTest;
package = pkgs.clickhouse;
};
clickhouse-lts = import ./clickhouse {
inherit runTest;
package = pkgs.clickhouse-lts;
};
cloud-init = runTest ./cloud-init.nix;
cloud-init-hostname = runTest ./cloud-init-hostname.nix;
cloudlog = runTest ./cloudlog.nix;
@@ -1485,7 +1492,7 @@ in
teleports = runTest ./teleports.nix;
thelounge = handleTest ./thelounge.nix { };
terminal-emulators = handleTest ./terminal-emulators.nix { };
thanos = handleTest ./thanos.nix { };
thanos = runTest ./thanos.nix;
tiddlywiki = runTest ./tiddlywiki.nix;
tigervnc = handleTest ./tigervnc.nix { };
tika = runTest ./tika.nix;

View File

@@ -1,10 +1,16 @@
{ pkgs, ... }:
{ pkgs, package, ... }:
{
name = "clickhouse";
meta.maintainers = with pkgs.lib.maintainers; [ jpds ];
meta.maintainers = with pkgs.lib.maintainers; [
jpds
thevar1able
];
nodes.machine = {
services.clickhouse.enable = true;
services.clickhouse = {
enable = true;
inherit package;
};
virtualisation.memorySize = 4096;
};

View File

@@ -1,8 +1,31 @@
{ runTest }:
{
runTest,
package,
}:
{
base = runTest ./base.nix;
kafka = runTest ./kafka.nix;
keeper = runTest ./keeper.nix;
s3 = runTest ./s3.nix;
base = runTest {
imports = [ ./base.nix ];
_module.args = {
inherit package;
};
};
kafka = runTest {
imports = [ ./kafka.nix ];
_module.args = {
inherit package;
};
};
keeper = runTest {
imports = [ ./keeper.nix ];
_module.args = {
inherit package;
};
};
s3 = runTest {
imports = [ ./s3.nix ];
_module.args = {
inherit package;
};
};
}

View File

@@ -1,4 +1,4 @@
{ pkgs, ... }:
{ pkgs, package, ... }:
let
kafkaNamedCollectionConfig = ''
@@ -28,7 +28,10 @@ let
in
{
name = "clickhouse-kafka";
meta.maintainers = with pkgs.lib.maintainers; [ jpds ];
meta.maintainers = with pkgs.lib.maintainers; [
jpds
thevar1able
];
nodes = {
clickhouse = {
@@ -38,7 +41,10 @@ in
};
};
services.clickhouse.enable = true;
services.clickhouse = {
enable = true;
inherit package;
};
virtualisation.memorySize = 4096;
};

View File

@@ -1,7 +1,15 @@
{ lib, pkgs, ... }:
{
lib,
pkgs,
package,
...
}:
rec {
name = "clickhouse-keeper";
meta.maintainers = with pkgs.lib.maintainers; [ jpds ];
meta.maintainers = with pkgs.lib.maintainers; [
jpds
thevar1able
];
nodes =
let
@@ -94,7 +102,10 @@ rec {
9444
];
services.clickhouse.enable = true;
services.clickhouse = {
enable = true;
inherit package;
};
systemd.services.clickhouse = {
after = [ "network-online.target" ];

View File

@@ -1,4 +1,4 @@
{ pkgs, ... }:
{ pkgs, package, ... }:
let
s3 = {
@@ -40,7 +40,10 @@ let
in
{
name = "clickhouse-s3";
meta.maintainers = with pkgs.lib.maintainers; [ jpds ];
meta.maintainers = with pkgs.lib.maintainers; [
jpds
thevar1able
];
nodes = {
clickhouse = {
@@ -50,7 +53,10 @@ in
};
};
services.clickhouse.enable = true;
services.clickhouse = {
enable = true;
inherit package;
};
virtualisation.diskSize = 15 * 1024;
virtualisation.memorySize = 4 * 1024;
};

View File

@@ -1,11 +1,17 @@
{ pkgs, ... }:
let
inherit (import ./ssh-keys.nix pkgs)
snakeOilEd25519PrivateKey
snakeOilEd25519PublicKey
;
remoteRepository = "/root/restic-backup";
remoteFromFileRepository = "/root/restic-backup-from-file";
remoteInhibitTestRepository = "/root/restic-backup-inhibit-test";
remoteNoInitRepository = "/root/restic-backup-no-init";
rcloneRepository = "rclone:local:/root/restic-rclone-backup";
sftpRepository = "sftp:alice@sftp:backups/test";
backupPrepareCommand = ''
touch /root/backupPrepareCommand
@@ -51,7 +57,34 @@ in
};
nodes = {
server =
sftp =
# Copied from openssh.nix
{ pkgs, ... }:
{
services.openssh = {
enable = true;
extraConfig = ''
Match Group sftponly
ChrootDirectory /srv/sftp
ForceCommand internal-sftp
'';
};
users.groups = {
sftponly = { };
};
users.users = {
alice = {
isNormalUser = true;
createHome = false;
group = "sftponly";
shell = "/run/current-system/sw/bin/nologin";
openssh.authorizedKeys.keys = [ snakeOilEd25519PublicKey ];
};
};
};
restic =
{ pkgs, ... }:
{
services.restic.backups = {
@@ -68,6 +101,20 @@ in
initialize = true;
timerConfig = null; # has no effect here, just checking that it doesn't break the service
};
remote-sftp = {
inherit
passwordFile
paths
exclude
pruneOpts
;
repository = sftpRepository;
initialize = true;
timerConfig = null; # has no effect here, just checking that it doesn't break the service
extraOptions = [
"sftp.command='ssh alice@sftp -o UserKnownHostsFile=/dev/null -o StrictHostKeyChecking=no -s sftp'"
];
};
remote-from-file-backup = {
inherit passwordFile exclude pruneOpts;
initialize = true;
@@ -143,28 +190,55 @@ in
};
testScript = ''
server.start()
server.wait_for_unit("dbus.socket")
server.fail(
restic.start()
sftp.start()
restic.wait_for_unit("dbus.socket")
sftp.wait_for_unit("sshd.service")
restic.systemctl("start network-online.target")
restic.wait_for_unit("network-online.target")
sftp.succeed(
"mkdir -p /srv/sftp/backups",
"chown alice:sftponly /srv/sftp/backups",
"chmod 0755 /srv/sftp/backups",
)
restic.succeed(
"mkdir -p /root/.ssh/",
"cat ${snakeOilEd25519PrivateKey} > /root/.ssh/id_ed25519",
"chmod 0600 /root/.ssh/id_ed25519",
)
restic.fail(
"restic-remotebackup snapshots",
"restic-remote-sftp snapshots",
'restic-remote-from-file-backup snapshots"',
"restic-rclonebackup snapshots",
"grep 'backup.* /opt' /root/fake-restic.log",
)
server.succeed(
restic.succeed(
# set up
"cp -rT ${testDir} /opt",
"touch /opt/excluded_file_1 /opt/excluded_file_2",
"mkdir -p /root/restic-rclone-backup",
)
server.fail(
restic.fail(
# test that noinit backup in fact does not initialize the repository
# and thus fails without a pre-initialized repository
"systemctl start restic-backups-remote-noinit-backup.service",
)
server.succeed(
restic.succeed(
# test that remotebackup runs custom commands and produces a snapshot
"timedatectl set-time '2016-12-13 13:45'",
"systemctl start restic-backups-remotebackup.service",
"rm /root/backupCleanupCommand",
'restic-remotebackup snapshots --json | ${pkgs.jq}/bin/jq "length | . == 1"',
)
restic.succeed(
# test that remotebackup runs custom commands and produces a snapshot
"timedatectl set-time '2016-12-13 13:45'",
"systemctl start restic-backups-remotebackup.service",
@@ -231,15 +305,29 @@ in
'restic-remotebackup snapshots --json | ${pkgs.jq}/bin/jq "length | . == 4"',
'restic-rclonebackup snapshots --json | ${pkgs.jq}/bin/jq "length | . == 4"',
# test that SFTP backup works by copying from the remotebackup
'restic-remote-sftp init --from-repo ${remoteRepository} --from-password-file ${passwordFile} --copy-chunker-params',
'restic-remote-sftp copy --from-repo ${remoteRepository} --from-password-file ${passwordFile}',
'restic-remote-sftp snapshots --json | ${pkgs.jq}/bin/jq "length | . == 4"',
# test that remoteprune brings us back to 1 snapshot in remotebackup
"systemctl start restic-backups-remoteprune.service",
'restic-remotebackup snapshots --json | ${pkgs.jq}/bin/jq "length | . == 1"',
# test that remoteprune brings us back to 1 snapshot in remotebackup
"systemctl start restic-backups-remoteprune.service",
'restic-remotebackup snapshots --json | ${pkgs.jq}/bin/jq "length | . == 1"',
)
# test that the inhibit option is working
server.systemctl("start --no-block restic-backups-inhibit-test.service")
server.wait_until_succeeds(
restic.systemctl("start --no-block restic-backups-inhibit-test.service")
restic.wait_until_succeeds(
"systemd-inhibit --no-legend --no-pager | grep -q restic",
5
)
# test that the inhibit option is working
restic.systemctl("start --no-block restic-backups-inhibit-test.service")
restic.wait_until_succeeds(
"systemd-inhibit --no-legend --no-pager | grep -q restic",
5
)

View File

@@ -137,17 +137,18 @@ import ./make-test-python.nix (
caserver.wait_for_unit("step-ca.service")
caserver.wait_until_succeeds("journalctl -o cat -u step-ca.service | grep '${pkgs.step-ca.version}'")
caclient.wait_for_unit("acme-finished-caclient.target")
catester.succeed("curl https://caclient/ | grep \"Welcome to nginx!\"")
caclient.wait_for_unit("acme-caclient.service")
# The order is run asynchonously, keep trying.
catester.wait_until_succeeds("curl https://caclient/ | grep \"Welcome to nginx!\"")
caclientcaddy.wait_for_unit("caddy.service")
# Its hard to know when Caddy has finished the ACME dance with
# step-ca, so we keep trying cURL until success.
catester.wait_until_succeeds("curl https://caclientcaddy/ | grep \"Welcome to Caddy!\"")
caclienth2o.wait_for_unit("acme-finished-caclienth2o.target")
caclienth2o.wait_for_unit("acme-caclienth2o.service")
caclienth2o.wait_for_unit("h2o.service")
catester.succeed("curl https://caclienth2o/ | grep \"Welcome to H2O!\"")
catester.wait_until_succeeds("curl https://caclienth2o/ | grep \"Welcome to H2O!\"")
'';
}
)

View File

@@ -1,3 +1,5 @@
{ ... }:
let
grpcPort = 19090;
queryPort = 9090;
@@ -30,10 +32,9 @@ let
};
};
};
in
import ./make-test-python.nix {
name = "prometheus";
{
name = "thanos";
nodes = {
prometheus =

View File

@@ -268,17 +268,40 @@ in
tableDDL = pkgs.writeText "table.sql" ''
CREATE TABLE IF NOT EXISTS dnstap.records (
timestamp DateTime64(6),
dataType LowCardinality(String),
dataTypeId UInt8,
messageType LowCardinality(String),
messageTypeId UInt8,
dataType Enum('Message' = 1),
messageType Enum(
'AuthQuery' = 1,
'AuthResponse' = 2,
'ResolverQuery' = 3,
'ResolverResponse' = 4,
'ClientQuery' = 5,
'ClientResponse' = 6,
'ForwarderQuery' = 7,
'ForwarderResponse' = 8,
'StubQuery' = 9,
'StubResponse' = 10,
'ToolQuery' = 11,
'ToolResponse' = 12,
'UpdateQuery' = 13,
'UpdateResponse' = 14
),
queryZone Nullable(String),
requestData Nullable(JSON),
responseAddress String,
responseData Nullable(JSON),
responsePort UInt16,
serverId LowCardinality(String),
serverVersion LowCardinality(String),
socketFamily LowCardinality(String),
socketProtocol LowCardinality(String),
socketFamily Enum('INET' = 1, 'INET6' = 2),
socketProtocol Enum(
'UDP' = 1,
'TCP' = 2,
'DOT' = 3,
'DOH' = 4,
'DNSCryptUDP' = 5,
'DNSCryptTCP' = 6,
'DOQ' = 7
),
sourceAddress String,
sourcePort UInt16,
)
@@ -304,7 +327,7 @@ in
JSONExtractString(requestData.question[1]::String, 'domainName') as domain,
JSONExtractString(requestData.question[1]::String, 'questionType') as record_type
FROM dnstap.records
WHERE messageTypeId = 5 # ClientQuery
WHERE messageType = 'ClientQuery'
'';
selectDomainCountQuery = pkgs.writeText "select-domain-count.sql" ''

View File

@@ -19,11 +19,11 @@
mkDerivation rec {
pname = "okteta";
version = "0.26.22";
version = "0.26.23";
src = fetchurl {
url = "mirror://kde/stable/okteta/${version}/src/${pname}-${version}.tar.xz";
sha256 = "sha256-vi7XhMj/PaMeK4V6FxU7Yi7XyWMaOBUenafZPpaP+n0=";
sha256 = "sha256-sExQmI6sJsUHaKtb1A9bNaNIxE1uDmqNVgVjzw6xo7E=";
};
nativeBuildInputs = [

View File

@@ -4968,6 +4968,19 @@ final: prev: {
meta.hydraPlatforms = [ ];
};
fine-cmdline-nvim = buildVimPlugin {
pname = "fine-cmdline.nvim";
version = "2025-06-15";
src = fetchFromGitHub {
owner = "VonHeikemen";
repo = "fine-cmdline.nvim";
rev = "7db181d1cb294581b12a036eadffffde762a118f";
sha256 = "0991l33f37vpc5plw3c5rwm92sn08gfrlzqy8y1cn06f4p6ll78b";
};
meta.homepage = "https://github.com/VonHeikemen/fine-cmdline.nvim/";
meta.hydraPlatforms = [ ];
};
firenvim = buildVimPlugin {
pname = "firenvim";
version = "2025-07-22";
@@ -15025,6 +15038,19 @@ final: prev: {
meta.hydraPlatforms = [ ];
};
themery-nvim = buildVimPlugin {
pname = "themery.nvim";
version = "2025-01-01";
src = fetchFromGitHub {
owner = "zaldih";
repo = "themery.nvim";
rev = "bfa58f4b279d21cb515b28023e1b68ec908584b2";
sha256 = "0wrd3965wss9qzz4qfy5ryfj71napm5ckx98lwxrxszah6pmz3fl";
};
meta.homepage = "https://github.com/zaldih/themery.nvim/";
meta.hydraPlatforms = [ ];
};
thesaurus_query-vim = buildVimPlugin {
pname = "thesaurus_query.vim";
version = "2022-12-11";

View File

@@ -380,6 +380,7 @@ https://github.com/bakpakin/fennel.vim/,,
https://github.com/wincent/ferret/,,
https://github.com/bogado/file-line/,,
https://github.com/lewis6991/fileline.nvim/,,
https://github.com/VonHeikemen/fine-cmdline.nvim/,HEAD,
https://github.com/glacambre/firenvim/,HEAD,
https://github.com/andviro/flake8-vim/,,
https://github.com/folke/flash.nvim/,HEAD,
@@ -1153,6 +1154,7 @@ https://github.com/let-def/texpresso.vim/,HEAD,
https://github.com/johmsalas/text-case.nvim/,HEAD,
https://github.com/jsongerber/thanks.nvim/,HEAD,
https://github.com/vhsconnect/themed-tabs.nvim/,HEAD,
https://github.com/zaldih/themery.nvim/,HEAD,
https://github.com/ron89/thesaurus_query.vim/,,
https://github.com/itchyny/thumbnail.vim/,,
https://github.com/nvzone/timerly/,HEAD,

View File

@@ -89,8 +89,8 @@ let
mktplcRef = {
publisher = "42Crunch";
name = "vscode-openapi";
version = "4.37.2";
hash = "sha256-XUD5lXybUdUavbiqCqv561NAPAbZ0Q9oLsQkrSRUmsU=";
version = "4.38.0";
hash = "sha256-J9hZhPrHkJEFkiyD8eACiJwbsPfYGMK42FkcwkTQ0RE=";
};
meta = {
changelog = "https://marketplace.visualstudio.com/items/42Crunch.vscode-openapi/changelog";
@@ -4853,8 +4853,8 @@ let
mktplcRef = {
name = "emacs-mcx";
publisher = "tuttieee";
version = "0.82.0";
hash = "sha256-JpqHwQksZ/NsgiZ7EqHxT1FG9DLeInhDg6B+UWOFkeM=";
version = "0.88.10";
hash = "sha256-Umfe+V3BzHsEow6nOvtvg9EN1T0O6SbVwt5g2YHkaSU=";
};
meta = {
changelog = "https://github.com/whitphx/vscode-emacs-mcx/blob/main/CHANGELOG.md";

View File

@@ -10,8 +10,8 @@ vscode-utils.buildVscodeMarketplaceExtension {
mktplcRef = {
publisher = "ms-azuretools";
name = "vscode-bicep";
version = "0.36.1";
hash = "sha256-yrSIHTGHZ1m6fLGrtVlT4UHyWpKuzGKdywBDsMepd4g=";
version = "0.37.4";
hash = "sha256-RBoScMaYWKfA9SONCLkFEcGwj8ffQ3ZlAOiyQY9LtVw=";
};
buildInputs = [

View File

@@ -8,13 +8,13 @@
}:
mkLibretroCore {
core = "mednafen-psx" + lib.optionalString withHw "-hw";
version = "0-unstable-2025-08-01";
version = "0-unstable-2025-08-06";
src = fetchFromGitHub {
owner = "libretro";
repo = "beetle-psx-libretro";
rev = "6eafe85d672ace484bd6b29eeb94eb84f0b41ee1";
hash = "sha256-+gja4vMD+o78BxCR1SY4wLks6zOjKfU7M3a7cYg+2lc=";
rev = "1e42a9076ab1ec5756d3f72e6d61923080fb2128";
hash = "sha256-3k2qgAgyo3o/qwNQZsc0J1dKueZqM7jYvm9gzNkEShw=";
};
extraBuildInputs = lib.optionals withHw [

View File

@@ -5,13 +5,13 @@
}:
mkLibretroCore {
core = "fbneo";
version = "0-unstable-2025-08-01";
version = "0-unstable-2025-08-13";
src = fetchFromGitHub {
owner = "libretro";
repo = "fbneo";
rev = "e90b821fc0507a6bdde3596ec32b7b59feae1d1a";
hash = "sha256-DbY+bQ4vNj4q2Q/tmEZXngdlUHqfZXTl16m14VG5gYY=";
rev = "525a07bd5abd52481a653dc790b987b8f50d0686";
hash = "sha256-O1QEvQ2ZZ7rU6KObV1hFaYLVWwDZ6Lu30JMbln7Z7DA=";
};
makefile = "Makefile";

View File

@@ -11,11 +11,11 @@
stdenv.mkDerivation rec {
pname = "pdfsam-basic";
version = "5.3.1";
version = "5.3.2";
src = fetchurl {
url = "https://github.com/torakiki/pdfsam/releases/download/v${version}/pdfsam-basic_${version}-1_amd64.deb";
hash = "sha256-Fhj/MJnnm8nsuJmSb6PigJT6Qm+CkGg8lV0NaUMfur0=";
hash = "sha256-Y0Q9uT6cyxIYTX0JxoS0r3TamPT1iLXr94Zex30AeWo=";
};
unpackPhase = ''

View File

@@ -802,7 +802,7 @@
}
},
"ungoogled-chromium": {
"version": "139.0.7258.66",
"version": "139.0.7258.127",
"deps": {
"depot_tools": {
"rev": "ea7a0baff0d8554cf6d38f525b4e7882c2b4ec18",
@@ -813,16 +813,16 @@
"hash": "sha256-m+z10s40Q/iYcoMw3o/+tmhIdqHMsYJjdGabHrK/aqo="
},
"ungoogled-patches": {
"rev": "139.0.7258.66-1",
"hash": "sha256-/8zIJk1RxmFPt81qKCXpEEOrH2Jg6cdHGPdtp0zxdHE="
"rev": "139.0.7258.127-1",
"hash": "sha256-CdzvDG4ZGRHVnRsLUDD8gWLzcwJJAqEZdEraqVYgs2U="
},
"npmHash": "sha256-R2gOpfPOUAmnsnUTIvzDPHuHNzL/b2fwlyyfTrywEcI="
},
"DEPS": {
"src": {
"url": "https://chromium.googlesource.com/chromium/src.git",
"rev": "a62d329947691f76c376a873eae39f56381103c8",
"hash": "sha256-RWqOw0Kogz2GwbICet7NdcGnZMrkkE4bu70jU+tbYFQ=",
"rev": "5dc2cf9cf870d324cd9fba708f26d2572cc6d4d8",
"hash": "sha256-YcOVErOKKruc3kPuXhmeibo3KL+Rrny1FEwF769+aEU=",
"recompress": true
},
"src/third_party/clang-format/script": {
@@ -897,8 +897,8 @@
},
"src/third_party/angle": {
"url": "https://chromium.googlesource.com/angle/angle.git",
"rev": "0145c376fadde16390298681252785f98ae90185",
"hash": "sha256-8ztvupTvp5v8lTq3eo/viR9X85qm+bw8299jxr6XslE="
"rev": "5f3636345f1d8afd495e2fcc474fd81e91c4866b",
"hash": "sha256-fx+QD0T85Js9jPQx2aghJU8UOL6WbR0bOkGY2i87A3w="
},
"src/third_party/angle/third_party/glmark2/src": {
"url": "https://chromium.googlesource.com/external/github.com/glmark2/glmark2",
@@ -1202,8 +1202,8 @@
},
"src/third_party/libaom/source/libaom": {
"url": "https://aomedia.googlesource.com/aom.git",
"rev": "0ddc6630b3723b14b164752d46c27752f078ddd3",
"hash": "sha256-cs1+5vBEFPqzi1vbxiSgujrLIoaXZROZaRJq2gRdUrE="
"rev": "90c632fc6c01cd8637186c783ca8012bab3c3260",
"hash": "sha256-e+rUkNOakv6WQrgx1ozoJTynk/GZy1zdsnYX4oz+6ks="
},
"src/third_party/crabbyavif/src": {
"url": "https://chromium.googlesource.com/external/github.com/webmproject/CrabbyAvif.git",
@@ -1432,8 +1432,8 @@
},
"src/third_party/skia": {
"url": "https://skia.googlesource.com/skia.git",
"rev": "cbc694239b06ecf694676aba22d5263dbc23ee5e",
"hash": "sha256-5vIwNP9RbtUVtgKKDiZd6NVkR2Ed3DUqZWESTUM+fIs="
"rev": "2d6f1aa4be9c33b013c322b2bc9cd99a682243b6",
"hash": "sha256-VysJkpCRRYNdCStnXvo6wyMCv1gLHecMwefKiwypARc="
},
"src/third_party/smhasher/src": {
"url": "https://chromium.googlesource.com/external/smhasher.git",
@@ -1597,8 +1597,8 @@
},
"src/v8": {
"url": "https://chromium.googlesource.com/v8/v8.git",
"rev": "b07b4e9376489c7f7c0ff2af5eceb4261b3bb784",
"hash": "sha256-MnrieVgkvlkWKZ0O790gDSCrgF9c+XEk/XLHQDzMqVY="
"rev": "505ec917b67c535519bebec58c62a34f145dd49f",
"hash": "sha256-fsf8j2Spe++vSnuO8763eWWmMhYqcyybpILb7OkkXq4="
}
}
}

View File

@@ -9,15 +9,15 @@
buildGoModule (finalAttrs: {
pname = "kubernetes-helm";
version = "3.18.4";
version = "3.18.5";
src = fetchFromGitHub {
owner = "helm";
repo = "helm";
rev = "v${finalAttrs.version}";
sha256 = "sha256-2xOrTguenFzX7rvwm1ojSqV6ARCUSPUs07y3ut9Teec=";
sha256 = "sha256-SVaNuTIBnM9TFk+xy7yvUXX+8BEbfQdbHPTWUuimVw4=";
};
vendorHash = "sha256-Z3OAbuoeAtChd9Sk4bbzgwIxmFrw+/1c4zyxpNP0xXg=";
vendorHash = "sha256-Gn2h7a4bu9nWPEiqW9uN8SnKSZ7NRfchfRoFfpp49+M=";
subPackages = [ "cmd/helm" ];
ldflags = [

View File

@@ -6,16 +6,16 @@
buildGoModule rec {
pname = "helm-diff";
version = "3.12.4";
version = "3.12.5";
src = fetchFromGitHub {
owner = "databus23";
repo = "helm-diff";
rev = "v${version}";
hash = "sha256-w57EhXjaOEZaQV4FcvzjV4rMUVIwLlUJ3XlD+SLcLa8=";
hash = "sha256-vylkjmQHnT69HqkSPGSpgEkP6eeknGq4BGr1eBEvTlw=";
};
vendorHash = "sha256-FSyWFJSQBCRpHNrQTPz392H0dE37w1JcwJmoL0dg9fE=";
vendorHash = "sha256-PPWL98qEdV/J96N0JsglxUsuT+yFiOg1t4DdiY++/OY=";
ldflags = [
"-s"

View File

@@ -153,11 +153,11 @@
"vendorHash": null
},
"azurerm": {
"hash": "sha256-mYADF+vzpYt9RMxjNrZnEnBgpF4s0h2qBxize52DLw8=",
"hash": "sha256-YbnWigxznOZtY/lElLo/SEXnF3LPm6QKflnBoJ1B1Wo=",
"homepage": "https://registry.terraform.io/providers/hashicorp/azurerm",
"owner": "hashicorp",
"repo": "terraform-provider-azurerm",
"rev": "v4.38.1",
"rev": "v4.39.0",
"spdx": "MPL-2.0",
"vendorHash": null
},
@@ -171,11 +171,11 @@
"vendorHash": null
},
"baiducloud": {
"hash": "sha256-bmKoxLvWc1mX1NaV3ksHeuRX8yYDKnfFhPiASPBVlnM=",
"hash": "sha256-sF+S14e6o66iJj/X0jm8sVRmuEJv9UsmJvcLFTFTpVY=",
"homepage": "https://registry.terraform.io/providers/baidubce/baiducloud",
"owner": "baidubce",
"repo": "terraform-provider-baiducloud",
"rev": "v1.22.9",
"rev": "v1.22.10",
"spdx": "MPL-2.0",
"vendorHash": null
},
@@ -225,13 +225,13 @@
"vendorHash": "sha256-r4Q7b7ZzK+ZDXhIabTSgP7HY5Q51Hz5ErnW+nV+ZIqA="
},
"buildkite": {
"hash": "sha256-pF46n0PJ2ru7s/1S6mznpJnlZx+3BQmPj5dlttjta+Q=",
"hash": "sha256-w+ljPDKyVlylr87tFhuu/7oCkY/fFeK+LPr7mY7rbP0=",
"homepage": "https://registry.terraform.io/providers/buildkite/buildkite",
"owner": "buildkite",
"repo": "terraform-provider-buildkite",
"rev": "v1.23.0",
"rev": "v1.24.0",
"spdx": "MIT",
"vendorHash": "sha256-PuhOICFZJi6Fnu0cwrXc5YtJ3m5D1tC8C1wj6m9cfPY="
"vendorHash": "sha256-2xZ2//qMKfgqob39k++fX6vJEx9YE1NJpGCbDyM1L10="
},
"ccloud": {
"hash": "sha256-Dpx0eugcHCJV8GNPqjxx4P9ohgJgB10DTnHr+CeN/iQ=",
@@ -372,11 +372,11 @@
"vendorHash": "sha256-quoFrJbB1vjz+MdV+jnr7FPACHuUe5Gx9POLubD2IaM="
},
"digitalocean": {
"hash": "sha256-Bdc28nkev+i91ze/oyPSPeVegw/+eEn2FleaosCvDE0=",
"hash": "sha256-kqJVwh3Myu8pfNfO2uVQFO/aU/7trDKktRdXdFQvnOg=",
"homepage": "https://registry.terraform.io/providers/digitalocean/digitalocean",
"owner": "digitalocean",
"repo": "terraform-provider-digitalocean",
"rev": "v2.62.0",
"rev": "v2.65.0",
"spdx": "MPL-2.0",
"vendorHash": null
},
@@ -525,13 +525,13 @@
"vendorHash": "sha256-eE9AY/79xQSbRl5kA0rwS8Oz8I9jaxT/KlVd0v0GAa8="
},
"google": {
"hash": "sha256-pDYqzdPUnCKpbQqe58o4CU605gdF8vovPR3fCAdf4zQ=",
"hash": "sha256-enfKikX5raeLzZCnslaiAJ6hF/7+AXpKlDbNDm2v1qE=",
"homepage": "https://registry.terraform.io/providers/hashicorp/google",
"owner": "hashicorp",
"repo": "terraform-provider-google",
"rev": "v6.46.0",
"rev": "v6.48.0",
"spdx": "MPL-2.0",
"vendorHash": "sha256-n6UUSCQt3mJESEfqVHX4sfr1XqOXu+u7Qejjps6RmBs="
"vendorHash": "sha256-IwUmrRZC2KXNzbKajKisaqKbv0RMIH8tgiKsOOlduIo="
},
"google-beta": {
"hash": "sha256-8woiWjYYaojpKykxd9eMT4qXfpHVkXFA9eN3qzhEu+8=",
@@ -660,11 +660,11 @@
"vendorHash": null
},
"ibm": {
"hash": "sha256-541obBfBV/odhFvJISxeBtBmaLGoUB7rYymA0U7rhpY=",
"hash": "sha256-llsHIVqRN1yKQnMYA0MIinbUk2TL+NYeI0UlUcpCnN0=",
"homepage": "https://registry.terraform.io/providers/IBM-Cloud/ibm",
"owner": "IBM-Cloud",
"repo": "terraform-provider-ibm",
"rev": "v1.81.0",
"rev": "v1.81.1",
"spdx": "MPL-2.0",
"vendorHash": "sha256-cWfISNNeVPb6BU2V3sLbvlnFKzf3fVniV5Lu1Kpb9f0="
},
@@ -931,22 +931,22 @@
"vendorHash": "sha256-LRIfxQGwG988HE5fftGl6JmBG7tTknvmgpm4Fu1NbWI="
},
"oci": {
"hash": "sha256-bfe55ApaalhJpQtkl8YD9k5U7uyuqMuzOcM/ksBRglw=",
"hash": "sha256-Fh3GSSO+MBumdx5BxmINKhci8x0zHZ1jzMcGLyT0DIQ=",
"homepage": "https://registry.terraform.io/providers/oracle/oci",
"owner": "oracle",
"repo": "terraform-provider-oci",
"rev": "v7.12.0",
"rev": "v7.13.0",
"spdx": "MPL-2.0",
"vendorHash": null
},
"okta": {
"hash": "sha256-Up75XRwe7bnns+ahHtQfK7IG2gptDKNIY8pWG5QcjVI=",
"hash": "sha256-+3IYynRuV+iYI8FMpQmLUstNgEf3oAnPah4LmX6UjZw=",
"homepage": "https://registry.terraform.io/providers/okta/okta",
"owner": "okta",
"repo": "terraform-provider-okta",
"rev": "v5.2.0",
"rev": "v5.3.0",
"spdx": "MPL-2.0",
"vendorHash": "sha256-7zB+ZdrisV+C2kbDWHCaR4uNV3TZAh4EAQcT4jdJpQs="
"vendorHash": "sha256-CdXsClQLswfo/xVr5V65vpmvQg26TZv539zK9uodOco="
},
"oktaasa": {
"hash": "sha256-2LhxgowqKvDDDOwdznusL52p2DKP+UiXALHcs9ZQd0U=",
@@ -1165,13 +1165,13 @@
"vendorHash": "sha256-Icua01a4ILF+oAO5nMeCGPZrWc3V/SVObWydO72CU3I="
},
"scaleway": {
"hash": "sha256-/LyxYC+x6e5SQ12iZLxtbgFkF9MvotUlBYdK3/BiiAo=",
"hash": "sha256-YUOfCTtlPn9UBnmmPNODUwEbGR4EkknkdIVdZpmDnQw=",
"homepage": "https://registry.terraform.io/providers/scaleway/scaleway",
"owner": "scaleway",
"repo": "terraform-provider-scaleway",
"rev": "v2.58.0",
"rev": "v2.59.0",
"spdx": "MPL-2.0",
"vendorHash": "sha256-Fsa4I8aYHiK9V8arwd64piASA8qAPmGZRqDPK5ec3uk="
"vendorHash": "sha256-VH20r9RBlygGXuriXCzs3xBar/l3blPR+UcgCobIdWU="
},
"secret": {
"hash": "sha256-MmAnA/4SAPqLY/gYcJSTnEttQTsDd2kEdkQjQj6Bb+A=",

View File

@@ -30,7 +30,7 @@ mkDerivation rec {
"out"
"dev"
];
version = "15.67.4";
version = "15.68.5";
src =
let
@@ -39,11 +39,11 @@ mkDerivation rec {
{
x86_64-linux = fetchurl {
url = "${base_url}/teamviewer_${version}_amd64.deb";
hash = "sha256-ibKRYgsvBmh18LfG29ve/yrDEFTdgsNZ3kJu8YkMbsw=";
hash = "sha256-+MTp2ArZTcGFr1YwHIRfBIpjkRm0i9C1Pt5TzDE1SNE=";
};
aarch64-linux = fetchurl {
url = "${base_url}/teamviewer_${version}_arm64.deb";
hash = "sha256-MDNxqmu4dJA6dWKy8EFNOy2V253+UgsYwmZ3RidQqFE=";
hash = "sha256-3IVZya1WTGl2AtQ2F9jyX2sDLBa2L2/sfsszhyvzu4A=";
};
}
.${stdenv.hostPlatform.system} or (throw "Unsupported system: ${stdenv.hostPlatform.system}");

View File

@@ -15,3 +15,9 @@ if [[ "$latest_version" == "$current_version" ]]; then
fi
update-source-version teamviewer "$latest_version"
systems=$(nix eval --json -f . teamviewer.meta.platforms | jq --raw-output '.[]')
for system in $systems; do
hash=$(nix --extra-experimental-features nix-command hash convert --to sri --hash-algo sha256 $(nix-prefetch-url $(nix eval --raw -f . teamviewer.src.url --system "$system")))
update-source-version teamviewer $latest_version $hash --system=$system --ignore-same-version --ignore-same-hash
done

View File

@@ -3,23 +3,23 @@
{
"kicad" = {
kicadVersion = {
version = "9.0.2";
version = "9.0.3";
src = {
rev = "bf9b9242aea7832d140dc25ff897fe01e2f36e41";
sha256 = "1v3nvp5ifa36hx3iw3whlp3j7hiy91fzihc0jc1daw0hnps7qy24";
rev = "08e2e9df692929a2087bbf1340a915aa2365c622";
sha256 = "19rij2hz79rsmikdbygxzll2l7im5qi3i6phz4sdiagkc5k8b3rb";
};
};
libVersion = {
version = "9.0.2";
version = "9.0.3";
libSources = {
symbols.rev = "9eab1c9c90a8aa84b0f7eec73076329d91764583";
symbols.sha256 = "134x4d5w89aahl4k9zai6vwcazibz17gsgzy04l9xn4zcf6v11qp";
templates.rev = "f93acff0f8c8c8e215ea125db060c86bf4b1f5d3";
symbols.rev = "77ee421d180de82fce2d8c00f1b13a9456b43526";
symbols.sha256 = "0r9aimyrv7p4ykqnwb9ac3fd0dv11zmv2ll6qkmm5s875s35hhfl";
templates.rev = "6e651a795134380ac0dc3df1417d11cfab228033";
templates.sha256 = "0zs29zn8qjgxv0w1vyr8yxmj02m8752zagn4vcraqgik46dwg2id";
footprints.rev = "855079c1514bbdf38565fedcacee7fb05ffad5aa";
footprints.sha256 = "0w44b7dzx6d3xw2vbw37k34zxy25bq46rsnv21x10227313vr2wm";
packages3d.rev = "26e8886b3049a07e8b2b0bed82634ff755783352";
packages3d.sha256 = "18cxlp5grvv5m63c3sb6m9l9cmijqqcjmxrkdzg63d5jp7w73smn";
footprints.rev = "3ef8a3e0691599c633864118a3241e1cbeb873f1";
footprints.sha256 = "1ysnj0973y05nn016hxrghccfv65cas772i369xflay0sns8anqf";
packages3d.rev = "4c91925fde1402cc6da61d97cfb30a3de08d5bb6";
packages3d.sha256 = "0njv4y31k62qhcx0xxcl94p34jgna8z4bs3hwjwzjfmp7ddl2dyx";
};
};
};

View File

@@ -5,9 +5,9 @@ let
in
{
sublime-merge = common {
buildVersion = "2102";
aarch64sha256 = "E//XrWlfvMeRWYfBXVTSSUPlDFY/rzSynJ4aP1WyZ0Y=";
x64sha256 = "Odb3ZvJCo4HTvJ7z31J/5wlyhSUpZRFBXP3f/Wkb7tU=";
buildVersion = "2110";
aarch64sha256 = "lG95VgRsicSRjve7ESTamU9dp/xBjR6yyLL+1wh6BXg=";
x64sha256 = "v5CFqS+bB0Oe0fZ+vP0zxrJ2SUctNXKqODmB8M9XMIY=";
} { };
sublime-merge-dev = common {

View File

@@ -16,14 +16,14 @@
python3Packages.buildPythonApplication rec {
pname = "tartube";
version = "2.5.156";
version = "2.5.164";
format = "setuptools";
src = fetchFromGitHub {
owner = "axcore";
repo = "tartube";
tag = "v${version}";
sha256 = "sha256-4M1tYq8nVC1/+SQMtt0D0YfLW1uYWPcGx7XjuvbBxFw=";
sha256 = "sha256-PPvbdxxGUYUKL+5exO5+iO5ObJgjzFejZIIDA17hvYo=";
};
nativeBuildInputs = [

View File

@@ -9,16 +9,16 @@
rustPlatform.buildRustPackage rec {
pname = "3cpio";
version = "0.8.0";
version = "0.10.2";
src = fetchFromGitHub {
owner = "bdrung";
repo = "3cpio";
tag = version;
hash = "sha256-1kdJSwe9v7ojdukj04/G/RDeEk0NVCXmiNoVaelqt4Y=";
hash = "sha256-UtXyJ4PDzi4BJ0nd9w/hygcJVfNd3H5WAIV+f23dtpk=";
};
cargoHash = "sha256-axPghG1T5NZYzGRZBwtdBJ5tQh+h8/vep/EmL5ADCjE=";
cargoHash = "sha256-XGTa5Ui4yPHmuC4tTWGMTKN/erHSaiJVmxHglbt+udg=";
# Tests attempt to access arbitrary filepaths
doCheck = false;

View File

@@ -25,14 +25,14 @@
stdenv.mkDerivation rec {
pname = "abiword";
version = "3.0.6";
version = "3.0.7";
src = fetchFromGitLab {
domain = "gitlab.gnome.org";
owner = "World";
repo = "AbiWord";
rev = "refs/tags/release-${version}";
hash = "sha256-PPK4O+NKXdl7DKPOgGlVyCFTol8hhmtq0wdTTtwKQ/4=";
hash = "sha256-dYbJ726Zuxs7+VTTCWHYQLsVZ/86hRUBQRac6toO4UI=";
};
nativeBuildInputs = [

View File

@@ -43,12 +43,12 @@ in
stdenv.mkDerivation (finalAttrs: {
pname = binName;
version = "0.23.2";
version = "0.24.0";
src = fetchFromGitHub {
owner = "toeverything";
repo = "AFFiNE";
tag = "v${finalAttrs.version}";
hash = "sha256-4WPnS+ZaiNgtib70ii/XfWkn2tNg2OsSAglD+mpnDvg=";
hash = "sha256-vI4lCucwNdrbmst78NUkHXtluZvrc7aHymzm1Zbls78=";
};
cargoDeps = rustPlatform.fetchCargoVendor {
@@ -98,7 +98,7 @@ stdenv.mkDerivation (finalAttrs: {
'';
dontInstall = true;
outputHashMode = "recursive";
outputHash = "sha256-tpn+TlSrGIABmSM9B3iQc39nZmGEf5MliKyaKOsM7yM=";
outputHash = "sha256-wSEAxOSLS0ul5vQDTj/bVXH8ViqDFsq6jHTaXJFAm/U=";
};
buildInputs = lib.optionals hostPlatform.isDarwin [

View File

@@ -8,16 +8,16 @@
rustPlatform.buildRustPackage rec {
pname = "afterburn";
version = "5.8.2";
version = "5.9.0";
src = fetchFromGitHub {
owner = "coreos";
repo = "afterburn";
tag = "v${version}";
sha256 = "sha256-hlcUtEc0uWFolCt+mZd7f68PJPa+i/mv+2aJh4Vhmsw=";
sha256 = "sha256-kMq3yoqIp2j5DRQFarEK9kss9DoVgAEkjUYJX5Ogu0g=";
};
cargoHash = "sha256-Wn4Np1rwHh2sL1sqKalJrIDgMffxJgD1C2QOAR8bDRo=";
cargoHash = "sha256-pWt2+SptdTiP4/oROw38qc6ekfbVWOf86BR18QC+ZPU=";
nativeBuildInputs = [ pkg-config ];
buildInputs = [ openssl ];

View File

@@ -5,18 +5,18 @@
nix-update-script,
}:
rustPlatform.buildRustPackage rec {
rustPlatform.buildRustPackage (finalAttrs: {
pname = "agenix-cli";
version = "0.1.0";
version = "0.1.2";
src = fetchFromGitHub {
owner = "cole-h";
repo = "agenix-cli";
tag = "v${version}";
sha256 = "sha256-0+QVY1sDhGF4hAN6m2FdKZgm9V1cuGGjY4aitRBnvKg=";
tag = "v${finalAttrs.version}";
sha256 = "sha256-eJp6t8h8uOP0YupYn8x6VAAmUbVrXypxNMGx4SK/6d8=";
};
cargoHash = "sha256-xpA9BTA7EK3Pw8EJOjIq1ulBAcX4yNhc4kqhxsoCbv0=";
cargoHash = "sha256-2xTkCdWKQVg8Sp0LDkC/LH9GYBXNpxdoLX30Ndz0muM=";
passthru.updateScript = nix-update-script { };
@@ -30,4 +30,4 @@ rustPlatform.buildRustPackage rec {
maintainers = with lib.maintainers; [ misuzu ];
mainProgram = "agenix";
};
}
})

View File

@@ -16,11 +16,11 @@
stdenv.mkDerivation rec {
pname = "aide";
version = "0.19.1";
version = "0.19.2";
src = fetchurl {
url = "https://github.com/aide/aide/releases/download/v${version}/${pname}-${version}.tar.gz";
sha256 = "sha256-bfi/XwQD10r329uR6zyPYf4H6WRmnbjPoe5+TuPpC1I=";
sha256 = "sha256-I3YrBfRhEe3rPIoFAWyHMcAb24wfkb5IwVbDGrhedMQ=";
};
buildInputs = [

View File

@@ -8,11 +8,11 @@
stdenvNoCC.mkDerivation (finalAttrs: {
pname = "alt-tab-macos";
version = "7.26.0";
version = "7.27.0";
src = fetchurl {
url = "https://github.com/lwouis/alt-tab-macos/releases/download/v${finalAttrs.version}/AltTab-${finalAttrs.version}.zip";
hash = "sha256-tDy+GFZw9hD2kelPOJioRvcmbPZ9bQu+IRDBEOamsJs=";
hash = "sha256-jjtgpfKzLj2cAUvpjlC9STmp8EN3y+rdQVKJvTHzoXM=";
};
sourceRoot = ".";

View File

@@ -40,13 +40,11 @@ stdenvNoCC.mkDerivation {
# [3]: https://gitlab.com/trueNAHO/antora-ui-default/-/commit/11f563294248e9b64124b9289d639e349f2e9f5f
src = fetchFromGitLab srcFetchFromGitLab;
phases = [ "installPhase" ];
# Install '$src/ui-bundle.zip' to '$out/ui-bundle.zip' instead of '$out' to
# prevent the ZIP from being misidentified as a binary [1].
#
# [1]: https://github.com/NixOS/nixpkgs/blob/8885a1e21ad43f8031c738a08029cd1d4dcbc2f7/pkgs/stdenv/generic/setup.sh#L792-L795
installPhase = ''
buildCommand = ''
mkdir --parents "$out"
cp "$src/ui-bundle.zip" "$out"
'';

View File

@@ -7,13 +7,13 @@
}:
stdenvNoCC.mkDerivation rec {
pname = "app2unit";
version = "1.0.0";
version = "1.0.3";
src = fetchFromGitHub {
owner = "Vladimir-csp";
repo = "app2unit";
tag = "v${version}";
sha256 = "sha256-xHqPCA9ycPcImmyMrJZEfnfrFZ3sKfP/mhJ86CHLTQ8=";
sha256 = "sha256-7eEVjgs+8k+/NLteSBKgn4gPaPLHC+3Uzlmz6XB0930=";
};
nativeBuildInputs = [ scdoc ];

View File

@@ -15,13 +15,13 @@ let
in
stdenv.mkDerivation (finalAttrs: {
pname = "apriltags";
version = "3.4.3";
version = "3.4.4";
src = fetchFromGitHub {
owner = "AprilRobotics";
repo = "AprilTags";
tag = "v${finalAttrs.version}";
hash = "sha256-1XbsyyadUvBZSpIc9KPGiTcp+3G7YqHepWoORob01Ss=";
hash = "sha256-fHVwRE7qAJZ5Q1SFUfS5du91CUcb3+3n12M/NThDEV4=";
};
nativeBuildInputs = [

View File

@@ -6,11 +6,11 @@
}:
stdenvNoCC.mkDerivation (finalAttrs: {
pname = "arkenfox-userjs";
version = "133.0";
version = "140.0";
src = fetchurl {
url = "https://raw.githubusercontent.com/arkenfox/user.js/${finalAttrs.version}/user.js";
hash = "sha256-rPcH24YqEBOzoPB9yxMlke/3tqpi9L7GVMsZ3MUP8WY=";
hash = "sha256-/cz0dnQXKa3c/DqUTAEwBV0I9Tc3x6uzU6rtYijg3Zo=";
};
dontUnpack = true;

View File

@@ -15,10 +15,10 @@
let
source = {
version = "2.27.0";
hash = "sha256-FKWK/yYMNBrGgfWtdUC9DpQ2y8mBn3/5G+buQNzzot4=";
npmDepsHash = "sha256-FpRO7lhgQNZ5wHQwHFIxkrYfmivgTopXKFcrQ48B20w=";
clientNpmDepsHash = "sha256-GHN49bo7m9pzvwNvkVtA0cwTv+rWSAKpBHG7jqXm/vo=";
version = "2.28.0";
hash = "sha256-bbsiaSGIaD5oFnhk3e+SWzYxv4dsRXrgMVbe1lsj4pw=";
npmDepsHash = "sha256-JC2uOXV+EwS6CGwyOUTXcymFwLSz/KUqIoB4ccSGgbw=";
clientNpmDepsHash = "sha256-6l8apOd3R259+SlcD6P6rx1FkRnB80keoBGcfbQNhGU=";
};
src = fetchFromGitHub {

View File

@@ -1,5 +1,5 @@
#!/usr/bin/env nix-shell
#!nix-shell -i bash -p curl gnused gawk nix-prefetch common-updater-scripts jq prefetch-npm-deps
#!nix-shell -i bash -p curl gnused gawk nix-prefetch nix-prefetch-git common-updater-scripts jq prefetch-npm-deps
set -euo pipefail

View File

@@ -6,13 +6,13 @@
buildGoModule rec {
pname = "bazel-gazelle";
version = "0.44.0";
version = "0.45.0";
src = fetchFromGitHub {
owner = "bazelbuild";
repo = "bazel-gazelle";
rev = "v${version}";
hash = "sha256-vkGLzrseERxl0LygFm1zCC7kK7j+pHpTbG2fy4fLztw=";
hash = "sha256-ulfZPb3MRIOVt8M6XVuuGKmgOgcglJcWsscj2BiMTpY=";
};
vendorHash = null;

View File

@@ -8,13 +8,13 @@
buildGoModule rec {
pname = "bearer";
version = "1.50.0";
version = "1.50.1";
src = fetchFromGitHub {
owner = "bearer";
repo = "bearer";
tag = "v${version}";
hash = "sha256-6GggGsimQShDs/F/H80aBykQYowH55plDQDRjiWKFsA=";
hash = "sha256-cUfuTYk3ckijSZbniHaZuprlv9rKNIxzILEdTGdvVQ0=";
};
vendorHash = "sha256-+2iiMb2+/a3GCUMVA9boJJxuFgB3NmxpTePyMEA46jw=";

View File

@@ -13,16 +13,16 @@
rustPlatform.buildRustPackage rec {
pname = "bootc";
version = "1.5.1";
version = "1.6.0";
cargoHash = "sha256-+FxydTK0Dmcj+doHMSoTgiues7Rrwxv/D+BOq4siKCk=";
cargoHash = "sha256-KGwXQ6+/w3uHuPqSADsqJSip+SMdC104dfW7tNxGwnc=";
doInstallCheck = true;
src = fetchFromGitHub {
owner = "bootc-dev";
repo = "bootc";
rev = "v${version}";
hash = "sha256-LmhgCiVFbhrePV/A/FaNjD7VytUZqSm9VDU+1z0O98U=";
hash = "sha256-TztsiC+DwD9yEAmjTuiuOi+Kf8WEYMsOVVnMKpSM3/g=";
};
nativeBuildInputs = [ pkg-config ];

View File

@@ -10,16 +10,16 @@
rustPlatform.buildRustPackage rec {
pname = "bottom";
version = "0.10.2";
version = "0.11.0";
src = fetchFromGitHub {
owner = "ClementTsang";
repo = "bottom";
tag = version;
hash = "sha256-hm0Xfd/iW+431HflvZErjzeZtSdXVb/ReoNIeETJ5Ik=";
hash = "sha256-7AK1Nf10nT2Zbu/s7rkCfGuxFa3iIFeh2hy5XbJTSPo=";
};
cargoHash = "sha256-feMgkCP6e3HsOppTYLtVrRn/vbSLLRKV0hp85gqr4qM=";
cargoHash = "sha256-IpAliZvmhOZw+94kgmfd3Rif8mcqe3LRR5q+i2JLY+s=";
nativeBuildInputs = [
autoAddDriverRunpath

View File

@@ -7,12 +7,12 @@
let
pname = "cables";
version = "0.7.0";
version = "0.7.1";
name = "${pname}-${version}";
src = fetchurl {
url = "https://github.com/cables-gl/cables_electron/releases/download/v${version}/cables-${version}-linux-x64.AppImage";
sha256 = "sha256-8PYHX23E91rUEfzU6fthSTVOnnHeoRjbcNFbuOyeBS8=";
sha256 = "sha256-CsKwb9anK7yHM+1mf9tPyjQ1GLYiUkrO7oP+GxFTqx0=";
};
appimageContents = appimageTools.extract {

View File

@@ -36,11 +36,11 @@
stdenv.mkDerivation (finalAttrs: {
pname = "calibre";
version = "8.6.0";
version = "8.7.0";
src = fetchurl {
url = "https://download.calibre-ebook.com/${finalAttrs.version}/calibre-${finalAttrs.version}.tar.xz";
hash = "sha256-FYWeUS78jvFV9nj/9RSRxPFYKYxSF04dIXZINSbn7WA=";
hash = "sha256-LP5Yfjdz2GB/6LvvvNd7XPuBYSTKyJ5JE1PeuPL6kyQ=";
};
patches = [

View File

@@ -10,11 +10,11 @@
stdenvNoCC.mkDerivation rec {
pname = "camunda-modeler";
version = "5.37.0";
version = "5.38.0";
src = fetchurl {
url = "https://github.com/camunda/camunda-modeler/releases/download/v${version}/camunda-modeler-${version}-linux-x64.tar.gz";
hash = "sha256-YcMe+YBxNYZ9bQzdixckbN5qrCqtaplWCw88i9GAcSA=";
hash = "sha256-KiRAsRzIeUc8akizH6zgKCyG55vrYhfWGw572etGgWg=";
};
sourceRoot = "camunda-modeler-${version}-linux-x64";

View File

@@ -8,16 +8,16 @@
rustPlatform.buildRustPackage rec {
pname = "cargo-deny";
version = "0.18.3";
version = "0.18.4";
src = fetchFromGitHub {
owner = "EmbarkStudios";
repo = "cargo-deny";
rev = version;
hash = "sha256-cFgc3bdNVLeuie4sVC+klmQ1/C6W3LkTgORMCfOte4Q=";
hash = "sha256-5aa13eFfGEJZBRB4/PAKKLwxw2wt8sBI7ZVOpgnO+t8=";
};
cargoHash = "sha256-3TfyFsBSjo8VEDrUehoV2ccXh+xY+iQ9xihj1Bl2MhI=";
cargoHash = "sha256-RW+drxVouQbiZsjEL+XZBE2VMzEiCkLTOC9jMxI76T8=";
nativeBuildInputs = [
pkg-config

View File

@@ -34,6 +34,10 @@ rustPlatform.buildRustPackage rec {
# requires internet access
"--skip=detects_target_dependencies"
"--skip=query::tests_lints::feature_missing"
# platform specific snapshots
"--skip=query::tests_lints::trait_method_target_feature_removed"
"--skip=query::tests_lints::unsafe_trait_method_requires_more_target_features"
"--skip=query::tests_lints::unsafe_trait_method_target_feature_added"
];
preCheck = ''

View File

@@ -14,13 +14,13 @@
stdenv.mkDerivation rec {
pname = "cdogs-sdl";
version = "2.3.0";
version = "2.3.1";
src = fetchFromGitHub {
repo = "cdogs-sdl";
owner = "cxong";
rev = version;
sha256 = "sha256-I4v13CPdA2KYwhlIJjz+qgKe2EoXUtV6iWeadrg4Usc=";
sha256 = "sha256-jdrmtI/FADZ0vJDtX4Kq0A9RJ1ELjsQZjO2nMDf/fT8=";
};
postPatch = ''

View File

@@ -8,16 +8,16 @@
let
argset = {
pname = "chezmoi";
version = "2.63.1";
version = "2.64.0";
src = fetchFromGitHub {
owner = "twpayne";
repo = "chezmoi";
rev = "v${argset.version}";
hash = "sha256-gf79aJhyN3qrCMg7IZqUxHCl6qj6GY5BOXjoJvpKql4=";
hash = "sha256-MiIZfT2ax5LszSboXOtDp0hOpOJ8gXqeBTXyoacl+BY=";
};
vendorHash = "sha256-2Pnj5QoCL8B5qF7YlQFJttj4nlOSobJKySnIvg+82Ew=";
vendorHash = "sha256-LVq++K5ElXeArEpXLnSxg+8D9XJoXCHozOPeJrFbDRE=";
nativeBuildInputs = [
installShellFiles

View File

@@ -11,14 +11,14 @@
python3Packages.buildPythonApplication {
pname = "chirp";
version = "0.4.0-unstable-2025-08-04";
version = "0.4.0-unstable-2025-08-13";
pyproject = true;
src = fetchFromGitHub {
owner = "kk7ds";
repo = "chirp";
rev = "a8fb306f5627f2478d55541d21f7e9ed51363010";
hash = "sha256-SQWKHkIf9d23AKnJQv58XlTmuL07HRj6oS8LW4BM+7Y=";
rev = "acb1a78384a804dab1f2f0cc453b3da972d39072";
hash = "sha256-+1hzT7peZWtiREeOJqpCyrZNUxOVchxysv9RIAVKPds=";
};
nativeBuildInputs = [

View File

@@ -10,16 +10,16 @@
}:
rustPlatform.buildRustPackage rec {
pname = "chirpstack-concentratord";
version = "4.5.0";
version = "4.5.1";
src = fetchFromGitHub {
owner = "chirpstack";
repo = "chirpstack-concentratord";
rev = "v${version}";
hash = "sha256-UlliScDD1OEH4hLzKVr0z74iI48TTQTDfSsTwHzk8kw=";
hash = "sha256-sqAroYaiDbVbl0Yqdc+Yl1rhYLjUv/Go+//nX4t7S0U=";
};
cargoHash = "sha256-NkP3sMSw/iEkzqdX7rR6qMRq7MyZNyF9HcjrVuVRBEk=";
cargoHash = "sha256-cg/icdN0ntbVdnEs6I0AJWVYkawsyV1gPYjDMhzzDBY=";
buildInputs = [
libloragw-2g4

View File

@@ -24,18 +24,18 @@
stdenv.mkDerivation (finalAttrs: {
pname = "clapgrep";
version = "25.05+1";
version = "25.07";
src = fetchFromGitHub {
owner = "luleyleo";
repo = "clapgrep";
tag = "v${finalAttrs.version}";
hash = "sha256-DL3voYSsNGjPb1CnPuJGg+7UgWYZO7cH5T2Z37BuDSE=";
hash = "sha256-XH0ei0x4QeCaVLDpRrHFgI6ExR5CSX7Pzg1PCrTyBec=";
};
cargoDeps = rustPlatform.fetchCargoVendor {
inherit (finalAttrs) src;
hash = "sha256-hTejIaXIAi8opZdE2X3vEi+VYoSti8RNB41ikVOWGPk=";
hash = "sha256-tKC3YgLECV3EMMzBLBPj0GntHk2oavXGpTwWG9EjH1U=";
};
nativeBuildInputs = [

View File

@@ -6,13 +6,13 @@
"packages": {
"": {
"dependencies": {
"@anthropic-ai/claude-code": "^1.0.74"
"@anthropic-ai/claude-code": "^1.0.81"
}
},
"node_modules/@anthropic-ai/claude-code": {
"version": "1.0.74",
"resolved": "https://registry.npmjs.org/@anthropic-ai/claude-code/-/claude-code-1.0.74.tgz",
"integrity": "sha512-Iahs887b3Zdk6xWkb+qDgz178nOWqfse35Ten2l+oOQqeS1A7Ct14BPZuQmLiWtkoSZxqFAsee3Gp+ITfPicrw==",
"version": "1.0.81",
"resolved": "https://registry.npmjs.org/@anthropic-ai/claude-code/-/claude-code-1.0.81.tgz",
"integrity": "sha512-kiRgAhQ2vuodkHDAZjuR0aaNchl9SZLq0QF46JKsOw0Ik1eyEN0tdsF++AV//Ub1j4iS1fGIrU10uE7aqFfKYw==",
"license": "SEE LICENSE IN README.md",
"bin": {
"claude": "cli.js"

View File

@@ -7,16 +7,16 @@
buildNpmPackage rec {
pname = "claude-code";
version = "1.0.74";
version = "1.0.81";
nodejs = nodejs_20; # required for sandboxed Nix builds on Darwin
src = fetchzip {
url = "https://registry.npmjs.org/@anthropic-ai/claude-code/-/claude-code-${version}.tgz";
hash = "sha256-cjiW39n74BV+s1ZKf/kgZVAg02XGWsoVfdzwPxuwe3g=";
hash = "sha256-MTugT72wrsUHQHUYx6HZPoE4kt1krYOhfNSSoOc/GjI=";
};
npmDepsHash = "sha256-z+ZU8rT0rKcWxG4fZut7rA2rChVdyOyCw62+CNNObZU=";
npmDepsHash = "sha256-1GBwoximrwJX5F7lp5KUXtt6uPABta8FBbYYoJ2Y7x8=";
postPatch = ''
cp ${./package-lock.json} package-lock.json

View File

@@ -0,0 +1,179 @@
{
lts ? false,
version,
hash,
nixUpdateExtraArgs ? [ ],
}:
{
lib,
stdenv,
llvmPackages_19,
fetchFromGitHub,
cmake,
ninja,
python3,
perl,
nasm,
yasm,
nixosTests,
darwin,
findutils,
libiconv,
rustSupport ? true,
rustc,
cargo,
rustPlatform,
nix-update-script,
}:
llvmPackages_19.stdenv.mkDerivation (finalAttrs: {
pname = "clickhouse" + lib.optionalString lts "-lts";
inherit version;
src = fetchFromGitHub rec {
owner = "ClickHouse";
repo = "ClickHouse";
tag = "v${finalAttrs.version}";
fetchSubmodules = true;
name = "clickhouse-${tag}.tar.gz";
inherit hash;
postFetch = ''
# delete files that make the source too big
rm -rf $out/contrib/llvm-project/llvm/test
rm -rf $out/contrib/llvm-project/clang/test
rm -rf $out/contrib/croaring/benchmarks
# fix case insensitivity on macos https://github.com/NixOS/nixpkgs/issues/39308
rm -rf $out/contrib/sysroot/linux-*
rm -rf $out/contrib/liburing/man
# compress to not exceed the 2GB output limit
# try to make a deterministic tarball
tar -I 'gzip -n' \
--sort=name \
--mtime=1970-01-01 \
--owner=0 --group=0 \
--numeric-owner --mode=go=rX,u+rw,a-s \
--transform='s@^@source/@S' \
-cf temp -C "$out" .
rm -r "$out"
mv temp "$out"
'';
};
strictDeps = true;
nativeBuildInputs = [
cmake
ninja
python3
perl
llvmPackages_19.lld
]
++ lib.optionals stdenv.hostPlatform.isx86_64 [
nasm
yasm
]
++ lib.optionals stdenv.hostPlatform.isDarwin [
llvmPackages_19.bintools
findutils
darwin.bootstrap_cmds
]
++ lib.optionals rustSupport [
rustc
cargo
rustPlatform.cargoSetupHook
];
buildInputs = lib.optionals stdenv.hostPlatform.isDarwin [ libiconv ];
dontCargoSetupPostUnpack = true;
postPatch = ''
patchShebangs src/ utils/
sed -i 's|/usr/bin/env perl|"${lib.getExe perl}"|' contrib/openssl-cmake/CMakeLists.txt
substituteInPlace utils/list-licenses/list-licenses.sh \
--replace-fail '$(git rev-parse --show-toplevel)' "$NIX_BUILD_TOP/$sourceRoot"
''
+ lib.optionalString (lib.versions.majorMinor version <= "25.6") ''
substituteInPlace src/Storages/System/StorageSystemLicenses.sh \
--replace-fail '$(git rev-parse --show-toplevel)' "$NIX_BUILD_TOP/$sourceRoot"
''
+ lib.optionalString stdenv.hostPlatform.isDarwin ''
substituteInPlace cmake/tools.cmake \
--replace-fail 'gfind' 'find' \
--replace-fail 'ggrep' 'grep' \
--replace-fail '--ld-path=''${LLD_PATH}' '-fuse-ld=lld'
''
# Rust is handled by cmake
+ lib.optionalString rustSupport ''
cargoSetupPostPatchHook() { true; }
'';
cmakeFlags = [
"-DENABLE_CHDIG=OFF"
"-DENABLE_TESTS=OFF"
"-DENABLE_DELTA_KERNEL_RS=0"
"-DCOMPILER_CACHE=disabled"
]
++ lib.optional (
stdenv.hostPlatform.isLinux && stdenv.hostPlatform.isAarch64
) "-DNO_ARMV81_OR_HIGHER=1";
env = {
CARGO_HOME = "$PWD/../.cargo/";
NIX_CFLAGS_COMPILE =
# undefined reference to '__sync_val_compare_and_swap_16'
lib.optionalString stdenv.hostPlatform.isx86_64 " -mcx16"
+
# Silence ``-Wimplicit-const-int-float-conversion` error in MemoryTracker.cpp and
# ``-Wno-unneeded-internal-declaration` TreeOptimizer.cpp.
lib.optionalString stdenv.hostPlatform.isDarwin
" -Wno-implicit-const-int-float-conversion -Wno-unneeded-internal-declaration";
};
# https://github.com/ClickHouse/ClickHouse/issues/49988
hardeningDisable = [ "fortify" ];
postInstall = ''
sed -i -e '\!<log>/var/log/clickhouse-server/clickhouse-server\.log</log>!d' \
$out/etc/clickhouse-server/config.xml
substituteInPlace $out/etc/clickhouse-server/config.xml \
--replace-fail "<errorlog>/var/log/clickhouse-server/clickhouse-server.err.log</errorlog>" "<console>1</console>" \
--replace-fail "<level>trace</level>" "<level>warning</level>"
'';
# Basic smoke test
doCheck = true;
checkPhase = lib.optionalString (stdenv.buildPlatform.canExecute stdenv.hostPlatform) ''
$NIX_BUILD_TOP/$sourceRoot/build/programs/clickhouse local --query 'SELECT 1' | grep 1
'';
# Builds in 7+h with 2 cores, and ~20m with a big-parallel builder.
requiredSystemFeatures = [ "big-parallel" ];
passthru = {
tests.clickhouse = if lts then nixosTests.clickhouse-lts else nixosTests.clickhouse;
updateScript = nix-update-script {
extraArgs = nixUpdateExtraArgs;
};
};
meta = with lib; {
homepage = "https://clickhouse.com";
description = "Column-oriented database management system";
license = licenses.asl20;
maintainers = with maintainers; [
orivej
mbalatsko
thevar1able
];
# not supposed to work on 32-bit https://github.com/ClickHouse/ClickHouse/pull/23959#issuecomment-835343685
platforms = lib.filter (x: (lib.systems.elaborate x).is64bit) (platforms.linux ++ platforms.darwin);
broken = stdenv.buildPlatform != stdenv.hostPlatform;
};
})

View File

@@ -0,0 +1,11 @@
import ./generic.nix {
version = "25.3.6.56-lts";
hash = "sha256-wpC6uw811IWImLWAatYbghp3aZ+esEEBFng6AHIesK4=";
lts = true;
nixUpdateExtraArgs = [
"--version-regex"
"^v?(.*-lts)$"
"--override-filename"
"pkgs/by-name/cl/clickhouse/lts.nix"
];
}

View File

@@ -1,169 +1,11 @@
{
lib,
stdenv,
llvmPackages_19,
fetchFromGitHub,
cmake,
ninja,
python3,
perl,
nasm,
yasm,
nixosTests,
darwin,
findutils,
libiconv,
rustSupport ? true,
rustc,
cargo,
rustPlatform,
}:
llvmPackages_19.stdenv.mkDerivation (finalAttrs: {
pname = "clickhouse";
version = "25.3.5.42";
src = fetchFromGitHub rec {
owner = "ClickHouse";
repo = "ClickHouse";
tag = "v${finalAttrs.version}-lts";
fetchSubmodules = true;
name = "clickhouse-${tag}.tar.gz";
hash = "sha256-LvGl9XJK6Emt7HnV/Orp7qEmJSr3TBJZtApL6GrWIMg=";
postFetch = ''
# delete files that make the source too big
rm -rf $out/contrib/llvm-project/llvm/test
rm -rf $out/contrib/llvm-project/clang/test
rm -rf $out/contrib/croaring/benchmarks
# fix case insensitivity on macos https://github.com/NixOS/nixpkgs/issues/39308
rm -rf $out/contrib/sysroot/linux-*
rm -rf $out/contrib/liburing/man
# compress to not exceed the 2GB output limit
# try to make a deterministic tarball
tar -I 'gzip -n' \
--sort=name \
--mtime=1970-01-01 \
--owner=0 --group=0 \
--numeric-owner --mode=go=rX,u+rw,a-s \
--transform='s@^@source/@S' \
-cf temp -C "$out" .
rm -r "$out"
mv temp "$out"
'';
};
strictDeps = true;
nativeBuildInputs = [
cmake
ninja
python3
perl
llvmPackages_19.lld
]
++ lib.optionals stdenv.hostPlatform.isx86_64 [
nasm
yasm
]
++ lib.optionals stdenv.hostPlatform.isDarwin [
llvmPackages_19.bintools
findutils
darwin.bootstrap_cmds
]
++ lib.optionals rustSupport [
rustc
cargo
rustPlatform.cargoSetupHook
import ./generic.nix {
version = "25.7.4.11-stable";
hash = "sha256-SKDnnBdl9Rwc+ONH1chXAOFIwRmVG2l5cPEwpaDogzU=";
lts = false;
nixUpdateExtraArgs = [
"--version-regex"
"^v?(.*-stable)$"
"--override-filename"
"pkgs/by-name/cl/clickhouse/package.nix"
];
buildInputs = lib.optionals stdenv.hostPlatform.isDarwin [ libiconv ];
dontCargoSetupPostUnpack = true;
postPatch = ''
patchShebangs src/
patchShebangs utils/
sed -i 's|/usr/bin/env perl|"${lib.getExe perl}"|' contrib/openssl-cmake/CMakeLists.txt
substituteInPlace src/Storages/System/StorageSystemLicenses.sh \
--replace-fail '$(git rev-parse --show-toplevel)' "$NIX_BUILD_TOP/$sourceRoot"
substituteInPlace utils/check-style/check-ungrouped-includes.sh \
--replace-fail '$(git rev-parse --show-toplevel)' "$NIX_BUILD_TOP/$sourceRoot"
substituteInPlace utils/list-licenses/list-licenses.sh \
--replace-fail '$(git rev-parse --show-toplevel)' "$NIX_BUILD_TOP/$sourceRoot"
''
+ lib.optionalString stdenv.hostPlatform.isDarwin ''
sed -i 's|gfind|find|' cmake/tools.cmake
sed -i 's|ggrep|grep|' cmake/tools.cmake
# Make sure Darwin invokes lld.ld64 not lld.
substituteInPlace cmake/tools.cmake \
--replace '--ld-path=''${LLD_PATH}' '-fuse-ld=lld'
''
+ lib.optionalString rustSupport ''
cargoSetupPostPatchHook() { true; }
'';
cmakeFlags = [
"-DENABLE_TESTS=OFF"
"-DENABLE_DELTA_KERNEL_RS=0"
"-DCOMPILER_CACHE=disabled"
]
++ lib.optional (
stdenv.hostPlatform.isLinux && stdenv.hostPlatform.isAarch64
) "-DNO_ARMV81_OR_HIGHER=1";
env = {
CARGO_HOME = "$PWD/../.cargo/";
NIX_CFLAGS_COMPILE =
# undefined reference to '__sync_val_compare_and_swap_16'
lib.optionalString stdenv.hostPlatform.isx86_64 " -mcx16"
+
# Silence ``-Wimplicit-const-int-float-conversion` error in MemoryTracker.cpp and
# ``-Wno-unneeded-internal-declaration` TreeOptimizer.cpp.
lib.optionalString stdenv.hostPlatform.isDarwin
" -Wno-implicit-const-int-float-conversion -Wno-unneeded-internal-declaration";
};
# https://github.com/ClickHouse/ClickHouse/issues/49988
hardeningDisable = [ "fortify" ];
postInstall = ''
rm -rf $out/share/clickhouse-test
sed -i -e '\!<log>/var/log/clickhouse-server/clickhouse-server\.log</log>!d' \
$out/etc/clickhouse-server/config.xml
substituteInPlace $out/etc/clickhouse-server/config.xml \
--replace-fail "<errorlog>/var/log/clickhouse-server/clickhouse-server.err.log</errorlog>" "<console>1</console>"
substituteInPlace $out/etc/clickhouse-server/config.xml \
--replace-fail "<level>trace</level>" "<level>warning</level>"
'';
# Basic smoke test
doCheck = true;
checkPhase = ''
$NIX_BUILD_TOP/$sourceRoot/build/programs/clickhouse local --query 'SELECT 1' | grep 1
'';
# Builds in 7+h with 2 cores, and ~20m with a big-parallel builder.
requiredSystemFeatures = [ "big-parallel" ];
passthru.tests.clickhouse = nixosTests.clickhouse;
meta = with lib; {
homepage = "https://clickhouse.com";
description = "Column-oriented database management system";
license = licenses.asl20;
maintainers = with maintainers; [
orivej
mbalatsko
thevar1able
];
# not supposed to work on 32-bit https://github.com/ClickHouse/ClickHouse/pull/23959#issuecomment-835343685
platforms = lib.filter (x: (lib.systems.elaborate x).is64bit) (platforms.linux ++ platforms.darwin);
broken = stdenv.buildPlatform != stdenv.hostPlatform;
};
})
}

View File

@@ -6,11 +6,11 @@
buildGraalvmNativeImage (finalAttrs: {
pname = "clj-kondo";
version = "2025.07.26";
version = "2025.07.28";
src = fetchurl {
url = "https://github.com/clj-kondo/clj-kondo/releases/download/v${finalAttrs.version}/clj-kondo-${finalAttrs.version}-standalone.jar";
sha256 = "sha256-jo8iY8vEtrGTQTV98y89i2OLWW4M3u6hsXZebd7cnUw=";
sha256 = "sha256-ioKRFkm+zBAAM7oyR4F6rTHEhViuRNuMXcr1xwnjcms=";
};
extraNativeImageBuildArgs = [

View File

@@ -151,7 +151,6 @@ stdenv.mkDerivation rec {
license = licenses.unfree;
mainProgram = "warp-cli";
maintainers = with maintainers; [
devpikachu
marcusramberg
];
platforms = [

View File

@@ -1,31 +1,38 @@
{
lib,
fetchFromGitHub,
buildGo123Module,
buildGoModule,
}:
buildGo123Module rec {
buildGoModule (finalAttrs: {
pname = "clusternet";
version = "0.17.3";
version = "0.18.1";
src = fetchFromGitHub {
owner = "clusternet";
repo = "clusternet";
tag = "v${version}";
hash = "sha256-uhRnJyUR7lbJvVxd3YNVxmTSTDksQsVcM5G8ZKO7Xbk=";
tag = "v${finalAttrs.version}";
hash = "sha256-MtiQM2msHv2gLaVpYoSrzJMZWwA0vMBIklwAQi+lG4g=";
};
vendorHash = "sha256-hY4bgQXwKjL4UT3omDYuxy9xN9XOr00mMvGssKOSsG4=";
vendorHash = "sha256-vG+k9ttXp/QqhbVKgwn2uo5kEk8OD+LBvJi5lBQfUk4=";
ldFlags = [
"-s"
"-w"
];
# Clusternet hub is disabled due to panic: inlined function github.com/clusternet/clusternet/pkg/hub/apiserver/shadow.(*crdHandler).addStorage.func9.1 missing func info
subPackages = [
"cmd/clusternet-agent"
"cmd/clusternet-controller-manager"
"cmd/clusternet-scheduler"
];
meta = {
description = "CNCF Sandbox Project for managing your Kubernetes clusters";
homepage = "https://github.com/clusternet/clusternet";
license = lib.licenses.asl20;
maintainers = with lib.maintainers; [ genga898 ];
};
}
})

View File

@@ -11,7 +11,7 @@
stdenv.mkDerivation rec {
pname = "codeql";
version = "2.22.2";
version = "2.22.3";
dontConfigure = true;
dontBuild = true;
@@ -19,7 +19,7 @@ stdenv.mkDerivation rec {
src = fetchzip {
url = "https://github.com/github/codeql-cli-binaries/releases/download/v${version}/codeql.zip";
hash = "sha256-4GbvOtRm9YG0lqKnFv859UEsGb6cCkzjfx7Xazs5two=";
hash = "sha256-75ayL/TftTM1nfwIFsVOhfqFi//ts6o8GeK/mYez04k=";
};
nativeBuildInputs = [

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