diff --git a/nixos/tests/all-tests.nix b/nixos/tests/all-tests.nix index 796c626f3dd..8316332e48e 100644 --- a/nixos/tests/all-tests.nix +++ b/nixos/tests/all-tests.nix @@ -302,6 +302,7 @@ in spacecookie = handleTest ./spacecookie.nix {}; spike = handleTest ./spike.nix {}; sonarr = handleTest ./sonarr.nix {}; + sslh = handleTest ./sslh.nix {}; strongswan-swanctl = handleTest ./strongswan-swanctl.nix {}; sudo = handleTest ./sudo.nix {}; switchTest = handleTest ./switch-test.nix {}; diff --git a/nixos/tests/sslh.nix b/nixos/tests/sslh.nix new file mode 100644 index 00000000000..2a800aa52d0 --- /dev/null +++ b/nixos/tests/sslh.nix @@ -0,0 +1,83 @@ +import ./make-test-python.nix { + name = "sslh"; + + nodes = { + server = { pkgs, lib, ... }: { + networking.firewall.allowedTCPPorts = [ 443 ]; + networking.interfaces.eth1.ipv6.addresses = [ + { + address = "fe00:aa:bb:cc::2"; + prefixLength = 64; + } + ]; + # sslh is really slow when reverse dns does not work + networking.hosts = { + "fe00:aa:bb:cc::2" = [ "server" ]; + "fe00:aa:bb:cc::1" = [ "client" ]; + }; + services.sslh = { + enable = true; + transparent = true; + appendConfig = '' + protocols: + ( + { name: "ssh"; service: "ssh"; host: "localhost"; port: "22"; probe: "builtin"; }, + { name: "http"; host: "localhost"; port: "80"; probe: "builtin"; }, + ); + ''; + }; + services.openssh.enable = true; + users.users.root.openssh.authorizedKeys.keyFiles = [ ./initrd-network-ssh/id_ed25519.pub ]; + services.nginx = { + enable = true; + virtualHosts."localhost" = { + addSSL = false; + default = true; + root = pkgs.runCommand "testdir" {} '' + mkdir "$out" + echo hello world > "$out/index.html" + ''; + }; + }; + }; + client = { ... }: { + networking.interfaces.eth1.ipv6.addresses = [ + { + address = "fe00:aa:bb:cc::1"; + prefixLength = 64; + } + ]; + networking.hosts."fe00:aa:bb:cc::2" = [ "server" ]; + environment.etc.sshKey = { + source = ./initrd-network-ssh/id_ed25519; # dont use this anywhere else + mode = "0600"; + }; + }; + }; + + testScript = '' + start_all() + + server.wait_for_unit("sslh.service") + server.wait_for_unit("nginx.service") + server.wait_for_unit("sshd.service") + server.wait_for_open_port(80) + server.wait_for_open_port(443) + server.wait_for_open_port(22) + + for arg in ["-6", "-4"]: + client.wait_until_succeeds(f"ping {arg} -c1 server") + + # check that ssh through sslh works + client.succeed( + f"ssh {arg} -p 443 -i /etc/sshKey -o StrictHostKeyChecking=accept-new server 'echo $SSH_CONNECTION > /tmp/foo{arg}'" + ) + + # check that 1/ the above ssh command had an effect 2/ transparent proxying really works + ip = "fe00:aa:bb:cc::1" if arg == "-6" else "192.168.1." + server.succeed(f"grep '{ip}' /tmp/foo{arg}") + + # check that http through sslh works + assert client.succeed(f"curl {arg} http://server:443").strip() == "hello world" + ''; +} diff --git a/pkgs/servers/sslh/default.nix b/pkgs/servers/sslh/default.nix index cbeacece3e1..68fe9c4b08e 100644 --- a/pkgs/servers/sslh/default.nix +++ b/pkgs/servers/sslh/default.nix @@ -1,4 +1,4 @@ -{ stdenv, fetchurl, libcap, libconfig, perl, tcp_wrappers, pcre }: +{ stdenv, fetchurl, libcap, libconfig, perl, tcp_wrappers, pcre, nixosTests }: stdenv.mkDerivation rec { pname = "sslh"; @@ -19,6 +19,10 @@ stdenv.mkDerivation rec { hardeningDisable = [ "format" ]; + passthru.tests = { + inherit (nixosTests) sslh; + }; + meta = with stdenv.lib; { description = "Applicative Protocol Multiplexer (e.g. share SSH and HTTPS on the same port)"; license = licenses.gpl2Plus;