What is Autoinstall (Ubuntu 24.04)?
Autoinstall is Ubuntu Server’s unattended installation in Subiquity. You provide a YAML answer file (user-data) via cloud-init datasources (e.g., NoCloud / NoCloud-Net) referenced by a kernel argument like autoinstall ds="nocloud-net;...". With NoCloud-Net, the installer downloads meta-data and user-data from HTTPS and completes hands-free—ideal for repeatable lab or fleet provisioning.
You will serve per-host NoCloud seeds at:
https://nocloud.maksonlee.com/b/<ID>/user-datahttps://nocloud.maksonlee.com/b/<ID>/meta-data
This demo uses <ID> = test. Seeds are generated dynamically with NGINX SSI.
Prerequisites
- DNS A/AAAA:
nocloud.maksonlee.com→ your server - Cloudflare DNS API token with Zone → DNS: Edit
- ISO:
ubuntu-24.04.2-live-server-amd64.iso - TCP 80/443 open
- Install NGINX and create directories
sudo apt update
sudo apt install -y nginx
sudo mkdir -p /var/www/html/nocloud/b
sudo chown -R www-data:www-data /var/www/html/nocloud
- Add SSI templates
/var/www/html/nocloud/b/_user.ssi
#cloud-config
autoinstall:
version: 1
identity:
hostname: <!--# echo var="host_id" -->
username: ubuntu
password: "$6$PWguV961aHQjVEUh$EbowTJLSSunVj2zejKxIlS9A6iRBoG8J8XKnTukaTvtyW5QUzK.XQDFv9nEDyBpSpEOmQGMteP5ucnBBI6YsV0"
timezone: Asia/Taipei
locale: en_US.UTF-8
keyboard: { layout: us }
ssh:
install-server: true
allow-pw: true
apt:
primary: [{ arches: [default], uri: http://archive.ubuntu.com/ubuntu/ }]
storage:
layout:
name: direct
match: { size: largest }
user-data:
preserve_hostname: false
package_update: true
packages: [htop]
runcmd:
- [bash, -lc, "lsb_release -a || true"]
- [bash, -lc, "lsblk -f"]
/var/www/html/nocloud/b/_meta.ssi
instance-id: <!--# echo var="host_id" -->
- Initial HTTP configuration (before certificate)
/etc/nginx/sites-available/nocloud
server {
listen 80;
server_name nocloud.maksonlee.com;
root /var/www/html/nocloud;
index index.html;
autoindex off;
types { } default_type application/octet-stream;
location / {
limit_except GET HEAD { deny all; }
try_files $uri =404;
add_header X-Content-Type-Options "nosniff";
add_header Cache-Control "public, max-age=60";
}
location ~ ^/b/([A-Za-z0-9._-]+)/user-data$ {
default_type text/plain;
ssi on; ssi_types *;
set $host_id $1;
try_files /b/_user.ssi =404;
add_header Cache-Control "no-store";
}
location ~ ^/b/([A-Za-z0-9._-]+)/meta-data$ {
default_type text/plain;
ssi on; ssi_types *;
set $host_id $1;
try_files /b/_meta.ssi =404;
add_header Cache-Control "no-store";
}
}
Enable and reload:
sudo ln -sf /etc/nginx/sites-available/nocloud /etc/nginx/sites-enabled/nocloud
sudo nginx -t && sudo systemctl reload nginx
curl -s http://nocloud.maksonlee.com/b/test/meta-data
curl -s http://nocloud.maksonlee.com/b/test/user-data
- Install Certbot and issue certificate with Cloudflare DNS-01
sudo apt update
sudo apt install -y certbot python3-certbot-dns-cloudflare
sudo mkdir -p /etc/letsencrypt
sudo bash -c 'cat > /etc/letsencrypt/cloudflare.ini <<EOF
dns_cloudflare_api_token = YOUR_CLOUDFLARE_DNS_TOKEN
EOF'
sudo chmod 600 /etc/letsencrypt/cloudflare.ini
sudo certbot certonly \
--dns-cloudflare \
--dns-cloudflare-credentials /etc/letsencrypt/cloudflare.ini \
-d nocloud.maksonlee.com \
-m admin@maksonlee.com --agree-tos --non-interactive
Verify:
sudo ls -l /etc/letsencrypt/live/nocloud.maksonlee.com/
- Final HTTPS configuration
/etc/nginx/sites-available/nocloud
server {
server_name nocloud.maksonlee.com;
root /var/www/html/nocloud;
index index.html;
autoindex off;
types { } default_type application/octet-stream;
location / {
limit_except GET HEAD { deny all; }
try_files $uri =404;
add_header X-Content-Type-Options "nosniff";
add_header Cache-Control "public, max-age=60";
}
location ~ ^/b/([A-Za-z0-9._-]+)/user-data$ {
default_type text/plain;
ssi on; ssi_types *;
set $host_id $1;
try_files /b/_user.ssi =404;
add_header Cache-Control "no-store";
}
location ~ ^/b/([A-Za-z0-9._-]+)/meta-data$ {
default_type text/plain;
ssi on; ssi_types *;
set $host_id $1;
try_files /b/_meta.ssi =404;
add_header Cache-Control "no-store";
}
listen 443 ssl;
ssl_certificate /etc/letsencrypt/live/nocloud.maksonlee.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/nocloud.maksonlee.com/privkey.pem;
include /etc/letsencrypt/options-ssl-nginx.conf;
ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem;
}
server {
listen 80;
server_name nocloud.maksonlee.com;
return 301 https://$host$request_uri;
}
Reload and test:
sudo nginx -t && sudo systemctl reload nginx
curl -s https://nocloud.maksonlee.com/b/test/meta-data
curl -s https://nocloud.maksonlee.com/b/test/user-data | head -n 20
- Install — add the GRUB kernel parameters
At the GRUB edit screen, append to the linux line after ---:
autoinstall ds="nocloud-net;s=https://nocloud.maksonlee.com/b/test/"


- Verify after install
hostnamectl
cat /etc/hostname
Expected: test.

Scale out
- For each host, change only
<ID>in the URL:
autoinstall ds="nocloud-net;s=https://nocloud.maksonlee.com/b/web-01/"
instance-idequals<ID>for clean first-boot runs.- Add packages in
_user.ssi, or create variants with additional SSI templates and routes.
Appendix: create a SHA-512 password hash
mkpasswd -m sha-512 'changeme'
Did this guide save you time?
Support this site