personal_infra/ansible/roles/datum_gateway
counterweight 3711421af5
ansible: move the cross-host ports to host_vars, delete services_config.yml
The four ports were the only entries in services_config.yml with a real
justification: each is read twice, by the role that deploys the service on its
own box AND by a socket-proxy or Caddy play that runs on the EDGE host and
publishes it. A role default is invisible to that second play.

But the shape was wrong in two ways. The file had to be named in vars_files: by
30 plays - opt-in configuration that someone will eventually forget - and five
role defaults silently interpolated service_settings.*, so bitcoin_knots,
fulcrum, datum_gateway and mempool were not self-contained: using any of them
without that one vars_file entry broke it.

Each port now lives in host_vars/<owning box>/main.yml:

  host_vars/knots_box_local/main.yml    bitcoin_p2p_port, datum_gateway_api_port,
                                        datum_gateway_stratum_port
  host_vars/fulcrum_box_local/main.yml  fulcrum_ssl_port
  host_vars/mempool_box_local/main.yml  mempool_frontend_port

host_vars auto-loads and outranks role defaults, so the owning role picks the
value up with no vars_files at all, and the edge play reads the same single
definition as hostvars['<host>'].<name>. The role defaults keep the protocol
standard (8333, 50002, ...) so each role still works standalone, with the live
deployment's value in host_vars winning.

Also fixed a fourth copy of an inventory identity: the mempool Caddy play had
"mempool-box:{{ ... }}" hardcoded in the upstream. It now derives the host from
hostvars['mempool_box_local'].ansible_host, so inventory is the only place any
box's name is written down.

services_config.yml is deleted, with 25 more vars_files entries across 19
playbooks. Between this and the previous commit, 87 vars_files entries are gone
and every variable in the repo now comes from group_vars/all, host_vars,
inventory, a role default, or that service's own *_vars.yml.

Verification: an edge-host probe resolves all eight ports and hostnames to
byte-identical values to the ones services_config.yml used to supply. Each
owning host resolves its own port through host_vars. All 37 playbooks'
--list-tasks output is unchanged. The four edge plays that consume these values
all check-diff changed=0 - the socket-proxy and Caddy units on vipy are
byte-identical, which is the direct proof the rewiring landed on the same
values. fulcrum and datum-gateway check-diff exactly as before (ok=28/changed=1
and ok=15/changed=1, both the known timer re-arm).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-13 21:02:57 +02:00
..
defaults ansible: move the cross-host ports to host_vars, delete services_config.yml 2026-09-13 21:02:57 +02:00
handlers datum-gateway: convert to a role, de-Uptime-Kuma the health check 2026-09-13 18:25:41 +02:00
tasks datum-gateway: convert to a role, de-Uptime-Kuma the health check 2026-09-13 18:25:41 +02:00
templates datum-gateway: convert to a role, de-Uptime-Kuma the health check 2026-09-13 18:25:41 +02:00
README.md datum-gateway: convert to a role, de-Uptime-Kuma the health check 2026-09-13 18:25:41 +02:00

datum_gateway

Builds and runs DATUM Gateway, the solo/pooled mining gateway, on knots-box. The calling playbook adds two more plays on the edge host: the dashboard via caddy_site, and the public Stratum port via socket_proxy.

Converted from deploy_datum_gateway_playbook.yml (802 lines) under Plan 6. The playbook is now 68 lines and keeps all three plays.

⚠ This is half of a system

The Bitcoin Knots node on the same host feeds this gateway through blocknotify=killall -USR1 datum_gateway in bitcoin.conf — see roles/bitcoin_knots/README.md, where that line was found to be missing from the template entirely. Changing either config means thinking about both.

Interrupting Stratum costs mining shares. Check before any run that restarts it:

ss -tn state established '( sport = :23334 )'

Two pieces of drift where the node was right

The repo and the node had diverged on values that matter, and the deployment would have applied the repo's:

node (correct) repo said
datum_mining_address bc1qvrj3g84… bc1qdse9dsg…
pool_pass_workers / _full_users false true

The address is the one that would have hurt: it is where block rewards are paid, and unlike fulcrum and bitcoin-knots the Restart datum-gateway handler here was never gated, so the change would have applied immediately rather than sitting inert. Both corrected in the vault and defaults, with notes.

Verify semantics rather than text when touching config.json — render it and compare parsed JSON, because the live file is single-line and the template is pretty-printed, so a textual diff is all noise:

json.load(open('live.json')) == json.load(open('rendered.json'))

config.json holds real secrets — diff is suppressed

The file carries bitcoind.rpcpassword and api.admin_password. --diff prints rendered content, so the task sets diff: false by default; pass -e datum_reveal_config=true to opt in.

Note pool_pass_workers / pool_pass_full_users are booleans, not passwords, despite the names — they control DATUM's pool-password passthrough. mining.pool_address is a Bitcoin address and public by nature.

Expect changed on the compile every run

Configure cmake build and Compile datum_gateway are bare command: tasks with no changed_when, so they always report changed and always re-run. The build is reproducible — Install datum_gateway binary sees identical content and does not replace it, so the installed binary keeps its original timestamp — but the compile itself is wasted work on every run. That is the idempotent floor, not drift.

Monitoring: one variable, no product knowledge

The check tests the gateway API and records the answer in its exit code, which systemd keeps: systemctl is-failed datum-gateway-healthcheck.service. Set healthcheck_push_url to report anywhere accepting an HTTP ping.

Unlike the other services here, only the health-check timer handler was gated by uptime_kuma_enabled; the main deployment restart worked throughout.