ALPHA: wire is a tool to deploy nixos systems wire.althaea.zone/
at v0.5.0 203 lines 6.0 kB view raw
1{ 2 lib, 3 name, 4 config, 5 ... 6}: 7let 8 inherit (lib) types; 9in 10{ 11 imports = 12 let 13 inherit (lib) mkAliasOptionModule; 14 in 15 [ 16 (mkAliasOptionModule [ "deployment" "targetHost" ] [ "deployment" "target" "hosts" ]) 17 (mkAliasOptionModule [ "deployment" "targetUser" ] [ "deployment" "target" "user" ]) 18 (mkAliasOptionModule [ "deployment" "targetPort" ] [ "deployment" "target" "port" ]) 19 ]; 20 21 options.deployment = { 22 target = lib.mkOption { 23 type = types.submodule { 24 imports = [ 25 (lib.mkAliasOptionModule [ "host" ] [ "hosts" ]) 26 ]; 27 options = { 28 hosts = lib.mkOption { 29 type = types.coercedTo types.str lib.singleton (types.listOf types.str); 30 description = "IPs or hostnames to attempt to connect to. They are tried in order."; 31 default = lib.singleton name; 32 apply = lib.unique; 33 }; 34 user = lib.mkOption { 35 type = types.str; 36 description = "User to use for ssh."; 37 default = "root"; 38 }; 39 port = lib.mkOption { 40 type = types.int; 41 default = 22; 42 description = "SSH port to use."; 43 }; 44 }; 45 }; 46 description = "Describes the target for this node"; 47 default = { }; 48 }; 49 50 buildOnTarget = lib.mkOption { 51 type = types.bool; 52 default = false; 53 description = "Whether to build the system on the target host or not."; 54 }; 55 56 allowLocalDeployment = lib.mkOption { 57 type = types.bool; 58 default = true; 59 description = "Whether to allow or deny this node being applied to localhost when the host's hostname matches the 60 node's name."; 61 }; 62 63 tags = lib.mkOption { 64 type = types.listOf types.str; 65 default = [ ]; 66 description = "Tags for node."; 67 example = [ 68 "arm" 69 "cloud" 70 ]; 71 }; 72 73 _keys = lib.mkOption { 74 internal = true; 75 readOnly = true; 76 }; 77 78 _hostPlatform = lib.mkOption { 79 internal = true; 80 readOnly = true; 81 }; 82 83 keys = lib.mkOption { 84 type = types.attrsOf ( 85 types.submodule ( 86 { 87 name, 88 config, 89 ... 90 }: 91 { 92 imports = 93 let 94 inherit (lib) mkAliasOptionModule; 95 in 96 [ 97 (mkAliasOptionModule [ "keyFile" ] [ "source" ]) 98 (mkAliasOptionModule [ "keyCommand" ] [ "source" ]) 99 (mkAliasOptionModule [ "text" ] [ "source" ]) 100 ]; 101 options = { 102 name = lib.mkOption { 103 type = types.str; 104 default = name; 105 description = "Filename of the secret."; 106 }; 107 destDir = lib.mkOption { 108 type = types.path; 109 default = "/run/keys/"; 110 description = "Destination directory for the secret. Change this to something other than `/run/keys/` for keys to persist past reboots."; 111 }; 112 path = lib.mkOption { 113 internal = true; 114 type = types.path; 115 default = "${config.destDir}/${config.name}"; 116 }; 117 group = lib.mkOption { 118 type = types.str; 119 default = "root"; 120 description = "Group to own the key. If this group does not exist this will silently fail and the key will be owned by gid 0."; 121 }; 122 user = lib.mkOption { 123 type = types.str; 124 default = "root"; 125 description = "User to own the key. If this user does not exist this will silently fail and the key will be owned by uid 0."; 126 }; 127 permissions = lib.mkOption { 128 type = types.str; 129 default = "0600"; 130 description = "Unix Octal permissions, in string format, for the key."; 131 }; 132 source = lib.mkOption { 133 type = types.oneOf [ 134 types.str 135 types.path 136 (types.listOf types.str) 137 ]; 138 description = "Source of the key. Either a path to a file, a literal string, or a command to generate the key."; 139 }; 140 uploadAt = lib.mkOption { 141 type = types.enum [ 142 "pre-activation" 143 "post-activation" 144 ]; 145 default = "pre-activation"; 146 description = "When to upload the key. Either `pre-activation` or `post-activation`."; 147 }; 148 environment = lib.mkOption { 149 type = types.attrsOf types.str; 150 default = { }; 151 description = "Key-Value environment variables to use when creating the key if the key source is a command."; 152 }; 153 }; 154 } 155 ) 156 ); 157 description = "Secrets to be deployed to the node."; 158 default = { }; 159 example = { 160 "wireless.env" = { 161 source = [ 162 "gpg" 163 "--decrypt" 164 "secrets/wireless.env.gpg" 165 ]; 166 destDir = "/etc/keys/"; 167 }; 168 169 "arbfile.txt" = { 170 source = ./arbfile.txt; 171 destDir = "/etc/arbs/"; 172 }; 173 174 "arberfile.txt" = { 175 source = '' 176 Hello World 177 ''; 178 destDir = "/etc/arbs/"; 179 }; 180 }; 181 }; 182 }; 183 184 config = { 185 deployment = { 186 _keys = lib.mapAttrsToList ( 187 _: value: 188 value 189 // { 190 source = { 191 # Attach type to internally tag serde enum 192 t = builtins.replaceStrings [ "path" "string" "list" ] [ "Path" "String" "Command" ] ( 193 builtins.typeOf value.source 194 ); 195 c = value.source; 196 }; 197 } 198 ) config.deployment.keys; 199 200 _hostPlatform = config.nixpkgs.hostPlatform.system; 201 }; 202 }; 203}