at master 5.6 kB view raw
1{ kanidmPackage, pkgs, ... }: 2let 3 certs = import ./common/acme/server/snakeoil-certs.nix; 4 serverDomain = certs.domain; 5 6 testCredentials = { 7 password = "Password1_cZPEwpCWvrReripJmAZdmVIZd8HHoHcl"; 8 }; 9 10 # copy certs to store to work around mount namespacing 11 certsPath = pkgs.runCommandNoCC "snakeoil-certs" { } '' 12 mkdir $out 13 cp ${certs."${serverDomain}".cert} $out/snakeoil.crt 14 cp ${certs."${serverDomain}".key} $out/snakeoil.key 15 ''; 16in 17{ 18 name = "kanidm-${kanidmPackage.version}"; 19 meta.maintainers = with pkgs.lib.maintainers; [ 20 Flakebi 21 oddlama 22 ]; 23 24 _module.args.kanidmPackage = pkgs.lib.mkDefault pkgs.kanidm; 25 26 nodes.server = 27 { pkgs, ... }: 28 { 29 services.kanidm = { 30 package = kanidmPackage; 31 enableServer = true; 32 serverSettings = { 33 origin = "https://${serverDomain}"; 34 domain = serverDomain; 35 bindaddress = "[::]:443"; 36 ldapbindaddress = "[::1]:636"; 37 tls_chain = "${certsPath}/snakeoil.crt"; 38 tls_key = "${certsPath}/snakeoil.key"; 39 }; 40 }; 41 42 security.pki.certificateFiles = [ certs.ca.cert ]; 43 44 networking.hosts."::1" = [ serverDomain ]; 45 networking.firewall.allowedTCPPorts = [ 443 ]; 46 47 users.users.kanidm.shell = pkgs.bashInteractive; 48 49 environment.systemPackages = [ 50 kanidmPackage 51 pkgs.openldap 52 pkgs.ripgrep 53 ]; 54 }; 55 56 nodes.client = 57 { nodes, ... }: 58 { 59 services.kanidm = { 60 package = kanidmPackage; 61 enableClient = true; 62 clientSettings = { 63 uri = "https://${serverDomain}"; 64 verify_ca = true; 65 verify_hostnames = true; 66 }; 67 enablePam = true; 68 unixSettings = { 69 pam_allowed_login_groups = [ "shell" ]; 70 }; 71 }; 72 73 networking.hosts."${nodes.server.networking.primaryIPAddress}" = [ serverDomain ]; 74 75 security.pki.certificateFiles = [ certs.ca.cert ]; 76 }; 77 78 testScript = 79 { nodes, ... }: 80 let 81 ldapBaseDN = builtins.concatStringsSep "," ( 82 map (s: "dc=" + s) (pkgs.lib.splitString "." serverDomain) 83 ); 84 85 # We need access to the config file in the test script. 86 filteredConfig = pkgs.lib.converge (pkgs.lib.filterAttrsRecursive ( 87 _: v: v != null 88 )) nodes.server.services.kanidm.serverSettings; 89 serverConfigFile = (pkgs.formats.toml { }).generate "server.toml" filteredConfig; 90 in 91 '' 92 server.start() 93 client.start() 94 server.wait_for_unit("kanidm.service") 95 client.systemctl("start network-online.target") 96 client.wait_for_unit("network-online.target") 97 98 with subtest("Test HTTP interface"): 99 server.wait_until_succeeds("curl -Lsf https://${serverDomain} | grep Kanidm") 100 101 with subtest("Test LDAP interface"): 102 server.succeed("ldapsearch -H ldaps://${serverDomain}:636 -b '${ldapBaseDN}' -x '(name=test)'") 103 104 with subtest("Recover idm_admin account"): 105 idm_admin_password = server.succeed("su - kanidm -c 'kanidmd recover-account -c ${serverConfigFile} idm_admin 2>&1 | rg -o \'[A-Za-z0-9]{48}\' '").strip().removeprefix("'").removesuffix("'") 106 107 with subtest("Test CLI login"): 108 client.wait_until_tty_matches("1", "login: ") 109 client.send_chars("root\n") 110 client.send_chars("kanidm login -D idm_admin\n") 111 client.wait_until_tty_matches("1", "Enter password: ") 112 client.send_chars(f"{idm_admin_password}\n") 113 client.wait_until_tty_matches("1", "Login Success for idm_admin") 114 115 with subtest("Test unixd connection"): 116 client.wait_for_unit("kanidm-unixd.service") 117 client.wait_for_file("/run/kanidm-unixd/sock") 118 client.wait_until_succeeds("kanidm-unix status | grep online") 119 120 with subtest("Test user creation"): 121 client.wait_for_unit("getty@tty1.service") 122 client.wait_until_succeeds("pgrep -f 'agetty.*tty1'") 123 client.succeed("kanidm person create testuser TestUser") 124 client.succeed("kanidm person posix set --shell \"$SHELL\" testuser") 125 client.send_chars("kanidm person posix set-password testuser\n") 126 client.wait_until_tty_matches("1", "Enter new") 127 client.send_chars("${testCredentials.password}\n") 128 client.wait_until_tty_matches("1", "Reenter") 129 client.send_chars("${testCredentials.password}\n") 130 output = client.succeed("getent passwd testuser") 131 assert "TestUser" in output 132 client.succeed("kanidm group create shell") 133 client.succeed("kanidm group posix set shell") 134 client.succeed("kanidm group add-members shell testuser") 135 136 with subtest("Test user login"): 137 client.send_key("alt-f2") 138 client.wait_until_succeeds("[ $(fgconsole) = 2 ]") 139 client.wait_for_unit("getty@tty2.service") 140 client.wait_until_succeeds("pgrep -f 'agetty.*tty2'") 141 client.wait_until_tty_matches("2", "login: ") 142 client.send_chars("testuser\n") 143 client.wait_until_tty_matches("2", "login: testuser") 144 client.wait_until_succeeds("pgrep login") 145 client.wait_until_tty_matches("2", "Password: ") 146 client.send_chars("${testCredentials.password}\n") 147 client.wait_until_succeeds("systemctl is-active user@$(id -u testuser).service") 148 client.send_chars("touch done\n") 149 client.wait_for_file("/home/testuser@${serverDomain}/done") 150 151 server.shutdown() 152 client.shutdown() 153 ''; 154}