diff --git a/nix/module.nix b/nix/module.nix index ef4000d..e492aae 100644 --- a/nix/module.nix +++ b/nix/module.nix @@ -1,37 +1,19 @@ -# NixOS Module for Eris Tarpit self: { config, lib, pkgs, ... }: let - inherit (builtins) toJSON toString; + inherit (builtins) toString; inherit (lib.modules) mkIf; inherit (lib.options) mkOption mkEnableOption literalExpression; - inherit (lib.types) package str port int listOf enum bool attrsOf path; + inherit (lib.types) package str int listOf enum bool attrsOf path submodule; inherit (lib.lists) optionals; cfg = config.services.eris; - - # Generate the config.json content - erisConfigFile = pkgs.writeText "eris-config.json" (toJSON { - listen_addr = cfg.listenAddress; - metrics_addr = cfg.metricsAddress; - backend_addr = cfg.backendAddress; - min_delay = cfg.minDelay; - max_delay = cfg.maxDelay; - max_tarpit_time = cfg.maxTarpitTime; - block_threshold = cfg.blockThreshold; - trap_patterns = cfg.trapPatterns; - whitelist_networks = cfg.whitelistNetworks; - markov_corpora_dir = "${cfg.dataDir}/corpora"; - lua_scripts_dir = "${cfg.dataDir}/scripts"; - data_dir = cfg.dataDir; - config_dir = "${cfg.stateDir}/conf"; - cache_dir = cfg.cacheDir; - }); + erisConfigFile = pkgs.writers.writeJSON "eris-config.json" cfg.settings; in { - ###### interface + ####### interface options = { services.eris = { enable = mkEnableOption "Eris Tarpit Service"; @@ -43,85 +25,7 @@ in { description = "The Eris package to use."; }; - listenAddress = mkOption { - type = str; - default = "0.0.0.0:8888"; - description = "The IP address and port for the main tarpit service to listen on."; - example = "127.0.0.1:9999"; - }; - - metricsAddress = mkOption { - type = str; - default = "0.0.0.0:9100"; - example = "127.0.0.1:9100"; - description = "The IP address and port for the Prometheus metrics endpoint."; - }; - - backendAddress = mkOption { - type = str; - default = "127.0.0.1:80"; - description = "The address of the backend service to proxy legitimate requests to."; - example = "10.0.0.5:8080"; - }; - - minDelay = mkOption { - type = int; - default = 1000; - description = "Minimum delay (in ms) between sending characters in tarpit mode."; - }; - - maxDelay = mkOption { - type = int; - default = 15000; - description = "Maximum delay (in ms) between sending characters in tarpit mode."; - }; - - maxTarpitTime = mkOption { - type = int; - default = 600; - description = "Maximum time (in seconds) a single connection can be held in the tarpit."; - }; - - blockThreshold = mkOption { - type = int; - default = 3; - description = "Number of hits from an IP before it gets permanently blocked."; - }; - - trapPatterns = mkOption { - type = listOf str; - default = [ - "/vendor/phpunit" - "eval-stdin.php" - "/wp-admin" - "/wp-login.php" - "/xmlrpc.php" - "/phpMyAdmin" - "/solr/" - "/.env" - "/config" - "/api/" - "/actuator/" - ]; - description = "List of URL path substrings that trigger the tarpit."; - example = literalExpression '' - [ "/.git/config", "/admin" ] - ''; - }; - - whitelistNetworks = mkOption { - type = listOf str; - default = [ - "192.168.0.0/16" - "10.0.0.0/8" - "172.16.0.0/12" - "127.0.0.0/8" - ]; - example = literalExpression "[ \"192.168.1.0/24\" ]"; - description = "List of CIDR networks whose IPs should never be tarpitted."; - }; - - logLevel = mkOption { + log_level = mkOption { type = enum ["error" "warn" "info" "debug" "trace"]; default = "info"; description = "Logging level for the Eris service."; @@ -132,6 +36,7 @@ in { default = "eris"; description = "User account under which Eris runs."; }; + group = mkOption { type = str; default = "eris"; @@ -188,6 +93,91 @@ in { ''; }; + settings = mkOption { + default = {}; + type = attrsOf (submodule { + options = { + listen_address = mkOption { + type = str; + default = "0.0.0.0:8888"; + description = "The IP address and port for the main tarpit service to listen on."; + example = "127.0.0.1:9999"; + }; + + metrics_address = mkOption { + type = str; + default = "0.0.0.0:9100"; + example = "127.0.0.1:9100"; + description = "The IP address and port for the Prometheus metrics endpoint."; + }; + + backend_address = mkOption { + type = str; + default = "127.0.0.1:80"; + description = "The address of the backend service to proxy legitimate requests to."; + example = "10.0.0.5:8080"; + }; + + min_delay = mkOption { + type = int; + default = 1000; + description = "Minimum delay (in ms) between sending characters in tarpit mode."; + }; + + max_delay = mkOption { + type = int; + default = 15000; + description = "Maximum delay (in ms) between sending characters in tarpit mode."; + }; + + max_tarpit_time = mkOption { + type = int; + default = 600; + description = "Maximum time (in seconds) a single connection can be held in the tarpit."; + }; + + block_threshold = mkOption { + type = int; + default = 3; + description = "Number of hits from an IP before it gets permanently blocked."; + }; + + trap_patterns = mkOption { + type = listOf str; + default = [ + "/vendor/phpunit" + "eval-stdin.php" + "/wp-admin" + "/wp-login.php" + "/xmlrpc.php" + "/phpMyAdmin" + "/solr/" + "/.env" + "/config" + "/api/" + "/actuator/" + ]; + description = "List of URL path substrings that trigger the tarpit."; + example = literalExpression '' + [ "/.git/config", "/admin" ] + ''; + }; + + whitelist_networks = mkOption { + type = listOf str; + default = [ + "192.168.0.0/16" + "10.0.0.0/8" + "172.16.0.0/12" + "127.0.0.0/8" + ]; + example = literalExpression "[ \"192.168.1.0/24\" ]"; + description = "List of CIDR networks whose IPs should never be tarpitted."; + }; + }; + }); + }; + # Firewall integration options nftablesIntegration = mkOption { type = bool;