nginx: detect duplicate modules

Nginx breaks at runtime when duplicate modules are added. To detect
this, add a `name` key to all modules.

Also remove the outdated modsecurity v2 module and unify `modsecurity`
and `modsecurity-nginx`.

Changed files
+68 -21
nixos
pkgs
servers
top-level
+1 -1
nixos/tests/nginx-modsecurity.nix
···
nodes.machine = { config, lib, pkgs, ... }: {
services.nginx = {
enable = true;
-
additionalModules = [ pkgs.nginxModules.modsecurity-nginx ];
+
additionalModules = [ pkgs.nginxModules.modsecurity ];
virtualHosts.localhost =
let modsecurity_conf = pkgs.writeText "modsecurity.conf" ''
SecRuleEngine On
+6
pkgs/servers/http/nginx/generic.nix
···
let
+
moduleNames = map (mod: mod.name or (throw "The nginx module with source ${toString mod.src} does not have a `name` attribute. This prevents duplicate module detection and is no longer supported."))
+
modules;
+
mapModules = attrPath: flip concatMap modules
(mod:
let supports = mod.supports or (_: true);
···
else throw "Module at ${toString mod.src} does not support nginx version ${nginxVersion}!");
in
+
+
assert assertMsg (unique moduleNames == moduleNames)
+
"nginx: duplicate modules: ${concatStringsSep ", " moduleNames}. A common cause for this is that services.nginx.additionalModules adds a module which the nixos module itself already adds.";
stdenv.mkDerivation {
inherit pname;
+60 -19
pkgs/servers/http/nginx/modules.nix
···
-
{ fetchFromGitHub, fetchFromGitLab, fetchhg, lib, pkgs }:
+
{ config, fetchFromGitHub, fetchFromGitLab, fetchhg, lib, pkgs }:
let
http_proxy_connect_module_generic = patchName: rec {
+
name = "http_proxy_connect";
src = fetchFromGitHub {
name = "http_proxy_connect_module_generic";
owner = "chobits";
···
rev = "96ae4e06381f821218f368ad0ba964f87cbe0266";
sha256 = "1nc7z31i7x9dzp67kzgvs34hs6ps749y26wcpi3wf5mm63i803rh";
};
-
patches = [
"${src}/patch/${patchName}.patch"
];
···
in
-
{
+
let self = {
fastcgi-cache-purge = throw "fastcgi-cache-purge was renamed to cache-purge";
ngx_aws_auth = throw "ngx_aws_auth was renamed to aws-auth";
akamai-token-validate = {
+
name = "akamai-token-validate";
src = fetchFromGitHub {
name = "akamai-token-validate";
owner = "kaltura";
···
};
auth-a2aclr = {
+
name = "auth-a2aclr";
src = fetchFromGitLab {
name = "auth-a2aclr";
owner = "arpa2";
···
};
aws-auth = {
+
name = "aws-auth";
src = fetchFromGitHub {
name = "aws-auth";
owner = "anomalizer";
···
};
brotli = {
+
name = "brotli";
src = let gitsrc = pkgs.fetchFromGitHub {
name = "brotli";
owner = "google";
···
};
cache-purge = {
+
name = "cache-purge";
src = fetchFromGitHub {
name = "cache-purge";
owner = "nginx-modules";
···
};
coolkit = {
+
name = "coolkit";
src = fetchFromGitHub {
name = "coolkit";
owner = "FRiCKLE";
···
};
dav = {
+
name = "dav";
src = fetchFromGitHub {
name = "dav";
owner = "arut";
···
};
develkit = {
+
name = "develkit";
src = fetchFromGitHub {
name = "develkit";
owner = "vision5";
···
};
echo = {
+
name = "echo";
src = fetchFromGitHub {
name = "echo";
owner = "openresty";
···
};
fancyindex = {
+
name = "fancyindex";
src = fetchFromGitHub {
name = "fancyindex";
owner = "aperezdc";
···
};
fluentd = {
+
name = "fluentd";
src = fetchFromGitHub {
name = "fluentd";
owner = "fluent";
···
};
geoip2 = {
+
name = "geoip2";
src = fetchFromGitHub {
name = "geoip2";
owner = "leev";
···
};
ipscrub = {
+
name = "ipscrub";
src = fetchFromGitHub
{
name = "ipscrub";
···
};
limit-speed = {
+
name = "limit-speed";
src = fetchFromGitHub {
name = "limit-speed";
owner = "yaoweibin";
···
};
live = {
+
name = "live";
src = fetchFromGitHub {
name = "live";
owner = "arut";
···
};
lua = {
+
name = "lua";
src = fetchFromGitHub {
name = "lua";
owner = "openresty";
···
};
lua-upstream = {
+
name = "lua-upstream";
src = fetchFromGitHub {
name = "lua-upstream";
owner = "openresty";
···
};
modsecurity = {
-
src = "${pkgs.modsecurity_standalone.nginx}/nginx/modsecurity";
-
inputs = [ pkgs.curl pkgs.apr pkgs.aprutil pkgs.apacheHttpd pkgs.yajl ];
-
preConfigure = ''
-
export NIX_CFLAGS_COMPILE="$NIX_CFLAGS_COMPILE -I${pkgs.aprutil.dev}/include/apr-1 -I${pkgs.apacheHttpd.dev}/include -I${pkgs.apr.dev}/include/apr-1 -I${pkgs.yajl}/include"
-
'';
-
};
-
-
modsecurity-nginx = {
+
name = "modsecurity";
src = fetchFromGitHub {
name = "modsecurity-nginx";
owner = "SpiderLabs";
···
};
moreheaders = {
+
name = "moreheaders";
src = fetchFromGitHub {
name = "moreheaders";
owner = "openresty";
···
};
mpeg-ts = {
+
name = "mpeg-ts";
src = fetchFromGitHub {
name = "mpeg-ts";
owner = "arut";
···
};
naxsi = {
-
src = fetchFromGitHub
-
{
-
name = "naxsi";
-
owner = "nbs-system";
-
repo = "naxsi";
-
rev = "95ac520eed2ea04098a76305fd0ad7e9158840b7";
-
sha256 = "0b5pnqkgg18kbw5rf2ifiq7lsx5rqmpqsql6hx5ycxjzxj6acfb3";
-
} + "/naxsi_src";
+
name = "naxsi";
+
src = fetchFromGitHub {
+
name = "naxsi";
+
owner = "nbs-system";
+
repo = "naxsi";
+
rev = "95ac520eed2ea04098a76305fd0ad7e9158840b7";
+
sha256 = "0b5pnqkgg18kbw5rf2ifiq7lsx5rqmpqsql6hx5ycxjzxj6acfb3";
+
} + "/naxsi_src";
};
njs = rec {
+
name = "njs";
src = fetchhg {
url = "https://hg.nginx.org/njs";
rev = "0.7.8";
···
};
opentracing = {
+
name = "opentracing";
src =
let src' = fetchFromGitHub {
name = "opentracing";
···
'';
in
{
+
name = "pagespeed";
src = ngx_pagespeed;
inputs = [ pkgs.zlib pkgs.libuuid ]; # psol deps
allowMemoryWriteExecute = true;
};
pam = {
+
name = "pam";
src = fetchFromGitHub {
name = "pam";
owner = "sto";
···
};
pinba = {
+
name = "pinba";
src = fetchFromGitHub {
name = "pinba";
owner = "tony2001";
···
};
push-stream = {
+
name = "push-stream";
src = fetchFromGitHub {
name = "push-stream";
owner = "wandenberg";
···
};
rtmp = {
+
name = "rtmp";
src = fetchFromGitHub {
name = "rtmp";
owner = "arut";
···
};
secure-token = {
+
name = "secure-token";
src = fetchFromGitHub {
name = "secure-token";
owner = "kaltura";
···
};
set-misc = {
+
name = "set-misc";
src = fetchFromGitHub {
name = "set-misc";
owner = "openresty";
···
};
shibboleth = {
+
name = "shibboleth";
src = fetchFromGitHub {
name = "shibboleth";
owner = "nginx-shib";
···
};
sla = {
+
name = "sla";
src = fetchFromGitHub {
name = "sla";
owner = "goldenclone";
···
};
slowfs-cache = {
+
name = "slowfs-cache";
src = fetchFromGitHub {
name = "slowfs-cache";
owner = "FRiCKLE";
···
};
sorted-querystring = {
+
name = "sorted-querystring";
src = fetchFromGitHub {
name = "sorted-querystring";
owner = "wandenberg";
···
};
spnego-http-auth = {
+
name = "spnego-http-auth";
src = fetchFromGitHub {
name = "spnego-http-auth";
owner = "stnoonan";
···
};
statsd = {
+
name = "statsd";
src = fetchFromGitHub {
name = "statsd";
owner = "harvesthq";
···
};
stream-sts = {
+
name = "stream-sts";
src = fetchFromGitHub {
name = "stream-sts";
owner = "vozlt";
···
};
sts = {
+
name = "sts";
src = fetchFromGitHub {
name = "sts";
owner = "vozlt";
···
};
subsFilter = {
+
name = "subsFilter";
src = fetchFromGitHub {
name = "subsFilter";
owner = "yaoweibin";
···
};
sysguard = {
+
name = "sysguard";
src = fetchFromGitHub {
name = "sysguard";
owner = "vozlt";
···
};
upload = {
+
name = "upload";
src = fetchFromGitHub {
name = "upload";
owner = "fdintino";
···
};
upstream-check = {
+
name = "upstream-check";
src = fetchFromGitHub {
name = "upstream-check";
owner = "yaoweibin";
···
};
upstream-tarantool = {
+
name = "upstream-tarantool";
src = fetchFromGitHub {
name = "upstream-tarantool";
owner = "tarantool";
···
};
url = {
+
name = "url";
src = fetchFromGitHub {
name = "url";
owner = "vozlt";
···
};
video-thumbextractor = {
+
name = "video-thumbextractor";
src = fetchFromGitHub {
name = "video-thumbextractor";
owner = "wandenberg";
···
};
vod = {
+
name = "vod";
src = fetchFromGitHub {
name = "vod";
owner = "kaltura";
···
};
vts = {
+
name = "vts";
src = fetchFromGitHub {
name = "vts";
owner = "vozlt";
···
sha256 = "sha256-x4ry5ljPeJQY+7Mp04/xYIGf22d6Nee7CSqHezdK4gQ=";
};
};
+
}; in self // lib.optionalAttrs config.allowAliases {
+
# deprecated or renamed packages
+
modsecurity-nginx = self.modsecurity;
}
+1 -1
pkgs/top-level/all-packages.nix
···
tengine = callPackage ../servers/http/tengine {
openssl = openssl_1_1;
-
modules = with nginxModules; [ rtmp dav moreheaders modsecurity-nginx ];
+
modules = with nginxModules; [ rtmp dav moreheaders modsecurity ];
tennix = callPackage ../games/tennix { };