Please review design for automated server installs

Overall the design seems very straightforward and easy to understand which I really like. There does seem to be a difference in how network: is handled versus filesystem:. network: is a complete pass through to netplan (which is great) where as the filesystem: is not a complete pass through to curtin the installer used under the hood.

While I do like that filesystem: allows the layouts and the automated server installer will then build a simple curtin layout, it would be nice to support a passthrough method just like network: passes through to netplan.

Curtin uses the key storage: to define the storage layout could the automated server installer support either storage: or filesystem: for those wanting to provide very specific storage layout configuration. In the case that both are provided it could be an error or storage could take precendence over filesystem: with a warning about that choice.

Thanks for the comments!

Yay!

There does seem to be a difference in how network: is handled versus filesystem:. network: is a complete pass through to netplan (which is great) where as the filesystem: is not a complete pass through to curtin the installer used under the hood.

So maybe I’ve been unclear here. The idea is very much that anything that is valid curtin storage config can go under filesystem: and just be passed through. What’s different to network/netplan is that the syntax is extended to allow other things (basically, netplan supports some degree of wildcarding natively, curtin does not). BTW, exactly how this extension of curtin syntax will work is the part of all this I am fuzziest on, if people have thoughts on how it should work in detail I’m all ears.

While I do like that filesystem: allows the layouts and the automated server installer will then build a simple curtin layout, it would be nice to support a passthrough method just like network: passes through to netplan.

As above, that’s the plan.

Curtin uses the key storage: to define the storage layout could the automated server installer support either storage: or filesystem: for those wanting to provide very specific storage layout configuration. In the case that both are provided it could be an error or storage could take precendence over filesystem: with a warning about that choice.

Do you mean the difference between block-meta simple and block-meta custom here? Subiquity currently always generates a config that puts curtin into custom mode. And hmmmmm I’d forgotten that simple and custom are configured by different top-level keys (“storage” for custom and “block-meta” for simple) so I think I see what you meant above now (and we can’t do a neat thing of just transplanting what’s under a key in the autoinstall file to some key in the curtin config). So let me brain dump for a bit:

There are three broad types of filesystem configuration we might expect the user to supply:

  1. configuration for the curtin’s block-meta simple mode
  2. configuration for curtin’s block-meta custom mode (actually probably some extension of this)
  3. one of the guided layouts such as lvm or lvm-luks

We could do this just by looking at which keys are present under the filesystem: top-level key: ‘block-meta’ for block meta simple, ‘config’ (and version?) for block-meta custom, ‘layout’ for a guided layout (and handle more than one of these being present by either defining a precedence or erroring). This seems simple enough.

Would you want the configuration for block-meta simple to support wildcarding in any sense?

I think in almost all cases you will need some type of matching either with wildcarding and/or regexing to make the storage selection flexible enough to be useful.

Being that netplan does support some form of wildcarding why not push that same level of support to curtin that way others benefit from that versus only adding it in the automated server installer. That would give more consistency in the installer being that it just consistently relies on the underlying tools to do the hard work.

Based on the current YAML design how is the code going to be able to distinguishes between the 3 different ways your describe storage can be defined. Seems very vague to me at the moment and a clear design there would be beneficial before implementation. It would also help to ensure that it could easily be validated before hand.

The block-meta mode can be specified, but it typically is derived from the presence of ‘storage’ config. The logic curtin implements looks like this:

  1. if the install source is a dd-able image, then we always use meta-simple path
  2. if ‘storage’ is present and the user isn’t setting the force-mode flag, we use meta-custom
  3. use the mode specified by the user.

Note, in meta-simple, curtin will look at storage-config (if present) to determine which disk should be the boot disk.

Generally, meta-simple enumerates host block devices, picks a target disk (ignoring multipath, mounted devices and such) will create a single partition, put ext4 on it and make it bootable.

I can’t think of a case where subiquity would ever not pass a storage config to curtin, so we’ll definitely down the meta-custom path. I don’t think subiquity should accept any block-meta keys; only accept ‘storage’ or ‘filesystems’ in the absence of ‘storage’.

