Merge branch 'staging-next' into staging

This commit is contained in:
Vladimír Čunát 2020-08-04 21:38:08 +02:00
commit 01c2ba8575
No known key found for this signature in database
GPG Key ID: E747DF1F9575A3AA
249 changed files with 8187 additions and 5893 deletions

View File

@ -54,12 +54,29 @@ end_of_line = unset
[*.lock]
indent_size = unset
[deps.nix]
insert_final_newline = unset
[gemset.nix]
insert_final_newline = unset
[node-packages.nix]
insert_final_newline = unset
[nixos/modules/services/networking/ircd-hybrid/*.{conf,in}]
trim_trailing_whitespace = unset
[nixos/tests/systemd-networkd-vrf.nix]
trim_trailing_whitespace = unset
[pkgs/applications/editors/emacs-modes/recipes-archive-melpa.json]
indent_size = unset
[pkgs/build-support/dotnetenv/Wrapper/**.*]
end_of_line = unset
insert_final_newline = unset
trim_trailing_whitespace = unset
[pkgs/development/lisp-modules/quicklisp-to-nix.nix]
indent_size = unset

6
.github/CODEOWNERS vendored
View File

@ -10,6 +10,12 @@
# This file
/.github/CODEOWNERS @edolstra
# GitHub actions
/.github/workflows @Mic92 @zowoq
# EditorConfig
/.editorconfig @Mic92 @zowoq
# Libraries
/lib @edolstra @nbp @infinisil
/lib/systems @nbp @ericson2314 @matthewbauer

View File

@ -1,4 +1,4 @@
name: actions
name: "Checking EditorConfig"
on:
pull_request:
@ -6,17 +6,24 @@ on:
- master
jobs:
editorconfig:
tests:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: technote-space/get-diff-action@v2.0.2
- name: editorconfig check
with:
fetch-depth: 0
- uses: technote-space/get-diff-action@v2.0.3
- name: fetch editorconfig-checker
env:
VERSION: "2.0.4"
VERSION: "2.1.0"
OS: "linux"
ARCH: "amd64"
ECC_URL: "https://github.com/editorconfig-checker/editorconfig-checker/releases/download"
run: |
curl -sSf -O -L -C - https://github.com/editorconfig-checker/editorconfig-checker/releases/download/$VERSION/ec-$OS-$ARCH.tar.gz && \
curl -sSf -O -L -C - $ECC_URL/$VERSION/ec-$OS-$ARCH.tar.gz && \
tar xzf ec-$OS-$ARCH.tar.gz && \
./bin/ec-$OS-$ARCH -disable-indentation ${{ env.GIT_DIFF }}
mv ./bin/ec-$OS-$ARCH ./bin/editorconfig-checker
- name: Checking EditorConfig
run: |
./bin/editorconfig-checker -disable-indentation \
${{ env.GIT_DIFF }}

View File

@ -7,9 +7,12 @@ jobs:
steps:
- name: Wait for ofborg CI
run: |
# wait for ~30min...
# eval sometimes takes a bit longer on staging.
if [[ "$BASE_BRANCH" == "refs/heads/staging" ]]; then
COUNTDOWN=$((COUNTDOWN*2))
fi
# ..in future a better fix would be to make ofborg mark CI as pending right away.
for i in $(seq 360); do
for i in $(seq "$COUNTDOWN"); do
res=$(curl --silent \
-H "Accept: application/vnd.github.antiope-preview+json" \
-H "Authorization: token ${GITHUB_TOKEN}" \
@ -26,6 +29,8 @@ jobs:
# ofborg is not checking forks.
if: github.repository_owner == 'NixOS'
env:
BASE_BRANCH: ${{ github.base_ref }}
COUNTDOWN: 360 # wait for ~30min...
GITHUB_TOKEN: ${{ github.token }}
COMMIT: ${{ github.event.pull_request.head.sha }}
OFBORG_APP_ID: 20500

View File

@ -40,6 +40,8 @@ pet = buildGoModule rec {
subPackages = [ "." ]; <co xml:id='ex-buildGoModule-2' />
runVend = true; <co xml:id='ex-buildGoModule-3' />
meta = with lib; {
description = "Simple command-line snippet manager, written in Go";
homepage = "https://github.com/knqyf263/pet";
@ -66,7 +68,7 @@ pet = buildGoModule rec {
</callout>
<callout arearefs='ex-buildGoModule-3'>
<para>
<varname>runVend</varname> runs the vend command to generate the vendor directory. This is useful if your code depends on c code and go mod tidy does not include the needed sources to build.
<varname>runVend</varname> runs the vend command to generate the vendor directory. This is useful if your code depends on c code and go mod tidy does not include the needed sources to build.
</para>
</callout>
</calloutlist>

View File

@ -48,8 +48,10 @@ rec {
else if isAttrs v then err "attrsets" v
# functions cant be printed of course
else if isFunction v then err "functions" v
# lets not talk about floats. There is no sensible `toString` for them.
else if isFloat v then err "floats" v
# Floats currently can't be converted to precise strings,
# condition warning on nix version once this isn't a problem anymore
# See https://github.com/NixOS/nix/pull/3480
else if isFloat v then libStr.floatToString v
else err "this value is" (toString v);

View File

@ -110,6 +110,11 @@ lib.mapAttrs (n: v: v // { shortName = n; }) {
fullName = ''BSD 4-clause "Original" or "Old" License'';
};
bsdProtection = spdx {
spdxId = "BSD-Protection";
fullName = "BSD Protection License";
};
bsl11 = {
fullName = "Business Source License 1.1";
url = "https://mariadb.com/bsl11";

View File

@ -612,6 +612,22 @@ rec {
*/
fixedWidthNumber = width: n: fixedWidthString width "0" (toString n);
/* Convert a float to a string, but emit a warning when precision is lost
during the conversion
Example:
floatToString 0.000001
=> "0.000001"
floatToString 0.0000001
=> trace: warning: Imprecise conversion from float to string 0.000000
"0.000000"
*/
floatToString = float: let
result = toString float;
precise = float == builtins.fromJSON result;
in if precise then result
else lib.warn "Imprecise conversion from float to string ${result}" result;
/* Check whether a value can be coerced to a string */
isCoercibleToString = x:
builtins.elem (builtins.typeOf x) [ "path" "string" "null" "int" "float" "bool" ] ||

View File

@ -1760,6 +1760,16 @@
githubId = 490965;
name = "Craig Swank";
};
cust0dian = {
email = "serg@effectful.software";
github = "cust0dian";
githubId = 389387;
name = "Serg Nesterov";
keys = [{
longkeyid = "rsa4096/0x1512F6EB84AECC8C";
fingerprint = "6E7D BA30 DB5D BA60 693C 3BE3 1512 F6EB 84AE CC8C";
}];
};
cwoac = {
email = "oliver@codersoffortune.net";
github = "cwoac";
@ -5193,6 +5203,12 @@
githubId = 13689192;
name = "Nguyn Gia Phong";
};
mcwitt = {
email = "mcwitt@gmail.com";
github = "mcwitt";
githubId = 319411;
name = "Matt Wittmann";
};
mdaiter = {
email = "mdaiter8121@gmail.com";
github = "mdaiter";

View File

@ -0,0 +1,179 @@
<section xmlns="http://docbook.org/ns/docbook"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:xi="http://www.w3.org/2001/XInclude"
version="5.0"
xml:id="sec-settings-options">
<title>Options for Program Settings</title>
<para>
Many programs have configuration files where program-specific settings can be declared. File formats can be separated into two categories:
<itemizedlist>
<listitem>
<para>
Nix-representable ones: These can trivially be mapped to a subset of Nix syntax. E.g. JSON is an example, since its values like <literal>{"foo":{"bar":10}}</literal> can be mapped directly to Nix: <literal>{ foo = { bar = 10; }; }</literal>. Other examples are INI, YAML and TOML. The following section explains the convention for these settings.
</para>
</listitem>
<listitem>
<para>
Non-nix-representable ones: These can't be trivially mapped to a subset of Nix syntax. Most generic programming languages are in this group, e.g. bash, since the statement <literal>if true; then echo hi; fi</literal> doesn't have a trivial representation in Nix.
</para>
<para>
Currently there are no fixed conventions for these, but it is common to have a <literal>configFile</literal> option for setting the configuration file path directly. The default value of <literal>configFile</literal> can be an auto-generated file, with convenient options for controlling the contents. For example an option of type <literal>attrsOf str</literal> can be used for representing environment variables which generates a section like <literal>export FOO="foo"</literal>. Often it can also be useful to also include an <literal>extraConfig</literal> option of type <literal>lines</literal> to allow arbitrary text after the autogenerated part of the file.
</para>
</listitem>
</itemizedlist>
</para>
<section xml:id="sec-settings-nix-representable">
<title>Nix-representable Formats (JSON, YAML, TOML, INI, ...)</title>
<para>
By convention, formats like this are handled with a generic <literal>settings</literal> option, representing the full program configuration as a Nix value. The type of this option should represent the format. The most common formats have a predefined type and string generator already declared under <literal>pkgs.formats</literal>:
<variablelist>
<varlistentry>
<term>
<varname>pkgs.formats.json</varname> { }
</term>
<listitem>
<para>
A function taking an empty attribute set (for future extensibility) and returning a set with JSON-specific attributes <varname>type</varname> and <varname>generate</varname> as specified <link linkend='pkgs-formats-result'>below</link>.
</para>
</listitem>
</varlistentry>
<varlistentry>
<term>
<varname>pkgs.formats.yaml</varname> { }
</term>
<listitem>
<para>
A function taking an empty attribute set (for future extensibility) and returning a set with YAML-specific attributes <varname>type</varname> and <varname>generate</varname> as specified <link linkend='pkgs-formats-result'>below</link>.
</para>
</listitem>
</varlistentry>
<varlistentry>
<term>
<varname>pkgs.formats.ini</varname> { <replaceable>listsAsDuplicateKeys</replaceable> ? false, ... }
</term>
<listitem>
<para>
A function taking an attribute set with values
<variablelist>
<varlistentry>
<term>
<varname>listsAsDuplicateKeys</varname>
</term>
<listitem>
<para>
A boolean for controlling whether list values can be used to represent duplicate INI keys
</para>
</listitem>
</varlistentry>
</variablelist>
It returns a set with INI-specific attributes <varname>type</varname> and <varname>generate</varname> as specified <link linkend='pkgs-formats-result'>below</link>.
</para>
</listitem>
</varlistentry>
<varlistentry>
<term>
<varname>pkgs.formats.toml</varname> { }
</term>
<listitem>
<para>
A function taking an empty attribute set (for future extensibility) and returning a set with TOML-specific attributes <varname>type</varname> and <varname>generate</varname> as specified <link linkend='pkgs-formats-result'>below</link>.
</para>
</listitem>
</varlistentry>
</variablelist>
</para>
<para xml:id="pkgs-formats-result">
These functions all return an attribute set with these values:
<variablelist>
<varlistentry>
<term>
<varname>type</varname>
</term>
<listitem>
<para>
A module system type representing a value of the format
</para>
</listitem>
</varlistentry>
<varlistentry>
<term>
<varname>generate</varname> <replaceable>filename</replaceable> <replaceable>jsonValue</replaceable>
</term>
<listitem>
<para>
A function that can render a value of the format to a file. Returns a file path.
<note>
<para>
This function puts the value contents in the Nix store. So this should be avoided for secrets.
</para>
</note>
</para>
</listitem>
</varlistentry>
</variablelist>
</para>
<example xml:id="ex-settings-nix-representable">
<title>Module with conventional <literal>settings</literal> option</title>
<para>
The following shows a module for an example program that uses a JSON configuration file. It demonstrates how above values can be used, along with some other related best practices. See the comments for explanations.
</para>
<programlisting>
{ options, config, lib, pkgs, ... }:
let
cfg = config.services.foo;
# Define the settings format used for this program
settingsFormat = pkgs.formats.json {};
in {
options.services.foo = {
enable = lib.mkEnableOption "foo service";
settings = lib.mkOption {
# Setting this type allows for correct merging behavior
type = settingsFormat.type;
default = {};
description = ''
Configuration for foo, see
&lt;link xlink:href="https://example.com/docs/foo"/&gt;
for supported values.
'';
};
};
config = lib.mkIf cfg.enable {
# We can assign some default settings here to make the service work by just
# enabling it. We use `mkDefault` for values that can be changed without
# problems
services.foo.settings = {
# Fails at runtime without any value set
log_level = lib.mkDefault "WARN";
# We assume systemd's `StateDirectory` is used, so we require this value,
# therefore no mkDefault
data_path = "/var/lib/foo";
# Since we use this to create a user we need to know the default value at
# eval time
user = lib.mkDefault "foo";
};
environment.etc."foo.json".source =
# The formats generator function takes a filename and the Nix value
# representing the format value and produces a filepath with that value
# rendered in the format
settingsFormat.generate "foo-config.json" cfg.settings;
# We know that the `user` attribute exists because we set a default value
# for it above, allowing us to use it without worries here
users.users.${cfg.settings.user} = {}
# ...
};
}
</programlisting>
</example>
</section>
</section>

View File

@ -183,4 +183,5 @@ in {
<xi:include href="meta-attributes.xml" />
<xi:include href="importing-modules.xml" />
<xi:include href="replace-modules.xml" />
<xi:include href="settings-options.xml" />
</chapter>

View File

@ -216,12 +216,12 @@ start_all()
</varlistentry>
<varlistentry>
<term>
<methodname>send_keys</methodname>
<methodname>send_key</methodname>
</term>
<listitem>
<para>
Simulate pressing keys on the virtual keyboard, e.g.,
<literal>send_keys("ctrl-alt-delete")</literal>.
<literal>send_key("ctrl-alt-delete")</literal>.
</para>
</listitem>
</varlistentry>
@ -232,7 +232,7 @@ start_all()
<listitem>
<para>
Simulate typing a sequence of characters on the virtual keyboard, e.g.,
<literal>send_keys("foobar\n")</literal> will type the string
<literal>send_chars("foobar\n")</literal> will type the string
<literal>foobar</literal> followed by the Enter key.
</para>
</listitem>

View File

@ -544,21 +544,42 @@ systemd.services.nginx.serviceConfig.ReadWritePaths = [ "/var/www" ];
to be used for every display-manager in NixOS.
</para>
</listitem>
<listitem>
<listitem>
<para>
The <literal>bitcoind</literal> module has changed to multi-instance, using submodules.
Therefore, it is now mandatory to name each instance, e.g.:
Therefore, it is now mandatory to name each instance.
To use this new multi-instance config with an existing bitcoind data directory and user,
you have to adjust the original config, e.g.:
<programlisting>
services.bitcoind = {
enable = true;
};
services.bitcoind = {
enable = true;
extraConfig = "...";
...
};
</programlisting>
requires a name now:
To something similar:
<programlisting>
services.bitcoind."example-mainnet" = {
enable = true;
};
services.bitcoind.mainnet = {
enable = true;
dataDir = "/var/lib/bitcoind";
user = "bitcoin";
extraConfig = "...";
...
};
</programlisting>
The key settings are:
<itemizedlist>
<listitem>
<para>
<literal>dataDir</literal> - to continue using the same data directory.
</para>
</listitem>
<listitem>
<para>
<literal>user</literal> - to continue using the same user so that bitcoind maintains access to its files.
</para>
</listitem>
</itemizedlist>
</para>
</listitem>
<listitem>

View File

@ -36,7 +36,7 @@ let
// lib.optionalAttrs (opt ? example) { example = substFunction opt.example; }
// lib.optionalAttrs (opt ? default) { default = substFunction opt.default; }
// lib.optionalAttrs (opt ? type) { type = substFunction opt.type; }
// lib.optionalAttrs (opt ? relatedPackages && opt.relatedPackages != []) { relatedPackages = genRelatedPackages opt.relatedPackages; }
// lib.optionalAttrs (opt ? relatedPackages && opt.relatedPackages != []) { relatedPackages = genRelatedPackages opt.relatedPackages opt.name; }
);
# Generate DocBook documentation for a list of packages. This is
@ -48,7 +48,7 @@ let
# - a list: that will be interpreted as an attribute path from `pkgs`,
# - an attrset: that can specify `name`, `path`, `package`, `comment`
# (either of `name`, `path` is required, the rest are optional).
genRelatedPackages = packages:
genRelatedPackages = packages: optName:
let
unpack = p: if lib.isString p then { name = p; }
else if lib.isList p then { path = p; }
@ -58,7 +58,7 @@ let
title = args.title or null;
name = args.name or (lib.concatStringsSep "." args.path);
path = args.path or [ args.name ];
package = args.package or (lib.attrByPath path (throw "Invalid package attribute path `${toString path}'") pkgs);
package = args.package or (lib.attrByPath path (throw "Invalid package attribute path `${toString path}' found while evaluating `relatedPackages' of option `${optName}'") pkgs);
in "<listitem>"
+ "<para><literal>${lib.optionalString (title != null) "${title} aka "}pkgs.${name} (${package.meta.name})</literal>"
+ lib.optionalString (!package.meta.available) " <emphasis>[UNAVAILABLE]</emphasis>"

View File

@ -8,17 +8,17 @@ use Time::HiRes qw(clock_gettime CLOCK_MONOTONIC);
sub new {
my ($class) = @_;
my $logFile = defined $ENV{LOGFILE} ? "$ENV{LOGFILE}" : "/dev/null";
my $log = new XML::Writer(OUTPUT => new IO::File(">$logFile"));
my $self = {
log => $log,
logQueue => Thread::Queue->new()
};
$self->{log}->startTag("logfile");
bless $self, $class;
return $self;
}

View File

@ -1 +1 @@
azure
azure

View File

@ -20,7 +20,7 @@ $ ./upload-image.sh ./examples/basic/image.nix
+ nix-build ./examples/basic/image.nix --out-link azure
/nix/store/qdpzknpskzw30vba92mb24xzll1dqsmd-azure-image
...
95.5 %, 0 Done, 0 Failed, 1 Pending, 0 Skipped, 1 Total, 2-sec Throughput (Mb/s): 932.9565
95.5 %, 0 Done, 0 Failed, 1 Pending, 0 Skipped, 1 Total, 2-sec Throughput (Mb/s): 932.9565
...
/subscriptions/aff271ee-e9be-4441-b9bb-42f5af4cbaeb/resourceGroups/nixos-images/providers/Microsoft.Compute/images/azure-image-todo-makethisbetter
```

View File

@ -37,8 +37,8 @@ if ! az disk show -g "${group}" -n "${img_name}" &>/dev/null; then
)"
azcopy copy "${img_file}" "${sasurl}" \
--blob-type PageBlob
--blob-type PageBlob
az disk revoke-access \
--resource-group "${group}" \
--name "${img_name}"

View File

@ -646,6 +646,8 @@
./services/networking/iperf3.nix
./services/networking/ircd-hybrid/default.nix
./services/networking/iwd.nix
./services/networking/jicofo.nix
./services/networking/jitsi-videobridge.nix
./services/networking/keepalived/default.nix
./services/networking/keybase.nix
./services/networking/kippo.nix
@ -852,6 +854,7 @@
./services/web-apps/icingaweb2/module-monitoring.nix
./services/web-apps/ihatemoney
./services/web-apps/jirafeau.nix
./services/web-apps/jitsi-meet.nix
./services/web-apps/limesurvey.nix
./services/web-apps/mattermost.nix
./services/web-apps/mediawiki.nix

View File

@ -31,27 +31,42 @@ let
let
os = val:
optionalString (val != null) "${val}";
os' = prefixx: val:
optionalString (val != null) (prefixx + "${val}");
os' = prefix: val:
optionalString (val != null) (prefix + "${val}");
flatten = key: value:
"&${key}=${value}";
in
"-s ${opt.type}://" + os opt.location + "?" + os' "name=" name
+ concatStrings (mapAttrsToList flatten opt.query);
"--stream.stream=\"${opt.type}://" + os opt.location + "?" + os' "name=" name
+ concatStrings (mapAttrsToList flatten opt.query) + "\"";
optionalNull = val: ret:
optional (val != null) ret;
optionString = concatStringsSep " " (mapAttrsToList streamToOption cfg.streams
++ ["-p ${toString cfg.port}"]
++ ["--controlPort ${toString cfg.controlPort}"]
++ optionalNull cfg.sampleFormat "--sampleFormat ${cfg.sampleFormat}"
++ optionalNull cfg.codec "-c ${cfg.codec}"
++ optionalNull cfg.streamBuffer "--streamBuffer ${cfg.streamBuffer}"
++ optionalNull cfg.buffer "-b ${cfg.buffer}"
++ optional cfg.sendToMuted "--sendToMuted");
# global options
++ [ "--stream.bind_to_address ${cfg.listenAddress}" ]
++ [ "--stream.port ${toString cfg.port}" ]
++ optionalNull cfg.sampleFormat "--stream.sampleformat ${cfg.sampleFormat}"
++ optionalNull cfg.codec "--stream.codec ${cfg.codec}"
++ optionalNull cfg.streamBuffer "--stream.stream_buffer ${cfg.streamBuffer}"
++ optionalNull cfg.buffer "--stream.buffer ${cfg.buffer}"
++ optional cfg.sendToMuted "--stream.send_to_muted"
# tcp json rpc
++ [ "--tcp.enabled ${toString cfg.tcp.enable}" ]
++ optionals cfg.tcp.enable [
"--tcp.address ${cfg.tcp.listenAddress}"
"--tcp.port ${toString cfg.tcp.port}" ]
# http json rpc
++ [ "--http.enabled ${toString cfg.http.enable}" ]
++ optionals cfg.http.enable [
"--http.address ${cfg.http.listenAddress}"
"--http.port ${toString cfg.http.port}"
] ++ optional (cfg.http.docRoot != null) "--http.doc_root \"${toString cfg.http.docRoot}\"");
in {
imports = [
(mkRenamedOptionModule [ "services" "snapserver" "controlPort"] [ "services" "snapserver" "tcp" "port" ])
];
###### interface
@ -67,6 +82,15 @@ in {
'';
};
listenAddress = mkOption {
type = types.str;
default = "::";
example = "0.0.0.0";
description = ''
The address where snapclients can connect.
'';
};
port = mkOption {
type = types.port;
default = 1704;
@ -75,14 +99,6 @@ in {
'';
};
controlPort = mkOption {
type = types.port;
default = 1705;
description = ''
The port for control connections (JSON-RPC).
'';
};
openFirewall = mkOption {
type = types.bool;
default = true;
@ -94,6 +110,90 @@ in {
inherit sampleFormat;
inherit codec;
streamBuffer = mkOption {
type = with types; nullOr int;
default = null;
description = ''
Stream read (input) buffer in ms.
'';
example = 20;
};
buffer = mkOption {
type = with types; nullOr int;
default = null;
description = ''
Network buffer in ms.
'';
example = 1000;
};
sendToMuted = mkOption {
type = types.bool;
default = false;
description = ''
Send audio to muted clients.
'';
};
tcp.enable = mkOption {
type = types.bool;
default = true;
description = ''
Whether to enable the JSON-RPC via TCP.
'';
};
tcp.listenAddress = mkOption {
type = types.str;
default = "::";
example = "0.0.0.0";
description = ''
The address where the TCP JSON-RPC listens on.
'';
};
tcp.port = mkOption {
type = types.port;
default = 1705;
description = ''
The port where the TCP JSON-RPC listens on.
'';
};
http.enable = mkOption {
type = types.bool;
default = true;
description = ''
Whether to enable the JSON-RPC via HTTP.
'';
};
http.listenAddress = mkOption {
type = types.str;
default = "::";
example = "0.0.0.0";
description = ''
The address where the HTTP JSON-RPC listens on.
'';
};
http.port = mkOption {
type = types.port;
default = 1780;
description = ''
The port where the HTTP JSON-RPC listens on.
'';
};
http.docRoot = mkOption {
type = with types; nullOr path;
default = null;
description = ''
Path to serve from the HTTP servers root.
'';
};
streams = mkOption {
type = with types; attrsOf (submodule {
options = {
@ -147,34 +247,7 @@ in {
};
'';
};
streamBuffer = mkOption {
type = with types; nullOr int;
default = null;
description = ''
Stream read (input) buffer in ms.
'';
example = 20;
};
buffer = mkOption {
type = with types; nullOr int;
default = null;
description = ''
Network buffer in ms.
'';
example = 1000;
};
sendToMuted = mkOption {
type = types.bool;
default = false;
description = ''
Send audio to muted clients.
'';
};
};
};
@ -206,7 +279,10 @@ in {
};
};
networking.firewall.allowedTCPPorts = optionals cfg.openFirewall [ cfg.port cfg.controlPort ];
networking.firewall.allowedTCPPorts =
optionals cfg.openFirewall [ cfg.port ]
++ optional cfg.tcp.enable cfg.tcp.port
++ optional cfg.http.enable cfg.http.port;
};
meta = {

View File

@ -18,7 +18,7 @@ in {
};
host = mkOption {
description = "Remote host where snapshots should be sent.";
description = "Remote host where snapshots should be sent. <literal>lz4</literal> is expected to be installed on this host.";
example = "example.com";
type = types.str;
};

View File

@ -3,8 +3,9 @@
let
cfg = config.services.zabbixAgent;
inherit (lib) mkDefault mkEnableOption mkIf mkOption;
inherit (lib) mkDefault mkEnableOption mkIf mkMerge mkOption;
inherit (lib) attrValues concatMapStringsSep literalExample optionalString types;
inherit (lib.generators) toKeyValue;
user = "zabbix-agent";
group = "zabbix-agent";
@ -14,19 +15,15 @@ let
paths = attrValues cfg.modules;
};
configFile = pkgs.writeText "zabbix_agent.conf" ''
LogType = console
Server = ${cfg.server}
ListenIP = ${cfg.listen.ip}
ListenPort = ${toString cfg.listen.port}
${optionalString (cfg.modules != {}) "LoadModulePath = ${moduleEnv}/lib"}
${concatMapStringsSep "\n" (name: "LoadModule = ${name}") (builtins.attrNames cfg.modules)}
${cfg.extraConfig}
'';
configFile = pkgs.writeText "zabbix_agent.conf" (toKeyValue { listsAsDuplicateKeys = true; } cfg.settings);
in
{
imports = [
(lib.mkRemovedOptionModule [ "services" "zabbixAgent" "extraConfig" ] "Use services.zabbixAgent.settings instead.")
];
# interface
options = {
@ -105,15 +102,18 @@ in
'';
};
# TODO: for bonus points migrate this to https://github.com/NixOS/rfcs/pull/42
extraConfig = mkOption {
default = "";
type = types.lines;
settings = mkOption {
type = with types; attrsOf (oneOf [ int str (listOf str) ]);
default = {};
description = ''
Configuration that is injected verbatim into the configuration file. Refer to
Zabbix Agent configuration. Refer to
<link xlink:href="https://www.zabbix.com/documentation/current/manual/appendix/config/zabbix_agentd"/>
for details on supported values.
'';
example = {
Hostname = "example.org";
DebugLevel = 4;
};
};
};
@ -124,6 +124,17 @@ in
config = mkIf cfg.enable {
services.zabbixAgent.settings = mkMerge [
{
LogType = "console";
Server = cfg.server;
ListenIP = cfg.listen.ip;
ListenPort = cfg.listen.port;
LoadModule = builtins.attrNames cfg.modules;
}
(mkIf (cfg.modules != {}) { LoadModulePath = "${moduleEnv}/lib"; })
];
networking.firewall = mkIf cfg.openFirewall {
allowedTCPPorts = [ cfg.listen.port ];
};

View File

@ -5,8 +5,9 @@ let
pgsql = config.services.postgresql;
mysql = config.services.mysql;
inherit (lib) mkDefault mkEnableOption mkIf mkOption;
inherit (lib) mkDefault mkEnableOption mkIf mkMerge mkOption;
inherit (lib) attrValues concatMapStringsSep literalExample optional optionalAttrs optionalString types;
inherit (lib.generators) toKeyValue;
user = "zabbix";
group = "zabbix";
@ -19,24 +20,7 @@ let
paths = attrValues cfg.modules;
};
configFile = pkgs.writeText "zabbix_proxy.conf" ''
LogType = console
ListenIP = ${cfg.listen.ip}
ListenPort = ${toString cfg.listen.port}
Server = ${cfg.server}
# TODO: set to cfg.database.socket if database type is pgsql?
DBHost = ${optionalString (cfg.database.createLocally != true) cfg.database.host}
${optionalString (cfg.database.createLocally != true) "DBPort = ${cfg.database.port}"}
DBName = ${cfg.database.name}
DBUser = ${cfg.database.user}
${optionalString (cfg.database.passwordFile != null) "Include ${passwordFile}"}
${optionalString (mysqlLocal && cfg.database.socket != null) "DBSocket = ${cfg.database.socket}"}
SocketDir = ${runtimeDir}
FpingLocation = /run/wrappers/bin/fping
${optionalString (cfg.modules != {}) "LoadModulePath = ${moduleEnv}/lib"}
${concatMapStringsSep "\n" (name: "LoadModule = ${name}") (builtins.attrNames cfg.modules)}
${cfg.extraConfig}
'';
configFile = pkgs.writeText "zabbix_proxy.conf" (toKeyValue { listsAsDuplicateKeys = true; } cfg.settings);
mysqlLocal = cfg.database.createLocally && cfg.database.type == "mysql";
pgsqlLocal = cfg.database.createLocally && cfg.database.type == "pgsql";
@ -44,6 +28,10 @@ let
in
{
imports = [
(lib.mkRemovedOptionModule [ "services" "zabbixProxy" "extraConfig" ] "Use services.zabbixProxy.settings instead.")
];
# interface
options = {
@ -182,15 +170,19 @@ in
'';
};
# TODO: for bonus points migrate this to https://github.com/NixOS/rfcs/pull/42
extraConfig = mkOption {
default = "";
type = types.lines;
settings = mkOption {
type = with types; attrsOf (oneOf [ int str (listOf str) ]);
default = {};
description = ''
Configuration that is injected verbatim into the configuration file. Refer to
Zabbix Proxy configuration. Refer to
<link xlink:href="https://www.zabbix.com/documentation/current/manual/appendix/config/zabbix_proxy"/>
for details on supported values.
'';
example = {
CacheSize = "1G";
SSHKeyLocation = "/var/lib/zabbix/.ssh";
StartPingers = 32;
};
};
};
@ -213,6 +205,26 @@ in
}
];
services.zabbixProxy.settings = mkMerge [
{
LogType = "console";
ListenIP = cfg.listen.ip;
ListenPort = cfg.listen.port;
Server = cfg.server;
# TODO: set to cfg.database.socket if database type is pgsql?
DBHost = optionalString (cfg.database.createLocally != true) cfg.database.host;
DBName = cfg.database.name;
DBUser = cfg.database.user;
SocketDir = runtimeDir;
FpingLocation = "/run/wrappers/bin/fping";
LoadModule = builtins.attrNames cfg.modules;
}
(mkIf (cfg.database.createLocally != true) { DBPort = cfg.database.port; })
(mkIf (cfg.database.passwordFile != null) { Include = [ "${passwordFile}" ]; })
(mkIf (mysqlLocal && cfg.database.socket != null) { DBSocket = cfg.database.socket; })
(mkIf (cfg.modules != {}) { LoadModulePath = "${moduleEnv}/lib"; })
];
networking.firewall = mkIf cfg.openFirewall {
allowedTCPPorts = [ cfg.listen.port ];
};

View File

@ -5,8 +5,9 @@ let
pgsql = config.services.postgresql;
mysql = config.services.mysql;
inherit (lib) mkDefault mkEnableOption mkIf mkOption;
inherit (lib) mkDefault mkEnableOption mkIf mkMerge mkOption;
inherit (lib) attrValues concatMapStringsSep literalExample optional optionalAttrs optionalString types;
inherit (lib.generators) toKeyValue;
user = "zabbix";
group = "zabbix";
@ -19,24 +20,7 @@ let
paths = attrValues cfg.modules;
};
configFile = pkgs.writeText "zabbix_server.conf" ''
LogType = console
ListenIP = ${cfg.listen.ip}
ListenPort = ${toString cfg.listen.port}
# TODO: set to cfg.database.socket if database type is pgsql?
DBHost = ${optionalString (cfg.database.createLocally != true) cfg.database.host}
${optionalString (cfg.database.createLocally != true) "DBPort = ${cfg.database.port}"}
DBName = ${cfg.database.name}
DBUser = ${cfg.database.user}
${optionalString (cfg.database.passwordFile != null) "Include ${passwordFile}"}
${optionalString (mysqlLocal && cfg.database.socket != null) "DBSocket = ${cfg.database.socket}"}
PidFile = ${runtimeDir}/zabbix_server.pid
SocketDir = ${runtimeDir}
FpingLocation = /run/wrappers/bin/fping
${optionalString (cfg.modules != {}) "LoadModulePath = ${moduleEnv}/lib"}
${concatMapStringsSep "\n" (name: "LoadModule = ${name}") (builtins.attrNames cfg.modules)}
${cfg.extraConfig}
'';
configFile = pkgs.writeText "zabbix_server.conf" (toKeyValue { listsAsDuplicateKeys = true; } cfg.settings);
mysqlLocal = cfg.database.createLocally && cfg.database.type == "mysql";
pgsqlLocal = cfg.database.createLocally && cfg.database.type == "pgsql";
@ -47,6 +31,7 @@ in
imports = [
(lib.mkRenamedOptionModule [ "services" "zabbixServer" "dbServer" ] [ "services" "zabbixServer" "database" "host" ])
(lib.mkRemovedOptionModule [ "services" "zabbixServer" "dbPassword" ] "Use services.zabbixServer.database.passwordFile instead.")
(lib.mkRemovedOptionModule [ "services" "zabbixServer" "extraConfig" ] "Use services.zabbixServer.settings instead.")
];
# interface
@ -176,15 +161,19 @@ in
'';
};
# TODO: for bonus points migrate this to https://github.com/NixOS/rfcs/pull/42
extraConfig = mkOption {
default = "";
type = types.lines;
settings = mkOption {
type = with types; attrsOf (oneOf [ int str (listOf str) ]);
default = {};
description = ''
Configuration that is injected verbatim into the configuration file. Refer to
Zabbix Server configuration. Refer to
<link xlink:href="https://www.zabbix.com/documentation/current/manual/appendix/config/zabbix_server"/>
for details on supported values.
'';
example = {
CacheSize = "1G";
SSHKeyLocation = "/var/lib/zabbix/.ssh";
StartPingers = 32;
};
};
};
@ -204,6 +193,26 @@ in
}
];
services.zabbixServer.settings = mkMerge [
{
LogType = "console";
ListenIP = cfg.listen.ip;
ListenPort = cfg.listen.port;
# TODO: set to cfg.database.socket if database type is pgsql?
DBHost = optionalString (cfg.database.createLocally != true) cfg.database.host;
DBName = cfg.database.name;
DBUser = cfg.database.user;
PidFile = "${runtimeDir}/zabbix_server.pid";
SocketDir = runtimeDir;
FpingLocation = "/run/wrappers/bin/fping";
LoadModule = builtins.attrNames cfg.modules;
}
(mkIf (cfg.database.createLocally != true) { DBPort = cfg.database.port; })
(mkIf (cfg.database.passwordFile != null) { Include = [ "${passwordFile}" ]; })
(mkIf (mysqlLocal && cfg.database.socket != null) { DBSocket = cfg.database.socket; })
(mkIf (cfg.modules != {}) { LoadModulePath = "${moduleEnv}/lib"; })
];
networking.firewall = mkIf cfg.openFirewall {
allowedTCPPorts = [ cfg.listen.port ];
};

View File

@ -0,0 +1,152 @@
{ config, lib, pkgs, ... }:
with lib;
let
cfg = config.services.jicofo;
in
{
options.services.jicofo = with types; {
enable = mkEnableOption "Jitsi Conference Focus - component of Jitsi Meet";
xmppHost = mkOption {
type = str;
example = "localhost";
description = ''
Hostname of the XMPP server to connect to.
'';
};
xmppDomain = mkOption {
type = nullOr str;
example = "meet.example.org";
description = ''
Domain name of the XMMP server to which to connect as a component.
If null, <option>xmppHost</option> is used.
'';
};
componentPasswordFile = mkOption {
type = str;
example = "/run/keys/jicofo-component";
description = ''
Path to file containing component secret.
'';
};
userName = mkOption {
type = str;
default = "focus";
description = ''
User part of the JID for XMPP user connection.
'';
};
userDomain = mkOption {
type = str;
example = "auth.meet.example.org";
description = ''
Domain part of the JID for XMPP user connection.
'';
};
userPasswordFile = mkOption {
type = str;
example = "/run/keys/jicofo-user";
description = ''
Path to file containing password for XMPP user connection.
'';
};
bridgeMuc = mkOption {
type = str;
example = "jvbbrewery@internal.meet.example.org";
description = ''
JID of the internal MUC used to communicate with Videobridges.
'';
};
config = mkOption {
type = attrsOf str;
default = { };
example = literalExample ''
{
"org.jitsi.jicofo.auth.URL" = "XMPP:jitsi-meet.example.com";
}
'';
description = ''
Contents of the <filename>sip-communicator.properties</filename> configuration file for jicofo.
'';
};
};
config = mkIf cfg.enable {
services.jicofo.config = mapAttrs (_: v: mkDefault v) {
"org.jitsi.jicofo.BRIDGE_MUC" = cfg.bridgeMuc;
};
users.groups.jitsi-meet = {};
systemd.services.jicofo = let
jicofoProps = {
"-Dnet.java.sip.communicator.SC_HOME_DIR_LOCATION" = "/etc/jitsi";
"-Dnet.java.sip.communicator.SC_HOME_DIR_NAME" = "jicofo";
"-Djava.util.logging.config.file" = "/etc/jitsi/jicofo/logging.properties";
};
in
{
description = "JItsi COnference FOcus";
wantedBy = [ "multi-user.target" ];
after = [ "network.target" ];
restartTriggers = [
config.environment.etc."jitsi/jicofo/sip-communicator.properties".source
];
environment.JAVA_SYS_PROPS = concatStringsSep " " (mapAttrsToList (k: v: "${k}=${toString v}") jicofoProps);
script = ''
${pkgs.jicofo}/bin/jicofo \
--host=${cfg.xmppHost} \
--domain=${if cfg.xmppDomain == null then cfg.xmppHost else cfg.xmppDomain} \
--secret=$(cat ${cfg.componentPasswordFile}) \
--user_name=${cfg.userName} \
--user_domain=${cfg.userDomain} \
--user_password=$(cat ${cfg.userPasswordFile})
'';
serviceConfig = {
Type = "exec";
DynamicUser = true;
User = "jicofo";
Group = "jitsi-meet";
CapabilityBoundingSet = "";
NoNewPrivileges = true;
ProtectSystem = "strict";
ProtectHome = true;
PrivateTmp = true;
PrivateDevices = true;
ProtectHostname = true;
ProtectKernelTunables = true;
ProtectKernelModules = true;
ProtectControlGroups = true;
RestrictAddressFamilies = [ "AF_INET" "AF_INET6" "AF_UNIX" ];
RestrictNamespaces = true;
LockPersonality = true;
RestrictRealtime = true;
RestrictSUIDSGID = true;
};
};
environment.etc."jitsi/jicofo/sip-communicator.properties".source =
pkgs.writeText "sip-communicator.properties" (
generators.toKeyValue {} cfg.config
);
environment.etc."jitsi/jicofo/logging.properties".source =
mkDefault "${pkgs.jicofo}/etc/jitsi/jicofo/logging.properties-journal";
};
meta.maintainers = with lib.maintainers; [ ];
}

View File

@ -0,0 +1,276 @@
{ config, lib, pkgs, ... }:
with lib;
let
cfg = config.services.jitsi-videobridge;
attrsToArgs = a: concatStringsSep " " (mapAttrsToList (k: v: "${k}=${toString v}") a);
# HOCON is a JSON superset that videobridge2 uses for configuration.
# It can substitute environment variables which we use for passwords here.
# https://github.com/lightbend/config/blob/master/README.md
#
# Substitution for environment variable FOO is represented as attribute set
# { __hocon_envvar = "FOO"; }
toHOCON = x: if isAttrs x && x ? __hocon_envvar then ("\${" + x.__hocon_envvar + "}")
else if isAttrs x then "{${ concatStringsSep "," (mapAttrsToList (k: v: ''"${k}":${toHOCON v}'') x) }}"
else if isList x then "[${ concatMapStringsSep "," toHOCON x }]"
else builtins.toJSON x;
# We're passing passwords in environment variables that have names generated
# from an attribute name, which may not be a valid bash identifier.
toVarName = s: "XMPP_PASSWORD_" + stringAsChars (c: if builtins.match "[A-Za-z0-9]" c != null then c else "_") s;
defaultJvbConfig = {
videobridge = {
ice = {
tcp = {
enabled = true;
port = 4443;
};
udp.port = 10000;
};
stats = {
enabled = true;
transports = [ { type = "muc"; } ];
};
apis.xmpp-client.configs = flip mapAttrs cfg.xmppConfigs (name: xmppConfig: {
hostname = xmppConfig.hostName;
domain = xmppConfig.domain;
username = xmppConfig.userName;
password = { __hocon_envvar = toVarName name; };
muc_jids = xmppConfig.mucJids;
muc_nickname = xmppConfig.mucNickname;
disable_certificate_verification = xmppConfig.disableCertificateVerification;
});
};
};
# Allow overriding leaves of the default config despite types.attrs not doing any merging.
jvbConfig = recursiveUpdate defaultJvbConfig cfg.config;
in
{
options.services.jitsi-videobridge = with types; {
enable = mkEnableOption "Jitsi Videobridge, a WebRTC compatible video router";
config = mkOption {
type = attrs;
default = { };
example = literalExample ''
{
videobridge = {
ice.udp.port = 5000;
websockets = {
enabled = true;
server-id = "jvb1";
};
};
}
'';
description = ''
Videobridge configuration.
See <link xlink:href="https://github.com/jitsi/jitsi-videobridge/blob/master/src/main/resources/reference.conf" />
for default configuration with comments.
'';
};
xmppConfigs = mkOption {
description = ''
XMPP servers to connect to.
See <link xlink:href="https://github.com/jitsi/jitsi-videobridge/blob/master/doc/muc.md" /> for more information.
'';
default = { };
example = literalExample ''
{
"localhost" = {
hostName = "localhost";
userName = "jvb";
domain = "auth.xmpp.example.org";
passwordFile = "/var/lib/jitsi-meet/videobridge-secret";
mucJids = "jvbbrewery@internal.xmpp.example.org";
};
}
'';
type = attrsOf (submodule ({ name, ... }: {
options = {
hostName = mkOption {
type = str;
example = "xmpp.example.org";
description = ''
Hostname of the XMPP server to connect to. Name of the attribute set is used by default.
'';
};
domain = mkOption {
type = nullOr str;
default = null;
example = "auth.xmpp.example.org";
description = ''
Domain part of JID of the XMPP user, if it is different from hostName.
'';
};
userName = mkOption {
type = str;
default = "jvb";
description = ''
User part of the JID.
'';
};
passwordFile = mkOption {
type = str;
example = "/run/keys/jitsi-videobridge-xmpp1";
description = ''
File containing the password for the user.
'';
};
mucJids = mkOption {
type = str;
example = "jvbbrewery@internal.xmpp.example.org";
description = ''
JID of the MUC to join. JiCoFo needs to be configured to join the same MUC.
'';
};
mucNickname = mkOption {
# Upstream DEBs use UUID, let's use hostname instead.
type = str;
description = ''
Videobridges use the same XMPP account and need to be distinguished by the
nickname (aka resource part of the JID). By default, system hostname is used.
'';
};
disableCertificateVerification = mkOption {
type = bool;
default = false;
description = ''
Whether to skip validation of the server's certificate.
'';
};
};
config = {
hostName = mkDefault name;
mucNickname = mkDefault (builtins.replaceStrings [ "." ] [ "-" ] (
config.networking.hostName + optionalString (config.networking.domain != null) ".${config.networking.domain}"
));
};
}));
};
nat = {
localAddress = mkOption {
type = nullOr str;
default = null;
example = "192.168.1.42";
description = ''
Local address when running behind NAT.
'';
};
publicAddress = mkOption {
type = nullOr str;
default = null;
example = "1.2.3.4";
description = ''
Public address when running behind NAT.
'';
};
};
extraProperties = mkOption {
type = attrsOf str;
default = { };
description = ''
Additional Java properties passed to jitsi-videobridge.
'';
};
openFirewall = mkOption {
type = bool;
default = false;
description = ''
Whether to open ports in the firewall for the videobridge.
'';
};
};
config = mkIf cfg.enable {
users.groups.jitsi-meet = {};
services.jitsi-videobridge.extraProperties = optionalAttrs (cfg.nat.localAddress != null) {
"org.ice4j.ice.harvest.NAT_HARVESTER_LOCAL_ADDRESS" = cfg.nat.localAddress;
"org.ice4j.ice.harvest.NAT_HARVESTER_PUBLIC_ADDRESS" = cfg.nat.publicAddress;
};
systemd.services.jitsi-videobridge2 = let
jvbProps = {
"-Dnet.java.sip.communicator.SC_HOME_DIR_LOCATION" = "/etc/jitsi";
"-Dnet.java.sip.communicator.SC_HOME_DIR_NAME" = "videobridge";
"-Djava.util.logging.config.file" = "/etc/jitsi/videobridge/logging.properties";
"-Dconfig.file" = pkgs.writeText "jvb.conf" (toHOCON jvbConfig);
} // (mapAttrs' (k: v: nameValuePair "-D${k}" v) cfg.extraProperties);
in
{
aliases = [ "jitsi-videobridge.service" ];
description = "Jitsi Videobridge";
after = [ "network.target" ];
wantedBy = [ "multi-user.target" ];
environment.JAVA_SYS_PROPS = attrsToArgs jvbProps;
script = (concatStrings (mapAttrsToList (name: xmppConfig:
"export ${toVarName name}=$(cat ${xmppConfig.passwordFile})\n"
) cfg.xmppConfigs))
+ ''
${pkgs.jitsi-videobridge}/bin/jitsi-videobridge --apis=none
'';
serviceConfig = {
Type = "exec";
DynamicUser = true;
User = "jitsi-videobridge";
Group = "jitsi-meet";
CapabilityBoundingSet = "";
NoNewPrivileges = true;
ProtectSystem = "strict";
ProtectHome = true;
PrivateTmp = true;
PrivateDevices = true;
ProtectHostname = true;
ProtectKernelTunables = true;
ProtectKernelModules = true;
ProtectControlGroups = true;
RestrictAddressFamilies = [ "AF_INET" "AF_INET6" "AF_UNIX" ];
RestrictNamespaces = true;
LockPersonality = true;
RestrictRealtime = true;
RestrictSUIDSGID = true;
TasksMax = 65000;
LimitNPROC = 65000;
LimitNOFILE = 65000;
};
};
environment.etc."jitsi/videobridge/logging.properties".source =
mkDefault "${pkgs.jitsi-videobridge}/etc/jitsi/videobridge/logging.properties-journal";
# (from videobridge2 .deb)
# this sets the max, so that we can bump the JVB UDP single port buffer size.
boot.kernel.sysctl."net.core.rmem_max" = mkDefault 10485760;
boot.kernel.sysctl."net.core.netdev_max_backlog" = mkDefault 100000;
networking.firewall.allowedTCPPorts = mkIf cfg.openFirewall
[ jvbConfig.videobridge.ice.tcp.port ];
networking.firewall.allowedUDPPorts = mkIf cfg.openFirewall
[ jvbConfig.videobridge.ice.udp.port ];
assertions = [{
message = "publicAddress must be set if and only if localAddress is set";
assertion = (cfg.nat.publicAddress == null) == (cfg.nat.localAddress == null);
}];
};
meta.maintainers = with lib.maintainers; [ ];
}

View File

@ -48,6 +48,14 @@ in
'';
};
rsaPrivateKeyFile = mkOption {
default = null;
type = types.nullOr types.path;
description = ''
Path of the private RSA keyfile.
'';
};
debugLevel = mkOption {
default = 0;
type = types.addCheck types.int (l: l >= 0 && l <= 5);
@ -139,6 +147,7 @@ in
Name = ${if data.name == null then "$HOST" else data.name}
DeviceType = ${data.interfaceType}
${optionalString (data.ed25519PrivateKeyFile != null) "Ed25519PrivateKeyFile = ${data.ed25519PrivateKeyFile}"}
${optionalString (data.rsaPrivateKeyFile != null) "PrivateKeyFile = ${data.rsaPrivateKeyFile}"}
${optionalString (data.listenAddress != null) "ListenAddress = ${data.listenAddress}"}
${optionalString (data.bindToAddress != null) "BindToAddress = ${data.bindToAddress}"}
Interface = tinc.${network}
@ -170,12 +179,15 @@ in
# Determine how we should generate our keys
if type tinc >/dev/null 2>&1; then
# Tinc 1.1+ uses the tinc helper application for key generation
${if data.ed25519PrivateKeyFile != null then " # Keyfile managed by nix" else ''
${if data.ed25519PrivateKeyFile != null then " # ed25519 Keyfile managed by nix" else ''
# Prefer ED25519 keys (only in 1.1+)
[ -f "/etc/tinc/${network}/ed25519_key.priv" ] || tinc -n ${network} generate-ed25519-keys
''}
# Otherwise use RSA keys
${if data.rsaPrivateKeyFile != null then " # RSA Keyfile managed by nix" else ''
[ -f "/etc/tinc/${network}/rsa_key.priv" ] || tinc -n ${network} generate-rsa-keys 4096
''}
# In case there isn't anything to do
true
else
# Tinc 1.0 uses the tincd application
[ -f "/etc/tinc/${network}/rsa_key.priv" ] || tincd -n ${network} -K 4096

View File

@ -321,7 +321,7 @@ in
enable = true;
virtualHosts = mapAttrs (hostName: cfg: mkMerge [ cfg.nginx {
root = mkForce "${pkg hostName cfg}/share/dokuwiki";
extraConfig = "fastcgi_param HTTPS on;";
extraConfig = lib.optionalString (cfg.nginx.addSSL || cfg.nginx.forceSSL || cfg.nginx.onlySSL || cfg.nginx.enableACME) "fastcgi_param HTTPS on;";
locations."~ /(conf/|bin/|inc/|install.php)" = {
extraConfig = "deny all;";
@ -359,7 +359,7 @@ in
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param REDIRECT_STATUS 200;
fastcgi_pass unix:${config.services.phpfpm.pools."dokuwiki-${hostName}".socket};
fastcgi_param HTTPS on;
${lib.optionalString (cfg.nginx.addSSL || cfg.nginx.forceSSL || cfg.nginx.onlySSL || cfg.nginx.enableACME) "fastcgi_param HTTPS on;"}
'';
};
}]) eachSite;

View File

@ -0,0 +1,333 @@
{ config, lib, pkgs, ... }:
with lib;
let
cfg = config.services.jitsi-meet;
# The configuration files are JS of format "var <<string>> = <<JSON>>;". In order to
# override only some settings, we need to extract the JSON, use jq to merge it with
# the config provided by user, and then reconstruct the file.
overrideJs =
source: varName: userCfg: appendExtra:
let
extractor = pkgs.writeText "extractor.js" ''
var fs = require("fs");
eval(fs.readFileSync(process.argv[2], 'utf8'));
process.stdout.write(JSON.stringify(eval(process.argv[3])));
'';
userJson = pkgs.writeText "user.json" (builtins.toJSON userCfg);
in (pkgs.runCommand "${varName}.js" { } ''
${pkgs.nodejs}/bin/node ${extractor} ${source} ${varName} > default.json
(
echo "var ${varName} = "
${pkgs.jq}/bin/jq -s '.[0] * .[1]' default.json ${userJson}
echo ";"
echo ${escapeShellArg appendExtra}
) > $out
'');
# Essential config - it's probably not good to have these as option default because
# types.attrs doesn't do merging. Let's merge explicitly, can still be overriden if
# user desires.
defaultCfg = {
hosts = {
domain = cfg.hostName;
muc = "conference.${cfg.hostName}";
focus = "focus.${cfg.hostName}";
};
bosh = "//${cfg.hostName}/http-bind";
};
in
{
options.services.jitsi-meet = with types; {
enable = mkEnableOption "Jitsi Meet - Secure, Simple and Scalable Video Conferences";
hostName = mkOption {
type = str;
example = "meet.example.org";
description = ''
Hostname of the Jitsi Meet instance.
'';
};
config = mkOption {
type = attrs;
default = { };
example = literalExample ''
{
enableWelcomePage = false;
defaultLang = "fi";
}
'';
description = ''
Client-side web application settings that override the defaults in <filename>config.js</filename>.
See <link xlink:href="https://github.com/jitsi/jitsi-meet/blob/master/config.js" /> for default
configuration with comments.
'';
};
extraConfig = mkOption {
type = lines;
default = "";
description = ''
Text to append to <filename>config.js</filename> web application config file.
Can be used to insert JavaScript logic to determine user's region in cascading bridges setup.
'';
};
interfaceConfig = mkOption {
type = attrs;
default = { };
example = literalExample ''
{
SHOW_JITSI_WATERMARK = false;
SHOW_WATERMARK_FOR_GUESTS = false;
}
'';
description = ''
Client-side web-app interface settings that override the defaults in <filename>interface_config.js</filename>.
See <link xlink:href="https://github.com/jitsi/jitsi-meet/blob/master/interface_config.js" /> for
default configuration with comments.
'';
};
videobridge = {
enable = mkOption {
type = bool;
default = true;
description = ''
Whether to enable Jitsi Videobridge instance and configure it to connect to Prosody.
Additional configuration is possible with <option>services.jitsi-videobridge</option>.
'';
};
passwordFile = mkOption {
type = nullOr str;
default = null;
example = "/run/keys/videobridge";
description = ''
File containing password to the Prosody account for videobridge.
If <literal>null</literal>, a file with password will be generated automatically. Setting
this option is useful if you plan to connect additional videobridges to the XMPP server.
'';
};
};
jicofo.enable = mkOption {
type = bool;
default = true;
description = ''
Whether to enable JiCoFo instance and configure it to connect to Prosody.
Additional configuration is possible with <option>services.jicofo</option>.
'';
};
nginx.enable = mkOption {
type = bool;
default = true;
description = ''
Whether to enable nginx virtual host that will serve the javascript application and act as
a proxy for the XMPP server. Further nginx configuration can be done by adapting
<option>services.nginx.virtualHosts.&lt;hostName&gt;</option>.
When this is enabled, ACME will be used to retrieve a TLS certificate by default. To disable
this, set the <option>services.nginx.virtualHosts.&lt;hostName&gt;.enableACME</option> to
<literal>false</literal> and if appropriate do the same for
<option>services.nginx.virtualHosts.&lt;hostName&gt;.forceSSL</option>.
'';
};
prosody.enable = mkOption {
type = bool;
default = true;
description = ''
Whether to configure Prosody to relay XMPP messages between Jitsi Meet components. Turn this
off if you want to configure it manually.
'';
};
};
config = mkIf cfg.enable {
services.prosody = mkIf cfg.prosody.enable {
enable = mkDefault true;
xmppComplianceSuite = mkDefault false;
modules = {
admin_adhoc = mkDefault false;
bosh = mkDefault true;
ping = mkDefault true;
roster = mkDefault true;
saslauth = mkDefault true;
tls = mkDefault true;
};
muc = [
{
domain = "conference.${cfg.hostName}";
name = "Jitsi Meet MUC";
roomLocking = false;
roomDefaultPublicJids = true;
extraConfig = ''
storage = "memory"
'';
}
{
domain = "internal.${cfg.hostName}";
name = "Jitsi Meet Videobridge MUC";
extraConfig = ''
storage = "memory"
admins = { "focus@auth.${cfg.hostName}", "jvb@auth.${cfg.hostName}" }
'';
#-- muc_room_cache_size = 1000
}
];
extraModules = [ "pubsub" ];
extraConfig = mkAfter ''
Component "focus.${cfg.hostName}"
component_secret = os.getenv("JICOFO_COMPONENT_SECRET")
'';
virtualHosts.${cfg.hostName} = {
enabled = true;
domain = cfg.hostName;
extraConfig = ''
authentication = "anonymous"
c2s_require_encryption = false
admins = { "focus@auth.${cfg.hostName}" }
'';
ssl = {
cert = "/var/lib/jitsi-meet/jitsi-meet.crt";
key = "/var/lib/jitsi-meet/jitsi-meet.key";
};
};
virtualHosts."auth.${cfg.hostName}" = {
enabled = true;
domain = "auth.${cfg.hostName}";
extraConfig = ''
authentication = "internal_plain"
'';
ssl = {
cert = "/var/lib/jitsi-meet/jitsi-meet.crt";
key = "/var/lib/jitsi-meet/jitsi-meet.key";
};
};
};
systemd.services.prosody.serviceConfig = mkIf cfg.prosody.enable {
EnvironmentFile = [ "/var/lib/jitsi-meet/secrets-env" ];
SupplementaryGroups = [ "jitsi-meet" ];
};
users.groups.jitsi-meet = {};
systemd.tmpfiles.rules = [
"d '/var/lib/jitsi-meet' 0750 root jitsi-meet - -"
];
systemd.services.jitsi-meet-init-secrets = {
wantedBy = [ "multi-user.target" ];
before = [ "jicofo.service" "jitsi-videobridge2.service" ] ++ (optional cfg.prosody.enable "prosody.service");
serviceConfig = {
Type = "oneshot";
};
script = let
secrets = [ "jicofo-component-secret" "jicofo-user-secret" ] ++ (optional (cfg.videobridge.passwordFile == null) "videobridge-secret");
videobridgeSecret = if cfg.videobridge.passwordFile != null then cfg.videobridge.passwordFile else "/var/lib/jitsi-meet/videobridge-secret";
in
''
cd /var/lib/jitsi-meet
${concatMapStringsSep "\n" (s: ''
if [ ! -f ${s} ]; then
tr -dc a-zA-Z0-9 </dev/urandom | head -c 64 > ${s}
chown root:jitsi-meet ${s}
chmod 640 ${s}
fi
'') secrets}
# for easy access in prosody
echo "JICOFO_COMPONENT_SECRET=$(cat jicofo-component-secret)" > secrets-env
chown root:jitsi-meet secrets-env
chmod 640 secrets-env
''
+ optionalString cfg.prosody.enable ''
${config.services.prosody.package}/bin/prosodyctl register focus auth.${cfg.hostName} "$(cat /var/lib/jitsi-meet/jicofo-user-secret)"
${config.services.prosody.package}/bin/prosodyctl register jvb auth.${cfg.hostName} "$(cat ${videobridgeSecret})"
# generate self-signed certificates
if [ ! -f /var/lib/jitsi-meet.crt ]; then
${getBin pkgs.openssl}/bin/openssl req \
-x509 \
-newkey rsa:4096 \
-keyout /var/lib/jitsi-meet/jitsi-meet.key \
-out /var/lib/jitsi-meet/jitsi-meet.crt \
-days 36500 \
-nodes \
-subj '/CN=${cfg.hostName}/CN=auth.${cfg.hostName}'
chmod 640 /var/lib/jitsi-meet/jitsi-meet.{crt,key}
chown root:jitsi-meet /var/lib/jitsi-meet/jitsi-meet.{crt,key}
fi
'';
};
services.nginx = mkIf cfg.nginx.enable {
enable = mkDefault true;
virtualHosts.${cfg.hostName} = {
enableACME = mkDefault true;
forceSSL = mkDefault true;
root = pkgs.jitsi-meet;
extraConfig = ''
ssi on;
'';
locations."@root_path".extraConfig = ''
rewrite ^/(.*)$ / break;
'';
locations."~ ^/([^/\\?&:'\"]+)$".tryFiles = "$uri @root_path";
locations."=/http-bind" = {
proxyPass = "http://localhost:5280/http-bind";
extraConfig = ''
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $host;
'';
};
locations."=/external_api.js" = mkDefault {
alias = "${pkgs.jitsi-meet}/libs/external_api.min.js";
};
locations."=/config.js" = mkDefault {
alias = overrideJs "${pkgs.jitsi-meet}/config.js" "config" (recursiveUpdate defaultCfg cfg.config) cfg.extraConfig;
};
locations."=/interface_config.js" = mkDefault {
alias = overrideJs "${pkgs.jitsi-meet}/interface_config.js" "interfaceConfig" cfg.interfaceConfig "";
};
};
};
services.jitsi-videobridge = mkIf cfg.videobridge.enable {
enable = true;
xmppConfigs."localhost" = {
userName = "jvb";
domain = "auth.${cfg.hostName}";
passwordFile = "/var/lib/jitsi-meet/videobridge-secret";
mucJids = "jvbbrewery@internal.${cfg.hostName}";
disableCertificateVerification = true;
};
};
services.jicofo = mkIf cfg.jicofo.enable {
enable = true;
xmppHost = "localhost";
xmppDomain = cfg.hostName;
userDomain = "auth.${cfg.hostName}";
userName = "focus";
userPasswordFile = "/var/lib/jitsi-meet/jicofo-user-secret";
componentPasswordFile = "/var/lib/jitsi-meet/jicofo-component-secret";
bridgeMuc = "jvbbrewery@internal.${cfg.hostName}";
config = {
"org.jitsi.jicofo.ALWAYS_TRUST_MODE_ENABLED" = "true";
};
};
};
meta.maintainers = with lib.maintainers; [ ];
}

View File

@ -139,7 +139,7 @@ in
boot.initrd.postMountCommands = mkIf cfg.flushBeforeStage2 ''
for iface in $ifaces; do
ip address flush "$iface"
ip link down "$iface"
ip link set "$iface" down
done
'';

View File

@ -56,6 +56,7 @@ let
bootloaderId = if args.efiBootloaderId == null then "NixOS${efiSysMountPoint'}" else args.efiBootloaderId;
timeout = if config.boot.loader.timeout == null then -1 else config.boot.loader.timeout;
users = if cfg.users == {} || cfg.version != 1 then cfg.users else throw "GRUB version 1 does not support user accounts.";
theme = f cfg.theme;
inherit efiSysMountPoint;
inherit (args) devices;
inherit (efi) canTouchEfiVariables;
@ -426,6 +427,19 @@ in
'';
};
theme = mkOption {
type = types.nullOr types.path;
example = literalExample "pkgs.nixos-grub2-theme";
default = null;
description = ''
Grub theme to be used.
<note><para>
This options has no effect for GRUB 1.
</para></note>
'';
};
splashMode = mkOption {
type = types.enum [ "normal" "stretch" ];
default = "stretch";
@ -697,7 +711,7 @@ in
in pkgs.writeScript "install-grub.sh" (''
#!${pkgs.runtimeShell}
set -e
export PERL5LIB=${with pkgs.perlPackages; makePerlPath [ FileSlurp XMLLibXML XMLSAX XMLSAXBase ListCompare JSON ]}
export PERL5LIB=${with pkgs.perlPackages; makePerlPath [ FileSlurp FileCopyRecursive XMLLibXML XMLSAX XMLSAXBase ListCompare JSON ]}
${optionalString cfg.enableCryptodisk "export GRUB_ENABLE_CRYPTODISK=y"}
'' + flip concatMapStrings cfg.mirroredBoots (args: ''
${pkgs.perl}/bin/perl ${install-grub-pl} ${grubConfig args} $@

View File

@ -6,9 +6,11 @@ use File::Basename;
use File::Path;
use File::stat;
use File::Copy;
use File::Copy::Recursive qw(rcopy pathrm);
use File::Slurp;
use File::Temp;
use JSON;
use File::Find;
require List::Compare;
use POSIX;
use Cwd;
@ -82,6 +84,7 @@ my $gfxpayloadBios = get("gfxpayloadBios");
my $bootloaderId = get("bootloaderId");
my $forceInstall = get("forceInstall");
my $font = get("font");
my $theme = get("theme");
$ENV{'PATH'} = get("path");
die "unsupported GRUB version\n" if $grubVersion != 1 && $grubVersion != 2;
@ -370,6 +373,28 @@ else {
fi
";
}
rmtree("$bootPath/theme") or die "cannot clean up theme folder in $bootPath\n" if -e "$bootPath/theme";
if ($theme) {
# Copy theme
rcopy($theme, "$bootPath/theme") or die "cannot copy $theme to $bootPath\n";
$conf .= "
# Sets theme.
set theme=" . ($grubBoot->path eq "/" ? "" : $grubBoot->path) . "/theme/theme.txt
export theme
# Load theme fonts, if any
";
find( { wanted => sub {
if ($_ =~ /\.pf2$/i) {
$font = File::Spec->abs2rel($File::Find::name, $theme);
$conf .= "
loadfont " . ($grubBoot->path eq "/" ? "" : $grubBoot->path) . "/theme/$font
";
}
}, no_chdir => 1 }, $theme );
}
}
$conf .= "$extraConfig\n";

View File

@ -58,6 +58,35 @@ in {
Run <literal>VBoxManage modifyvm --help</literal> to see more options.
'';
};
extraDisk = mkOption {
description = ''
Optional extra disk/hdd configuration.
The disk will be an 'ext4' partition on a separate VMDK file.
'';
default = null;
example = {
label = "storage";
mountPoint = "/home/demo/storage";
size = 100 * 1024;
};
type = types.nullOr (types.submodule {
options = {
size = mkOption {
type = types.int;
description = "Size in MiB";
};
label = mkOption {
type = types.str;
default = "vm-extra-storage";
description = "Label for the disk partition";
};
mountPoint = mkOption {
type = types.str;
description = "Path where to mount this disk.";
};
};
});
};
};
};
@ -96,6 +125,20 @@ in {
echo "creating VirtualBox pass-through disk wrapper (no copying involved)..."
VBoxManage internalcommands createrawvmdk -filename disk.vmdk -rawdisk $diskImage
${optionalString (cfg.extraDisk != null) ''
echo "creating extra disk: data-disk.raw"
dataDiskImage=data-disk.raw
truncate -s ${toString cfg.extraDisk.size}M $dataDiskImage
parted --script $dataDiskImage -- \
mklabel msdos \
mkpart primary ext4 1MiB -1
eval $(partx $dataDiskImage -o START,SECTORS --nr 1 --pairs)
mkfs.ext4 -F -L ${cfg.extraDisk.label} $dataDiskImage -E offset=$(sectorsToBytes $START) $(sectorsToKilobytes $SECTORS)K
echo "creating extra disk: data-disk.vmdk"
VBoxManage internalcommands createrawvmdk -filename data-disk.vmdk -rawdisk $dataDiskImage
''}
echo "creating VirtualBox VM..."
vmName="${cfg.vmName}";
VBoxManage createvm --name "$vmName" --register \
@ -106,6 +149,10 @@ in {
VBoxManage storagectl "$vmName" --name SATA --add sata --portcount 4 --bootable on --hostiocache on
VBoxManage storageattach "$vmName" --storagectl SATA --port 0 --device 0 --type hdd \
--medium disk.vmdk
${optionalString (cfg.extraDisk != null) ''
VBoxManage storageattach "$vmName" --storagectl SATA --port 1 --device 0 --type hdd \
--medium data-disk.vmdk
''}
echo "exporting VirtualBox VM..."
mkdir -p $out
@ -119,11 +166,19 @@ in {
'';
};
fileSystems."/" = {
device = "/dev/disk/by-label/nixos";
autoResize = true;
fsType = "ext4";
};
fileSystems = {
"/" = {
device = "/dev/disk/by-label/nixos";
autoResize = true;
fsType = "ext4";
};
} // (lib.optionalAttrs (cfg.extraDisk != null) {
${cfg.extraDisk.mountPoint} = {
device = "/dev/disk/by-label/" + cfg.extraDisk.label;
autoResize = true;
fsType = "ext4";
};
});
boot.growPartition = true;
boot.loader.grub.device = "/dev/sda";

View File

@ -162,6 +162,7 @@ in
jellyfin = handleTest ./jellyfin.nix {};
jenkins = handleTest ./jenkins.nix {};
jirafeau = handleTest ./jirafeau.nix {};
jitsi-meet = handleTest ./jitsi-meet.nix {};
k3s = handleTest ./k3s.nix {};
kafka = handleTest ./kafka.nix {};
keepalived = handleTest ./keepalived.nix {};
@ -310,6 +311,7 @@ in
simple = handleTest ./simple.nix {};
slurm = handleTest ./slurm.nix {};
smokeping = handleTest ./smokeping.nix {};
snapcast = handleTest ./snapcast.nix {};
snapper = handleTest ./snapper.nix {};
sogo = handleTest ./sogo.nix {};
solr = handleTest ./solr.nix {};
@ -369,6 +371,7 @@ in
yabar = handleTest ./yabar.nix {};
yggdrasil = handleTest ./yggdrasil.nix {};
zfs = handleTest ./zfs.nix {};
zigbee2mqtt = handleTest ./zigbee2mqtt.nix {};
zoneminder = handleTest ./zoneminder.nix {};
zookeeper = handleTest ./zookeeper.nix {};
zsh-history = handleTest ./zsh-history.nix {};

View File

@ -13,7 +13,7 @@ import ./make-test-python.nix ({ pkgs, ... }: {
machine.succeed("modprobe bcachefs")
machine.succeed("bcachefs version")
machine.succeed("ls /dev")
machine.succeed(
"mkdir /tmp/mnt",
"udevadm settle",

View File

@ -43,7 +43,7 @@ in {
nodes = {
client = { ... }: {
services.borgbackup.jobs = {
local = {
paths = dataDir;
repo = localRepo;

View File

@ -5,7 +5,7 @@ let
hostPort = 10080;
containerIp = "192.168.0.100";
containerPort = 80;
in
in
import ./make-test-python.nix ({ pkgs, ...} : {
name = "containers-portforward";

View File

@ -1,7 +1,7 @@
import ./make-test-python.nix (
{
nodes = {
router = {config, pkgs, ...}: {
router = {config, pkgs, ...}: {
config = {
# This machine simulates a router with IPv6 forwarding and a static IPv6 address.
boot.kernel.sysctl = {

View File

@ -16,10 +16,10 @@ import ./make-test.nix ({ pkgs, ...} : {
services.openssh.extraConfig = "PermitEmptyPasswords yes";
users.extraUsers.root.password = "";
};
};
};
testScript = ''
startAll;
$docker->waitForUnit("sockets.target");
$docker->succeed("docker run nix nix-store --version");
$docker->succeed("docker run bash bash --version");

View File

@ -37,6 +37,7 @@
};
services.postfix.enable = true;
nix = {
distributedBuilds = true;
buildMachines = [{
hostName = "localhost";
systems = [ system ];

View File

@ -0,0 +1,55 @@
import ./make-test-python.nix ({ pkgs, ... }: {
name = "jitsi-meet";
meta = with pkgs.stdenv.lib.maintainers; {
maintainers = [ mmilata ];
};
nodes = {
client = { nodes, pkgs, ... }: {
};
server = { config, pkgs, ... }: {
services.jitsi-meet = {
enable = true;
hostName = "server";
};
services.jitsi-videobridge.openFirewall = true;
networking.firewall.allowedTCPPorts = [ 80 443 ];
services.nginx.virtualHosts.server = {
enableACME = true;
forceSSL = true;
};
security.acme.email = "me@example.org";
security.acme.acceptTerms = true;
security.acme.server = "https://example.com"; # self-signed only
};
};
testScript = ''
server.wait_for_unit("jitsi-videobridge2.service")
server.wait_for_unit("jicofo.service")
server.wait_for_unit("nginx.service")
server.wait_for_unit("prosody.service")
server.wait_until_succeeds(
"journalctl -b -u jitsi-videobridge2 -o cat | grep -q 'Performed a successful health check'"
)
server.wait_until_succeeds(
"journalctl -b -u jicofo -o cat | grep -q 'connected .JID: focus@auth.server'"
)
server.wait_until_succeeds(
"journalctl -b -u prosody -o cat | grep -q 'Authenticated as focus@auth.server'"
)
server.wait_until_succeeds(
"journalctl -b -u prosody -o cat | grep -q 'focus.server:component: External component successfully authenticated'"
)
server.wait_until_succeeds(
"journalctl -b -u prosody -o cat | grep -q 'Authenticated as jvb@auth.server'"
)
client.wait_for_unit("network.target")
assert "<title>Jitsi Meet</title>" in client.succeed("curl -sSfkL http://server/")
'';
})

View File

@ -7,7 +7,7 @@ import ./make-test-python.nix ({ pkgs, ... }:
};
nodes =
{
{
client = { };
server =

View File

@ -45,7 +45,7 @@ import ./make-test-python.nix ({ pkgs, ... }:
node.start()
''
+ runMongoDBTest pkgs.mongodb-3_4
+ runMongoDBTest pkgs.mongodb-3_6
+ runMongoDBTest pkgs.mongodb-3_6
+ runMongoDBTest pkgs.mongodb-4_0
+ runMongoDBTest pkgs.mongodb-4_2
+ ''

View File

@ -3,7 +3,7 @@ import ../make-test-python.nix ({ pkgs, lib, ... }:
with lib;
let
krb5 =
krb5 =
{ enable = true;
domain_realm."nfs.test" = "NFS.TEST";
libdefaults.default_realm = "NFS.TEST";
@ -31,7 +31,7 @@ in
{
name = "nfsv4-with-kerberos";
nodes = {
client = { lib, ... }:
{ inherit krb5 users;

View File

@ -1,4 +1,4 @@
let
let
certs = import ./common/acme/server/snakeoil-certs.nix;
in
import ./make-test-python.nix {

View File

@ -1,4 +1,4 @@
let
let
certs = import ./common/acme/server/snakeoil-certs.nix;
in
import ./make-test-python.nix {

58
nixos/tests/snapcast.nix Normal file
View File

@ -0,0 +1,58 @@
import ./make-test-python.nix ({ pkgs, ...} :
let
port = 10004;
tcpPort = 10005;
httpPort = 10080;
in {
name = "snapcast";
meta = with pkgs.stdenv.lib.maintainers; {
maintainers = [ hexa ];
};
nodes = {
server = {
services.snapserver = {
enable = true;
port = port;
tcp.port = tcpPort;
http.port = httpPort;
streams = {
mpd = {
type = "pipe";
location = "/run/snapserver/mpd";
};
bluetooth = {
type = "pipe";
location = "/run/snapserver/bluetooth";
};
};
};
};
};
testScript = ''
import json
get_rpc_version = {"id": "1", "jsonrpc": "2.0", "method": "Server.GetRPCVersion"}
start_all()
server.wait_for_unit("snapserver.service")
server.wait_until_succeeds("ss -ntl | grep -q ${toString port}")
server.wait_until_succeeds("ss -ntl | grep -q ${toString tcpPort}")
server.wait_until_succeeds("ss -ntl | grep -q ${toString httpPort}")
with subtest("check that pipes are created"):
server.succeed("test -p /run/snapserver/mpd")
server.succeed("test -p /run/snapserver/bluetooth")
with subtest("test tcp json-rpc"):
server.succeed(f"echo '{json.dumps(get_rpc_version)}' | nc -w 1 localhost ${toString tcpPort}")
with subtest("test http json-rpc"):
server.succeed(
"curl --fail http://localhost:${toString httpPort}/jsonrpc -d '{json.dumps(get_rpc_version)}'"
)
'';
})

View File

@ -24,9 +24,8 @@ in {
testScript = ''
machine.wait_for_unit("syncthing-init.service")
config = machine.succeed("cat /var/lib/syncthing/.config/syncthing/config.xml")
assert "testFolder" in config
assert "${testId}" in config
'';
})

View File

@ -159,6 +159,8 @@ in {
node2.wait_for_unit("network.target")
node3.wait_for_unit("network.target")
# NOTE: please keep in mind that the trailing whitespaces in the following strings
# are intentional as the output is compared against the raw `iproute2`-output.
client_ipv4_table = """
192.168.1.2 dev vrf1 proto static metric 100
192.168.2.3 dev vrf2 proto static metric 100
@ -194,18 +196,16 @@ in {
client.succeed("ping -c5 192.168.1.2")
client.succeed("ping -c5 192.168.2.3")
# Test whether SSH through a VRF IP is possible.
# (Note: this seems to be an issue on Linux 5.x, so I decided to add this to
# ensure that we catch this when updating the default kernel).
# with subtest("tcp traffic through vrf works"):
# node1.wait_for_open_port(22)
# client.succeed(
# "cat ${snakeOilPrivateKey} > privkey.snakeoil"
# )
# client.succeed("chmod 600 privkey.snakeoil")
# client.succeed(
# "ssh -o UserKnownHostsFile=/dev/null -o StrictHostKeyChecking=no -i privkey.snakeoil root@192.168.1.2 true"
# )
# Test whether TCP through a VRF IP is possible.
with subtest("tcp traffic through vrf works"):
node1.wait_for_open_port(22)
client.succeed(
"cat ${snakeOilPrivateKey} > privkey.snakeoil"
)
client.succeed("chmod 600 privkey.snakeoil")
client.succeed(
"ulimit -l 2048; ip vrf exec vrf1 ssh -o UserKnownHostsFile=/dev/null -o StrictHostKeyChecking=no -i privkey.snakeoil root@192.168.1.2 true"
)
# Only configured routes through the VRF from the main routing table should
# work. Additional IPs are only reachable when binding to the vrf interface.

View File

@ -1,4 +1,4 @@
import ./make-test.nix ({ pkgs, ... }: let
import ./make-test-python.nix ({ pkgs, ... }: let
snakeOil = pkgs.runCommand "snakeoil-certs" {
outputs = [ "out" "cacert" "cert" "key" "crl" ];
buildInputs = [ pkgs.gnutls.bin ];
@ -105,187 +105,178 @@ in {
newServerSystem = nodes.newServer.config.system.build.toplevel;
switchToNewServer = "${newServerSystem}/bin/switch-to-configuration test";
in ''
sub su ($$) {
my ($user, $cmd) = @_;
my $esc = $cmd =~ s/'/'\\${"'"}'/gr;
return "su - $user -c '$esc'";
}
from shlex import quote
sub setupClientsFor ($$;$) {
my ($org, $user, $extraInit) = @_;
for my $client ($client1, $client2) {
$client->nest("initialize client for user $user", sub {
$client->succeed(
(su $user, "rm -rf /home/$user/.task"),
(su $user, "task rc.confirmation=no config confirmation no")
);
def su(user, cmd):
return f"su - {user} -c {quote(cmd)}"
my $exportinfo = $server->succeed(
"nixos-taskserver user export $org $user"
);
$exportinfo =~ s/'/'\\'''/g;
def no_extra_init(client, org, user):
pass
$client->nest("importing taskwarrior configuration", sub {
my $cmd = su $user, "eval '$exportinfo' >&2";
my ($status, $out) = $client->execute_($cmd);
if ($status != 0) {
$client->log("output: $out");
die "command `$cmd' did not succeed (exit code $status)\n";
}
});
eval { &$extraInit($client, $org, $user) };
def setup_clients_for(org, user, extra_init=no_extra_init):
for client in [client1, client2]:
with client.nested(f"initialize client for user {user}"):
client.succeed(
su(user, f"rm -rf /home/{user}/.task"),
su(user, "task rc.confirmation=no config confirmation no"),
)
$client->succeed(su $user,
"task config taskd.server server:${portStr} >&2"
);
exportinfo = server.succeed(f"nixos-taskserver user export {org} {user}")
$client->succeed(su $user, "task sync init >&2");
});
}
}
with client.nested("importing taskwarrior configuration"):
client.succeed(su(user, f"eval {quote(exportinfo)} >&2"))
sub restartServer {
$server->succeed("systemctl restart taskserver.service");
$server->waitForOpenPort(${portStr});
}
extra_init(client, org, user)
sub readdImperativeUser {
$server->nest("(re-)add imperative user bar", sub {
$server->execute("nixos-taskserver org remove imperativeOrg");
$server->succeed(
"nixos-taskserver org add imperativeOrg",
"nixos-taskserver user add imperativeOrg bar"
);
setupClientsFor "imperativeOrg", "bar";
});
}
client.succeed(su(user, "task config taskd.server server:${portStr} >&2"))
sub testSync ($) {
my $user = $_[0];
subtest "sync for user $user", sub {
$client1->succeed(su $user, "task add foo >&2");
$client1->succeed(su $user, "task sync >&2");
$client2->fail(su $user, "task list >&2");
$client2->succeed(su $user, "task sync >&2");
$client2->succeed(su $user, "task list >&2");
};
}
client.succeed(su(user, "task sync init >&2"))
def restart_server():
server.systemctl("restart taskserver.service")
server.wait_for_open_port(${portStr})
def re_add_imperative_user():
with server.nested("(re-)add imperative user bar"):
server.execute("nixos-taskserver org remove imperativeOrg")
server.succeed(
"nixos-taskserver org add imperativeOrg",
"nixos-taskserver user add imperativeOrg bar",
)
setup_clients_for("imperativeOrg", "bar")
def test_sync(user):
with subtest(f"sync for user {user}"):
client1.succeed(su(user, "task add foo >&2"))
client1.succeed(su(user, "task sync >&2"))
client2.fail(su(user, "task list >&2"))
client2.succeed(su(user, "task sync >&2"))
client2.succeed(su(user, "task list >&2"))
def check_client_cert(user):
# debug level 3 is a workaround for gnutls issue https://gitlab.com/gnutls/gnutls/-/issues/1040
cmd = (
f"gnutls-cli -d 3"
f" --x509cafile=/home/{user}/.task/keys/ca.cert"
f" --x509keyfile=/home/{user}/.task/keys/private.key"
f" --x509certfile=/home/{user}/.task/keys/public.cert"
f" --port=${portStr} server < /dev/null"
)
return su(user, cmd)
sub checkClientCert ($) {
my $user = $_[0];
# debug level 3 is a workaround for gnutls issue https://gitlab.com/gnutls/gnutls/-/issues/1040
my $cmd = "gnutls-cli -d 3".
" --x509cafile=/home/$user/.task/keys/ca.cert".
" --x509keyfile=/home/$user/.task/keys/private.key".
" --x509certfile=/home/$user/.task/keys/public.cert".
" --port=${portStr} server < /dev/null";
return su $user, $cmd;
}
# Explicitly start the VMs so that we don't accidentally start newServer
$server->start;
$client1->start;
$client2->start;
server.start()
client1.start()
client2.start()
$server->waitForUnit("taskserver.service");
server.wait_for_unit("taskserver.service")
$server->succeed(
"nixos-taskserver user list testOrganisation | grep -qxF alice",
"nixos-taskserver user list testOrganisation | grep -qxF foo",
"nixos-taskserver user list anotherOrganisation | grep -qxF bob"
);
server.succeed(
"nixos-taskserver user list testOrganisation | grep -qxF alice",
"nixos-taskserver user list testOrganisation | grep -qxF foo",
"nixos-taskserver user list anotherOrganisation | grep -qxF bob",
)
$server->waitForOpenPort(${portStr});
server.wait_for_open_port(${portStr})
$client1->waitForUnit("multi-user.target");
$client2->waitForUnit("multi-user.target");
client1.wait_for_unit("multi-user.target")
client2.wait_for_unit("multi-user.target")
setupClientsFor "testOrganisation", "alice";
setupClientsFor "testOrganisation", "foo";
setupClientsFor "anotherOrganisation", "bob";
setup_clients_for("testOrganisation", "alice")
setup_clients_for("testOrganisation", "foo")
setup_clients_for("anotherOrganisation", "bob")
testSync $_ for ("alice", "bob", "foo");
for user in ["alice", "bob", "foo"]:
test_sync(user)
$server->fail("nixos-taskserver user add imperativeOrg bar");
readdImperativeUser;
server.fail("nixos-taskserver user add imperativeOrg bar")
re_add_imperative_user()
testSync "bar";
test_sync("bar")
subtest "checking certificate revocation of user bar", sub {
$client1->succeed(checkClientCert "bar");
with subtest("checking certificate revocation of user bar"):
client1.succeed(check_client_cert("bar"))
$server->succeed("nixos-taskserver user remove imperativeOrg bar");
restartServer;
server.succeed("nixos-taskserver user remove imperativeOrg bar")
restart_server()
$client1->fail(checkClientCert "bar");
client1.fail(check_client_cert("bar"))
$client1->succeed(su "bar", "task add destroy everything >&2");
$client1->fail(su "bar", "task sync >&2");
};
client1.succeed(su("bar", "task add destroy everything >&2"))
client1.fail(su("bar", "task sync >&2"))
readdImperativeUser;
re_add_imperative_user()
subtest "checking certificate revocation of org imperativeOrg", sub {
$client1->succeed(checkClientCert "bar");
with subtest("checking certificate revocation of org imperativeOrg"):
client1.succeed(check_client_cert("bar"))
$server->succeed("nixos-taskserver org remove imperativeOrg");
restartServer;
server.succeed("nixos-taskserver org remove imperativeOrg")
restart_server()
$client1->fail(checkClientCert "bar");
client1.fail(check_client_cert("bar"))
$client1->succeed(su "bar", "task add destroy even more >&2");
$client1->fail(su "bar", "task sync >&2");
};
client1.succeed(su("bar", "task add destroy even more >&2"))
client1.fail(su("bar", "task sync >&2"))
readdImperativeUser;
re_add_imperative_user()
subtest "check whether declarative config overrides user bar", sub {
restartServer;
testSync "bar";
};
with subtest("check whether declarative config overrides user bar"):
restart_server()
test_sync("bar")
subtest "check manual configuration", sub {
# Remove the keys from automatic CA creation, to make sure the new
# generation doesn't use keys from before.
$server->succeed('rm -rf ${cfg.dataDir}/keys/* >&2');
$server->succeed('${switchToNewServer} >&2');
$server->waitForUnit("taskserver.service");
$server->waitForOpenPort(${portStr});
def init_manual_config(client, org, user):
cfgpath = f"/home/{user}/.task"
$server->succeed(
"nixos-taskserver org add manualOrg",
"nixos-taskserver user add manualOrg alice"
);
client.copy_from_host(
"${snakeOil.cacert}",
f"{cfgpath}/ca.cert",
)
for file in ["alice.key", "alice.cert"]:
client.copy_from_host(
f"${snakeOil}/{file}",
f"{cfgpath}/{file}",
)
setupClientsFor "manualOrg", "alice", sub {
my ($client, $org, $user) = @_;
my $cfgpath = "/home/$user/.task";
for file in [f"{user}.key", f"{user}.cert"]:
client.copy_from_host(
f"${snakeOil}/{file}",
f"{cfgpath}/{file}",
)
$client->copyFileFromHost("${snakeOil.cacert}", "$cfgpath/ca.cert");
for my $file ('alice.key', 'alice.cert') {
$client->copyFileFromHost("${snakeOil}/$file", "$cfgpath/$file");
}
client.succeed(
su("alice", f"task config taskd.ca {cfgpath}/ca.cert"),
su("alice", f"task config taskd.key {cfgpath}/{user}.key"),
su(user, f"task config taskd.certificate {cfgpath}/{user}.cert"),
)
for my $file ("$user.key", "$user.cert") {
$client->copyFileFromHost(
"${snakeOil}/$file", "$cfgpath/$file"
);
}
$client->copyFileFromHost(
"${snakeOil.cacert}", "$cfgpath/ca.cert"
);
$client->succeed(
(su "alice", "task config taskd.ca $cfgpath/ca.cert"),
(su "alice", "task config taskd.key $cfgpath/$user.key"),
(su $user, "task config taskd.certificate $cfgpath/$user.cert")
);
};
testSync "alice";
};
with subtest("check manual configuration"):
# Remove the keys from automatic CA creation, to make sure the new
# generation doesn't use keys from before.
server.succeed("rm -rf ${cfg.dataDir}/keys/* >&2")
server.succeed(
"${switchToNewServer} >&2"
)
server.wait_for_unit("taskserver.service")
server.wait_for_open_port(${portStr})
server.succeed(
"nixos-taskserver org add manualOrg",
"nixos-taskserver user add manualOrg alice",
)
setup_clients_for("manualOrg", "alice", init_manual_config)
test_sync("alice")
'';
})

