Skip to content

bitcoin-dev-tools/ipc-dash

Repository files navigation

Bitcoin Core IPC Dashboard

A NixOS configuration that deploys a Bitcoin Core node with IPC-based monitoring. A Rust exporter connects to bitcoind's multiprocess IPC socket, exports metrics to Prometheus, and visualizes them on a public Grafana dashboard over HTTPS.

Architecture

bitcoind (-ipcbind=unix)
    |
    v  Unix socket (Cap'n Proto IPC)
ipc-exporter-rust  :9332
    |
    v  Prometheus scrape
Prometheus  :9090
    |
    v  data source
Grafana  :3000 (anonymous read-only)
    |
    v  reverse proxy
Caddy  :443 (Cloudflare DNS ACME)

Deploying Your Own

Prerequisites

  • A VPS running NixOS (tested on Hetzner Cloud CX22)
  • sops and age installed locally
  • A Cloudflare API token with DNS edit permissions for your domain
  • just command runner

1. Clone and configure

git clone <this-repo>
cd ipc-dash

2. Update deployment settings

Edit the settings block in flake.nix to match your server:

  • hostName -- your hostname
  • domain -- your domain (used for Caddy and Grafana)
  • networkInterface -- your server's network interface
  • ipAddress / prefixLength -- your server's IP
  • gateway -- your provider's gateway
  • sshKeys -- your SSH public key(s)

3. Update justfile

In justfile, set host to your server's IP or hostname.

4. Set up secrets

The included secrets.yaml is encrypted with keys you can't decrypt. Delete it and create your own:

# Generate a local age key (skip if you already have one)
age-keygen -o ~/.config/sops/age/keys.txt

# Get your local public key
age-keygen -y ~/.config/sops/age/keys.txt

Edit .sops.yaml and replace both keys:

  • &local -- your local age public key
  • &server -- leave as placeholder for now (filled after first deploy)
keys:
  - &local age1your-local-key-here
  - &server age1your-server-key-here
creation_rules:
  - path_regex: secrets\.yaml$
    key_groups:
      - age:
          - *local
          - *server

For the initial deploy, temporarily comment out the &server key and its reference so you can encrypt with just your local key:

rm secrets.yaml

# Create plaintext, then encrypt in-place
cat > secrets.yaml <<'EOF'
caddy-cloudflare-token: your-cloudflare-api-token
grafana-secret-key: some-random-hex-string
EOF
sops --encrypt --in-place secrets.yaml

5. Initial deploy

just deploy

This uses nixos-anywhere to wipe and install NixOS on the target.

6. Add server key to sops

sops-nix automatically derives an age key from the server's SSH host key for decryption -- no manual key generation needed on the server. But you need the corresponding public key in .sops.yaml so that sops can encrypt secrets the server can read.

Get the age public key from the server's SSH host key:

ssh root@<your-server> "cat /etc/ssh/ssh_host_ed25519_key.pub" | nix-shell -p ssh-to-age --run ssh-to-age

Paste the output into .sops.yaml as the &server key, uncomment it, then re-encrypt:

echo y | sops updatekeys secrets.yaml

7. Deploy the full configuration

just switch

This builds locally and runs nixos-rebuild switch on the remote.

After deploy, verify:

# Check service status
just status

# Check metrics endpoint
ssh root@<your-server> curl -s localhost:9332/metrics | head -20

File Overview

File Purpose
flake.nix Nix flake with nixpkgs, disko, sops-nix, and ipc-exporter inputs
configuration.nix All NixOS services: bitcoind, ipc-exporter, tor, prometheus, grafana, caddy, sops
disk-config.nix Disk partitioning layout (disko)
hardware-configuration.nix Hardware-specific config (generated by nixos-anywhere)
grafana/bitcoin-ipc.json Grafana dashboard for IPC-exported Bitcoin Core metrics
grafana/node-dashboard.json Grafana dashboard for system/node metrics
.sops.yaml sops encryption key configuration
secrets.yaml Encrypted secrets (Cloudflare token, Grafana secret key)
justfile Command runner recipes for deploy, switch, sync, etc.

About

Bitcoin Core IPC-based dashboard

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published