Applications AWS

Waltz 1.84.0 on AWS User Guide

| Product: Waltz 1.84.0 on Ubuntu 24.04 on AWS

Overview

This guide covers launching and using the Waltz 1.84.0 on Ubuntu 24.04 AMI from cloudimg on Amazon EC2. It is one version of the cloudimg help desk, IT service and project management listing on AWS Marketplace; you pick it as the software version when you subscribe and launch.

Waltz is the FINOS open source enterprise architecture tool. It holds one queryable model of your estate: the applications you run and the organisational units that own them, the people involved with each, the data flows between systems and the data types they carry, and capability, process and service taxonomies (Waltz calls them viewpoints) that you rate applications against, with surveys, attestations, assessments, report grids, diagrams and a REST API.

What the cloudimg image adds:

  • Empty and ready on first sign in. The database holds Waltz's own reference data (roles, involvement kinds, rating schemes, the five empty viewpoint categories) and no applications, people, organisational units or flows, so you start with your own estate. There is no sample data and no default user apart from your administrator.
  • A per instance administrator. First boot creates the PostgreSQL database with its own random password, the administrator admin with every Waltz role and a password unique to your instance, and the TLS certificate. Nothing secret is baked into the image.
  • nginx is the sign in. Waltz's built in password login signs its tokens with a key that is the same in every Waltz installation, so this image does not use it. nginx asks for a user name and password (HTTP Basic authentication over HTTPS, bcrypt hashes) and tells Waltz who signed in through Waltz's own header based sign in mode. nginx overwrites that header on every request, so a client cannot send its own copy and sign in as someone else.
  • Waltz is reachable only through nginx. Waltz listens on the loopback address only, and the firewall drops any connection to its port, or to PostgreSQL's, that does not come from the instance itself. Only nginx and root may connect to Waltz's port on the instance.
  • HTTPS from the first boot. nginx serves Waltz on port 443 with a certificate generated on your instance, port 80 redirects to HTTPS, and requests for a host name the instance does not serve get no answer. A change (anything other than a read) sent from another web site is refused.
  • Security updated Java libraries, without changing Waltz. Seven libraries bundled in the Waltz release are replaced by later patch releases of the same lines (Jackson 2.21.7, the PostgreSQL JDBC driver 42.2.28 and FreeMarker 2.3.35, Step 11); Waltz's own code is the official release, unmodified.
  • No database migration tool on the image. The schema is built once when the image is made, so Liquibase is not installed.
  • Metadata and private network access blocked. nginx, Waltz, PostgreSQL and the first boot service are blocked from the instance metadata service, Waltz itself may connect only to the local database, and the waltz user cannot reach addresses inside your VPC, loopback services or IPv6. The AMI requires IMDSv2.
  • Fully patched Ubuntu 24.04 LTS at build time, with unattended security upgrades switched on.

What is on the image: Waltz 1.84.0 (the official FINOS release from GitHub, checksum verified, run as the waltz user on OpenJDK 17), nginx, PostgreSQL 16, Ubuntu 24.04 LTS, cloud-init and the AWS Systems Manager agent.

Default user: ubuntu · Architecture: x86_64 · Recommended instance type: m5.large

Prerequisites

  • An AWS account subscribed to the listing, an EC2 key pair and a VPC subnet with a route to the internet (or a private route you use for management).
  • A security group that allows TCP 22 (SSH) from your admin network, and TCP 443 (Waltz) and TCP 80 (redirects to HTTPS) from the networks your staff work from. Your architecture model describes your systems and who owns them, so keep 80 and 443 as narrow as you can.

Step 1: Launch the instance

In the AWS Marketplace listing choose Continue to Subscribe, then Continue to Configuration, pick Waltz 1.84.0 on Ubuntu 24.04 as the software version and your Region, then Launch through EC2. Choose m5.large (or larger for a large estate or many users), your key pair and a security group as above.

With the AWS CLI (replace the values in angle brackets):

aws ec2 run-instances --region <region> --image-id <ami-id-from-the-listing> \
  --instance-type m5.large --key-name <your-key-pair> \
  --security-group-ids <your-security-group> --subnet-id <your-subnet> \
  --metadata-options HttpTokens=required,HttpEndpoint=enabled \
  --tag-specifications 'ResourceType=instance,Tags=[{Key=Name,Value=waltz}]'