View File

@ -44,7 +44,7 @@ import ./make-test-python.nix ({ ... }: {
configured.succeed(
"curl --fail -o /dev/null 127.0.0.1:3000 --user somelogin:somesecret"
)
with subtest("restart preserves changes"):
# given running wiki
default.wait_for_unit("tiddlywiki.service")

View File

@ -34,4 +34,4 @@ import ./make-test-python.nix ({ pkgs, ... }: {
"curl -L http://localhost:9090/metrics | grep 'promhttp_metric_handler_requests_total{code=\"500\"} 0'"
)
'';
})
})

View File

@ -55,13 +55,13 @@
}:
stdenv.mkDerivation rec {
pname = "ardour";
version = "6.0";
version = "6.2";
# don't fetch releases from the GitHub mirror, they are broken
src = fetchgit {
url = "git://git.ardour.org/ardour/ardour.git";
rev = version;
sha256 = "162jd96zahl05fdmjwvpdfjxbhd6ifbav6xqa0vv6rsdl4zk395q";
sha256 = "17jxbqavricy01x4ymq6d302djsqfnv84m7dm4fd8cpka0dqjp1y";
};
patches = [

View File

@ -2,13 +2,13 @@
stdenv.mkDerivation rec {
pname = "BJumblr";
version = "0.2";
version = "1.4.0";
src = fetchFromGitHub {
owner = "sjaehn";
repo = pname;
rev = "v${version}";
sha256 = "14z8113zkwykbhm1a8h2xs972dgifvlfij92b08jckyc7cbz84ys";
rev = version;
sha256 = "03x1gvri9yk000fvvc8zvvywf38cc41vkyhhp9xby71b23n5wbn0";
};
nativeBuildInputs = [ pkgconfig ];

View File

@ -3,7 +3,7 @@
stdenv.mkDerivation rec {
pname = "cava";
version = "0.7.1";
version = "0.7.2";
buildInputs = [
alsaLib
@ -16,7 +16,7 @@ stdenv.mkDerivation rec {
owner = "karlstav";
repo = "cava";
rev = version;
sha256 = "0p2g3xxl2n425bghs1qnff30jaj9cba94j2gbhgxmwaxhz26vbk7";
sha256 = "1chc08spjf5i17n8y48aqzdxsj8vvf0r2l62ldw2pqgw60dacvs1";
};
nativeBuildInputs = [ autoreconfHook ];

View File

@ -12,13 +12,13 @@
mkDerivation rec {
pname = "projectm";
version = "3.1.3";
version = "3.1.7";
src = fetchFromGitHub {
owner = "projectM-visualizer";
repo = "projectM";
rev = "v${version}";
sha256 = "1mjnahr694phksmvc069y89rv85s4l2z9fixkc3l1f5qj2vgn4sy";
sha256 = "1wm5fym6c1yb972pmil7j9axinqqwrj68cwd2sc7ky8c5z2fsdna";
};
nativeBuildInputs = [

View File

@ -2,13 +2,13 @@
stdenv.mkDerivation rec {
pname = "realTimeConfigQuickScan";
version = "unstable-2020-08-03";
version = "unstable-2020-07-23";
src = fetchFromGitHub {
owner = "raboof";
repo = pname;
rev = "4b482db17f8d8567ba0abf33459ceb5f756f088c";
sha256 = "00l69gzwla9gjv5kpklgxlwnl48wnh8h6w0k8i69qr2cxigg4rhj";
rev = "4697ba093d43d512b74a73b89531cb8c5adaa274";
sha256 = "16kanzp5i353x972zjkwgi3m8z90wc58613mlfzb0n01djdnm6k5";
};
buildInputs = [ perlPackages.perl makeWrapper ];
@ -16,28 +16,35 @@ stdenv.mkDerivation rec {
dontBuild = true;
installPhase = ''
runHook preInstall
mkdir -p $out/bin
mkdir -p $out/share/doc
mkdir -p $out/share/$pname
mkdir -p $out/share/doc/$pname
# Install Script Files:
# *.pm files
for i in *.pm; do
install -Dm 755 "$i" "$out/share/$i"
install -Dm 755 "$i" "$out/share/$pname/$i"
done
# Install doc files:
install -D COPYING "$out/share/doc/COPYING"
install -D README.md "$out/share/doc/README.md"
install -D COPYING "$out/share/doc/$pname/COPYING"
install -D README.md "$out/share/doc/$pname/README.md"
# Install Executable scripts:
install -Dm 755 realTimeConfigQuickScan.pl "$out/bin/realTimeConfigQuickScan"
install -Dm 755 QuickScan.pl "$out/bin/QuickScan"
wrapProgram $out/bin/realTimeConfigQuickScan \
--set PERL5LIB "$out/share"
wrapProgram $out/bin/QuickScan \
--set PERL5LIB "$out/share:${with perlPackages; makePerlPath [ Tk ]}"
runHook postInstall
'';
postFixup = ''
wrapProgram $out/bin/realTimeConfigQuickScan \
--set PERL5LIB "$out/share/$pname"
wrapProgram $out/bin/QuickScan \
--set PERL5LIB "$out/share/$pname:${with perlPackages; makePerlPath [ Tk ]}"
'';
meta = with stdenv.lib; {
description = "Linux configuration checker for systems to be used for real-time audio";
homepage = "https://github.com/raboof/realtimeconfigquickscan";
license = licenses.gpl2;
license = licenses.gpl2Plus;
maintainers = with maintainers; [ magnetophon ];
platforms = platforms.linux ;
};

View File

@ -1,5 +1,6 @@
{ stdenv, lib, fetchFromGitHub, cmake, pkgconfig
, alsaLib, asio, avahi, boost170, flac, libogg, libvorbis, soxr }:
, alsaLib, asio, avahi, boost170, flac, libogg, libvorbis, soxr
, nixosTests }:
let
@ -57,6 +58,8 @@ stdenv.mkDerivation rec {
cp -r ../doc/* ../*.md $out/share/doc/snapcast
'';
passthru.tests.snapcast = nixosTests.snapcast;
meta = with lib; {
description = "Synchronous multi-room audio player";
homepage = "https://github.com/badaix/snapcast";

View File

@ -35,23 +35,30 @@ let
gtk3 # Fix error: GLib-GIO-ERROR **: Settings schema 'org.gtk.Settings.FileChooser' is not installed
];
dontBuild = true;
dontConfigure = true;
unpackPhase = ''
ar p $src data.tar.xz | tar xJ ./usr/
'';
installPhase = ''
runHook preInstall
mkdir -p $out
mv usr/bin usr/share $out
rm -rf $out/share/lintian
runHook postInstall
'';
preFixup = ''
gappsWrapperArgs+=(
--prefix "PATH" : "${gvfs}/bin" \
--prefix "PATH" : "${gvfs}/bin"
)
'';
buildCommand = ''
mkdir -p $out/usr/
ar p $src data.tar.xz | tar -C $out -xJ ./usr
sed -i -e "s|Exec=.*$|Exec=$out/bin/${pname}|" $out/usr/share/applications/${pname}.desktop
mv $out/usr/* $out/
rm -r $out/share/lintian
rm -r $out/usr/
sed -i "s/${pname})/.${pname}-wrapped)/" $out/bin/${pname}
fixupPhase
postFixup = ''
share=$out/share/${pname}
patchelf --set-interpreter "$(cat $NIX_CC/nix-support/dynamic-linker)" \
@ -70,6 +77,8 @@ let
ln -s ${pkgs.git}/bin/git $dugite/git/libexec/git-core/git
find $share -name "*.node" -exec patchelf --set-rpath "${atomEnv.libPath}:$share" {} \;
sed -i -e "s|Exec=.*$|Exec=$out/bin/${pname}|" $out/share/applications/${pname}.desktop
'';
meta = with stdenv.lib; {

View File

@ -8,13 +8,13 @@
stdenv.mkDerivation rec {
pname = "lite";
version = "1.06";
version = "1.11";
src = fetchFromGitHub {
owner = "rxi";
repo = pname;
rev = "v${version}";
sha256 = "1lw4a6xv8pdlgwnhh870caij4iyzxdyjw4qmm4fswja9mbqkj32f";
sha256 = "0wxqfb4ly8g7w5qph76xys95b55ackkags8jgd1nasmiyi8gcd5a";
};
nativeBuildInputs = [ makeWrapper pkg-config ];

View File

@ -116,11 +116,14 @@ let
in
symlinkJoin {
name = "neovim-${stdenv.lib.getVersion neovim}";
# Remove the symlinks created by symlinkJoin which we need to perform
# extra actions upon
postBuild = ''
# Remove the symlinks created by symlinkJoin which we need to perform
# extra actions upon
rm $out/share/applications/nvim.desktop $out/bin/nvim
rm $out/bin/nvim
makeWrapper ${lib.escapeShellArgs initialMakeWrapperArgs} ${extraMakeWrapperArgs}
''
+ lib.optionalString stdenv.isLinux ''
rm $out/share/applications/nvim.desktop
substitute ${neovim}/share/applications/nvim.desktop $out/share/applications/nvim.desktop \
--replace 'TryExec=nvim' "TryExec=$out/bin/nvim" \
--replace 'Name=Neovim' 'Name=WrappedNeovim'

View File

@ -4,13 +4,13 @@
stdenv.mkDerivation rec {
pname = "quilter";
version = "2.2.4";
version = "2.5.0";
src = fetchFromGitHub {
owner = "lainsce";
repo = pname;
rev = version;
sha256 = "0xmnfqqdn7p84aksb8yzs14ikgy5driylr6m4p5ffsb6i9aa0i9h";
sha256 = "0622mh46z3fi6zvipmgj8k4d4gj1c2781l10frk7wqq1sysjrxps";
};
nativeBuildInputs = [

View File

@ -13,8 +13,8 @@ let
else throw "ImageMagick is not supported on this platform.";
cfg = {
version = "7.0.10-19";
sha256 = "12ilfdbxllkaa3bs9z86d2nkklqz5c0l57kqj91l2ixjlvra64w0";
version = "7.0.10-25";
sha256 = "15y07kgy4mx3qyxsbd9g6s2yaa2mxnfvfzas35jw0vz6qjjyaw5c";
patches = [];
};
in

View File

@ -11,11 +11,11 @@
stdenv.mkDerivation rec {
pname = "drawio";
version = "13.5.1";
version = "13.5.7";
src = fetchurl {
url = "https://github.com/jgraph/drawio-desktop/releases/download/v${version}/draw.io-x86_64-${version}.rpm";
sha256 = "00ggm867c5005qfm35qf8a94d87ln91irb1ir6012am2k5bn8c8p";
sha256 = "1b2sb44zsa6g5nnsa7drn4fn61jfz3a3g3bisai85fyjff746ipc";
};
nativeBuildInputs = [

View File

@ -0,0 +1,72 @@
{ stdenv, fetchFromGitHub, lazarus, fpc, pango, cairo, glib
, atk, gtk2, libX11, gdk-pixbuf, busybox, python3, makeWrapper }:
with stdenv;
let
bgrabitmap = fetchFromGitHub {
owner = "bgrabitmap";
repo = "bgrabitmap";
rev = "v11.1";
sha256 = "0bcmiiwly4a7w8p3m5iskzvk8rz87qhc0gcijrdvwg87cafd88gz";
};
bgracontrols = fetchFromGitHub {
owner = "bgrabitmap";
repo = "bgracontrols";
rev = "v6.7.2";
sha256 = "0cwxzv0rl6crkf6f67mvga5cn5pyhr6ksm8cqhpxjiqi937dnyxx";
};
in stdenv.mkDerivation rec {
pname = "lazpaint";
version = "7.1.3";
src = fetchFromGitHub {
owner = "bgrabitmap";
repo = "lazpaint";
rev = "v${version}";
sha256 = "1sfb5hmhzscz3nv4cmc192jimkg70l4z3q3yxkivhw1hwwsv9cbg";
};
nativeBuildInputs = [ lazarus fpc makeWrapper ];
buildInputs = [ pango cairo glib atk gtk2 libX11 gdk-pixbuf ];
NIX_LDFLAGS = "--as-needed -rpath ${lib.makeLibraryPath buildInputs}";
buildPhase = ''
cp -r --no-preserve=mode ${bgrabitmap} bgrabitmap
cp -r --no-preserve=mode ${bgracontrols} bgracontrols
lazbuild --lazarusdir=${lazarus}/share/lazarus \
--build-mode=Release \
bgrabitmap/bgrabitmap/bgrabitmappack.lpk \
bgracontrols/bgracontrols.lpk \
lazpaintcontrols/lazpaintcontrols.lpk \
lazpaint/lazpaint.lpi
'';
installPhase = ''
# Reuse existing install script
cd lazpaint/release/debian
substituteInPlace makedeb.sh --replace "rm -rf" "ls"
patchShebangs ./makedeb.sh
PATH=$PATH:${busybox}/bin ./makedeb.sh
cp -r staging/usr $out
# Python is needed for scripts
makeWrapper $out/share/lazpaint/lazpaint $out/bin/lazpaint \
--prefix PATH : ${stdenv.lib.makeBinPath [ python3 ]}
substituteInPlace $out/share/applications/lazpaint.desktop \
--replace /usr/share/pixmaps/lazpaint.png $out/share/pixmaps/lazpaint.png \
--replace /usr/share/lazpaint/lazpaint $out/bin/lazpaint
'';
meta = with stdenv.lib; {
description = "Image editor like PaintBrush or Paint.Net";
homepage = "https://sourceforge.net/projects/lazpaint/";
license = licenses.gpl3;
platforms = platforms.linux;
maintainers = with maintainers; [ gnidorah ];
};
}

View File

@ -18,13 +18,13 @@
mkDerivation rec {
pname = "nomacs";
version = "3.15.1616";
version = "3.16.224";
src = fetchFromGitHub {
owner = "nomacs";
repo = "nomacs";
rev = version;
sha256 = "0g1saqf31zncqdiwk7aaf951j3g33bg0vcjcr5mvg600jxiinw8j";
sha256 = "05d4hqg0gl3g9s2xf1hr7mc7g4cqarcap4nzxxa51fsphw2b8x16";
};
enableParallelBuilding = true;

View File

@ -74,7 +74,7 @@ let
akregator = callPackage ./akregator.nix {};
ark = callPackage ./ark {};
baloo-widgets = callPackage ./baloo-widgets.nix {};
bovo = callPackage ./bovo.nix {};
bovo = callPackage ./bovo.nix {};
bomber = callPackage ./bomber.nix {};
calendarsupport = callPackage ./calendarsupport.nix {};
dolphin = callPackage ./dolphin.nix {};
@ -113,6 +113,7 @@ let
kdialog = callPackage ./kdialog.nix {};
keditbookmarks = callPackage ./keditbookmarks.nix {};
kfind = callPackage ./kfind.nix {};
kfloppy = callPackage ./kfloppy.nix {};
kgeography = callPackage ./kgeography.nix {};
kget = callPackage ./kget.nix {};
kgpg = callPackage ./kgpg.nix {};

View File

@ -0,0 +1,20 @@
{ mkDerivation, lib, extra-cmake-modules, kdoctools, kcompletion, kxmlgui }:
mkDerivation {
name = "kfloppy";
meta = with lib; {
homepage = "https://kde.org/applications/en/utilities/org.kde.kfloppy";
description = "KFloppy is a utility to format 3.5\" and 5.25\" floppy disks";
maintainers = with maintainers; [ freezeboy ];
license = licenses.gpl2Plus;
platforms = platforms.linux;
};
nativeBuildInputs = [
extra-cmake-modules
];
buildInputs = [
kdoctools
kcompletion
kxmlgui
];
}

View File

@ -5,7 +5,7 @@
grantleetheme, karchive, kcodecs, kconfig, kconfigwidgets, kcontacts,
kdepim-apps-libs, kiconthemes, kidentitymanagement, kio, kjobwidgets, kldap,
kmailtransport, kmbox, kmime, kwindowsystem, libgravatar, libkdepim, libkleo,
pimcommon, qca-qt5, qtwebengine, qtwebkit, syntax-highlighting
pimcommon, qca-qt5, qtwebengine, syntax-highlighting
}:
mkDerivation {
@ -18,7 +18,7 @@ mkDerivation {
buildInputs = [
akonadi-notes akonadi-search gpgme grantlee grantleetheme karchive kcodecs
kconfig kconfigwidgets kdepim-apps-libs kiconthemes kio kjobwidgets kldap
kmailtransport kmbox kmime kwindowsystem libgravatar libkdepim qca-qt5 qtwebkit
kmailtransport kmbox kmime kwindowsystem libgravatar libkdepim qca-qt5
syntax-highlighting
];
propagatedBuildInputs = [

View File

@ -1,24 +1,30 @@
{ clipnotify, makeWrapper, xsel, dmenu, utillinux, gawk, stdenv, fetchFromGitHub, lib }:
{ clipnotify, makeWrapper, xsel, dmenu, utillinux, gawk, stdenv, fetchFromGitHub, fetchpatch, lib }:
let
runtimePath = lib.makeBinPath [ clipnotify xsel dmenu utillinux gawk ];
in
stdenv.mkDerivation rec {
pname = "clipmenu";
version = "6.0.1";
version = "6.1.0";
src = fetchFromGitHub {
owner = "cdown";
repo = "clipmenu";
rev = version;
sha256 = "0053j4i14lz5m2bzc5sch5id5ilr1bl196mp8fp0q8x74w3vavs9";
sha256 = "0ddj5xcwrdb2qvrndvhv8j6swcqc8dvv5i00pqk35rfk5mrl4hwv";
};
patches = [
(fetchpatch {
url = "https://github.com/cdown/clipmenu/commit/443b58583ef216e2405e4a38d401f7c36386d21e.patch";
sha256 = "12m4rpw7jbr31c919llbsmn8dcf7yh9aijln4iym6h2lylzqzzdz";
})
];
makeFlags = [ "PREFIX=$(out)" ];
buildInputs = [ makeWrapper ];
nativeBuildInputs = [ xsel clipnotify ];
installPhase = ''
mkdir -p $out/bin
cp clipdel clipmenu clipmenud $out/bin
for bin in $out/bin/*; do
wrapProgram "$bin" --prefix PATH : "${runtimePath}"
done

View File

@ -2,20 +2,19 @@
let
pname = "joplin-desktop";
version = "1.0.216";
desktopItem = makeDesktopItem {
name = "Joplin";
exec = "joplin-desktop";
type = "Application";
desktopName = "Joplin";
};
in appimageTools.wrapType2 rec {
version = "1.0.233";
name = "${pname}-${version}";
src = fetchurl {
url = "https://github.com/laurent22/joplin/releases/download/v${version}/Joplin-${version}.AppImage";
sha256 = "17rb7h98h9i2p5kw5gznx5swpz6yxqdxwc9x5cgbkc31vk10iszn";
sha256 = "1fmk56b9b70ly1r471mhppr8fz1wm2gpxji1v760ynha8fqy7qg1";
};
appimageContents = appimageTools.extractType2 {
inherit name src;
};
in appimageTools.wrapType2 rec {
inherit name src;
profile = ''
export LC_ALL=C.UTF-8
@ -25,9 +24,12 @@ in appimageTools.wrapType2 rec {
multiPkgs = null; # no 32bit needed
extraPkgs = appimageTools.defaultFhsEnvArgs.multiPkgs;
extraInstallCommands = ''
mkdir -p $out/share/applications
ln -s ${desktopItem}/share/applications/* $out/share/applications
mv $out/bin/{${name},${pname}}
install -m 444 -D ${appimageContents}/joplin.desktop $out/share/applications/joplin.desktop
install -m 444 -D ${appimageContents}/joplin.png \
$out/share/pixmaps/joplin.png
substituteInPlace $out/share/applications/joplin.desktop \
--replace 'Exec=AppRun' 'Exec=${pname}'
'';

View File

@ -1,15 +1,15 @@
{ stdenv, fetchurl, fetchsvn, makeWrapper, unzip, jre, libXxf86vm }:
let
pname = "josm";
version = "16731";
version = "16812";
srcs = {
jar = fetchurl {
url = "https://josm.openstreetmap.de/download/josm-snapshot-${version}.jar";
sha256 = "0r94jcqciggjwjxfz5q3m81sx6cvh94hq5r9mpw44dvpnyfjj6p6";
sha256 = "1ld0c87mhifbdnlrr7a9jmgn3s5xklzbpwcl1m6j1lc18ajs1awq";
};
macosx = fetchurl {
url = "https://josm.openstreetmap.de/download/macosx/josm-macosx-${version}.zip";
sha256 = "1ilcqy6ssi1jfnbw9nzpd4qlf2dmskfywy2lfm07y4w4gyjsp6w9";
sha256 = "0vhawcgzh06k2dfqav28n3sv1ij1ziz6bgi4k7m0diix6ia7hlar";
};
pkg = fetchsvn {
url = "https://josm.openstreetmap.de/svn/trunk/native/linux/tested";

View File

@ -2,16 +2,16 @@
rustPlatform.buildRustPackage rec {
pname = "kondo";
version = "0.3";
version = "0.4";
src = fetchFromGitHub {
owner = "tbillington";
repo = pname;
rev = "v${version}";
sha256 = "1rrg0xfm3vn5jh861r4ismrga673g7v6qnzl2v1haflgjhvdazwd";
sha256 = "0kl2zn6ir3w75ny25ksgxl93vlyb13gzx2795zyimqqnsrdpbbrf";
};
cargoSha256 = "1y7g8gw9hsm997d6i99c3dj2gb8y8cgws5001n85f9bpnlvvmf9y";
cargoSha256 = "1ax81a2828z3yla1psg5xi8ild65m6zcsvx48ncz902mpzqlj92b";
meta = with stdenv.lib; {
description = "Save disk space by cleaning unneeded files from software projects";

View File

@ -0,0 +1,29 @@
{ rustPlatform, fetchFromGitHub, lib, fzf, makeWrapper }:
rustPlatform.buildRustPackage rec {
pname = "navi";
version = "2.7.1";
src = fetchFromGitHub {
owner = "denisidoro";
repo = "navi";
rev = "v${version}";
sha256 = "12p9l41k7isaapr0xbsm7brkjrv7i8826y029i12psz92nsynk29";
};
cargoSha256 = "11dc3gc7fyikbbgacmljhysr2sl7lmq6w3bsfcf2cqny39r25yp0";
nativeBuildInputs = [ makeWrapper ];
postInstall = ''
wrapProgram $out/bin/navi --prefix PATH : ${lib.makeBinPath [ fzf ]}
'';
meta = with lib; {
description = "An interactive cheatsheet tool for the command-line and application launchers";
homepage = "https://github.com/denisidoro/navi";
license = licenses.asl20;
platforms = platforms.unix;
maintainers = with maintainers; [ cust0dian ];
};
}

View File

@ -1,4 +1,4 @@
{ stdenv, lib, fetchFromGitHub, cmake, openssl, qttools
{ stdenv, lib, fetchpatch, fetchFromGitHub, cmake, openssl, qttools
, ApplicationServices, Carbon, Cocoa, CoreServices, ScreenSaver
, xlibsWrapper, libX11, libXi, libXtst, libXrandr, xinput, avahi-compat
, withGUI ? true, wrapQtAppsHook }:
@ -14,7 +14,14 @@ stdenv.mkDerivation rec {
sha256 = "1jk60xw4h6s5crha89wk4y8rrf1f3bixgh5mzh3cq3xyrkba41gh";
};
patches = [ ./build-tests.patch
patches = [
./build-tests.patch
(fetchpatch {
name = "CVE-2020-15117.patch";
url = "https://github.com/symless/synergy-core/commit/"
+ "0a97c2be0da2d0df25cb86dfd642429e7a8bea39.patch";
sha256 = "03q8m5n50fms7fjfjgmqrgy9mrxwi9kkz3f3vlrs2x5h21dl6bmj";
})
] ++ lib.optional stdenv.isDarwin ./macos_build_fix.patch;
# Since the included gtest and gmock don't support clang and the

View File

@ -2,16 +2,16 @@
buildGoModule rec {
pname = "amfora";
version = "1.3.0";
version = "1.4.0";
src = fetchFromGitHub {
owner = "makeworld-the-better-one";
repo = "amfora";
rev = "v${version}";
sha256 = "0bnjwsyi6l9p27rajwh0nq53zi4km7qpgyb08q17j0vd87gpdhka";
sha256 = "1z4r1yqy5nkfa7yqcsqpqfdcghw8idryzb3s6d6ibca47r0qlcvw";
};
vendorSha256 = "1rj2m3rg8ixclj5jr0nmp266vwj1mg5ampxn04i3wgaayy49dbdi";
vendorSha256 = "0xj2s14dq10fwqqxjn4d8x6zljd5d15gjbja2gb75rfv09s4fdgv";
meta = with lib; {
description = "A fancy terminal browser for the Gemini protocol";

View File

@ -1,5 +1,5 @@
{ newScope, config, stdenv, llvmPackages_9, llvmPackages_10
, makeWrapper, ed, gnugrep
, makeWrapper, ed, gnugrep, coreutils
, glib, gtk3, gnome3, gsettings-desktop-schemas, gn, fetchgit
, libva ? null
, pipewire_0_2
@ -196,7 +196,7 @@ in stdenv.mkDerivation {
'' + ''
# libredirect causes chromium to deadlock on startup
export LD_PRELOAD="\$(echo -n "\$LD_PRELOAD" | tr ':' '\n' | ${gnugrep}/bin/grep -v /lib/libredirect\\\\.so$ | tr '\n' ':')"
export LD_PRELOAD="\$(echo -n "\$LD_PRELOAD" | ${coreutils}/bin/tr ':' '\n' | ${gnugrep}/bin/grep -v /lib/libredirect\\\\.so$ | ${coreutils}/bin/tr '\n' ':')"
export XDG_DATA_DIRS=$XDG_ICON_DIRS:$GSETTINGS_SCHEMAS_PATH\''${XDG_DATA_DIRS:+:}\$XDG_DATA_DIRS

View File

@ -0,0 +1,34 @@
# Generated by debian-patches.sh from debian-patches.txt
let
prefix = "https://sources.debian.org/data/main/e/elinks/0.13.2-1/debian/patches";
in
[
{
url = "${prefix}/03_459467_ui.leds.enable_0.diff";
sha256 = "0l35lglmnvyzz3xyy18nksra14gsp7yc67rskbzmr61szg8b9jqr";
}
{
url = "${prefix}/04_436817_nostrip.diff";
sha256 = "0ixvxaba1ww375gpdh7r67srp3xsfb5vyz2sfv1pgj6mczwg8v24";
}
{
url = "${prefix}/07_617713_cache_control.diff";
sha256 = "0drn4r33ywvmihr0drsp2jwz7mlf5z5fv8ra7fpkdavx45xqaf15";
}
{
url = "${prefix}/10-reproducible-build.diff";
sha256 = "024yp3xsh0hw29l1wikfmk9j3mqval6pdr4xi7rzffrlaknh58h5";
}
{
url = "${prefix}/14_debug_disable_Werror.diff";
sha256 = "0s620r88ikfljflb5nd133cww2wc0i85ag8lzpvrsmg0q00hfmax";
}
{
url = "${prefix}/16_POST_BUFFER_SIZE.diff";
sha256 = "17vkvy0d0rabmgk8iqwgdsrgjn6dbb9cf6760qbz82zlb37s09nh";
}
{
url = "${prefix}/11-reproducible-build.diff";
sha256 = "1z17g9z68lh12fs6fkralfghh8bs1bs5mlq83d15l4bn3za3s0sl";
}
]

View File

@ -0,0 +1,8 @@
elinks/0.13.2-1
03_459467_ui.leds.enable_0.diff
04_436817_nostrip.diff
07_617713_cache_control.diff
10-reproducible-build.diff
14_debug_disable_Werror.diff
16_POST_BUFFER_SIZE.diff
11-reproducible-build.diff

View File

@ -1,4 +1,4 @@
{ stdenv, fetchurl, fetchpatch, ncurses, xlibsWrapper, bzip2, zlib, openssl
{ stdenv, fetchurl, fetchpatch, ncurses, xlibsWrapper, bzip2, zlib, brotli, openssl, autoconf, automake, gettext, pkgconfig, libev
, gpm
, # Incompatible licenses, LGPLv3 - GPLv2
enableGuile ? false, guile ? null
@ -11,18 +11,15 @@ assert enableGuile -> guile != null;
assert enablePython -> python != null;
stdenv.mkDerivation rec {
pname = "elinks";
version = "0.12pre6";
pname = "elinks-0.13.2";
version = "0.13.2";
src = fetchurl {
url = "http://elinks.or.cz/download/${pname}-${version}.tar.bz2";
sha256 = "1nnakbi01g7yd3zqwprchh5yp45br8086b0kbbpmnclabcvlcdiq";
url = "https://deb.debian.org/debian/pool/main/e/elinks/elinks_${version}.orig.tar.gz";
sha256 = "0xkpqnqy0x8sizx4snca0pw3q98gkhnw5a05yf144j1x1y2nb14c";
};
patches = [
./gc-init.patch
./openssl-1.1.patch
];
patches = map fetchurl (import ./debian-patches.nix);
postPatch = (stdenv.lib.optional stdenv.isDarwin) ''
patch -p0 < ${fetchpatch {
@ -31,12 +28,15 @@ stdenv.mkDerivation rec {
}}
'';
buildInputs = [ ncurses xlibsWrapper bzip2 zlib openssl spidermonkey ]
buildInputs = [ ncurses xlibsWrapper bzip2 zlib brotli openssl libev ]
++ stdenv.lib.optional stdenv.isLinux gpm
++ stdenv.lib.optional enableGuile guile
++ stdenv.lib.optional enablePython python
++ stdenv.lib.optional enablePerl perl
++ stdenv.lib.optional enableSpidermonkey spidermonkey
;
nativeBuildInputs = [ autoconf automake gettext pkgconfig ];
configureFlags = [
"--enable-finger"
@ -45,18 +45,24 @@ stdenv.mkDerivation rec {
"--enable-cgi"
"--enable-bittorrent"
"--enable-nntp"
"--with-openssl=${openssl.dev}"
"--with-bzip2=${bzip2.dev}"
"--enable-256-colors"
"--with-libev"
] ++ stdenv.lib.optional enableGuile "--with-guile"
++ stdenv.lib.optional enablePython "--with-python"
++ stdenv.lib.optional enablePerl "--with-perl"
++ stdenv.lib.optional enableSpidermonkey "--with-spidermonkey=${spidermonkey}"
;
preConfigure = ''
patchShebangs ./autogen.sh
./autogen.sh
'';
meta = with stdenv.lib; {
description = "Full-featured text-mode web browser";
homepage = "http://elinks.or.cz";
description = "Full-featured text-mode web browser (package based on the fork felinks)";
homepage = "https://github.com/rkd77/felinks";
license = licenses.gpl2;
platforms = with platforms; linux ++ darwin;
maintainers = with maintainers; [ iblech ];
};
}

View File

@ -1,17 +0,0 @@
Fix libgc initialization in the presence of Guile 2.0.
--- elinks-0.12pre5/src/main/main.c 2009-07-07 14:23:17.000000000 +0200
+++ elinks-0.12pre5/src/main/main.c 2011-04-28 23:20:15.000000000 +0200
@@ -339,6 +339,11 @@ int
main(int argc, char *argv[])
{
#ifdef CONFIG_GC
+ /* Guile 2.x uses libgc too and it initializes it this way, so we
+ * must make sure to initialize it the same way, or it will just
+ * segfault. */
+ GC_all_interior_pointers = 0;
+
GC_INIT();
GC_set_warn_proc(gc_warning);
#endif

View File

@ -1,51 +0,0 @@
diff --git a/src/network/ssl/socket.c b/src/network/ssl/socket.c
index 45b4b4a8..0385a431 100644
--- a/src/network/ssl/socket.c
+++ b/src/network/ssl/socket.c
@@ -67,7 +67,9 @@ static void
ssl_set_no_tls(struct socket *socket)
{
#ifdef CONFIG_OPENSSL
- ((ssl_t *) socket->ssl)->options |= SSL_OP_NO_TLSv1;
+#ifdef SSL_OP_NO_TLSv1
+ SSL_set_options((ssl_t *)socket->ssl, SSL_OP_NO_TLSv1);
+#endif
#elif defined(CONFIG_GNUTLS)
{
/* GnuTLS does not support SSLv2 because it is "insecure".
@@ -145,9 +147,11 @@ ssl_connect(struct socket *socket)
}
if (client_cert) {
- SSL_CTX *ctx = ((SSL *) socket->ssl)->ctx;
+ SSL_CTX *ctx = SSL_get_SSL_CTX((SSL *) socket->ssl);
- SSL_CTX_use_certificate_chain_file(ctx, client_cert);
+ SSL_CTX_use_certificate_chain_file(
+ (SSL *) socket->ssl,
+ client_cert);
SSL_CTX_use_PrivateKey_file(ctx, client_cert,
SSL_FILETYPE_PEM);
}
diff --git a/src/network/ssl/ssl.c b/src/network/ssl/ssl.c
index c008121d..c06a80a7 100644
--- a/src/network/ssl/ssl.c
+++ b/src/network/ssl/ssl.c
@@ -50,11 +50,16 @@ init_openssl(struct module *module)
* cannot initialize the PRNG and so every attempt to use SSL fails.
* It's actually an OpenSSL FAQ, and according to them, it's up to the
* application coders to seed the RNG. -- William Yodlowsky */
- if (RAND_egd(RAND_file_name(f_randfile, sizeof(f_randfile))) < 0) {
+ RAND_file_name(f_randfile, sizeof(f_randfile));
+#ifdef HAVE_RAND_EGD
+ if (RAND_egd(f_randfile) < 0) {
/* Not an EGD, so read and write to it */
+#endif
if (RAND_load_file(f_randfile, -1))
RAND_write_file(f_randfile);
+#ifdef HAVE_RAND_EGD
}
+#endif
SSLeay_add_ssl_algorithms();
context = SSL_CTX_new(SSLv23_client_method());

View File

@ -7,10 +7,10 @@ in
rec {
firefox = common rec {
pname = "firefox";
ffversion = "78.0.1";
ffversion = "79.0";
src = fetchurl {
url = "mirror://mozilla/firefox/releases/${ffversion}/source/firefox-${ffversion}.source.tar.xz";
sha512 = "mdO6masIpiZBvYi6kpYUTSnsOda04CUs2CL1LNf1Yad+rfY4ga4aFuLtfKqfgV5IcIIl86XeiC+0grd4irbCYg==";
sha512 = "0zgf7wdcz992a4dy1rj0ax0k65an7h9p9iihka3jy4jd7w4g2d0x4mxz5iqn2y26hmgnkvjb921zh28biikahgygqja3z2pcx26ic0r";
};
patches = [
@ -33,12 +33,40 @@ rec {
};
};
firefox-esr-68 = (common rec {
firefox-esr-78 = common rec {
pname = "firefox-esr";
ffversion = "68.10.0esr";
ffversion = "78.1.0esr";
src = fetchurl {
url = "mirror://mozilla/firefox/releases/${ffversion}/source/firefox-${ffversion}.source.tar.xz";
sha512 = "xcGDNWA2SFHnz46lFlm8T7YCOblgElzbIP4x90LXV//a748xT4ANyRIU7o41gDPcKvlxwIu7pHTvYVixAYgWUw==";
sha512 = "223v796vjsvgs3yw442c8qbsbh43l1aniial05rl70hx44rh9sg108ripj8q83p5l9m0sp67x6ixd2xvifizv6461a1zra1rvbb1caa";
};
patches = [
./no-buildconfig-ffx76.patch
];
meta = {
description = "A web browser built from Firefox Extended Support Release source tree";
homepage = "http://www.mozilla.com/en-US/firefox/";
maintainers = with lib.maintainers; [ eelco andir ];
platforms = lib.platforms.unix;
badPlatforms = lib.platforms.darwin;
broken = stdenv.buildPlatform.is32bit; # since Firefox 60, build on 32-bit platforms fails with "out of memory".
# not in `badPlatforms` because cross-compilation on 64-bit machine might work.
license = lib.licenses.mpl20;
};
updateScript = callPackage ./update.nix {
attrPath = "firefox-esr-78-unwrapped";
versionKey = "ffversion";
};
};
firefox-esr-68 = (common rec {
pname = "firefox-esr";
ffversion = "68.11.0esr";
src = fetchurl {
url = "mirror://mozilla/firefox/releases/${ffversion}/source/firefox-${ffversion}.source.tar.xz";
sha512 = "0zg41jnbnpsa07xaizwfsmfav0cgxdqnh8i4yanxy49a45gigk895zqrx2if7pfsmdnj9zpwj9prj8cpnpsfhv6p62f3g2596aa9kvx";
};
patches = [

View File

@ -2,16 +2,16 @@
buildGoModule rec {
pname = "helmfile";
version = "0.119.1";
version = "0.125.1";
src = fetchFromGitHub {
owner = "roboll";
repo = "helmfile";
rev = "v${version}";
sha256 = "1j9b0xw59w5ailwa7dqgbsdigviw8ng5r4jbsk9b80izcig805zz";
sha256 = "0ym9q1rww3r54czkrckdd1ahlym6n61l2563nmj48hkn5d4qxqbm";
};
vendorSha256 = "11bw10s5wifzw2cy1100hyjv4xv7an7b05lcw6sphwyy56gsp2fy";
vendorSha256 = "04mga3jc2c01daygjcn245mv30lc2ibax0mpb1wjk3s8lkl4cxcz";
nativeBuildInputs = [ makeWrapper ];

View File

@ -1,18 +1,18 @@
{ lib, buildGoModule, fetchFromGitHub, go-bindata }:
{ lib, buildGoModule, fetchFromGitHub, go-bindata, installShellFiles }:
buildGoModule rec {
pname = "istioctl";
version = "1.6.5";
version = "1.6.6";
src = fetchFromGitHub {
owner = "istio";
repo = "istio";
rev = version;
sha256 = "0xga0vjr2nfbxwbawly8vg9vnpavxbmc1agg2a3cp1ncmzfrgpcx";
sha256 = "0njchcb58lxk0cixk2rz4qj7b0zpp6zf3i5dda43j4hfsb37mifj";
};
vendorSha256 = "15l9z2a8p46jvmkl0vvm6s196mlics0qgmpm3yq3bn6cqnybdsij";
vendorSha256 = "0cc0lmjsxrn3f78k95wklf3yn5k7h8slwnwmssy1i1h0bkcg1bai";
nativeBuildInputs = [ go-bindata ];
nativeBuildInputs = [ go-bindata installShellFiles ];
# Bundle charts
preBuild = ''
@ -28,10 +28,17 @@ buildGoModule rec {
"istio.io/pkg/version.buildTag=${version}"
"istio.io/pkg/version.buildHub=docker.io/istio"
];
in ["-ldflags=${lib.concatMapStringsSep " " (attr: "-X ${attr}") attrs}"];
in ["-ldflags=-s -w ${lib.concatMapStringsSep " " (attr: "-X ${attr}") attrs}"];
subPackages = [ "istioctl/cmd/istioctl" ];
postInstall = ''
$out/bin/istioctl collateral --man --bash --zsh
installManPage *.1
installShellCompletion istioctl.bash
installShellCompletion --zsh _istioctl
'';
meta = with lib; {
description = "Istio configuration command line utility for service operators to debug and diagnose their Istio mesh";
homepage = "https://istio.io/latest/docs/reference/commands/istioctl";

View File

@ -1,24 +1,35 @@
{ buildGoModule, fetchFromGitHub, lib }:
{ buildGoModule, fetchFromGitHub, lib, installShellFiles }:
buildGoModule rec {
pname = "jx";
version = "2.1.90";
version = "2.1.121";
src = fetchFromGitHub {
owner = "jenkins-x";
repo = "jx";
rev = "v${version}";
sha256 = "1m2gq1hh8fjgxwx2sipq56q5mlz0m3npnbsw103n2kq4xv1qf3f6";
sha256 = "0bjpnh962w5wz4gj5my9g52dawxj8zccvpkxlxy1n7c3dkzjxx5j";
};
vendorSha256 = "0kj6x7323fx1qhrlg789a21mh1fvhil7ng2fhmbmlwq0fcrngdnj";
vendorSha256 = "0l9djgvnrgdnw7nsf05yq7qpzzzm3gasgh9a7dyc16pp2kxvza6k";
subPackages = [ "cmd/jx" ];
nativeBuildInputs = [ installShellFiles ];
buildFlagsArray = ''
-ldflags=
-s -w
-X github.com/jenkins-x/jx/pkg/version.Version=${version}
-X github.com/jenkins-x/jx/pkg/version.Revision=${version}
-X github.com/jenkins-x/jx/pkg/version.Revision=${src.rev}
-X github.com/jenkins-x/jx/pkg/version.GitTreeState=clean
'';
postInstall = ''
for shell in bash zsh; do
$out/bin/jx completion $shell > jx.$shell
installShellCompletion jx.$shell
done
'';
meta = with lib; {

View File

@ -2,16 +2,16 @@
buildGoModule rec {
pname = "kpt";
version = "0.31.0";
version = "0.32.0";
src = fetchFromGitHub {
owner = "GoogleContainerTools";
repo = pname;
rev = "v${version}";
sha256 = "1l5mpml6pf37b76wdq6il00k5q6rvw9ds7807m103k27p7pcqgdx";
sha256 = "1pgv15zgv30dpv148bn6x0anv9q6x78y6ldmzarb9fbjpk6j0wxl";
};
vendorSha256 = "1yb6dwbnimqfamdg57vq68q853fq04qfnh3sfbjg82sd8pz8069g";
vendorSha256 = "0l8xdnv2m6byd5dwvs3zgcj1lsci7ax4xvx178a8a78sgkqalvmq";
postInstall = ''
rm $out/bin/{mdtogo,formula}

View File

@ -2,7 +2,7 @@
buildGoPackage rec {
pname = "kube-router";
version = "1.0.0";
version = "1.0.1";
goPackagePath = "github.com/cloudnativelabs/kube-router";
@ -10,7 +10,7 @@ buildGoPackage rec {
owner = "cloudnativelabs";
repo = pname;
rev = "v${version}";
sha256 = "0b6rsiq3pwp7wknmblgd8kszh9bd7nhvlsnyyamqnhlfjl97929x";
sha256 = "00bypaccv8q9xdcz6vlvl1qxqxqssl21bs4nkd1a6q8b4jpl339z";
};
buildFlagsArray = ''

View File

@ -1,7 +1,7 @@
{ stdenv, fetchFromGitHub, buildGoModule }:
buildGoModule {
pname = "linkerd-unstablle";
pname = "linkerd-unstable";
version = "2020-05-01";
src = fetchFromGitHub {

View File

@ -4,13 +4,14 @@ with pythonPackages;
buildPythonApplication rec {
pname = "rss2email";
version = "3.11";
version = "3.12.1";
propagatedBuildInputs = [ feedparser beautifulsoup4 html2text ];
propagatedBuildInputs = [ feedparser html2text ];
checkInputs = [ beautifulsoup4 ];
src = fetchurl {
url = "mirror://pypi/r/rss2email/${pname}-${version}.tar.gz";
sha256 = "1vk5slp2mhmc1qj30igqkyq3z5h2bl1ayhafqrjapa6cg6rbvhrn";
sha256 = "0zqpibh31rl6xlfw9y66d9hfhwrnzy5cjzbksczyw3lh4dfzsql0";
};
outputs = [ "out" "man" "doc" ];
@ -39,7 +40,7 @@ buildPythonApplication rec {
description = "A tool that converts RSS/Atom newsfeeds to email.";
homepage = "https://pypi.python.org/pypi/rss2email";
license = licenses.gpl2;
maintainers = with maintainers; [ jb55 Profpatsch ];
maintainers = with maintainers; [ jb55 Profpatsch ekleog ];
};
passthru.tests = {
smoke-test = nixosTests.rss2email;

View File

@ -13,11 +13,11 @@ let
in
stdenv.mkDerivation rec {
pname = "openbazaar-client";
version = "2.4.6";
version = "2.4.7";
src = fetchurl {
url = "https://github.com/OpenBazaar/openbazaar-desktop/releases/download/v${version}/openbazaar2client_${version}_amd64.deb";
sha256 = "1p190az8llqh3089aygwash10wqqqfnjl2wvksn6bvx5wm5dpg1p";
sha256 = "04wwljaiqm8rsdrzngqrzrjzfrjsrfsaa60c904zhbhmsqc7y4f1";
};
dontBuild = true;

View File

@ -4,13 +4,13 @@
stdenv.mkDerivation rec {
pname = "ettercap";
version = "0.8.3";
version = "0.8.3.1";
src = fetchFromGitHub {
owner = "Ettercap";
repo = "ettercap";
rev = "v${version}";
sha256 = "0m40bmbrv9a8qlg54z3b5f8r541gl9vah5hm0bbqcgyyljpg39bz";
sha256 = "1sdf1ssa81ib6k0mc5m2jzbjl4jd1yv6ahv5dwx2x9w4b2pyqg1c";
};
strictDeps = true;

View File

@ -21,13 +21,13 @@
stdenv.mkDerivation rec {
pname = "elementary-planner";
version = "2.4.5";
version = "2.4.6";
src = fetchFromGitHub {
owner = "alainm23";
repo = "planner";
rev = version;
sha256 = "0jj901b2v4vfgv0i7d02xhhylfh6rcanaybk52i7ci92ff2gzgcb";
sha256 = "0z0997yq809wbsk3w21xv4fcrgqcb958qdlksf4rhzhfnwbiii6y";
};
nativeBuildInputs = [

View File

@ -5,13 +5,13 @@
stdenv.mkDerivation rec {
pname = "limesuite";
version = "20.01.0";
version = "20.07.1";
src = fetchFromGitHub {
owner = "myriadrf";
repo = "LimeSuite";
rev = "v${version}";
sha256 = "01z4idcby2lm34bbnpbp400ski7p61jjiir6sy6dalnvsl52m7vx";
sha256 = "14mxqc350j3rk1202n0ax1rfx49sy40965zj90d4pnakbgz5xr7g";
};
nativeBuildInputs = [ cmake ];

View File

@ -1,7 +1,7 @@
{ stdenv, fetchFromGitHub, cmake, soapysdr, avahi }:
let
version = "0.5.1";
version = "0.5.2";
in stdenv.mkDerivation {
pname = "soapyremote";
@ -11,7 +11,7 @@ in stdenv.mkDerivation {
owner = "pothosware";
repo = "SoapyRemote";
rev = "soapy-remote-${version}";
sha256 = "1qlpjg8mh564q26mni8g6bb8w9nj7hgcq86278fszxpwpnk3jsvk";
sha256 = "124sy9v08fm51ds1yzrxspychn34y0rl6y48mzariianazvzmfax";
};
nativeBuildInputs = [ cmake ];

View File

@ -2,11 +2,11 @@
stdenv.mkDerivation rec {
pname = "picard-tools";
version = "2.23.1";
version = "2.23.3";
src = fetchurl {
url = "https://github.com/broadinstitute/picard/releases/download/${version}/picard.jar";
sha256 = "1g4539x2081jgrbn207nsimpq9q5izd4z6cx7s8lr8p8ab8spbmk";
sha256 = "08wgi0hijfbchr2srmndxq3h2fijvyvr8b6zv680fpcjixm5bbhf";
};
nativeBuildInputs = [ makeWrapper ];

View File

@ -5,7 +5,7 @@
# - The exact version can be specified through the `version` argument to
# the derivation; it defaults to the latest stable version.
{ stdenv, fetchFromGitHub, writeText, pkgconfig
{ stdenv, fetchFromGitHub, writeText, pkgconfig, gnumake42
, ocamlPackages, ncurses
, buildIde ? !(stdenv.isDarwin && stdenv.lib.versionAtLeast version "8.10")
, glib, gnome3, wrapGAppsHook
@ -107,7 +107,9 @@ self = stdenv.mkDerivation {
inherit sha256;
};
nativeBuildInputs = [ pkgconfig ];
nativeBuildInputs = [ pkgconfig ]
++ stdenv.lib.optional (!versionAtLeast "8.6") gnumake42
;
buildInputs = [ ncurses ocamlPackages.ocaml ocamlPackages.findlib ]
++ stdenv.lib.optional (!versionAtLeast "8.10") ocamlPackages.camlp5
++ [ ocamlPackages.num ]

View File

@ -2,13 +2,13 @@
stdenv.mkDerivation rec {
pname = "lean";
version = "3.16.5";
version = "3.18.4";
src = fetchFromGitHub {
owner = "leanprover-community";
repo = "lean";
rev = "v${version}";
sha256 = "0s1ay6qgpkxhygfbfrl1cw2pd8bpgw2dw71rzhza20ndqwk8nqs5";
sha256 = "1pmc2wi1pa346w89ayrrjv9xk6v6myg2zmx1wj4pd9qxv7ivrbsn";
};
nativeBuildInputs = [ cmake ];

View File

@ -9,16 +9,16 @@
rustPlatform.buildRustPackage rec {
pname = "delta";
version = "0.3.0";
version = "0.4.0";
src = fetchFromGitHub {
owner = "dandavison";
repo = pname;
rev = version;
sha256 = "0y3gkan5v0d6637yf5p5a9dklyv5zngw7a8pyqzj4ixys72ixg20";
sha256 = "1i4ddz2fivn5h35059b68z3lfw48psak79aab6pk7d8iamz4njb9";
};
cargoSha256 = "15sh2lsc16nf9w7sp3avy77f4vyj0rdsm6m1bn60y8gmv2r16v6i";
cargoSha256 = "1na6wqjm69diwhkyxlzk0jm3qwkdrah3w6i8p7dhzrsx434lhmya";
nativeBuildInputs = [ installShellFiles ];

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