Skip to content

Commit f5bca07

Browse files
committed
fix: enable webssh and prometheus auth on upgrade
- Ensures prometheus basicAuth credentials are properly configured in grafana.yml - Ensures webssh forward_auth is properly configured in Traefik routes - Grafana configuration is now generated at every Grafana restart
1 parent a20ede3 commit f5bca07

4 files changed

Lines changed: 120 additions & 42 deletions

File tree

imageroot/actions/configure-module/20configure

Lines changed: 0 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@
88
import json
99
import sys
1010
import agent
11-
import agent.tasks
1211
import os
1312
import uuid
1413

@@ -169,47 +168,6 @@ with open('prometheus.env', 'w') as pfp:
169168
pfp.write(f"PROMETHEUS_PATH={config['prometheus_path']}\n")
170169
pfp.write(f"PROMETHEUS_RETENTION={metrics_retention_days}d\n")
171170

172-
# Grafana configuration
173-
db = agent.read_envfile('db.env')
174-
secret = agent.read_envfile('secret.env')
175-
prometheus_user = secret.get('PROMETHEUS_AUTH_USERNAME', 'prometheus')
176-
prometheus_pass = secret.get('PROMETHEUS_AUTH_PASSWORD', 'prometheus')
177-
with open('grafana.yml', 'w') as fp:
178-
fp.write("apiVersion: 1\n")
179-
fp.write("datasources:\n")
180-
fp.write(' - name: Local Promethus\n')
181-
fp.write(' type: prometheus\n')
182-
fp.write(' uid: prometheus\n')
183-
fp.write(' access: proxy\n')
184-
fp.write(f' url: http://127.0.0.1:{ports[7]}{config["prometheus_path"]}\n')
185-
fp.write(' basicAuth: true\n')
186-
fp.write(f' basicAuthUser: {prometheus_user}\n')
187-
fp.write(' secureJsonData:\n')
188-
fp.write(f' basicAuthPassword: {prometheus_pass}\n')
189-
190-
fp.write(' - name: Local Loki\n')
191-
fp.write(' type: loki\n')
192-
fp.write(' uid: loki\n')
193-
fp.write(' access: proxy\n')
194-
fp.write(f' url: http://127.0.0.1:{ports[5]}\n')
195-
196-
fp.write(' - name: Local Timescale\n')
197-
fp.write(' type: postgres\n')
198-
fp.write(' uid: timescale\n')
199-
fp.write(f' url: 127.0.0.1:{db.get("POSTGRES_PORT")}\n')
200-
fp.write(f' user: grafana\n')
201-
fp.write(' secureJsonData:\n')
202-
fp.write(f' password: {db.get("GRAFANA_POSTGRES_PASSWORD")}\n')
203-
fp.write(' jsonData:\n')
204-
fp.write(' database: report\n')
205-
fp.write(' sslmode: disable\n')
206-
fp.write(' maxOpenConns: 100\n')
207-
fp.write(' maxIdleConns: 100\n')
208-
fp.write(' maxIdleConnsAuto: true\n')
209-
fp.write(' connMaxLifetime: 14400\n')
210-
fp.write(' postgresVersion: 1500\n')
211-
fp.write(' timescaledb: true\n')
212-
213171
network = agent.read_envfile('network.env')
214172