First boot creates the database and takes about two minutes after the instance is running; Waltz then needs up to a minute more to start.

Step 2: Connect to your instance

Version SSH user
Waltz 1.84.0 on Ubuntu 24.04 ubuntu
ssh -i <your-key.pem> ubuntu@<public-ip>

Step 3: Check the services

First boot creates the PostgreSQL cluster and the database, the administrator and the certificate; nginx and Waltz start only after it has finished. waltz-egress-guard loads the firewall rules for Waltz at every boot:

systemctl is-active nginx waltz postgresql@16-main waltz-egress-guard waltz-firstboot
sudo test -f /var/lib/cloudimg/waltz-firstboot.done && echo FIRSTBOOT_DONE

All five units are active and the first boot marker is present:

active
active
active
active
active
FIRSTBOOT_DONE

Only SSH and nginx can be reached from the network. Waltz and PostgreSQL listen for the instance itself; Waltz binds all IPv4 addresses, and the firewall drops every connection to its port that does not come from the loopback address (Step 10):

sudo ss -lntp | awk 'NR>1 && $4 !~ /^127\.0\.0\.5[34]/ {split($6, p, "\""); print $4, p[2]}' | sort
0.0.0.0:22 sshd
0.0.0.0:443 nginx
0.0.0.0:80 nginx
0.0.0.0:8443 java
127.0.0.1:5432 postgres
[::]:22 sshd
[::]:443 nginx
[::]:80 nginx

Step 4: Get your URL and password

sudo cat /root/waltz-credentials.txt

The file is readable by root only:

# Waltz 1.84.0 - generated on first boot by waltz-firstboot.service
# These credentials are unique to this instance; none was baked into the image. Keep this file secret.

WALTZ_URL=https://ec2-<public-ip-dashed>.compute-1.amazonaws.com/
WALTZ_ADMIN_USER=admin
WALTZ_ADMIN_PASSWORD=<WALTZ_ADMIN_PASSWORD>
#
# Open WALTZ_URL in a browser (self-signed certificate minted on this instance's first boot; port 80 redirects to https)
# and sign in with the user and password above (the browser's sign-in prompt). admin holds every Waltz role.
# Add a person:            sudo waltz-set-password <name>     then grant roles: Profile > System Admin > Manage Users
# New admin password:      sudo waltz-set-password admin
# Change the served name:  sudo waltz-set-hostname <your-dns-name>
# Database (local only):   sudo -u postgres psql waltz
# User guide: https://www.cloudimg.co.uk/guides/waltz-1-84-0-on-ubuntu-24-04-aws/

The URL uses the instance's public DNS name from the EC2 instance metadata, and the certificate also names the public and private IP addresses. nginx answers only to the names in the certificate. The name is fixed at first boot, so if you stop and start the instance without an Elastic IP and its public address changes, run sudo waltz-set-hostname with the new name (Step 8), or better, give the instance an Elastic IP or your own DNS name.

