Developer Tools Azure

Dokku on Ubuntu 24.04 LTS on Azure

| Product: Dokku on Ubuntu 24.04 LTS by cloudimg

This image ships Dokku on Ubuntu 24.04 LTS, ready to take a git push and build, deploy and route your application the moment the machine boots. Dokku is installed from the project's official apt repository, pinned to a known release, with Docker Engine and nginx preinstalled as the build and routing layer.

Dokku is an open source, self hosted Platform as a Service. It brings the Heroku workflow to a single server you own: you push your application with git and Dokku builds it, using Cloud Native or Heroku buildpacks, a Dockerfile or a prebuilt image, runs it as a container, and publishes it behind an nginx reverse proxy on its own hostname. A single command line manages the whole lifecycle: apps, environment variables, databases and services through plugins, scaling, domains, TLS and logs.

What this appliance does and does not do

Read this section before you deploy. It is the difference between an appliance that does what you think it does and one that quietly does not.

What Dokku is good at. Dokku gives one server the ergonomics of a managed platform. Push code and it builds and deploys it, maps a hostname, and keeps it running, with a clean CLI for config, scaling, logs, databases and TLS. It is ideal for side projects, internal tools, review and staging environments, and small production workloads where you want push to deploy simplicity without a managed platform bill.

What Dokku is not. Dokku is a single node PaaS. This image does not include, and Dokku itself is not:

  • a multi node cluster or an orchestrator: it runs apps on this one server, it does not schedule across a fleet,
  • a web control panel: Dokku is managed entirely from the command line and over SSH,
  • a managed database service: it provisions databases as local containers through plugins, which you operate yourself,
  • a hosted platform with an account and a billing plan: everything runs on infrastructure you own and administer.

What makes this image different

It is honest about having no credential. Dokku's access model is SSH public keys added to the dokku user for git push deploys. There is no password, no web login and no default account. This image ships with no deploy key baked in at all, so nothing usable is embedded in it: you add your own key on first use, and only your key can deploy.

Docker and nginx are preinstalled and proven. The container runtime and the reverse proxy are installed, enabled and health checked during the build, and the whole app lifecycle is proven end to end before the image is sealed by actually deploying a container and serving it over HTTP. What you boot is a working PaaS, not a set of packages you still have to wire together.

Routing is configured for you on first boot. On the first boot of every instance, a first boot service resolves the machine's public address and sets Dokku's global application domain to <public-ip>.nip.io, so your first deployed app gets a working hostname with no DNS to configure. You can point your own domain at it whenever you like.

The base stays patched. The Ubuntu base is fully updated at build time and keeps receiving security updates through the normal unattended-upgrades path for the life of the release.

1. Deploy the virtual machine

Deploy the image from the Azure Marketplace. The defaults in this guide assume:

  • Size: Standard_B2s (2 vCPU, 4 GB) runs the appliance and image based deploys comfortably. If you build large applications from source with buildpacks, size up to 4 GB or more of RAM so the build step has headroom.
  • Inbound ports: SSH (22) for deploying and managing, and HTTP (80) plus HTTPS (443) for your applications' traffic. Open 80/443 in your Network Security Group when you are ready to serve apps.
  • Authentication: your own SSH public key for the azureuser administrator.

2. Connect and read the connection info

ssh azureuser@<vm-ip>

Every instance writes its own connection details on first boot. Read them:

sudo cat /root/dokku-info.txt

This shows the global application domain set for this instance, the git remote pattern for pushing apps, and the exact commands to add your SSH key. Nothing in this file is a secret: the appliance ships with no credential, so this is connection information, not a password.

3. Confirm Dokku, Docker and nginx are healthy

dokku version
docker info --format 'Docker {{.ServerVersion}}, {{.Containers}} containers, storage {{.Driver}}'
systemctl is-active docker.service nginx.service
sudo test -f /var/lib/cloudimg/dokku-firstboot.done && echo "firstboot sentinel present"

You should see the pinned Dokku version, a healthy Docker engine, both docker and nginx reported active, and the first boot sentinel present. That is the whole platform confirmed up on one screen.

Dokku, Docker and nginx healthy with the first boot complete on Ubuntu 24.04

4. Add your SSH key so you can deploy

Deploys are authorised by SSH public key. From your workstation, add your public key to Dokku so your git push is accepted. The image ships with no key, so this is the first thing you do:

# On your workstation: send your public key to the server and register it with Dokku.
cat ~/.ssh/id_ed25519.pub | ssh azureuser@<vm-ip> "sudo dokku ssh-keys:add admin"

The key mechanism itself is easy to verify on the machine. This generates a throwaway key, registers it, lists the registered keys, then removes it again, so you can see exactly how ssh-keys:add, ssh-keys:list and ssh-keys:remove behave:

ssh-keygen -q -t ed25519 -N '' -f /tmp/dokku_demo_key <<<y >/dev/null
sudo dokku ssh-keys:add demokey /tmp/dokku_demo_key.pub
sudo dokku ssh-keys:list
sudo dokku ssh-keys:remove demokey
rm -f /tmp/dokku_demo_key /tmp/dokku_demo_key.pub
echo "key add / list / remove all worked"

Each registered key is what lets a matching git push dokku main authenticate as the dokku user and trigger a deploy.

Adding, listing and removing a Dokku deploy SSH key

5. Deploy and serve your first app

The fastest way to see the platform working is to deploy a prebuilt image. This creates an app, deploys a tiny web image with git:from-image, and confirms it is served through nginx on its own hostname:

dokku apps:destroy demo --force 2>/dev/null || true
dokku apps:create demo
dokku git:from-image demo nginxdemos/hello:plain-text
APPURL="$(dokku url demo)"; echo "app URL: ${APPURL}"
HOST="$(echo "${APPURL}" | sed 's#https\?://##')"
for i in $(seq 1 12); do
  CODE="$(curl -s -o /dev/null -w '%{http_code}' -H "Host: ${HOST}" http://127.0.0.1/)"
  [ "${CODE}" = "200" ] && break; sleep 3
done
echo "served HTTP ${CODE} at ${APPURL}"

Dokku pulls the image, starts the container and writes the nginx vhost for demo.<your-domain>. The app answers with HTTP 200 at the URL shown. Because the global domain is a nip.io address derived from your public IP, that hostname already resolves from anywhere once you open port 80.

A first app deployed on Dokku and served through nginx with HTTP 200

6. The git push workflow

The real Dokku workflow is git push. Once your key is registered (section 4), from your application's own git repository on your workstation you add the Dokku remote and push a branch. Dokku detects the language, builds the app with buildpacks or your Dockerfile, and deploys it:

# On your workstation, inside your app's git repository:
git remote add dokku dokku@<vm-ip>:myapp
git push dokku main
# Dokku builds and deploys it, then serves it at http://myapp.<your-domain>

You create the app once before the first push (dokku apps:create myapp, on the server or over ssh dokku@<vm-ip> apps:create myapp). Every subsequent git push is a new release.

7. Manage apps: config, scaling, logs and plugins

Everything about a running app is managed from the CLI. These are read only reports against the demo app you deployed above:

dokku apps:list
dokku ps:report demo | sed -n '1,8p'
dokku config:show demo 2>/dev/null || echo "(no config vars set yet)"
dokku logs demo --num 10 2>/dev/null | tail -n 10
dokku plugin:list | sed -n '1,10p'

Set configuration and secrets with dokku config:set demo KEY=value, scale process types with dokku ps:scale demo web=2, add a hostname with dokku domains:add demo app.example.com, and attach a database by installing the relevant plugin (for example dokku-postgres) and linking it to the app. The bundled plugins listed above are the core set; official service plugins add databases, caches and more.

Managing a Dokku app: process report, config and plugin list

8. Add your own domain and TLS

To serve an app on your own domain, point a DNS record at the server's public IP and add the domain to the app, then let Dokku's Let's Encrypt plugin provision a certificate:

# Point app.example.com at this server, then:
dokku domains:add myapp app.example.com
sudo dokku plugin:install https://github.com/dokku/dokku-letsencrypt.git
dokku letsencrypt:set myapp email you@example.com
dokku letsencrypt:enable myapp

Dokku obtains and renews the certificate and reconfigures nginx to serve https://app.example.com. Keep port 443 open in your Network Security Group.

9. First boot and troubleshooting

First boot is handled by dokku-firstboot.service, which sets this instance's global application domain and writes /root/dokku-info.txt. To inspect it:

systemctl status dokku-firstboot.service --no-pager | sed -n '1,6p'
dokku domains:report --global

If first boot did not complete (for example the machine lost power mid first boot), re-run it:

# Re-run first boot if it did not complete.
sudo rm -f /var/lib/cloudimg/dokku-firstboot.done
sudo systemctl restart dokku-firstboot.service

To change the global domain yourself at any time, run dokku domains:set-global your-domain.com. Existing apps keep their own explicit domains.

10. Licensing

Dokku is licensed under the MIT License, a permissive licence, and is installed unmodified from the project's official apt repository. Docker Engine and nginx are installed from their respective official repositories. The underlying Ubuntu operating system is installed from Ubuntu's public apt archive and stays patchable through the normal unattended-upgrades path for the life of the release.

Support

Every cloudimg deployment is backed by 24/7 support. If you have any questions about this image, contact us at support@cloudimg.co.uk.