Skip to content

Commit c53570d

Browse files
committed
feat(scripts): add GA queue dashboard helper
Adds a lightweight terminal dashboard script for monitoring GA queue state, active jobs, and recent worker log signals during long-running imports.
1 parent 102d3ed commit c53570d

1 file changed

Lines changed: 104 additions & 0 deletions

File tree

scripts/ga-dashboard.sh

Lines changed: 104 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,104 @@
1+
#!/usr/bin/env bash
2+
3+
set -euo pipefail
4+
5+
INTERVAL_SECONDS="${1:-5}"
6+
TOP_STARTED="${TOP_STARTED:-20}"
7+
RECENT_LOG_LINES="${RECENT_LOG_LINES:-10}"
8+
9+
if [[ -d "./venv" ]]; then
10+
# shellcheck disable=SC1091
11+
source "./venv/bin/activate"
12+
fi
13+
14+
cleanup() {
15+
echo
16+
echo "[ga-dashboard] stopped"
17+
}
18+
trap cleanup INT TERM
19+
20+
while true; do
21+
clear
22+
echo "OpenCRE GA Dashboard $(date '+%Y-%m-%d %H:%M:%S') (refresh=${INTERVAL_SECONDS}s)"
23+
echo "Press Ctrl-C to stop"
24+
echo
25+
26+
python - <<'PY'
27+
from datetime import datetime, timezone
28+
from rq import Queue
29+
from rq.registry import StartedJobRegistry, FailedJobRegistry, DeferredJobRegistry, ScheduledJobRegistry
30+
from application.utils import redis
31+
32+
queue_names = ["high", "default", "low", "ga"]
33+
conn = redis.connect()
34+
35+
print("Queue status")
36+
print("-----------")
37+
for qn in queue_names:
38+
q = Queue(qn, connection=conn)
39+
started = StartedJobRegistry(qn, connection=conn).get_job_ids()
40+
failed = FailedJobRegistry(qn, connection=conn).get_job_ids()
41+
deferred = DeferredJobRegistry(qn, connection=conn).get_job_ids()
42+
scheduled = ScheduledJobRegistry(qn, connection=conn).get_job_ids()
43+
print(
44+
f"{qn:7} queued={len(q):4} started={len(started):3} "
45+
f"failed={len(failed):3} deferred={len(deferred):3} scheduled={len(scheduled):3}"
46+
)
47+
48+
print("\nStarted GA jobs")
49+
print("---------------")
50+
ga_q = Queue("ga", connection=conn)
51+
ga_started = StartedJobRegistry("ga", connection=conn).get_job_ids()
52+
now = datetime.now(timezone.utc)
53+
if not ga_started:
54+
print("(none)")
55+
else:
56+
top_n = int(__import__("os").environ.get("TOP_STARTED", "20"))
57+
for jid in ga_started[:top_n]:
58+
job = ga_q.fetch_job(jid)
59+
if not job:
60+
print(f"- {jid} | <missing>")
61+
continue
62+
started_at = getattr(job, "started_at", None)
63+
age = "?"
64+
if started_at is not None:
65+
age = str(now - started_at).split(".", 1)[0]
66+
print(f"- {jid} | age={age} | {job.description}")
67+
68+
needle = {
69+
"CAPEC->DevSecOps Maturity Model (DSOMM)",
70+
"DevSecOps Maturity Model (DSOMM)->CAPEC",
71+
}
72+
hits = []
73+
for bucket, ids in (
74+
("queued", ga_q.job_ids),
75+
("started", ga_started),
76+
("failed", FailedJobRegistry("ga", connection=conn).get_job_ids()),
77+
("deferred", DeferredJobRegistry("ga", connection=conn).get_job_ids()),
78+
("scheduled", ScheduledJobRegistry("ga", connection=conn).get_job_ids()),
79+
):
80+
for jid in ids:
81+
job = ga_q.fetch_job(jid)
82+
if not job:
83+
continue
84+
desc = (job.description or "").strip()
85+
if desc in needle:
86+
hits.append((bucket, jid, desc))
87+
88+
print("\nCAPEC<->DSOMM status")
89+
print("--------------------")
90+
if not hits:
91+
print("(not present in ga queue/registries)")
92+
else:
93+
for bucket, jid, desc in hits:
94+
print(f"- {bucket:9} {jid} | {desc}")
95+
PY
96+
97+
echo
98+
echo "Recent GA worker log signals"
99+
echo "----------------------------"
100+
rg -n "ga: |Successfully completed|exception raised|Transient GA error|Performing GraphDB queries" "worker-"*.log -S \
101+
| tail -n "${RECENT_LOG_LINES}" || true
102+
103+
sleep "${INTERVAL_SECONDS}"
104+
done

0 commit comments

Comments
 (0)