@forgecart/flight-observability 0.202608221935.0 → 0.202608300703.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
|
@@ -25,6 +25,42 @@ pg_idle_in_tx:
|
|
|
25
25
|
usage: GAUGE
|
|
26
26
|
description: Number of idle-in-transaction backends
|
|
27
27
|
|
|
28
|
+
# Attribution for the FcIdleInTxAge class (run 32930565055 forensics: a 9.7min
|
|
29
|
+
# idle-in-tx squatter blocked a scope boot and nothing named the owner). Top-1
|
|
30
|
+
# oldest idle-in-tx session WITH identity labels. Cardinality is safe by
|
|
31
|
+
# construction: zero rows — and therefore ZERO series — whenever no squatter
|
|
32
|
+
# exists; during an incident exactly one label tuple lives for the session's
|
|
33
|
+
# lifetime. query_head is whitespace-collapsed and truncated so a label value
|
|
34
|
+
# can never carry a full statement.
|
|
35
|
+
pg_idle_in_tx_top:
|
|
36
|
+
query: >-
|
|
37
|
+
SELECT
|
|
38
|
+
COALESCE(datname, '') AS datname,
|
|
39
|
+
COALESCE(usename, '') AS usename,
|
|
40
|
+
COALESCE(application_name, '') AS application_name,
|
|
41
|
+
COALESCE(left(regexp_replace(query, '\s+', ' ', 'g'), 60), '') AS query_head,
|
|
42
|
+
EXTRACT(EPOCH FROM (now() - xact_start))::float AS age_seconds
|
|
43
|
+
FROM pg_stat_activity
|
|
44
|
+
WHERE backend_type = 'client backend' AND state = 'idle in transaction'
|
|
45
|
+
ORDER BY xact_start ASC
|
|
46
|
+
LIMIT 1
|
|
47
|
+
metrics:
|
|
48
|
+
- datname:
|
|
49
|
+
usage: LABEL
|
|
50
|
+
description: Database of the oldest idle-in-transaction session
|
|
51
|
+
- usename:
|
|
52
|
+
usage: LABEL
|
|
53
|
+
description: Role of the oldest idle-in-transaction session
|
|
54
|
+
- application_name:
|
|
55
|
+
usage: LABEL
|
|
56
|
+
description: application_name of the oldest idle-in-transaction session
|
|
57
|
+
- query_head:
|
|
58
|
+
usage: LABEL
|
|
59
|
+
description: First 60 chars of the session's last statement (whitespace-collapsed)
|
|
60
|
+
- age_seconds:
|
|
61
|
+
usage: GAUGE
|
|
62
|
+
description: Age of the oldest idle-in-transaction session (seconds)
|
|
63
|
+
|
|
28
64
|
pg_citus_backends:
|
|
29
65
|
query: >-
|
|
30
66
|
SELECT
|
|
@@ -62,3 +98,25 @@ pg_outbox:
|
|
|
62
98
|
- oldest_unsent_seconds:
|
|
63
99
|
usage: GAUGE
|
|
64
100
|
description: Age of the oldest due-but-unsent outbox row (seconds)
|
|
101
|
+
|
|
102
|
+
# Marketing-event flush health (#1074) — the sensor run 32584944772 lacked: a
|
|
103
|
+
# batch consumed with zero dispatch was invisible. WHERE-form ON PURPOSE, not
|
|
104
|
+
# pg_outbox's FILTER shape: FILTER predicates are evaluated at the aggregate
|
|
105
|
+
# node over an unqualified scan, so on the unreaped firehose table every
|
|
106
|
+
# scrape would seq-scan ALL rows; the WHERE form is served by the partial
|
|
107
|
+
# index IDX_marketing_event_outbox_unflushed and stays O(backlog) — the 097
|
|
108
|
+
# shop_outbox_metrics() precedent. Column names quoted (TypeORM camelCase).
|
|
109
|
+
pg_marketing_outbox:
|
|
110
|
+
query: >-
|
|
111
|
+
SELECT
|
|
112
|
+
count(*)::float AS backlog,
|
|
113
|
+
COALESCE(EXTRACT(EPOCH FROM (now() - min("ingestedAt"))), 0)::float AS oldest_pending_seconds
|
|
114
|
+
FROM marketing_event_outbox
|
|
115
|
+
WHERE "flushedAt" IS NULL
|
|
116
|
+
metrics:
|
|
117
|
+
- backlog:
|
|
118
|
+
usage: GAUGE
|
|
119
|
+
description: Pending (unflushed) marketing-event outbox rows
|
|
120
|
+
- oldest_pending_seconds:
|
|
121
|
+
usage: GAUGE
|
|
122
|
+
description: Age of the oldest pending marketing-event outbox row (seconds)
|
package/dist/rules/fc-alerts.yml
CHANGED
|
@@ -54,7 +54,7 @@ groups:
|
|
|
54
54
|
severity: warning
|
|
55
55
|
annotations:
|
|
56
56
|
summary: 'Idle-in-transaction backend older than 120s'
|
|
57
|
-
description: 'Oldest idle-in-tx = {{ $value }}s — a held-open transaction pins a real coordinator connection through the pooler (tech-debt #10).'
|
|
57
|
+
description: 'Oldest idle-in-tx = {{ $value }}s — a held-open transaction pins a real coordinator connection through the pooler (tech-debt #10). Owner: db={{ with query "topk(1, pg_idle_in_tx_top_age_seconds)" }}{{ . | first | label "datname" }} user={{ . | first | label "usename" }} app={{ . | first | label "application_name" }} q="{{ . | first | label "query_head" }}"{{ end }}'
|
|
58
58
|
|
|
59
59
|
- name: fc-alerts-pooler
|
|
60
60
|
rules:
|
|
@@ -156,6 +156,14 @@ groups:
|
|
|
156
156
|
annotations:
|
|
157
157
|
summary: 'Oldest due-but-unsent outbox row over 120s'
|
|
158
158
|
description: 'oldest = {{ $value }}s, backlog = {{ with query "fc:outbox:backlog" }}{{ . | first | value }}{{ end }} — the relay is stalled or the broker is refusing publishes.'
|
|
159
|
+
- alert: FcMarketingFlushLag
|
|
160
|
+
expr: fc:marketing:flush_lag_seconds > 60
|
|
161
|
+
for: 5m
|
|
162
|
+
labels:
|
|
163
|
+
severity: warning
|
|
164
|
+
annotations:
|
|
165
|
+
summary: 'Oldest pending marketing-event outbox row over 60s'
|
|
166
|
+
description: 'oldest = {{ $value }}s, backlog = {{ with query "fc:marketing:backlog" }}{{ . | first | value }}{{ end }} — flush workers stalled, claim starvation, or every claimer erroring (#1074).'
|
|
159
167
|
|
|
160
168
|
- name: fc-alerts-doctrine
|
|
161
169
|
rules:
|
|
@@ -388,6 +388,23 @@ groups:
|
|
|
388
388
|
expr: max(pg_outbox_oldest_unsent_seconds)
|
|
389
389
|
- record: fc:outbox:backlog
|
|
390
390
|
expr: max(pg_outbox_backlog)
|
|
391
|
+
- name: fc-marketing
|
|
392
|
+
interval: 15s
|
|
393
|
+
rules:
|
|
394
|
+
# Marketing-event flush health (#1074) — pg_marketing_outbox is the
|
|
395
|
+
# WHERE-form probe (partial-index-served; never the FILTER full-scan).
|
|
396
|
+
- record: fc:marketing:backlog
|
|
397
|
+
expr: max(pg_marketing_outbox_backlog)
|
|
398
|
+
- record: fc:marketing:flush_lag_seconds
|
|
399
|
+
expr: max(pg_marketing_outbox_oldest_pending_seconds)
|
|
400
|
+
# Planned-vs-fired imbalance panel — both counters at-least-once, so
|
|
401
|
+
# panels read rate trends, never exact equality (#1074).
|
|
402
|
+
- record: fc:automation:planned_match_rate
|
|
403
|
+
expr: sum(rate(fc_automation_dispatch_matches_total[5m]))
|
|
404
|
+
- record: fc:automation:fire_rate
|
|
405
|
+
expr: sum by (outcome) (rate(fc_automation_fire_total[5m]))
|
|
406
|
+
- record: fc:automation:rule_cache_rate
|
|
407
|
+
expr: sum by (outcome) (rate(fc_automation_rule_cache_total[5m]))
|
|
391
408
|
- name: fc-workspace
|
|
392
409
|
interval: 15s
|
|
393
410
|
rules:
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@forgecart/flight-observability",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.202608300703.0",
|
|
4
4
|
"private": false,
|
|
5
5
|
"description": "Flight Deck dashboards, fc: recording/alert rules, and the pg-custom-queries contract — the version-pinned sync artifact between shop-beta and forgecart/cloud (launch#46 P4).",
|
|
6
6
|
"files": [
|