From 2f249a1e808b850d3cf9bab710bd6351f7ee0bb4 Mon Sep 17 00:00:00 2001 From: Dmitry Voronin Date: Sat, 1 Jun 2024 10:37:49 +0300 Subject: [PATCH 1/5] wip --- container/Change.nix | 34 ++++ container/Paste.nix | 129 ++++++++++++ container/Postgres.nix | 60 ++++++ container/Proxy.nix | 54 +++++ container/pastebin/Config.nix | 281 ++++++++++++++++++++++++++ container/pastebin/default.nix | 35 ++++ container/proxy/host/Paste.nix | 20 ++ host/desktop/Container.nix | 46 +++++ host/desktop/default.nix | 1 + host/work/Container.nix | 25 +++ host/work/default.nix | 1 + module/common/Kernel.nix | 52 ++--- module/common/httptoolkit/default.nix | 56 +++++ 13 files changed, 768 insertions(+), 26 deletions(-) create mode 100644 container/Change.nix create mode 100644 container/Paste.nix create mode 100644 container/Postgres.nix create mode 100644 container/Proxy.nix create mode 100644 container/pastebin/Config.nix create mode 100644 container/pastebin/default.nix create mode 100644 container/proxy/host/Paste.nix create mode 100644 host/desktop/Container.nix create mode 100644 host/work/Container.nix create mode 100644 module/common/httptoolkit/default.nix diff --git a/container/Change.nix b/container/Change.nix new file mode 100644 index 0000000..b3c0c43 --- /dev/null +++ b/container/Change.nix @@ -0,0 +1,34 @@ +{ pkgs +, storage +, const +, domain +, host +, util +, mkContainer +, mkContainerConfig +, ... } @args: let + path = "${storage}/change"; +in { + systemd.tmpfiles.rules = map ( + dirName: "d '${path}/${dirName}' 1777 root root - -" + ) [ "data" ]; + + containers.change = mkContainer { + autoStart = true; + localAddress = "10.1.0.41"; + privateNetwork = true; + + bindMounts = { + "/datastore" = { + hostPath = "${path}/data"; + isReadOnly = false; + }; + }; + + config = { config, lib, pkgs, ... }: mkContainerConfig { + services.changedetection-io = { + enable = true; + }; + }; + }; +} diff --git a/container/Paste.nix b/container/Paste.nix new file mode 100644 index 0000000..2e68566 --- /dev/null +++ b/container/Paste.nix @@ -0,0 +1,129 @@ +{ pkgs +, storage +, const +, domain +, host +, util +, mkContainer +, mkContainerConfig +, mkServer +, ... } @args: let + path = "${storage}/paste"; + package = (pkgs.callPackage ./pastebin args); + fqdn = "paste.${domain}"; +in { + systemd.tmpfiles.rules = map ( + dirName: "d '${path}/${dirName}' 1777 root root - -" + ) [ "data" "tmp" "nginxtmp" "config" ]; + + containers.paste = mkContainer { + autoStart = true; + hostAddress = host; + localAddress = "10.1.0.14"; + privateNetwork = true; + + bindMounts = { + "/srv/data" = { + hostPath = "${path}/data"; + isReadOnly = false; + }; + "/tmp" = { + hostPath = "${path}/tmp"; + isReadOnly = false; + }; + "/var/lib/nginx/tmp" = { + hostPath = "${path}/nginxtmp"; + isReadOnly = false; + }; + "/srv/config" = { + hostPath = "${path}/config"; + isReadOnly = false; + }; + }; + + config = { config, lib, ... }: mkContainerConfig { + system.stateVersion = const.stateVersion; + + users.users.root.password = ""; + users.mutableUsers = false; + + networking = { + useHostResolvConf = lib.mkForce false; + firewall.enable = false; + }; + + environment = { + systemPackages = [ package pkgs.neovim ]; + variables = { + }; + }; + + systemd.packages = [ package ]; + + users.users.paste = { + group = "nginx"; + isSystemUser = true; + }; + + services.phpfpm.pools.paste = { + user = "paste"; + group = "nginx"; + + phpPackage = pkgs.php; + + settings = { + "pm" = "dynamic"; + "php_admin_value[error_log]" = "stderr"; + "php_admin_flag[log_errors]" = true; + "listen.owner" = "nginx"; + "catch_workers_output" = true; + "pm.max_children" = "32"; + "pm.start_servers" = "2"; + "pm.min_spare_servers" = "2"; + "pm.max_spare_servers" = "4"; + "pm.max_requests" = "500"; + }; + + phpEnv = { + # CONFIG_PATH = "${package}/cfg"; + }; + }; + + services.nginx = { + enable = true; + virtualHosts.${fqdn} = mkServer { + default = true; + root = "${package}"; + + locations = { + "/".extraConfig = '' + rewrite ^ /index.php; + ''; + + "~ \\.php$".extraConfig = util.trimTabs '' + fastcgi_split_path_info ^(.+\.php)(/.+)$; + fastcgi_pass unix:${config.services.phpfpm.pools.paste.socket}; + include ${config.services.nginx.package}/conf/fastcgi.conf; + include ${config.services.nginx.package}/conf/fastcgi_params; + ''; + + "~ \\.(js|css|ttf|woff2?|png|jpe?g|svg)$".extraConfig = util.trimTabs '' + add_header Cache-Control "public, max-age=15778463"; + add_header X-Content-Type-Options nosniff; + add_header X-XSS-Protection "1; mode=block"; + add_header X-Robots-Tag none; + add_header X-Download-Options noopen; + add_header X-Permitted-Cross-Domain-Policies none; + add_header Referrer-Policy no-referrer; + access_log off; + ''; + }; + + extraConfig = util.trimTabs '' + try_files $uri /index.php; + ''; + }; + }; + }; + }; +} diff --git a/container/Postgres.nix b/container/Postgres.nix new file mode 100644 index 0000000..266bcbc --- /dev/null +++ b/container/Postgres.nix @@ -0,0 +1,60 @@ +{ pkgs +, storage +, const +, domain +, host +, util +, mkContainer +, mkContainerConfig +, ... } @args: let + path = "${storage}/postgres"; +in { + systemd.tmpfiles.rules = map ( + dirName: "d '${path}/${dirName}' 1777 root root - -" + ) [ "data" ]; + + containers.postgres = mkContainer { + autoStart = true; + localAddress = "10.1.0.3"; + privateNetwork = true; + + bindMounts = { + "/var/lib/postgresql/data" = { + hostPath = "${path}/data"; + isReadOnly = false; + }; + }; + + config = { config, lib, pkgs, ... }: mkContainerConfig { + system.stateVersion = const.stateVersion; + + users.users.root.password = ""; + users.mutableUsers = false; + + networking = { + useHostResolvConf = lib.mkForce false; + firewall.enable = false; + }; + + services.postgresql = let + databases = [ + "privatebin" + ]; + in { + enable = true; + package = pkgs.postgresql_14; + dataDir = "/var/lib/postgresql/data/14"; + enableTCPIP = true; + authentication = '' + host all all ${host}/32 trust + host privatebin privatebin 10.1.0.14/32 trust + ''; + ensureDatabases = databases; + ensureUsers = map (name: { + inherit name; + ensureDBOwnership = true; + }) databases; + }; + }; + }; +} diff --git a/container/Proxy.nix b/container/Proxy.nix new file mode 100644 index 0000000..050fb69 --- /dev/null +++ b/container/Proxy.nix @@ -0,0 +1,54 @@ +{ pkgs +, storage +, const +, domain +, host +, util +, mkContainer +, mkContainerConfig +, ... } @args: let + path = "${storage}/proxy"; + virtualHosts = util.catSet (util.ls ./proxy/host) args; +in { + systemd.tmpfiles.rules = map ( + dirName: "d '${path}/${dirName}' 1777 root root - -" + ) [ "challenge" "letsencrypt" ]; + + containers.proxy = mkContainer { + autoStart = true; + hostAddress = host; + localAddress = "10.1.0.2"; + privateNetwork = true; + + bindMounts = { + "/etc/letsencrypt" = { + hostPath = "${path}/letsencrypt"; + isReadOnly = true; + }; + "/var/www/.well-known" = { + hostPath = "${path}/challenge"; + isReadOnly = false; + }; + }; + + config = { config, lib, pkgs, ... }: mkContainerConfig { + system.stateVersion = const.stateVersion; + + users.users.root.password = ""; + users.mutableUsers = false; + + networking = { + useHostResolvConf = lib.mkForce false; + firewall.enable = false; + }; + + environment.systemPackages = with pkgs; [ certbot ]; + + services.nginx = { + inherit virtualHosts; + + enable = true; + }; + }; + }; +} diff --git a/container/pastebin/Config.nix b/container/pastebin/Config.nix new file mode 100644 index 0000000..e149bbd --- /dev/null +++ b/container/pastebin/Config.nix @@ -0,0 +1,281 @@ +{ util, ... }: { + text = util.trimTabs '' + ;project page." + + ; (optional) notice to display + ; notice = "Note: This is a test service: Data may be deleted anytime. Kittens will die if you abuse this service." + + ; by default PrivateBin will guess the visitors language based on the browsers + ; settings. Optionally you can enable the language selection menu, which uses + ; a session cookie to store the choice until the browser is closed. + languageselection = false + + ; set the language your installs defaults to, defaults to English + ; if this is set and language selection is disabled, this will be the only language + ; languagedefault = "en" + + ; (optional) URL shortener address to offer after a new paste is created. + ; It is suggested to only use this with self-hosted shorteners as this will leak + ; the pastes encryption key. + ; urlshortener = "https://shortener.example.com/api?link=" + + ; (optional) Let users create a QR code for sharing the paste URL with one click. + ; It works both when a new paste is created and when you view a paste. + ; qrcode = true + + ; (optional) Let users send an email sharing the paste URL with one click. + ; It works both when a new paste is created and when you view a paste. + ; email = true + + ; (optional) IP based icons are a weak mechanism to detect if a comment was from + ; a different user when the same username was used in a comment. It might get + ; used to get the IP of a comment poster if the server salt is leaked and a + ; SHA512 HMAC rainbow table is generated for all (relevant) IPs. + ; Can be set to one these values: + ; "none" / "identicon" (default) / "jdenticon" / "vizhash". + ; icon = "none" + + ; Content Security Policy headers allow a website to restrict what sources are + ; allowed to be accessed in its context. You need to change this if you added + ; custom scripts from third-party domains to your templates, e.g. tracking + ; scripts or run your site behind certain DDoS-protection services. + ; Check the documentation at https://content-security-policy.com/ + ; Notes: + ; - If you use any bootstrap theme, you can remove the allow-popups from the + ; sandbox restrictions. + ; - If you use the bootstrap5 theme, you must change default-src to 'self' to + ; enable display of the svg icons + ; - By default this disallows to load images from third-party servers, e.g. when + ; they are embedded in pastes. If you wish to allow that, you can adjust the + ; policy here. See https://github.com/PrivateBin/PrivateBin/wiki/FAQ#why-does-not-it-load-embedded-images + ; for details. + ; - The 'unsafe-eval' is used in two cases; to check if the browser supports + ; async functions and display an error if not and for Chrome to enable + ; webassembly support (used for zlib compression). You can remove it if Chrome + ; doesn't need to be supported and old browsers don't need to be warned. + ; cspheader = "default-src 'none'; base-uri 'self'; form-action 'none'; manifest-src 'self'; connect-src * blob:; script-src 'self' 'unsafe-eval'; style-src 'self'; font-src 'self'; frame-ancestors 'none'; img-src 'self' data: blob:; media-src blob:; object-src blob:; sandbox allow-same-origin allow-scripts allow-forms allow-popups allow-modals allow-downloads" + + ; stay compatible with PrivateBin Alpha 0.19, less secure + ; if enabled will use base64.js version 1.7 instead of 2.1.9 and sha1 instead of + ; sha256 in HMAC for the deletion token + ; zerobincompatibility = false + + ; Enable or disable the warning message when the site is served over an insecure + ; connection (insecure HTTP instead of HTTPS), defaults to true. + ; Secure transport methods like Tor and I2P domains are automatically whitelisted. + ; It is **strongly discouraged** to disable this. + ; See https://github.com/PrivateBin/PrivateBin/wiki/FAQ#why-does-it-show-me-an-error-about-an-insecure-connection for more information. + ; httpwarning = true + + ; Pick compression algorithm or disable it. Only applies to pastes/comments + ; created after changing the setting. + ; Can be set to one these values: "none" / "zlib" (default). + ; compression = "zlib" + + [expire] + ; expire value that is selected per default + ; make sure the value exists in [expire_options] + default = "1week" + + [expire_options] + ; Set each one of these to the number of seconds in the expiration period, + ; or 0 if it should never expire + 5min = 300 + 10min = 600 + 1hour = 3600 + 1day = 86400 + 1week = 604800 + ; Well this is not *exactly* one month, it's 30 days: + 1month = 2592000 + 1year = 31536000 + never = 0 + + [formatter_options] + ; Set available formatters, their order and their labels + plaintext = "Plain Text" + syntaxhighlighting = "Source Code" + markdown = "Markdown" + + [traffic] + ; time limit between calls from the same IP address in seconds + ; Set this to 0 to disable rate limiting. + limit = 10 + + ; (optional) Set IPs addresses (v4 or v6) or subnets (CIDR) which are exempted + ; from the rate-limit. Invalid IPs will be ignored. If multiple values are to + ; be exempted, the list needs to be comma separated. Leave unset to disable + ; exemptions. + ; exempted = "1.2.3.4,10.10.10/24" + + ; (optional) If you want only some source IP addresses (v4 or v6) or subnets + ; (CIDR) to be allowed to create pastes, set these here. Invalid IPs will be + ; ignored. If multiple values are to be exempted, the list needs to be comma + ; separated. Leave unset to allow anyone to create pastes. + ; creators = "1.2.3.4,10.10.10/24" + + ; (optional) if your website runs behind a reverse proxy or load balancer, + ; set the HTTP header containing the visitors IP address, i.e. X_FORWARDED_FOR + ; header = "X_FORWARDED_FOR" + + [purge] + ; minimum time limit between two purgings of expired pastes, it is only + ; triggered when pastes are created + ; Set this to 0 to run a purge every time a paste is created. + limit = 300 + + ; maximum amount of expired pastes to delete in one purge + ; Set this to 0 to disable purging. Set it higher, if you are running a large + ; site + batchsize = 10 + + ;[model] + ; name of data model class to load and directory for storage + ; the default model "Filesystem" stores everything in the filesystem + ;class = Filesystem + ;[model_options] + ;dir = PATH "data" + + ;[model] + ; example of a Google Cloud Storage configuration + ;class = GoogleCloudStorage + ;[model_options] + ;bucket = "my-private-bin" + ;prefix = "pastes" + ;uniformacl = false + + ;[model] + ; example of DB configuration for MySQL + ;class = Database + ;[model_options] + ;dsn = "mysql:host=localhost;dbname=privatebin;charset=UTF8" + ;tbl = "privatebin_" ; table prefix + ;usr = "privatebin" + ;pwd = "Z3r0P4ss" + ;opt[12] = true ; PDO::ATTR_PERSISTENT + + ;[model] + ; example of DB configuration for SQLite + ;class = Database + ;[model_options] + ;dsn = "sqlite:" PATH "data/db.sq3" + ;usr = null + ;pwd = null + ;opt[12] = true ; PDO::ATTR_PERSISTENT + + [model] + ; example of DB configuration for PostgreSQL + class = Database + [model_options] + dsn = "pgsql:host=10.1.0.3;dbname=privatebin" + tbl = "privatebin_" ; table prefix + usr = "privatebin" + pwd = "privatebin" + opt[12] = true ; PDO::ATTR_PERSISTENT + + ;[model] + ; example of S3 configuration for Rados gateway / CEPH + ;class = S3Storage + ;[model_options] + ;region = "" + ;version = "2006-03-01" + ;endpoint = "https://s3.my-ceph.invalid" + ;use_path_style_endpoint = true + ;bucket = "my-bucket" + ;accesskey = "my-rados-user" + ;secretkey = "my-rados-pass" + + ;[model] + ; example of S3 configuration for AWS + ;class = S3Storage + ;[model_options] + ;region = "eu-central-1" + ;version = "latest" + ;bucket = "my-bucket" + ;accesskey = "access key id" + ;secretkey = "secret access key" + + ;[model] + ; example of S3 configuration for AWS using its SDK default credential provider chain + ; if relying on environment variables, the AWS SDK will look for the following: + ; - AWS_ACCESS_KEY_ID + ; - AWS_SECRET_ACCESS_KEY + ; - AWS_SESSION_TOKEN (if needed) + ; for more details, see https://docs.aws.amazon.com/sdk-for-php/v3/developer-guide/guide_credentials.html#default-credential-chain + ;class = S3Storage + ;[model_options] + ;region = "eu-central-1" + ;version = "latest" + ;bucket = "my-bucket" + + [yourls] + ; When using YOURLS as a "urlshortener" config item: + ; - By default, "urlshortener" will point to the YOURLS API URL, with or without + ; credentials, and will be visible in public on the PrivateBin web page. + ; Only use this if you allow short URL creation without credentials. + ; - Alternatively, using the parameters in this section ("signature" and + ; "apiurl"), "urlshortener" needs to point to the base URL of your PrivateBin + ; instance with "?shortenviayourls&link=" appended. For example: + ; urlshortener = "''${basepath}?shortenviayourls&link=" + ; This URL will in turn call YOURLS on the server side, using the URL from + ; "apiurl" and the "access signature" from the "signature" parameters below. + + ; (optional) the "signature" (access key) issued by YOURLS for the using account + ; signature = "" + ; (optional) the URL of the YOURLS API, called to shorten a PrivateBin URL + ; apiurl = "https://yourls.example.com/yourls-api.php" + ''; +} diff --git a/container/pastebin/default.nix b/container/pastebin/default.nix new file mode 100644 index 0000000..a59dc88 --- /dev/null +++ b/container/pastebin/default.nix @@ -0,0 +1,35 @@ +{ php, pkgs, util, ... } @args: let + cfg = pkgs.writeText "PrivateBinConfig" (import ./Config.nix args).text; +in php.buildComposerProject (finalAttrs: { + pname = "PrivateBin"; + version = "1.7.3"; + + src = pkgs.fetchFromGitHub { + owner = "PrivateBin"; + repo = "PrivateBin"; + rev = finalAttrs.version; + hash = "sha256-9aTpLixvvyy3xTk8QQFj4rI6gFtElO4naPgTARtpo1k="; + }; + + vendorHash = "sha256-JGuO8kXLLXqq76EccdNSoHwYO5OuJT3Au1O2O2szAHI="; + + installPhase = '' + runHook preInstall + + mv $out/share/php/PrivateBin/* $out + rm -r $out/share + + cp ${cfg} $out/cfg/conf.php + + touch $out/.env + pushd $out + + runHook postInstall + ''; + + postFixup = '' + substituteInPlace $out/index.php --replace-fail \ + "define('PATH', ''')" \ + "define('PATH', '$out/')" + ''; +}) diff --git a/container/proxy/host/Paste.nix b/container/proxy/host/Paste.nix new file mode 100644 index 0000000..b053571 --- /dev/null +++ b/container/proxy/host/Paste.nix @@ -0,0 +1,20 @@ +{ domain, util, mkServer, ... }: { + "paste.${domain}" = mkServer { + extraConfig = util.trimTabs '' + listen 443 ssl; + set $paste 10.1.0.14:80; + + location = / { + return 403; + } + location / { + proxy_pass http://$paste$request_uri; + } + + ssl_certificate /etc/letsencrypt/live/${domain}/fullchain.pem; + ssl_certificate_key /etc/letsencrypt/live/${domain}/privkey.pem; + include /etc/letsencrypt/conf/options-ssl-nginx.conf; + ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem; + ''; + }; +} diff --git a/host/desktop/Container.nix b/host/desktop/Container.nix new file mode 100644 index 0000000..a25172c --- /dev/null +++ b/host/desktop/Container.nix @@ -0,0 +1,46 @@ +{ pkgs, const, lib, config, util, ... }: let + args = let + storage = "/storage/hot/container"; + domain = "local"; + host = "192.168.1.3"; + in { + inherit storage domain host pkgs const lib config util; + + mkContainer = cfg: lib.recursiveUpdate cfg { + hostAddress = host; + }; + + mkContainerConfig = cfg: lib.recursiveUpdate cfg { + system.stateVersion = const.stateVersion; + + users.users.root.password = ""; + users.mutableUsers = false; + + networking = { + useHostResolvConf = lib.mkForce false; + firewall.enable = false; + }; + }; + + mkServer = cfg: lib.recursiveUpdate cfg { + forceSSL = false; + }; + }; +in { + networking.nat = { + enable = true; + internalInterfaces = [ "ve-+" ]; + externalInterface = "enp4s0"; + }; + + # NOTE: Remove this. + networking.extraHosts = '' + 10.1.0.2 paste.local + ''; + + imports = [ + (import ../../container/Paste.nix args) + (import ../../container/Postgres.nix args) + (import ../../container/Proxy.nix args) + ]; +} diff --git a/host/desktop/default.nix b/host/desktop/default.nix index 277f895..297578d 100644 --- a/host/desktop/default.nix +++ b/host/desktop/default.nix @@ -1,5 +1,6 @@ { ... }: { imports = [ + ./Container.nix ./Filesystem.nix ]; } diff --git a/host/work/Container.nix b/host/work/Container.nix new file mode 100644 index 0000000..a79278b --- /dev/null +++ b/host/work/Container.nix @@ -0,0 +1,25 @@ +{ pkgs, const, lib, config, util, ... }: let + args = let + storage = "/tmp/container"; + domain = "local"; + host = "192.168.0.174"; + in { + inherit storage domain host pkgs const lib config util; + }; +in { + networking.nat = { + enable = true; + internalInterfaces = [ "ve-+" ]; + externalInterface = "enp4s0"; + }; + + # NOTE: Remove this. + networking.extraHosts = '' + 10.1.0.2 paste.local + ''; + + imports = [ + (import ../../container/Paste.nix args) + (import ../../container/Proxy.nix args) + ]; +} diff --git a/host/work/default.nix b/host/work/default.nix index 6ac0fae..94f3dbb 100644 --- a/host/work/default.nix +++ b/host/work/default.nix @@ -1,5 +1,6 @@ { lib, ... }: { imports = [ + ./Container.nix ./Fprint.nix ]; diff --git a/module/common/Kernel.nix b/module/common/Kernel.nix index 91b3f1a..718e91a 100644 --- a/module/common/Kernel.nix +++ b/module/common/Kernel.nix @@ -3,24 +3,24 @@ boot.kernelPackages = pkgs.linuxPackages_latest; boot.kernel.sysctl = { - # Spoof protection. - "net.ipv4.conf.default.rp_filter" = 1; - "net.ipv4.conf.all.rp_filter" = 1; + # # Spoof protection. + # "net.ipv4.conf.default.rp_filter" = 1; + # "net.ipv4.conf.all.rp_filter" = 1; - # Packet forwarding. - "net.ipv4.ip_forward" = 1; - # "net.ipv6.conf.all.forwarding" = 1; + # # Packet forwarding. + # "net.ipv4.ip_forward" = 1; + # # "net.ipv6.conf.all.forwarding" = 1; - # MITM protection. - "net.ipv4.conf.all.accept_redirects" = 0; - "net.ipv6.conf.all.accept_redirects" = 0; + # # MITM protection. + # "net.ipv4.conf.all.accept_redirects" = 0; + # "net.ipv6.conf.all.accept_redirects" = 0; - # Do not send ICMP redirects (we are not a router). - "net.ipv4.conf.all.send_redirects" = 0; + # # Do not send ICMP redirects (we are not a router). + # "net.ipv4.conf.all.send_redirects" = 0; - # Do not accept IP source route packets (we are not a router). - "net.ipv4.conf.all.accept_source_route" = 0; - "net.ipv6.conf.all.accept_source_route" = 0; + # # Do not accept IP source route packets (we are not a router). + # "net.ipv4.conf.all.accept_source_route" = 0; + # "net.ipv6.conf.all.accept_source_route" = 0; # Allow sysrq. "kernel.sysrq" = 1; @@ -36,23 +36,23 @@ "kernel.core_uses_pid" = 1; "kernel.kptr_restrict" = 2; - # IP hardening. - "net.ipv4.conf.all.log_martians" = 1; - "net.ipv4.conf.default.accept_redirects" = 0; - "net.ipv4.conf.default.accept_source_route" = 0; - "net.ipv4.conf.default.log_martians" = 0; - "net.ipv4.tcp_timestamps" = 0; - "net.ipv6.conf.default.accept_redirects" = 0; + # # IP hardening. + # "net.ipv4.conf.all.log_martians" = 1; + # "net.ipv4.conf.default.accept_redirects" = 0; + # "net.ipv4.conf.default.accept_source_route" = 0; + # "net.ipv4.conf.default.log_martians" = 0; + # "net.ipv4.tcp_timestamps" = 0; + # "net.ipv6.conf.default.accept_redirects" = 0; # Increase file watchers. "fs.inotify.max_user_instances" = 999999; "fs.inotify.max_user_watches" = 999999; "fs.inotify.max_user_event" = 999999; - # Disable ipv6. - "net.ipv6.conf.all.disable_ipv6" = 1; - "net.ipv6.conf.default.disable_ipv6" = 1; - "net.ipv6.conf.lo.disable_ipv6" = 1; - "net.ipv6.conf.eth0.disable_ipv6" = 1; + # # Disable ipv6. + # "net.ipv6.conf.all.disable_ipv6" = 1; + # "net.ipv6.conf.default.disable_ipv6" = 1; + # "net.ipv6.conf.lo.disable_ipv6" = 1; + # "net.ipv6.conf.eth0.disable_ipv6" = 1; }; } diff --git a/module/common/httptoolkit/default.nix b/module/common/httptoolkit/default.nix new file mode 100644 index 0000000..5f07a7c --- /dev/null +++ b/module/common/httptoolkit/default.nix @@ -0,0 +1,56 @@ +# Apple San Francisco and New York fonts. +# They are not available in Nixpkgs repo, so this script +# downloads the fonts from Apple website and adds them to Nix store. +{ lib, stdenv, fetchurl, pkgs }: stdenv.mkDerivation { + pname = "httptoolkit"; + version = "1.15.0"; + + src = fetchurl { + url = "https://github.com/httptoolkit/httptoolkit-desktop/releases/download/v1.15.0/HttpToolkit-linux-x64-1.15.0.zip"; + hash = "sha256-wb4is5IX1/Sjea4tggFP48snAx7+Bp4ux+306xFBMtM="; + }; + + nativeBuildInputs = with pkgs; [ + autoPatchelfHook + unzip + ]; + + sourceRoot = "."; + + buildInputs = with pkgs; [ + alsa-lib + atk + cairo + cups + dbus + expat + glib + gtk3 + libGL + libxkbcommon + mesa + nss + pango + playwright + xorg.libXcomposite + xorg.libXrandr + xorg.libxcb + ]; + + preBuild = '' + addAutoPatchelfSearchPath . + ''; + + installPhase = '' + runHook preInstall + mkdir -p $out/bin + cp -r * $out/bin + install -m755 -D httptoolkit $out/bin + runHook postInstall + ''; + + meta = with lib; { + homapage = "https://github.com/httptoolkit/httptoolkit-desktop"; + platform = platforms.linux; + }; +} -- 2.46.0 From 36fbc143d342150540f2683ad61458551e1dc9cd Mon Sep 17 00:00:00 2001 From: Dmitry Voronin Date: Sun, 9 Jun 2024 15:17:40 +0300 Subject: [PATCH 2/5] wip --- container/Change.nix | 7 ++--- container/Postgres.nix | 2 -- container/Proxy.nix | 49 +++++++++++++++++++++++++++++++- container/proxy/host/Change.nix | 20 +++++++++++++ container/proxy/host/Default.nix | 2 ++ host/desktop/Container.nix | 5 +++- host/work/Container.nix | 20 +++++++++++++ 7 files changed, 96 insertions(+), 9 deletions(-) create mode 100644 container/proxy/host/Change.nix create mode 100644 container/proxy/host/Default.nix diff --git a/container/Change.nix b/container/Change.nix index b3c0c43..47bcc7c 100644 --- a/container/Change.nix +++ b/container/Change.nix @@ -1,9 +1,5 @@ { pkgs , storage -, const -, domain -, host -, util , mkContainer , mkContainerConfig , ... } @args: let @@ -19,7 +15,7 @@ in { privateNetwork = true; bindMounts = { - "/datastore" = { + "/var/lib/changedetection-io" = { hostPath = "${path}/data"; isReadOnly = false; }; @@ -28,6 +24,7 @@ in { config = { config, lib, pkgs, ... }: mkContainerConfig { services.changedetection-io = { enable = true; + behindProxy = true; }; }; }; diff --git a/container/Postgres.nix b/container/Postgres.nix index 266bcbc..c459dc3 100644 --- a/container/Postgres.nix +++ b/container/Postgres.nix @@ -1,9 +1,7 @@ { pkgs , storage , const -, domain , host -, util , mkContainer , mkContainerConfig , ... } @args: let diff --git a/container/Proxy.nix b/container/Proxy.nix index 050fb69..3d5d3ad 100644 --- a/container/Proxy.nix +++ b/container/Proxy.nix @@ -1,9 +1,9 @@ { pkgs , storage , const -, domain , host , util +, domain , mkContainer , mkContainerConfig , ... } @args: let @@ -48,6 +48,53 @@ in { inherit virtualHosts; enable = true; + recommendedOptimisation = true; + recommendedProxySettings = true; + appendConfig = util.trimTabs '' + worker_processes 4; + ''; + eventsConfig = util.trimTabs '' + worker_connections 4096; + ''; + appendHttpConfig = util.trimTabs '' + server { + server_name default_server; + listen 80; + + location / { + return 301 https://$host$request_uri; + } + } + + map $http_accept_language $resume { + default https://git.${domain}/voronind/resume/releases/download/latest/voronind_en.pdf; + ~ru https://git.${domain}/voronind/resume/releases/download/latest/voronind_ru.pdf; + } + + server { + server_name ${domain}; + listen 443 ssl; + + ssl_certificate /etc/letsencrypt/live/${domain}/fullchain.pem; + ssl_certificate_key /etc/letsencrypt/live/${domain}/privkey.pem; + include /etc/letsencrypt/conf/options-ssl-nginx.conf; + ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem; + + return 301 $resume; + } + + server { + listen 443 ssl default_server; + server_name _; + + ssl_certificate /etc/letsencrypt/live/${domain}/fullchain.pem; + ssl_certificate_key /etc/letsencrypt/live/${domain}/privkey.pem; + include /etc/letsencrypt/conf/options-ssl-nginx.conf; + ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem; + + return 403; + } + ''; }; }; }; diff --git a/container/proxy/host/Change.nix b/container/proxy/host/Change.nix new file mode 100644 index 0000000..9c855d7 --- /dev/null +++ b/container/proxy/host/Change.nix @@ -0,0 +1,20 @@ +{ domain, util, mkServer, ... }: { + "change.${domain}" = mkServer { + extraConfig = util.trimTabs '' + listen 443 ssl; + set $change 10.1.0.41:5000; + + location / { + allow 192.168.1.0/24; + allow 10.1.0.1; + deny all; + proxy_pass http://$change$request_uri; + } + + ssl_certificate /etc/letsencrypt/live/${domain}/fullchain.pem; + ssl_certificate_key /etc/letsencrypt/live/${domain}/privkey.pem; + include /etc/letsencrypt/conf/options-ssl-nginx.conf; + ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem; + ''; + }; +} diff --git a/container/proxy/host/Default.nix b/container/proxy/host/Default.nix new file mode 100644 index 0000000..f365d8e --- /dev/null +++ b/container/proxy/host/Default.nix @@ -0,0 +1,2 @@ +{ domain, util, mkServer, ... }: { +} diff --git a/host/desktop/Container.nix b/host/desktop/Container.nix index a25172c..8dd6a1b 100644 --- a/host/desktop/Container.nix +++ b/host/desktop/Container.nix @@ -33,12 +33,15 @@ in { externalInterface = "enp4s0"; }; - # NOTE: Remove this. + # TODO: Remove this. networking.extraHosts = '' 10.1.0.2 paste.local + 10.1.0.2 change.local + 10.1.0.2 local ''; imports = [ + (import ../../container/Change.nix args) (import ../../container/Paste.nix args) (import ../../container/Postgres.nix args) (import ../../container/Proxy.nix args) diff --git a/host/work/Container.nix b/host/work/Container.nix index a79278b..fcb3216 100644 --- a/host/work/Container.nix +++ b/host/work/Container.nix @@ -5,6 +5,26 @@ host = "192.168.0.174"; in { inherit storage domain host pkgs const lib config util; + + mkContainer = cfg: lib.recursiveUpdate cfg { + hostAddress = host; + }; + + mkContainerConfig = cfg: lib.recursiveUpdate cfg { + system.stateVersion = const.stateVersion; + + users.users.root.password = ""; + users.mutableUsers = false; + + networking = { + useHostResolvConf = lib.mkForce false; + firewall.enable = false; + }; + }; + + mkServer = cfg: lib.recursiveUpdate cfg { + forceSSL = false; + }; }; in { networking.nat = { -- 2.46.0 From 2cc71a7a349d9ed4353c6785f849c709cab4ae2a Mon Sep 17 00:00:00 2001 From: Dmitry Voronin Date: Sun, 9 Jun 2024 15:31:53 +0300 Subject: [PATCH 3/5] wip --- container/Change.nix | 28 ++++++++++++++-------------- container/Paste.nix | 22 ++++++++++------------ container/Postgres.nix | 21 +++++++++------------ container/Proxy.nix | 24 ++++++++++-------------- container/proxy/host/Default.nix | 2 -- host/desktop/Container.nix | 9 +++++++-- 6 files changed, 50 insertions(+), 56 deletions(-) delete mode 100644 container/proxy/host/Default.nix diff --git a/container/Change.nix b/container/Change.nix index 47bcc7c..2471ef3 100644 --- a/container/Change.nix +++ b/container/Change.nix @@ -1,19 +1,17 @@ -{ pkgs -, storage +{ storage +, domain , mkContainer , mkContainerConfig +, mkContainerDir , ... } @args: let - path = "${storage}/change"; + address = "10.1.0.41"; + path = "${storage}/change"; in { - systemd.tmpfiles.rules = map ( - dirName: "d '${path}/${dirName}' 1777 root root - -" - ) [ "data" ]; - - containers.change = mkContainer { - autoStart = true; - localAddress = "10.1.0.41"; - privateNetwork = true; + systemd.tmpfiles.rules = map (dir: mkContainerDir "${path}/${dir}") [ + "data" + ]; + containers.change = mkContainer address { bindMounts = { "/var/lib/changedetection-io" = { hostPath = "${path}/data"; @@ -21,10 +19,12 @@ in { }; }; - config = { config, lib, pkgs, ... }: mkContainerConfig { + config = { ... }: mkContainerConfig { services.changedetection-io = { - enable = true; - behindProxy = true; + enable = true; + baseURL = "https://change.${domain}"; + behindProxy = true; + listenAddress = address; }; }; }; diff --git a/container/Paste.nix b/container/Paste.nix index 2e68566..c05c2b2 100644 --- a/container/Paste.nix +++ b/container/Paste.nix @@ -2,26 +2,24 @@ , storage , const , domain -, host , util , mkContainer , mkContainerConfig +, mkContainerDir , mkServer , ... } @args: let - path = "${storage}/paste"; - package = (pkgs.callPackage ./pastebin args); + address = "10.1.0.14"; fqdn = "paste.${domain}"; + package = (pkgs.callPackage ./pastebin args); + path = "${storage}/paste"; in { - systemd.tmpfiles.rules = map ( - dirName: "d '${path}/${dirName}' 1777 root root - -" - ) [ "data" "tmp" "nginxtmp" "config" ]; - - containers.paste = mkContainer { - autoStart = true; - hostAddress = host; - localAddress = "10.1.0.14"; - privateNetwork = true; + systemd.tmpfiles.rules = map (dir: mkContainerDir "${path}/${dir}") [ + "data" + "tmp" + "nginxtmp" + ]; + containers.paste = mkContainer address { bindMounts = { "/srv/data" = { hostPath = "${path}/data"; diff --git a/container/Postgres.nix b/container/Postgres.nix index c459dc3..9c664cc 100644 --- a/container/Postgres.nix +++ b/container/Postgres.nix @@ -1,21 +1,18 @@ -{ pkgs -, storage +{ storage , const , host , mkContainer , mkContainerConfig +, mkContainerDir , ... } @args: let - path = "${storage}/postgres"; + address = "10.1.0.3"; + path = "${storage}/postgres"; in { - systemd.tmpfiles.rules = map ( - dirName: "d '${path}/${dirName}' 1777 root root - -" - ) [ "data" ]; - - containers.postgres = mkContainer { - autoStart = true; - localAddress = "10.1.0.3"; - privateNetwork = true; + systemd.tmpfiles.rules = map (dir: mkContainerDir "${path}/${dir}") [ + "data" + ]; + containers.postgres = mkContainer address { bindMounts = { "/var/lib/postgresql/data" = { hostPath = "${path}/data"; @@ -23,7 +20,7 @@ in { }; }; - config = { config, lib, pkgs, ... }: mkContainerConfig { + config = { lib, pkgs, ... }: mkContainerConfig { system.stateVersion = const.stateVersion; users.users.root.password = ""; diff --git a/container/Proxy.nix b/container/Proxy.nix index 3d5d3ad..5aa39ce 100644 --- a/container/Proxy.nix +++ b/container/Proxy.nix @@ -1,25 +1,21 @@ -{ pkgs -, storage +{ storage , const -, host , util , domain , mkContainer , mkContainerConfig +, mkContainerDir , ... } @args: let - path = "${storage}/proxy"; + address = "10.1.0.2"; + path = "${storage}/proxy"; virtualHosts = util.catSet (util.ls ./proxy/host) args; in { - systemd.tmpfiles.rules = map ( - dirName: "d '${path}/${dirName}' 1777 root root - -" - ) [ "challenge" "letsencrypt" ]; - - containers.proxy = mkContainer { - autoStart = true; - hostAddress = host; - localAddress = "10.1.0.2"; - privateNetwork = true; + systemd.tmpfiles.rules = map (dir: mkContainerDir "${path}/${dir}") [ + "challenge" + "letsencrypt" + ]; + containers.proxy = mkContainer address { bindMounts = { "/etc/letsencrypt" = { hostPath = "${path}/letsencrypt"; @@ -31,7 +27,7 @@ in { }; }; - config = { config, lib, pkgs, ... }: mkContainerConfig { + config = { lib, pkgs, ... }: mkContainerConfig { system.stateVersion = const.stateVersion; users.users.root.password = ""; diff --git a/container/proxy/host/Default.nix b/container/proxy/host/Default.nix deleted file mode 100644 index f365d8e..0000000 --- a/container/proxy/host/Default.nix +++ /dev/null @@ -1,2 +0,0 @@ -{ domain, util, mkServer, ... }: { -} diff --git a/host/desktop/Container.nix b/host/desktop/Container.nix index 8dd6a1b..591d288 100644 --- a/host/desktop/Container.nix +++ b/host/desktop/Container.nix @@ -6,8 +6,11 @@ in { inherit storage domain host pkgs const lib config util; - mkContainer = cfg: lib.recursiveUpdate cfg { - hostAddress = host; + mkContainer = address: cfg: lib.recursiveUpdate cfg { + autoStart = true; + hostAddress = host; + localAddress = address; + privateNetwork = true; }; mkContainerConfig = cfg: lib.recursiveUpdate cfg { @@ -22,6 +25,8 @@ }; }; + mkContainerDir = path: "d '${path}' 1777 root root - -"; + mkServer = cfg: lib.recursiveUpdate cfg { forceSSL = false; }; -- 2.46.0 From 0e04f0ccd6a0fceca813e58024446342a1121b6e Mon Sep 17 00:00:00 2001 From: Dmitry Voronin Date: Sun, 9 Jun 2024 16:26:05 +0300 Subject: [PATCH 4/5] wip --- container/Cloud.nix | 27 +++++++++++++++++++++++++++ container/Paste.nix | 20 ++------------------ container/Postgres.nix | 13 +------------ container/Proxy.nix | 13 +------------ 4 files changed, 31 insertions(+), 42 deletions(-) create mode 100644 container/Cloud.nix diff --git a/container/Cloud.nix b/container/Cloud.nix new file mode 100644 index 0000000..c4b98c4 --- /dev/null +++ b/container/Cloud.nix @@ -0,0 +1,27 @@ +{ storage +, mkContainer +, mkContainerConfig +, mkContainerDir +, ... } @args: let + address = "10.1.0.13"; + path = "${storage}/cloud"; +in { + systemd.tmpfiles.rules = map (dir: mkContainerDir "${path}/${dir}") [ + "data" + ]; + + containers.postgres = mkContainer address { + bindMounts = { + "/var/www/html" = { + hostPath = "${path}/data"; + isReadOnly = false; + }; + }; + + config = { ... }: mkContainerConfig { + services.nextcloud = { + enable = true; + }; + }; + }; +} diff --git a/container/Paste.nix b/container/Paste.nix index c05c2b2..49915d3 100644 --- a/container/Paste.nix +++ b/container/Paste.nix @@ -1,6 +1,5 @@ { pkgs , storage -, const , domain , util , mkContainer @@ -39,23 +38,8 @@ in { }; }; - config = { config, lib, ... }: mkContainerConfig { - system.stateVersion = const.stateVersion; - - users.users.root.password = ""; - users.mutableUsers = false; - - networking = { - useHostResolvConf = lib.mkForce false; - firewall.enable = false; - }; - - environment = { - systemPackages = [ package pkgs.neovim ]; - variables = { - }; - }; - + config = { config, ... }: mkContainerConfig { + environment.systemPackages = [ package ]; systemd.packages = [ package ]; users.users.paste = { diff --git a/container/Postgres.nix b/container/Postgres.nix index 9c664cc..8d9efdb 100644 --- a/container/Postgres.nix +++ b/container/Postgres.nix @@ -1,5 +1,4 @@ { storage -, const , host , mkContainer , mkContainerConfig @@ -20,17 +19,7 @@ in { }; }; - config = { lib, pkgs, ... }: mkContainerConfig { - system.stateVersion = const.stateVersion; - - users.users.root.password = ""; - users.mutableUsers = false; - - networking = { - useHostResolvConf = lib.mkForce false; - firewall.enable = false; - }; - + config = { pkgs, ... }: mkContainerConfig { services.postgresql = let databases = [ "privatebin" diff --git a/container/Proxy.nix b/container/Proxy.nix index 5aa39ce..9a8cbe1 100644 --- a/container/Proxy.nix +++ b/container/Proxy.nix @@ -1,5 +1,4 @@ { storage -, const , util , domain , mkContainer @@ -27,17 +26,7 @@ in { }; }; - config = { lib, pkgs, ... }: mkContainerConfig { - system.stateVersion = const.stateVersion; - - users.users.root.password = ""; - users.mutableUsers = false; - - networking = { - useHostResolvConf = lib.mkForce false; - firewall.enable = false; - }; - + config = { pkgs, ... }: mkContainerConfig { environment.systemPackages = with pkgs; [ certbot ]; services.nginx = { -- 2.46.0 From 095e97e6b6a3d3c37b31e88b7b231173016855ef Mon Sep 17 00:00:00 2001 From: Dmitry Voronin Date: Sun, 9 Jun 2024 21:31:45 +0300 Subject: [PATCH 5/5] wi --- container/Change.nix | 22 +++++------- container/Cloud.nix | 29 ++++++++++------ container/Paste.nix | 30 ++++++----------- container/Postgres.nix | 24 ++++++-------- container/Proxy.nix | 21 ++++-------- container/default.nix | 59 +++++++++++++++++++++++++++++++++ container/proxy/host/Change.nix | 8 +++-- container/proxy/host/Cloud.nix | 26 +++++++++++++++ container/proxy/host/Paste.nix | 8 +++-- flake.nix | 2 +- host/desktop/Container.nix | 29 +++------------- host/work/Container.nix | 20 ----------- 12 files changed, 153 insertions(+), 125 deletions(-) create mode 100644 container/default.nix create mode 100644 container/proxy/host/Cloud.nix diff --git a/container/Change.nix b/container/Change.nix index 2471ef3..c3b4bd8 100644 --- a/container/Change.nix +++ b/container/Change.nix @@ -1,30 +1,24 @@ -{ storage -, domain -, mkContainer -, mkContainerConfig -, mkContainerDir -, ... } @args: let - address = "10.1.0.41"; - path = "${storage}/change"; +{ container, ... } @args: let + cfg = container.config.change; in { - systemd.tmpfiles.rules = map (dir: mkContainerDir "${path}/${dir}") [ + systemd.tmpfiles.rules = container.mkContainerDir cfg [ "data" ]; - containers.change = mkContainer address { + containers.change = container.mkContainer cfg { bindMounts = { "/var/lib/changedetection-io" = { - hostPath = "${path}/data"; + hostPath = "${cfg.storage}/data"; isReadOnly = false; }; }; - config = { ... }: mkContainerConfig { + config = { ... }: container.mkContainerConfig cfg { services.changedetection-io = { enable = true; - baseURL = "https://change.${domain}"; + baseURL = cfg.domain; behindProxy = true; - listenAddress = address; + listenAddress = cfg.address; }; }; }; diff --git a/container/Cloud.nix b/container/Cloud.nix index c4b98c4..9165443 100644 --- a/container/Cloud.nix +++ b/container/Cloud.nix @@ -1,26 +1,33 @@ -{ storage -, mkContainer -, mkContainerConfig -, mkContainerDir -, ... } @args: let - address = "10.1.0.13"; - path = "${storage}/cloud"; +{ pkgs, container, ... } @args: let + cfg = container.config.cloud; in { - systemd.tmpfiles.rules = map (dir: mkContainerDir "${path}/${dir}") [ + systemd.tmpfiles.rules = container.mkContainerDir cfg [ "data" ]; - containers.postgres = mkContainer address { + containers.cloud = container.mkContainer cfg { bindMounts = { "/var/www/html" = { - hostPath = "${path}/data"; + hostPath = "${cfg.storage}/data"; isReadOnly = false; }; }; - config = { ... }: mkContainerConfig { + config = { ... }: container.mkContainerConfig cfg { services.nextcloud = { enable = true; + hostName = cfg.domain; + config = { + adminuser = "root"; + adminpassFile = "${pkgs.writeText "NextcloudPassword" "root"}"; + dbtype = "pgsql"; + dbhost = "10.1.0.3"; + + }; + settings = { + trusted_domains = [ cfg.address ]; + trusted_proxies = [ container.config.proxy.address ]; + }; }; }; }; diff --git a/container/Paste.nix b/container/Paste.nix index 49915d3..ff4a698 100644 --- a/container/Paste.nix +++ b/container/Paste.nix @@ -1,44 +1,34 @@ -{ pkgs -, storage -, domain -, util -, mkContainer -, mkContainerConfig -, mkContainerDir -, mkServer -, ... } @args: let - address = "10.1.0.14"; - fqdn = "paste.${domain}"; +{ pkgs, util, container, ... } @args: let + cfg = container.config.paste; package = (pkgs.callPackage ./pastebin args); - path = "${storage}/paste"; in { - systemd.tmpfiles.rules = map (dir: mkContainerDir "${path}/${dir}") [ + systemd.tmpfiles.rules = container.mkContainerDir cfg [ "data" "tmp" "nginxtmp" ]; - containers.paste = mkContainer address { + containers.paste = container.mkContainer cfg { bindMounts = { "/srv/data" = { - hostPath = "${path}/data"; + hostPath = "${cfg.storage}/data"; isReadOnly = false; }; "/tmp" = { - hostPath = "${path}/tmp"; + hostPath = "${cfg.storage}/tmp"; isReadOnly = false; }; "/var/lib/nginx/tmp" = { - hostPath = "${path}/nginxtmp"; + hostPath = "${cfg.storage}/nginxtmp"; isReadOnly = false; }; "/srv/config" = { - hostPath = "${path}/config"; + hostPath = "${cfg.storage}/config"; isReadOnly = false; }; }; - config = { config, ... }: mkContainerConfig { + config = { config, ... }: container.mkContainerConfig cfg { environment.systemPackages = [ package ]; systemd.packages = [ package ]; @@ -73,7 +63,7 @@ in { services.nginx = { enable = true; - virtualHosts.${fqdn} = mkServer { + virtualHosts.${cfg.domain} = container.mkServer { default = true; root = "${package}"; diff --git a/container/Postgres.nix b/container/Postgres.nix index 8d9efdb..6988a4a 100644 --- a/container/Postgres.nix +++ b/container/Postgres.nix @@ -1,28 +1,23 @@ -{ storage -, host -, mkContainer -, mkContainerConfig -, mkContainerDir -, ... } @args: let - address = "10.1.0.3"; - path = "${storage}/postgres"; +{ container, ... } @args: let + cfg = container.config.postgres; in { - systemd.tmpfiles.rules = map (dir: mkContainerDir "${path}/${dir}") [ + systemd.tmpfiles.rules = container.mkContainerDir cfg [ "data" ]; - containers.postgres = mkContainer address { + containers.postgres = container.mkContainer cfg { bindMounts = { "/var/lib/postgresql/data" = { - hostPath = "${path}/data"; + hostPath = "${cfg.storage}/data"; isReadOnly = false; }; }; - config = { pkgs, ... }: mkContainerConfig { + config = { pkgs, ... }: container.mkContainerConfig cfg { services.postgresql = let databases = [ "privatebin" + "nextcloud" ]; in { enable = true; @@ -30,8 +25,9 @@ in { dataDir = "/var/lib/postgresql/data/14"; enableTCPIP = true; authentication = '' - host all all ${host}/32 trust - host privatebin privatebin 10.1.0.14/32 trust + host all all ${container.host}/32 trust + host privatebin privatebin ${container.config.paste.address}/32 trust + host nextcloud nextcloud ${container.config.cloud.address}/32 trust ''; ensureDatabases = databases; ensureUsers = map (name: { diff --git a/container/Proxy.nix b/container/Proxy.nix index 9a8cbe1..437f057 100644 --- a/container/Proxy.nix +++ b/container/Proxy.nix @@ -1,32 +1,25 @@ -{ storage -, util -, domain -, mkContainer -, mkContainerConfig -, mkContainerDir -, ... } @args: let - address = "10.1.0.2"; - path = "${storage}/proxy"; +{ domain, util, container, ... } @args: let + cfg = container.config.proxy; virtualHosts = util.catSet (util.ls ./proxy/host) args; in { - systemd.tmpfiles.rules = map (dir: mkContainerDir "${path}/${dir}") [ + systemd.tmpfiles.rules = container.mkContainerDir cfg [ "challenge" "letsencrypt" ]; - containers.proxy = mkContainer address { + containers.proxy = container.mkContainer cfg { bindMounts = { "/etc/letsencrypt" = { - hostPath = "${path}/letsencrypt"; + hostPath = "${cfg.storage}/letsencrypt"; isReadOnly = true; }; "/var/www/.well-known" = { - hostPath = "${path}/challenge"; + hostPath = "${cfg.storage}/challenge"; isReadOnly = false; }; }; - config = { pkgs, ... }: mkContainerConfig { + config = { pkgs, ... }: container.mkContainerConfig cfg { environment.systemPackages = with pkgs; [ certbot ]; services.nginx = { diff --git a/container/default.nix b/container/default.nix new file mode 100644 index 0000000..02debf5 --- /dev/null +++ b/container/default.nix @@ -0,0 +1,59 @@ +{ lib +, const +, host +, storage +, domain +, ... }: { + inherit host; + + mkContainer = config: cfg: lib.recursiveUpdate cfg { + autoStart = true; + hostAddress = host; + localAddress = config.address; + privateNetwork = true; + }; + + mkContainerConfig = config: cfg: lib.recursiveUpdate cfg { + system.stateVersion = const.stateVersion; + + users.users.root.password = ""; + users.mutableUsers = false; + + networking = { + useHostResolvConf = lib.mkForce false; + firewall.enable = false; + }; + }; + + mkContainerDir = cfg: dirs: map (path: "d '${cfg.storage}/${path}' 1777 root root - -") dirs; + + mkServer = cfg: lib.recursiveUpdate cfg { + forceSSL = false; + }; + + config = { + change = { + address = "10.1.0.41"; + domain = "change.${domain}"; + storage = "${storage}/change"; + }; + cloud = { + address = "10.1.0.13"; + domain = "cloud.${domain}"; + storage = "${storage}/cloud"; + }; + paste = { + address = "10.1.0.14"; + domain = "paste.${domain}"; + storage = "${storage}/paste"; + }; + proxy = { + address = "10.1.0.2"; + storage = "${storage}/proxy"; + }; + postgres = { + address = "10.1.0.3"; + storage = "${storage}/postgres"; + }; + }; +} diff --git a/container/proxy/host/Change.nix b/container/proxy/host/Change.nix index 9c855d7..0da2a3b 100644 --- a/container/proxy/host/Change.nix +++ b/container/proxy/host/Change.nix @@ -1,8 +1,10 @@ -{ domain, util, mkServer, ... }: { - "change.${domain}" = mkServer { +{ domain, util, container, ... }: let + cfg = container.config.change; +in { + ${cfg.domain} = container.mkServer { extraConfig = util.trimTabs '' listen 443 ssl; - set $change 10.1.0.41:5000; + set $change ${cfg.address}:5000; location / { allow 192.168.1.0/24; diff --git a/container/proxy/host/Cloud.nix b/container/proxy/host/Cloud.nix new file mode 100644 index 0000000..971c21a --- /dev/null +++ b/container/proxy/host/Cloud.nix @@ -0,0 +1,26 @@ +{ domain, util, container, ... }: let + cfg = container.config.cloud; +in { + ${cfg.domain} = container.mkServer { + extraConfig = util.trimTabs '' + listen 443 ssl; + set $cloud ${cfg.address}:80; + + location ~ ^/(settings/admin|settings/users|settings/apps|login|api) { + allow 192.168.1.0/24; + allow 10.1.0.1; + deny all; + proxy_pass http://$cloud$request_uri; + } + location / { + proxy_pass http://$cloud$request_uri; + } + + ssl_certificate /etc/letsencrypt/live/${domain}/fullchain.pem; + ssl_certificate_key /etc/letsencrypt/live/${domain}/privkey.pem; + include /etc/letsencrypt/conf/options-ssl-nginx.conf; + ssl_dhparam /etc/letsencrypt/conf/ssl-dhparams.pem; + ''; + }; +} + diff --git a/container/proxy/host/Paste.nix b/container/proxy/host/Paste.nix index b053571..1e677d0 100644 --- a/container/proxy/host/Paste.nix +++ b/container/proxy/host/Paste.nix @@ -1,8 +1,10 @@ -{ domain, util, mkServer, ... }: { - "paste.${domain}" = mkServer { +{ domain, util, container, ... }: let + cfg = container.config.paste; +in { + ${cfg.domain} = container.mkServer { extraConfig = util.trimTabs '' listen 443 ssl; - set $paste 10.1.0.14:80; + set $paste ${cfg.address}:80; location = / { return 403; diff --git a/flake.nix b/flake.nix index b819e46..d14d6de 100644 --- a/flake.nix +++ b/flake.nix @@ -125,7 +125,7 @@ # Constant values. const = { droidStateVersion = "22.11"; - stateVersion = "23.11"; + stateVersion = "24.05"; timeZone = "Europe/Moscow"; url = "https://git.voronind.com/voronind/nixos.git"; }; diff --git a/host/desktop/Container.nix b/host/desktop/Container.nix index 591d288..f11a4e0 100644 --- a/host/desktop/Container.nix +++ b/host/desktop/Container.nix @@ -6,30 +6,7 @@ in { inherit storage domain host pkgs const lib config util; - mkContainer = address: cfg: lib.recursiveUpdate cfg { - autoStart = true; - hostAddress = host; - localAddress = address; - privateNetwork = true; - }; - - mkContainerConfig = cfg: lib.recursiveUpdate cfg { - system.stateVersion = const.stateVersion; - - users.users.root.password = ""; - users.mutableUsers = false; - - networking = { - useHostResolvConf = lib.mkForce false; - firewall.enable = false; - }; - }; - - mkContainerDir = path: "d '${path}' 1777 root root - -"; - - mkServer = cfg: lib.recursiveUpdate cfg { - forceSSL = false; - }; + container = import ../../container args; }; in { networking.nat = { @@ -40,13 +17,15 @@ in { # TODO: Remove this. networking.extraHosts = '' - 10.1.0.2 paste.local 10.1.0.2 change.local + 10.1.0.2 cloud.local + 10.1.0.2 paste.local 10.1.0.2 local ''; imports = [ (import ../../container/Change.nix args) + (import ../../container/Cloud.nix args) (import ../../container/Paste.nix args) (import ../../container/Postgres.nix args) (import ../../container/Proxy.nix args) diff --git a/host/work/Container.nix b/host/work/Container.nix index fcb3216..a79278b 100644 --- a/host/work/Container.nix +++ b/host/work/Container.nix @@ -5,26 +5,6 @@ host = "192.168.0.174"; in { inherit storage domain host pkgs const lib config util; - - mkContainer = cfg: lib.recursiveUpdate cfg { - hostAddress = host; - }; - - mkContainerConfig = cfg: lib.recursiveUpdate cfg { - system.stateVersion = const.stateVersion; - - users.users.root.password = ""; - users.mutableUsers = false; - - networking = { - useHostResolvConf = lib.mkForce false; - firewall.enable = false; - }; - }; - - mkServer = cfg: lib.recursiveUpdate cfg { - forceSSL = false; - }; }; in { networking.nat = { -- 2.46.0