Small Flask app that generates a cloud-init NoCloud seed ISO (cidata) from validated inputs.
- Parameterized cloud-init
meta-data+user-data - Strict input validation (allow-lists)
- Per-request temp directories with TTL cleanup
- Minimal HTMX form UI
- Download token endpoint
- Python 3.10+
genisoimageavailable on the host- macOS:
brew install cdrtools - Ubuntu/Debian:
sudo apt-get install genisoimage
- macOS:
Create and use the virtual environment:
python3 -m venv .venv
.venv/bin/pip install -r requirements.txtDevelopment:
.venv/bin/python app.pyProduction (WSGI):
.venv/bin/gunicorn -w 2 -b 0.0.0.0:5000 wsgi:appOpen http://localhost:5000 and submit the form.
Build:
docker build -t cloudinit-generator .Run:
docker run --rm -p 5000:5000 cloudinit-generatorOverride worker count:
docker run --rm -e WSGI_PROCESSES=2 -p 5000:5000 cloudinit-generator- Users:
appadmin(sudo + SSH keys),appuser - Directory:
/opt/appsowned byappuser
GET /- HTML formPOST /generate- validate input and generate ISO (HTMX response)GET /download/<token>- download generated ISO
- Image name:
^[a-zA-Z0-9._-]{1,64}$ - Id:
^[a-zA-Z0-9_-]{1,32}$ - Hostname: RFC 1123 lowercase
- SSH keys:
- One per line, no tabs/control chars
- Types:
ssh-rsa,ssh-ed25519,ecdsa-sha2-nistp256/384/521 - Max 50 keys, max 4096 chars per line
Generated files live in a per-request temp directory under the OS temp folder and are cleaned after roughly 60 minutes on subsequent requests.
