Kiosk

#runbook hosts homepi4, weatherpi4
  • This runbook covers the Raspberry Pi kiosk hosts homepi4 and weatherpi4. Both use nix/services/kiosk.nix. The display stack is Cage on Wayland; Firefox runs in kiosk/private-window mode against the configured kiosk URL. For container-backed kiosks, the default URL is http://localhost:8080.

  • Quick checks

    • Check Cage and Firefox:

    • nix run .#<host> -- systemctl --no-pager --full status cage-tty1.service
      nix run .#<host> -- pgrep -a firefox
    • Expected:

      • cage-tty1.service is active (running)

      • Cage runs /nix/store/...-kiosk-firefox

      • Firefox runs with --kiosk --private-window http://localhost:8080

    • Check the container-backed app:

    • nix run .#<host> -- systemctl --no-pager --full status docker-kiosk.service
      nix run .#<host> -- docker ps
      nix run .#<host> -- journalctl -u docker-kiosk.service -n 50 --no-pager
    • Expected:

      • docker-kiosk.service is active

      • Container kiosk is running ghcr.io/jonpulsifer/hub:latest

      • Port mapping includes 0.0.0.0:8080-&gt;8080/tcp

      • Recent logs include GET / 200 and, for the weather app, GET /api/weather 200

  • If the screen shows Firefox "Oops"

    • This is usually Firefox loading before the local container is ready. The module uses a wrapper that waits for the kiosk URL before launching Firefox, but after manual switches or service restarts it is still worth checking the order of events.

    • Check whether the app is serving:

    • nix run .#<host> -- journalctl -u docker-kiosk.service -n 80 --no-pager
    • If the app is healthy and logging GET / 200, refresh the display by restarting Cage:

    • nix run .#<host> -- sudo systemctl restart cage-tty1.service
    • Verify Firefox relaunched:

    • nix run .#<host> -- pgrep -a firefox
      nix run .#<host> -- journalctl -u docker-kiosk.service -n 20 --no-pager
  • If Cage is inactive

    • Check whether it is enabled and part of the graphical target:

    • nix run .#<host> -- systemctl is-enabled cage-tty1.service
      nix run .#<host> -- readlink -f /etc/systemd/system/default.target
      nix run .#<host> -- systemctl --no-pager list-dependencies graphical.target
    • Start it manually if needed:

    • nix run .#<host> -- sudo systemctl start cage-tty1.service
    • If this happens immediately after nixos-rebuild switch, note that NixOS may report:

    • NOT restarting the following changed units: cage-tty1.service
    • In that case, restart Cage once:

    • nix run .#<host> -- sudo systemctl restart cage-tty1.service
  • If the container is down

    • Restart the container service:

    • nix run .#<host> -- sudo systemctl restart docker-kiosk.service
      nix run .#<host> -- systemctl --no-pager --full status docker-kiosk.service
    • Then restart Cage so Firefox reconnects to the now-running app:

    • nix run .#<host> -- sudo systemctl restart cage-tty1.service
  • Deploying changes

    • Build before switching:

    • nix build .#nixosConfigurations.<host>.config.system.build.toplevel --no-link
    • Switch a kiosk host:

    • nixos-rebuild switch --flake .#<host> --target-host <host> --sudo
    • For weatherpi4 over Tailscale:

    • nixos-rebuild switch --flake .#weatherpi4 --target-host weatherpi4.pirate-musical.ts.net --sudo
    • After a switch, check whether Cage was restarted. If the switch output says it was not restarted, run:

    • nix run .#<host> -- sudo systemctl restart cage-tty1.service

Linked references 4

Hosts/weatherpi4

Weather kiosk (Runbooks/Kiosk). Config: nix/hosts/weatherpi4.nix.

Hosts/homepi4

Kiosk Pi in a SmartiPi Touch 2 case with the Raspberry Pi 7" Touch Display — a physical twin of Hosts/weatherpi4 (same Pi 4B 8 GB, same pi4 + common + iperf3 + kiosk NixOS modules; only Wi-Fi SSIDs differ). Runbooks/Kiosk.

Fleet
HostPurposeHardwareNotes
Hosts/cloudpi4utility PiPi 4B 4 GBstill Ubuntu 22.04, not NixOS
Hosts/homepi4kioskPi 4B 8 GBRunbooks/Kiosk; use homepi4-wifi.lolwtf.ca
Hosts/weatherpi4kioskPi 4B 8 GBreach over Tailscale; Runbooks/Kiosk
Hosts/dnsDNSPi 5 8 GB
Hosts/rackpi5rack statusPi 5 8 GBdiskless — RAM image from spore (ADR/0008 Diskless netboot for rackpi5)
Hosts/sporeNFS/PXE boot serverPi 5 8 GB, NVMeboot-critical for rackpi5; monitored by folly
Hosts/radiopi0radioPi Zero Wunmanaged — Raspbian buster, Pirate Radio case + pHAT BEAT DAC
Runbooks

Runbooks/Kiosk — the Raspberry Pi kiosk hosts (homepi4, weatherpi4): Cage/Wayland, Firefox, container-backed apps