feat: add Cloudflare tunnel hosting

This commit is contained in:
Jet 2026-05-28 14:50:07 -07:00
parent e6c1b82679
commit 23e087ae4b
No known key found for this signature in database
15 changed files with 839 additions and 30 deletions

View file

@ -4,8 +4,89 @@ let
prometheusPort = 9090;
lokiPort = 3100;
grafanaPort = 3030;
grafanaDomain = "grafana-noisebell.extremist.software";
nodeExporterPort = 9100;
blackboxExporterPort = 9115;
publicDashboardToken = "6e6f69736562656c6c7075626c696330";
sharePublicDashboard = pkgs.writeShellApplication {
name = "noisebell-grafana-share-public-dashboard";
runtimeInputs = [
pkgs.coreutils
pkgs.curl
pkgs.jq
];
text = ''
set -euo pipefail
base_url=http://127.0.0.1:${toString grafanaPort}
dashboard_uid=noisebell-public
public_uid=${publicDashboardToken}
access_token=${publicDashboardToken}
password=$(tr -d '\r\n' < /var/lib/grafana/admin_password)
ready=0
for _ in $(seq 1 60); do
if curl -fsS -u "admin:$password" "$base_url/api/health" >/dev/null; then
ready=1
break
fi
sleep 1
done
if [ "$ready" -ne 1 ]; then
echo "Grafana did not become ready at $base_url" >&2
exit 1
fi
dashboard_ready=0
for _ in $(seq 1 60); do
if curl -fsS -u "admin:$password" "$base_url/api/dashboards/uid/$dashboard_uid" >/dev/null; then
dashboard_ready=1
break
fi
sleep 1
done
if [ "$dashboard_ready" -ne 1 ]; then
echo "Grafana dashboard '$dashboard_uid' was not provisioned" >&2
exit 1
fi
existing=$(curl -fsS -u "admin:$password" \
"$base_url/api/dashboards/uid/$dashboard_uid/public-dashboards/" 2>/dev/null || true)
existing_uid=""
existing_token=""
if [ -n "$existing" ]; then
existing_uid=$(jq -r '.uid // empty' <<<"$existing")
existing_token=$(jq -r '.accessToken // empty' <<<"$existing")
fi
if [ -n "$existing_uid" ] && { [ "$existing_uid" != "$public_uid" ] || [ "$existing_token" != "$access_token" ]; }; then
curl -fsS -u "admin:$password" \
-X DELETE \
"$base_url/api/dashboards/uid/$dashboard_uid/public-dashboards/$existing_uid" >/dev/null
existing_uid=""
fi
if [ -n "$existing_uid" ]; then
body=$(jq -cn '{timeSelectionEnabled:true,isEnabled:true,annotationsEnabled:false,share:"public"}')
curl -fsS -u "admin:$password" \
-H 'Content-Type: application/json' \
-X PATCH \
--data "$body" \
"$base_url/api/dashboards/uid/$dashboard_uid/public-dashboards/$existing_uid" >/dev/null
else
body=$(jq -cn \
--arg uid "$public_uid" \
--arg accessToken "$access_token" \
'{uid:$uid,accessToken:$accessToken,timeSelectionEnabled:true,isEnabled:true,annotationsEnabled:false,share:"public"}')
curl -fsS -u "admin:$password" \
-H 'Content-Type: application/json' \
-X POST \
--data "$body" \
"$base_url/api/dashboards/uid/$dashboard_uid/public-dashboards/" >/dev/null
fi
'';
};
blackboxConfig = pkgs.writeText "noisebell-blackbox.yml" ''
modules:
@ -78,7 +159,7 @@ let
dashboard = pkgs.writeText "noisebell-dashboard.json" (builtins.toJSON {
uid = "noisebell";
title = "Noisebell DO + Pi";
title = "Noisebell Full Debug";
tags = [
"noisebell"
"prometheus"
@ -297,9 +378,136 @@ let
];
});
publicDashboard = pkgs.writeText "noisebell-public-dashboard.json" (builtins.toJSON {
uid = "noisebell-public";
title = "Noisebell Public";
tags = [
"noisebell"
"public"
"prometheus"
];
timezone = "browser";
schemaVersion = 39;
version = 1;
refresh = "30s";
time = {
from = "now-6h";
to = "now";
};
panels = [
(prometheusPanel {
id = 1;
title = "Door State";
type = "stat";
x = 0;
y = 0;
w = 6;
h = 6;
targets = [ (promTarget "A" "noisebell_cache_status" "{{status}}") ];
})
(prometheusPanel {
id = 2;
title = "Public Status Endpoint";
type = "stat";
x = 6;
y = 0;
w = 6;
h = 6;
targets = [ (promTarget "A" "probe_success{job=\"noisebell-http-probes\",instance=\"https://noisebell.extremist.software/status\"}" "status endpoint") ];
})
(prometheusPanel {
id = 3;
title = "Noisebell Service Health";
type = "stat";
x = 12;
y = 0;
w = 6;
h = 6;
targets = [ (promTarget "A" "up{job=~\"noisebell-(cache|pi-app|pi-relay)\"}" "{{job}}") ];
})
(prometheusPanel {
id = 4;
title = "Cache Poll Health";
x = 0;
y = 6;
w = 12;
targets = [
(promTarget "A" "noisebell_cache_poll_consecutive_failures" "consecutive failures")
(promTarget "B" "rate(noisebell_cache_poll_failure_total[5m])" "failure rate")
(promTarget "C" "rate(noisebell_cache_poll_success_total[5m])" "success rate")
(promTarget "D" "noisebell_cache_poll_last_duration_seconds" "last duration")
];
})
(prometheusPanel {
id = 5;
title = "Last Poll Result";
type = "stat";
x = 12;
y = 6;
w = 12;
targets = [
(promTarget "A" "noisebell_cache_poll_last_result" "result {{result}}")
(promTarget "B" "time() - noisebell_cache_poll_last_attempt_timestamp_seconds" "seconds since attempt")
(promTarget "C" "time() - noisebell_cache_poll_last_success_timestamp_seconds" "seconds since success")
];
})
(prometheusPanel {
id = 6;
title = "Poll Failure Types";
x = 0;
y = 14;
w = 12;
targets = [
(promTarget "A" "rate(noisebell_cache_poll_http_error_total[5m])" "http error")
(promTarget "B" "rate(noisebell_cache_poll_request_timeout_total[5m])" "timeout")
(promTarget "C" "rate(noisebell_cache_poll_request_connect_total[5m])" "connect")
(promTarget "D" "rate(noisebell_cache_poll_request_other_total[5m])" "request other")
(promTarget "E" "rate(noisebell_cache_poll_parse_failure_total[5m])" "parse")
];
})
(prometheusPanel {
id = 7;
title = "Pi App Delivery";
x = 12;
y = 14;
w = 12;
targets = [
(promTarget "A" "rate(noisebell_pi_notify_success_total[5m])" "success")
(promTarget "B" "rate(noisebell_pi_notify_attempt_failure_total[5m])" "attempt failures")
(promTarget "C" "rate(noisebell_pi_notify_failure_total[5m])" "final failures")
];
})
(prometheusPanel {
id = 8;
title = "Relay Delivery";
x = 0;
y = 22;
w = 12;
targets = [
(promTarget "A" "rate(noisebell_relay_forwarded_total[5m])" "forwarded")
(promTarget "B" "rate(noisebell_relay_attempt_failure_total[5m])" "attempt failures")
(promTarget "C" "rate(noisebell_relay_failed_total[5m])" "final failures")
(promTarget "D" "noisebell_relay_last_duration_seconds" "last duration")
];
})
(prometheusPanel {
id = 9;
title = "Pi Hardware Summary";
x = 12;
y = 22;
w = 12;
targets = [
(promTarget "A" "noisebell_pi_temperature_celsius" "temperature C")
(promTarget "B" "noisebell_pi_throttled_flags" "throttled flags")
];
})
];
});
dashboardDir = pkgs.runCommand "noisebell-grafana-dashboards" { } ''
mkdir -p "$out"
cp ${dashboard} "$out/noisebell.json"
cp ${publicDashboard} "$out/noisebell-public.json"
'';
blackboxRelabels = [
@ -608,22 +816,26 @@ in
enable = true;
settings = {
server = {
http_addr = "0.0.0.0";
http_addr = "127.0.0.1";
http_port = grafanaPort;
domain = "noisebell-do";
root_url = "http://noisebell-do:${toString grafanaPort}/";
domain = grafanaDomain;
root_url = "https://${grafanaDomain}/";
};
analytics.reporting_enabled = false;
metrics.enabled = true;
security = {
admin_user = "admin";
admin_password = "$__file{/var/lib/grafana/admin_password}";
secret_key = "$__file{/var/lib/grafana/secret_key}";
disable_initial_admin_creation = true;
disable_initial_admin_creation = false;
cookie_secure = true;
strict_transport_security = true;
strict_transport_security_max_age_seconds = 31536000;
};
auth.disable_login_form = true;
auth.disable_login_form = false;
users.allow_sign_up = false;
"auth.anonymous" = {
enabled = true;
org_role = "Viewer";
enabled = false;
};
};
provision = {
@ -670,5 +882,21 @@ in
umask 077
${pkgs.coreutils}/bin/head -c 64 /dev/urandom | ${pkgs.coreutils}/bin/base64 --wrap=0 > /var/lib/grafana/secret_key
fi
if [ ! -s /var/lib/grafana/admin_password ]; then
umask 077
${pkgs.coreutils}/bin/head -c 36 /dev/urandom | ${pkgs.coreutils}/bin/base64 --wrap=0 > /var/lib/grafana/admin_password
fi
'';
systemd.services.noisebell-grafana-public-dashboard = {
description = "Ensure deterministic Noisebell public Grafana dashboard share";
wantedBy = [ "multi-user.target" ];
after = [ "grafana.service" ];
wants = [ "grafana.service" ];
restartTriggers = [ dashboardDir ];
serviceConfig = {
Type = "oneshot";
ExecStart = "${sharePublicDashboard}/bin/noisebell-grafana-share-public-dashboard";
};
};
}