summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMel <mel@rnrd.eu>2025-08-22 03:15:45 +0200
committerMel <mel@rnrd.eu>2025-08-22 03:15:45 +0200
commit9e4dc7114f74ed5b86cca8d34cb62b333081a4fe (patch)
treee8e56264d19e8969c696d95221a0f95191e11bf6
parent053dcf87674a3c75245f87ee69beab197e8fb7a8 (diff)
downloadnetwork-9e4dc7114f74ed5b86cca8d34cb62b333081a4fe.tar.zst
network-9e4dc7114f74ed5b86cca8d34cb62b333081a4fe.zip
Grab real remote IP through Cloudflare proxy
Signed-off-by: Mel <mel@rnrd.eu>
-rw-r--r--flake.lock26
-rw-r--r--flake.nix9
-rw-r--r--modules/foundation/www/default.nix63
3 files changed, 79 insertions, 19 deletions
diff --git a/flake.lock b/flake.lock
index fc4718c..f78d47f 100644
--- a/flake.lock
+++ b/flake.lock
@@ -25,6 +25,30 @@
"type": "github"
}
},
+ "cloudflare-ips-v4": {
+ "flake": false,
+ "locked": {
+ "narHash": "sha256-V4dThTb8iw02hjngubVtSJbEeWgOS1e/ODt1fLjLZvk=",
+ "type": "file",
+ "url": "https://www.cloudflare.com/ips-v4"
+ },
+ "original": {
+ "type": "file",
+ "url": "https://www.cloudflare.com/ips-v4"
+ }
+ },
+ "cloudflare-ips-v6": {
+ "flake": false,
+ "locked": {
+ "narHash": "sha256-BgpkXCAh/MmK3GTAElKiGJctCYUN+/UgvpuawqGmitE=",
+ "type": "file",
+ "url": "https://www.cloudflare.com/ips-v6"
+ },
+ "original": {
+ "type": "file",
+ "url": "https://www.cloudflare.com/ips-v6"
+ }
+ },
"darwin": {
"inputs": {
"nixpkgs": [
@@ -149,6 +173,8 @@
"root": {
"inputs": {
"agenix": "agenix",
+ "cloudflare-ips-v4": "cloudflare-ips-v4",
+ "cloudflare-ips-v6": "cloudflare-ips-v6",
"flake-compat": "flake-compat",
"home-manager": "home-manager",
"nixos-hardware": "nixos-hardware",
diff --git a/flake.nix b/flake.nix
index 53de231..16ef267 100644
--- a/flake.nix
+++ b/flake.nix
@@ -25,6 +25,15 @@
url = "github:sjhgvr/oisd";
flake = false;
};
+
+ cloudflare-ips-v4 = {
+ url = "https://www.cloudflare.com/ips-v4";
+ flake = false;
+ };
+ cloudflare-ips-v6 = {
+ url = "https://www.cloudflare.com/ips-v6";
+ flake = false;
+ };
};
outputs = inputs @ { self, nixpkgs, nixpkgs-unstable, home-manager, agenix, ... }:
diff --git a/modules/foundation/www/default.nix b/modules/foundation/www/default.nix
index 97e2f2f..5030799 100644
--- a/modules/foundation/www/default.nix
+++ b/modules/foundation/www/default.nix
@@ -4,6 +4,8 @@
pkgs,
lib,
util,
+ cloudflare-ips-v4,
+ cloudflare-ips-v6,
...
}:
@@ -13,6 +15,9 @@ let
mkIf
mkEnableOption
mkOption
+ concatMapStrings
+ concatLines
+ splitString
;
inherit (config.age) secrets;
@@ -109,25 +114,45 @@ in
statusPage = true;
- commonHttpConfig = ''
- log_format json_combined escape=json '{'
- '"time_local":"$time_local",'
- '"remote_addr":"$remote_addr",'
- '"remote_user":"$remote_user",'
- '"request":"$request",'
- '"status": "$status",'
- '"body_bytes_sent":"$body_bytes_sent",'
- '"request_length":"$request_length",'
- '"request_time":"$request_time",'
- '"http_referrer":"$http_referer",'
- '"http_user_agent":"$http_user_agent",'
- '"upstream_response_time":"$upstream_response_time",'
- '"upstream_addr":"$upstream_addr",'
- '"upstream_status":"$upstream_status"'
- '}';
- access_log /var/log/nginx/access.log json_combined;
- error_log /var/log/nginx/error.log warn;
- '';
+ commonHttpConfig =
+ let
+ logs = ''
+ log_format json_combined escape=json '{'
+ '"time_local":"$time_local",'
+ '"remote_addr":"$remote_addr",'
+ '"remote_user":"$remote_user",'
+ '"request":"$request",'
+ '"status": "$status",'
+ '"body_bytes_sent":"$body_bytes_sent",'
+ '"request_length":"$request_length",'
+ '"request_time":"$request_time",'
+ '"http_referrer":"$http_referer",'
+ '"http_user_agent":"$http_user_agent",'
+ '"upstream_response_time":"$upstream_response_time",'
+ '"upstream_addr":"$upstream_addr",'
+ '"upstream_status":"$upstream_status",'
+ '"cf_connecting_ip":"$http_cf_connecting_ip"'
+ '}';
+ access_log /var/log/nginx/access.log json_combined;
+ error_log /var/log/nginx/error.log warn;
+ '';
+
+ cloudflareAddresses = builtins.filter (ip: ip != "") (
+ splitString "\n" ''
+ ${builtins.readFile cloudflare-ips-v4}
+ ${builtins.readFile cloudflare-ips-v6}
+ ''
+ );
+
+ realIpLine = ip: "set_real_ip_from ${ip};\n";
+
+ cloudflare = ''
+ ${concatMapStrings realIpLine cloudflareAddresses}
+
+ real_ip_header CF-Connecting-IP;
+ '';
+ in
+ concatLines [ logs cloudflare ];
virtualHosts = {
base = mkIf cfg.public (defaultHost rnrdUrl "rnrd.eu" cfg.defaultPage "base");