Background
I want to create separate nixos-containers for each of the service I’ll host on my server.
Writing nixos-container configurations is very repetitive though, so I thought about creating a module that will make it easier to set them up.
I realised that even if I create a services.custom-container module, I can only define a single container. (Implemented here: https://codeberg.org/BlastboomStrice/dotfiles/src/commit/432096d86b25cefdb2036ded50944645de5214dc/.config/nixos-config/modules/nixos/containers/container-stirling-pdf.nix)
I want to create a module that will let me define multiple containers from a single module and set up something in my configuration.nix file like this:
services.custom-containers = {
containerA = {
# options
};
containerB = {
# options
};
};
I would like to avoid creating a seperate module for each container:
Counter-example
services.custom-containerA = {
# options
};
services.custom-containerB = {
# options
};
My whole configuration is hosted here: https://codeberg.org/BlastboomStrice/dotfiles
(Btw, I will probably (or may not) make another post later on how to inject freeform code inside a module, to inject configuration of various services inside different nixos-containers I will create. I’m not very sure if that’s the path I want to follow, but that whole thing is not that important in this post.)
Issue
My main issue is that I don’t know how to generate multiple containers from a single module.
The official nixos-containers options work exactly like that (containers.<name>).
- How do I set up a module like that? A module that will generate multiple nixos-containers (with some preset values or values from some custom options of mine).
- How can each container be assigned by the name I give when I define it? For example, I’d want the following container generated to be named
containerA, where can I find and use the<name>value?services.custom-containers = { containerA = { # options }; };
What the docs say
From what I understand, I must create an option (named what though?) of type attrsOf and a submodule nested inside of it with the options I want to pass to the container.
I’m not really sure how to do this.
I’ve checked the manual and the wiki for help:
- Info about the submodule: https://nixos.org/manual/nixos/unstable/#section-option-types-submodule
- Info about
attrsOf: https://nixos.org/manual/nixos/unstable/#sec-option-types-composed
Things I’ve tried
Since the docs didn’t help me that much to understand what I exactly have to do, I tried to gather inspiration (but failed) from the nixos-container module itself: https://github.com/NixOS/nixpkgs/blob/e73de5be04e0eff4190a1432b946d469c794e7b4/nixos/modules/virtualisation/nixos-containers.nix
I found a very related part in the code:
containers = mkOption {
type = types.attrsOf (
types.submodule (
But I didn’t understand how to properly use it (as a sidenote, in the manual it seems to do types.submodule {, not types.submodule (, it uses the curly bracket instead of parenthesis, but whatever).
Other solutions
I could give up and avoid complexity by defining a module per container, but this will have possibly thousands of repeated lines and this makes it hard to manage the code, especially if I want to update something (I’ll have to edit all the modules).