To check the sign in end to end from the instance itself (HTTPS redirect, an unknown host name refused, the anonymous health check, wrong and stock passwords refused, the administrator's password signing in as admin with the administrator role, a forged identity header ignored, and a change request answered):

sudo waltz-cred-roundtrip
OK https 301 + unknown Host refused + healthz anonymous (forged remote-user ignored) + 401 without/wrong/stock credentials + admin whoami ADMIN + JSON POST

Step 5: Sign in

Open the WALTZ_URL in your browser. The certificate is self signed, so your browser asks you to confirm it the first time (or install your own, Step 8). Your browser then asks for a user name and password: enter admin and the password from Step 4. There is no Waltz sign in page and no sign out link, because nginx does the sign in; close the browser to sign out.

The home page shows Waltz's news, your changes and your application groups. The news text, "Welcome to the new WIP 1.26 Release of Waltz", is the placeholder Waltz ships; replace it under Profile, System Admin, Static Panels:

The Waltz home page with the Org Units, People, Data and Function menus, the News and Actions panel, the Changes panel and the Application Groups panel with no group subscriptions yet

Your administrator password. To change it, or if you lose it, set a new one from the instance. Without an option it generates a random password and writes it to the credentials file; with --stdin it reads the password you type (16 to 72 letters and digits):

sudo waltz-set-password admin
sudo waltz-set-password admin --stdin

Step 6: Add people and model your estate

Add people. Each person who signs in needs a user name and password in nginx's password file. Create one from the instance; the command prints the new password once, or reads yours with --stdin:

sudo waltz-set-password <name>
sudo waltz-set-password <name> --stdin

User names are lower case letters, digits, ., _ and -. A new person can sign in straight away and read everything, but has no Waltz roles, so they cannot change anything. Grant roles under Profile, System Admin, Manage Users: search for the user, tick the roles they need (for example App editor or Org Unit editor). To remove a person's sign in, delete their line from the password file:

sudo htpasswd -D /etc/nginx/waltz.htpasswd <name>

The Waltz User Management page with the Individual User Admin and Bulk User Admin tabs, the add a new user link, the user search and the single user admin

System Admin. Profile, System Admin holds user management, maintenance (rebuilding hierarchies after bulk changes) and Waltz's reference data: actors, assessment definitions, involvement kinds, measurable categories, rating schemes, settings and static panels:

The Waltz System Admin page with the User Management section (Manage Users, User Logs, Active Users, Custom Roles, Fine grained permissions, Analytics Dashboard), the Maintenance section and the start of the Reference Data section

Model your estate. A practical order is: the organisational unit hierarchy (Org Units), then your applications (Profile, Register App, or bulk upload), the people involved with each, the data types your systems exchange (Data), the logical flows between applications, and finally your capability, process or service taxonomies under the Function menu, against which you rate each application. Waltz's bulk upload screens and its REST API (/api/..., signed in with a user name and password like the browser) load larger estates; after a bulk load run Hierarchy Maintenance under System Admin.

Step 7: Settings that stay as they are

Waltz keeps its configuration in the settings table, shown under Profile, System Admin, Settings. Three of them make nginx the sign in, and first boot writes them; leave them as they are:

sudo -u postgres psql -X -qAt -d waltz -c "SELECT name || ' = ' || value FROM settings WHERE name LIKE 'server.authentication%' OR name = 'web.authentication' ORDER BY name"
server.authentication.filter = org.finos.waltz.web.endpoints.auth.HeaderBasedAuthenticationFilter
server.authentication.filter.headerbased.param = remote-user
web.authentication = sso

web.authentication = sso hides Waltz's own sign in and password reset screens. Waltz's settings file is /opt/waltz/.waltz/waltz.properties (owned by root, readable by the waltz group, mode 0640); it holds the database password and the address Waltz uses in links. If you change anything in it, run sudo systemctl restart waltz.

Step 8: Your own DNS name and certificate

Point a DNS record at the instance (an Elastic IP keeps the address stable), then set the name Waltz is served as. This mints a new self signed certificate for the name, points nginx and Waltz's base URL at it, updates the URL in /root/waltz-credentials.txt, and keeps the name across reboots:

sudo waltz-set-hostname <your-domain>

To use a certificate from a public or internal certificate authority instead (for example one issued by Let's Encrypt for <your-domain>), copy it over the generated pair and reload nginx (running waltz-set-hostname again replaces it with a self signed one):

sudo install -m 0644 <your-domain>.crt /etc/nginx/ssl/waltz.crt
sudo install -m 0600 <your-domain>.key /etc/nginx/ssl/waltz.key
sudo nginx -t && sudo systemctl reload nginx

Step 9: What Waltz can connect to

Waltz itself (waltz.service) may connect only to the loopback address, which it needs for its database; it makes no outbound connections and has no update check or telemetry. As a second layer, the waltz user cannot reach the instance metadata service, link local or reserved addresses, multicast, loopback services other than the database and the local DNS resolver, any IPv6 address or any address inside your VPC. The rules are rebuilt at every boot from your VPC's address ranges, which waltz-egress-guard reads from the instance metadata. You can see them with sudo nft list chain inet cloudimg_waltz output.

If a future Waltz integration needs a host on a private address, list it (one CIDR per line) in /etc/cloudimg/waltz-egress-allow and run sudo systemctl reload waltz-egress-guard; Waltz's own service would also need its IPAddressAllow widened, so contact support first.

Step 10: Security checks

nginx asks for a password on every path except the anonymous health check /healthz, which answers as Waltz's anonymous user. A wrong password and the upstream demo login admin/admin are refused, a client's own identity header is ignored, plain HTTP redirects to HTTPS, and a request for a name the instance does not serve gets no answer:

H=$(sudo grep '^WALTZ_URL=' /root/waltz-credentials.txt | cut -d= -f2- | sed -E 's#https://([^/]+)/#\1#')
for p in / /api/user/whoami /api/settings /.git/config; do
  curl -sk -o /dev/null -w "%{http_code}  $p\n" --resolve "$H:443:127.0.0.1" "https://$H$p"
done
curl -sk -o /dev/null -w 'admin/admin -> %{http_code}\n' -u admin:admin --resolve "$H:443:127.0.0.1" "https://$H/api/user/whoami"
curl -sk -o /dev/null -w 'forged identity header -> %{http_code}\n' -H 'remote-user: admin' --resolve "$H:443:127.0.0.1" "https://$H/api/user/whoami"
curl -sk -H 'remote-user: admin' --resolve "$H:443:127.0.0.1" "https://$H/healthz"; echo
curl -s -o /dev/null -w 'http:// -> %{http_code}\n' --resolve "$H:80:127.0.0.1" "http://$H/"
curl -sk -o /dev/null -w 'unknown host name -> %{http_code}\n' --resolve "other.example:443:127.0.0.1" "https://other.example/" || true
401  /
401  /api/user/whoami
401  /api/settings
404  /.git/config
admin/admin -> 401
forged identity header -> 401
{"userName":"anonymous","roles":[]}
http:// -> 301
unknown host name -> 000

From any other machine, Waltz's port 8443 and PostgreSQL's port 5432 do not answer, even if your security group allows them: the firewall on the instance (an inet table, so IPv4 and IPv6 alike) drops every connection to them that is not from 127.0.0.1 to 127.0.0.1 on the loopback interface. Waltz has no IPv6 listener at all:

sudo nft list chain inet cloudimg_waltz input
iifname "lo" ip saddr 127.0.0.1 ip daddr 127.0.0.1 tcp dport { 5432, 8443 } accept
tcp dport { 5432, 8443 } counter packets N bytes N drop comment "cloudimg-app-port"

The certificate was generated on this instance and names its own addresses:

H=$(sudo grep '^WALTZ_URL=' /root/waltz-credentials.txt | cut -d= -f2- | sed -E 's#https://([^/]+)/#\1#')
echo | openssl s_client -connect 127.0.0.1:443 -servername "$H" 2>/dev/null | openssl x509 -noout -subject -ext subjectAltName
subject=CN = ec2-<public-ip-dashed>.compute-1.amazonaws.com, O = cloudimg
X509v3 Subject Alternative Name:
    DNS:ec2-<public-ip-dashed>.compute-1.amazonaws.com, IP Address:<public-ip>, IP Address:<private-ip>, IP Address:127.0.0.1, DNS:localhost

None of the services can reach the instance metadata service, and Waltz itself may reach the loopback address only (IPAddressAllow=localhost with everything else denied):

systemctl show nginx waltz postgresql@16-main waltz-firstboot -p Id -p IPAddressDeny
IPAddressDeny=224.0.0.0/4 198.18.0.0/15 fd00:ec2::254/128 240.0.0.0/4 168.63.129.16/32 192.0.0.0/24 169.254.169.254/32
Id=nginx.service

IPAddressDeny=::/0 0.0.0.0/0
Id=waltz.service

IPAddressDeny=240.0.0.0/4 169.254.169.254/32 198.18.0.0/15 224.0.0.0/4 192.0.0.0/24 168.63.129.16/32 fd00:ec2::254/128
Id=postgresql@16-main.service

IPAddressDeny=168.63.129.16/32 224.0.0.0/4 192.0.0.0/24 fd00:ec2::254/128 240.0.0.0/4 198.18.0.0/15 169.254.169.254/32
Id=waltz-firstboot.service

Step 11: Backup, storage and maintenance

Everything you enter is in the PostgreSQL database waltz (/var/lib/postgresql/16/main), on the root volume, so the simplest backup is an EBS snapshot of it. For a database copy of your own while Waltz is running:

sudo -u postgres pg_dump -Fc waltz > <backup-dir>/waltz-$(date +%F).dump

Keep /opt/waltz/.waltz/waltz.properties and /etc/nginx/waltz.htpasswd with the dump; restore the dump with pg_restore into an empty waltz database while Waltz is stopped.

To give the database more room, enlarge the root volume in the EC2 console (Volumes, Modify); Ubuntu grows the file system on the next boot.

The Waltz code is owned by root and read only to the waltz user. New Waltz releases arrive as new versions of this listing, and support can help you move your data to one. Operating system security updates install automatically; run sudo apt-get update && sudo apt-get upgrade to apply everything else. nginx, Waltz and PostgreSQL restart cleanly and Waltz keeps all of its data.

The libraries this image updates. The Waltz 1.84.0 release bundles 75 Java libraries. The image ships them as the release built them, except for seven, each replaced by a later patch release of the same line from Maven Central (checksum pinned): jackson-core, jackson-databind, jackson-dataformat-csv, jackson-dataformat-yaml and jackson-datatype-jdk8 2.21.1 to 2.21.7, the PostgreSQL JDBC driver 42.2.5 to 42.2.28, and FreeMarker 2.3.32 to 2.3.35. Waltz starts from an explicit class path and records which library every class came from, so you can check that the updated ones are in use:

sudo grep -o -E 'lib/(jackson-(core|databind)|postgresql|freemarker)-[0-9.]+\.jar' /run/waltz/class-load.log | sort -u
lib/freemarker-2.3.35.jar
lib/jackson-core-2.21.7.jar
lib/jackson-databind-2.21.7.jar
lib/postgresql-42.2.28.jar
Component Path
Waltz /opt/waltz/app (owned by root; libraries in WEB-INF/lib, class path in classpath)
Settings and database password /opt/waltz/.waltz/waltz.properties (root:waltz, mode 0640)
Database PostgreSQL 16 database waltz (/var/lib/postgresql/16/main), 127.0.0.1:5432 only
Sign in (user names and bcrypt hashes) /etc/nginx/waltz.htpasswd (root:www-data, mode 0640)
nginx site /etc/nginx/sites-available/cloudimg-waltz
Certificate and key /etc/nginx/ssl/waltz.crt, /etc/nginx/ssl/waltz.key
Firewall rules waltz-egress-guard.service (table inet cloudimg_waltz), allow list /etc/cloudimg/waltz-egress-allow
Helpers /usr/local/sbin/waltz-set-password, waltz-set-hostname, waltz-cred-roundtrip
Credentials /root/waltz-credentials.txt (mode 0600)
Source and library manifest /usr/share/doc/cloudimg-waltz/SOURCE.txt, jars.sha256, LICENSE

Step 12: Security recommendations

  • Allow port 22 from your admin network only, and ports 80 and 443 only from the networks your staff work from.
  • Use your own DNS name and a certificate your users' browsers trust (Step 8).
  • Change the administrator password (Step 5), give each person their own sign in (Step 6) and only the Waltz roles they need, and remove sign ins people no longer need.
  • Leave the three authentication settings as they are (Step 7) and keep Waltz's port closed to the network.
  • Copy database dumps off the instance, keep the operating system patched, and snapshot the root volume regularly.

Support and licensing

Waltz is open source under the Apache License 2.0, developed by FINOS (the Fintech Open Source Foundation) and its contributors; there is no per user licence fee. The image ships the Waltz 1.84.0 release unmodified apart from the seven library updates in Step 11, and /usr/share/doc/cloudimg-waltz/SOURCE.txt names the release assets it came from and every library change. The AMI price covers cloudimg's hardening, first boot setup and support.

  • Email: support@cloudimg.co.uk
  • Website: https://www.cloudimg.co.uk
  • Support: 24/7, with a 24 hour response SLA

Waltz and FINOS are trademarks of the Linux Foundation. All product and company names are trademarks or registered trademarks of their respective holders. Use of them does not imply any affiliation with or endorsement by them.