215173
# Listen also on VPN server address
Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
#!/usr/bin/env python3
2+
3+
#
4+
# Copyright (C) 2026 Nethesis S.r.l.
5+
# SPDX-License-Identifier: GPL-3.0-or-later
6+
#
7+
8+
import json
9+
import agent
10+
11+
# Load configuration
12+
try:
13+
with open('config.json', 'r') as f:
14+
config = json.load(f)
15+
except FileNotFoundError:
16+
with open('grafana.yml', 'w') as fp:
17+
fp.write("apiVersion: 1\n")
18+
fp.write("datasources: []\n")
19+
exit(0)
20+
21+
# Load secrets and database configuration
22+
secret = agent.read_envfile('secret.env')
23+
db = agent.read_envfile('db.env')
24+
25+
# Get Prometheus credentials
26+
prometheus_user = secret.get('PROMETHEUS_AUTH_USERNAME', 'prometheus')
27+
prometheus_pass = secret.get('PROMETHEUS_AUTH_PASSWORD', 'prometheus')
28+
29+
# Get nework configuration
30+
loki = agent.read_envfile('loki.env')
31+
loki_port = loki.get('LOKI_HTTP_PORT')
32+
network = agent.read_envfile('network.env')
33+
api_port = network.get('API_PORT')
34+
35+
# Generate grafana.yml
36+
with open('grafana.yml', 'w') as fp:
37+
fp.write("apiVersion: 1\n")
38+
fp.write("datasources:\n")
39+
fp.write(' - name: Local Promethus\n')
40+
fp.write(' type: prometheus\n')
41+
fp.write(' uid: prometheus\n')
42+
fp.write(' access: proxy\n')
43+
fp.write(f' url: http://127.0.0.1:{api_port}{config["prometheus_path"]}\n')
44+
fp.write(' basicAuth: true\n')
45+
fp.write(f' basicAuthUser: {prometheus_user}\n')
46+
fp.write(' secureJsonData:\n')
47+
fp.write(f' basicAuthPassword: {prometheus_pass}\n')
48+
49+
fp.write(' - name: Local Loki\n')
50+
fp.write(' type: loki\n')
51+
fp.write(' uid: loki\n')
52+
fp.write(' access: proxy\n')
53+
fp.write(f' url: http://127.0.0.1:{loki_port}\n')
54+
55+
fp.write(' - name: Local Timescale\n')
56+
fp.write(' type: postgres\n')
57+
fp.write(' uid: timescale\n')
58+
fp.write(f' url: 127.0.0.1:{db.get("POSTGRES_PORT")}\n')
59+
fp.write(f' user: grafana\n')
60+
fp.write(' secureJsonData:\n')
61+
fp.write(f' password: {db.get("GRAFANA_POSTGRES_PASSWORD")}\n')
62+
fp.write(' jsonData:\n')
63+
fp.write(' database: report\n')
64+
fp.write(' sslmode: disable\n')
65+
fp.write(' maxOpenConns: 100\n')
66+
fp.write(' maxIdleConns: 100\n')
67+
fp.write(' maxIdleConnsAuto: true\n')
68+
fp.write(' connMaxLifetime: 14400\n')
69+
fp.write(' postgresVersion: 1500\n')
70+
fp.write(' timescaledb: true\n')

imageroot/systemd/user/grafana.service

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ EnvironmentFile=%S/state/environment
1010
Restart=always
1111
TimeoutStopSec=70
1212
ExecStartPre=/bin/rm -f %t/grafana.pid %t/grafana.ctr-id
13+
ExecStartPre=runagent expand-grafana-config
1314
ExecStart=/usr/bin/podman run \
1415
--conmon-pidfile %t/grafana.pid \
1516
--cidfile %t/grafana.ctr-id \
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
#!/usr/bin/env python3
2+
3+
#
4+
# Copyright (C) 2026 Nethesis S.r.l.
5+
# SPDX-License-Identifier: GPL-3.0-or-later
6+
#
7+
8+
import json
9+
import sys
10+
import agent
11+
import os
12+
13+
(start,end) = os.environ["TCP_PORTS_RANGE"].split('-')
14+
ports = [*range(int(start), int(end)+1)]
15+
16+
try:
17+
with open('config.json', 'r') as tmp:
18+
config = json.load(tmp)
19+
except:
20+
sys.exit(0)
21+
22+
# Exit if not configured
23+
if not config.get('webssh_path'):
24+
sys.exit(0)
25+
26+
try:
27+
network = agent.read_envfile('network.env')
28+
webssh_port = network.get('WEBSSH_PORT')
29+
except:
30+
sys.exit(0)
31+
32+
# Configure Traefik to route requests to the webssh service with forward_auth
33+
set_route_data = {
34+
'instance': os.environ['MODULE_ID'] + '_webssh',
35+
'url': f'http://127.0.0.1:{webssh_port}',
36+
'http2https': True,
37+
'host': config.get('host', ''),
38+
'path': config['webssh_path'],
39+
'strip_prefix': True,
40+
'lets_encrypt_check': True,
41+
'lets_encrypt_cleanup': True,
42+
'forward_auth': {
43+
'address': f'http://127.0.0.1:{ports[3]}/api/auth',
44+
},
45+
}
46+
if config.get('lets_encrypt'):
47+
set_route_data['lets_encrypt'] = config['lets_encrypt']
48+
49+
agent.set_route(set_route_data)

0 commit comments

Comments
 (0)