W.r.t the wildcarding, this has been suggested. In particular areas that could utilize some abstract values are:

  • sizes for partitions, raids, lvms (accepting percentages)
  • disk serial/wwn/path values

[comment amended to remove the confusion between answers.yaml and autoinstall.]

Hi, just a question on:

when the answer to a question is not present in a preseed, d-i stops and asks the user for input. autoinstalls are not like this: by default, if there is any autoinstall config at all, the installer takes the default for any unanswered question (and fails if there is no default).

What happens if subiquity refreshes and introduces a new question with no default? I think this would break existing autoinstalling setups, making them stop at the new question. Can we prevent this from happening? We could require defaults for each question, but there are cases where defaults don’t really make sense (e.g. the user’s password).

Right. We’d better avoid doing this then!

I don’t think there’s any overarching approach here and I’m not sure what is even possible. If we add new questions, we should avoid adding ones that don’t have defaults. If we have to add a question with no default (and I really can’t think why we’d do that), then yes, everyone gets to update their configs. Which sucks, which is why we should try to avoid doing it.

It would be nice to have also a ‘file’ boot option for preseeding in addition to the ‘url’ option and the fixed /autoinstall.yaml path. Consider the following use case:

an usb bootable disk with one or more official ubuntu iso images (unmodified) and one or more grub menu entries specifying different preseed files for different types of installation. The preseed files would preferably be installed in the filesystem of the usb disk and not inside the iso or initrd, which should be left unchanged. For example:

menuentry "Install 1" {
    loopback loop /ubuntu/ubuntu-20.04-server.iso
    linux (loop)/casper/vmlinuz iso-scan/filename=/ubuntu/ubuntu-20.04-server.iso file=/isodevice/configs/autoinstall-1.yaml 
    initrd (loop)/casper/initrd
}
menuentry "Install 2" {
    loopback loop /ubuntu/ubuntu-20.04-server.iso
    linux (loop)/casper/vmlinuz iso-scan/filename=/ubuntu/ubuntu-20.04-server.iso file=/isodevice/configs/autoinstall-2.yaml 
    initrd (loop)/casper/initrd
}

where /isodevice should be the mount point of the usb partition where the iso is found by the installer and loop mounted on /cdrom.

Your proposed design provides a fixed /autoinstall.yaml file on a filesystem with label “autoinstall”, but in this way we can’t have more than one preseed on the same install media. With a file option we could select different files on the same media. Also file=“LABEL=<label>/<path>” or “UUID=<uuid>/<path>” would be even better.

Hmm, that’s an interesting idea. I’ll think about it!

One thing that I’d like to see is a document / page which provides a few complete examples of an autoinstall.yaml file. Having a complete example will help piece together all of the various options, and will also help with getting the proper indentation for each of the components.

I agree with dz1. A ‘file’ parameter similar to the one used for Debian installer preseed which can be passed with the boot command would be nice.

It would also be helpful if we can pass in additional custom parameters with the boot command and use those parameter within autoinstall.yaml.

Does early_command/late_command/error_command support running scripts from the usb drive?

My use case would be to have a usb drive with multiple unmodified isos, only one autoinstall.yaml, and multiple install scripts which is specified by different grub menu entries.

Grub menu would look like:

menuentry “Install K8S” {
loopback loop /ubuntu1804.iso
iso-scan/filename=/ubuntu1804.iso
linux (loop)/casper/vmlinuz boot=casper
initrd (loop)/casper/initrd
file=/root/isodevice/autoinstall.yaml
early_script=/root/isodevice/someConfigCheck
late_script=/root/isodevice/installK8s
}

autoinstall.yaml would look like:

version: 1
early-commands:
- ${early_script}.sh
identity:
username: xxxx
password: $crypted_pass
late-commands:
- curtin in-target – ${late_script}.sh

For people following this topic but not the server category generally, I’ve just posted an update Cloud-init and the live server installer that is relevant to some of the recent posts.

As for examples: yes clearly we need them. I should probably try to write up some hypothetical ones (and they try to keep them up to date as things inevitably shift slightly when the implementation actually happens).