@obsunified/collector 2.2.0 → 2.2.1
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.
- package/dist/index.d.ts +53 -3
- package/dist/index.js +10459 -9696
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
- package/src/__tests__/autosre-closed-loop.test.ts +964 -17
- package/src/lib/analyses-runner.ts +44 -7
- package/src/lib/autosre-change-correlation.ts +39 -12
- package/src/lib/autosre-findings.ts +68 -30
- package/src/lib/autosre-ontology-cache.test.ts +78 -0
- package/src/lib/autosre-ontology.ts +52 -28
- package/src/lib/autosre-remediation-gate.ts +799 -335
- package/src/lib/housekeeping.test.ts +70 -0
- package/src/lib/housekeeping.ts +91 -83
- package/src/lib/store/ingest.ts +8 -56
- package/src/migrations/051_incident_active_dedup_unique.sql +31 -0
- package/src/migrations/alert-state-notified.test.ts +3 -3
- package/src/migrations-postgres/051_incident_active_dedup_unique.sql +31 -0
- package/src/plugins/alerts-evaluator.ts +15 -3
- package/src/plugins/autosre-routes.ts +223 -108
- package/src/plugins/connected-routes/manifest.ts +1 -4
- package/src/plugins/connected-routes.ts +48 -78
- package/src/plugins/evidence-retrieval-routes.test.ts +32 -0
- package/src/plugins/evidence-retrieval-routes.ts +372 -30
package/dist/index.d.ts
CHANGED
|
@@ -154,6 +154,8 @@ interface HousekeepingSummary {
|
|
|
154
154
|
ontology_nodes?: number;
|
|
155
155
|
change_events?: number;
|
|
156
156
|
incident_investigations?: number;
|
|
157
|
+
/** `leased` incidents whose lease expired and were returned to `open` (RFC 0013 § 11). */
|
|
158
|
+
incident_leases_reaped?: number;
|
|
157
159
|
investigation_findings?: number;
|
|
158
160
|
remediation_proposals?: number;
|
|
159
161
|
}
|
|
@@ -1116,7 +1118,9 @@ declare function computeChangeBlastRadius(db: SqlDb, projectId: string, changeId
|
|
|
1116
1118
|
minComparableSample?: number;
|
|
1117
1119
|
}): Promise<ChangeBlastRadiusResult | null>;
|
|
1118
1120
|
|
|
1119
|
-
declare function recordInvestigationFinding(db: SqlDb, projectId: string, input: InvestigationFindingInput
|
|
1121
|
+
declare function recordInvestigationFinding(db: SqlDb, projectId: string, input: InvestigationFindingInput, options?: {
|
|
1122
|
+
logger?: Logger;
|
|
1123
|
+
}): Promise<InvestigationFinding>;
|
|
1120
1124
|
declare function getInvestigationFinding(db: SqlDb, projectId: string, findingId: string, environment?: string): Promise<InvestigationFinding | null>;
|
|
1121
1125
|
declare function searchInvestigationFindings(db: SqlDb, options: {
|
|
1122
1126
|
projectId: string;
|
|
@@ -1274,13 +1278,30 @@ declare function acquireIncidentLease(db: SqlDb, projectId: string, incidentId:
|
|
|
1274
1278
|
}>;
|
|
1275
1279
|
/**
|
|
1276
1280
|
* SSRF-safe, HMAC-SHA256 signed AutoSRE incident webhook outbox delivery
|
|
1277
|
-
* (RFC 0013 § 6.A).
|
|
1281
|
+
* (RFC 0013 § 6.A). Mirrors the alert webhook delivery: literal host check,
|
|
1282
|
+
* DNS classification (fail closed on private/unresolvable), no redirects and
|
|
1283
|
+
* a 5s timeout.
|
|
1284
|
+
*
|
|
1285
|
+
* Grant handoff (RFC 0013 § 6.B): when `webhook.grant` is supplied the payload
|
|
1286
|
+
* is an `autosre.remediation.grant_issued` event carrying `proposalId`,
|
|
1287
|
+
* `status` and the plaintext `grantToken`. The plaintext token exists only at
|
|
1288
|
+
* approve/propose time (the DB keeps its hash), so the caller that mints it
|
|
1289
|
+
* must hand it to this function in the same request. Grant deliveries do not
|
|
1290
|
+
* count against the incident's 5-attempt dispatch budget.
|
|
1278
1291
|
*/
|
|
1279
1292
|
declare function dispatchIncidentWebhook(db: SqlDb, projectId: string, incidentId: string, webhook: {
|
|
1280
1293
|
url: string;
|
|
1281
1294
|
secret?: string;
|
|
1295
|
+
environment?: string;
|
|
1282
1296
|
allowPrivateNetworks?: boolean;
|
|
1297
|
+
hostLookup?: HostLookup;
|
|
1283
1298
|
fetchImpl?: typeof fetch;
|
|
1299
|
+
logger?: Logger;
|
|
1300
|
+
grant?: {
|
|
1301
|
+
proposalId: string;
|
|
1302
|
+
status: string;
|
|
1303
|
+
grantToken: string;
|
|
1304
|
+
};
|
|
1284
1305
|
}): Promise<{
|
|
1285
1306
|
delivered: boolean;
|
|
1286
1307
|
status?: number;
|
|
@@ -1293,7 +1314,9 @@ declare class RemediationGateError extends Error {
|
|
|
1293
1314
|
/**
|
|
1294
1315
|
* Pre-execution remediation proposal gate (RFC 0013 § 6.B & P1 #4).
|
|
1295
1316
|
*/
|
|
1296
|
-
declare function proposeRemediationAction(db: SqlDb, projectId: string, input: RemediationProposalInput
|
|
1317
|
+
declare function proposeRemediationAction(db: SqlDb, projectId: string, input: RemediationProposalInput, options?: {
|
|
1318
|
+
logger?: Logger;
|
|
1319
|
+
}): Promise<RemediationProposal>;
|
|
1297
1320
|
declare function getRemediationProposal(db: SqlDb, projectId: string, proposalId: string, environment?: string): Promise<RemediationProposal | null>;
|
|
1298
1321
|
declare function listRemediationProposals(db: SqlDb, options: {
|
|
1299
1322
|
projectId: string;
|
|
@@ -1306,6 +1329,10 @@ declare function listRemediationProposals(db: SqlDb, options: {
|
|
|
1306
1329
|
/**
|
|
1307
1330
|
* Human dashboard session approval for `pending_human_approval` proposals
|
|
1308
1331
|
* (RFC 0013 § 6.B & P1 #4). Mints a single-use `grantToken`.
|
|
1332
|
+
*
|
|
1333
|
+
* The status precondition lives in the UPDATE's WHERE clause (D1 and Postgres
|
|
1334
|
+
* have no multi-statement transactions beyond `batch`), so two concurrent
|
|
1335
|
+
* approvals cannot both mint a token: only one sees `meta.changes === 1`.
|
|
1309
1336
|
*/
|
|
1310
1337
|
declare function approveRemediationProposal(db: SqlDb, projectId: string, proposalId: string, options: {
|
|
1311
1338
|
environment?: string;
|
|
@@ -1319,19 +1346,31 @@ declare function rejectRemediationProposal(db: SqlDb, projectId: string, proposa
|
|
|
1319
1346
|
/**
|
|
1320
1347
|
* Single-use grant redemption with optimistic `expectedCurrentState` verification
|
|
1321
1348
|
* against `ontology_nodes` (RFC 0013 § 6.B & P1 #4).
|
|
1349
|
+
*
|
|
1350
|
+
* The status, token-hash and expiry preconditions are part of the claiming
|
|
1351
|
+
* UPDATE, and the outcome is read from `meta.changes`: of N concurrent claims
|
|
1352
|
+
* for one token exactly one sees `changes === 1`; the rest get a 409. The
|
|
1353
|
+
* incident transition rides in the same `batch` and is guarded by an EXISTS on
|
|
1354
|
+
* the winning claim, so a losing claim cannot touch the incident.
|
|
1322
1355
|
*/
|
|
1323
1356
|
declare function claimRemediationGrant(db: SqlDb, projectId: string, proposalId: string, options: {
|
|
1324
1357
|
environment?: string;
|
|
1325
1358
|
grantToken: string;
|
|
1326
1359
|
runnerId?: string;
|
|
1327
1360
|
nowIso?: string;
|
|
1361
|
+
logger?: Logger;
|
|
1328
1362
|
}): Promise<RemediationProposal>;
|
|
1329
1363
|
/**
|
|
1330
1364
|
* Records remediation completion, updates `ontology_nodes` to desired state,
|
|
1331
1365
|
* and arms the +2m/+5m/+15m post-remediation watchdog on the finding.
|
|
1366
|
+
*
|
|
1367
|
+
* Only the runner that holds the claim may complete, and only while the claim
|
|
1368
|
+
* window is open (`now <= claim_expires_at`); otherwise 409. All follow-up
|
|
1369
|
+
* writes are guarded on the completion UPDATE having applied.
|
|
1332
1370
|
*/
|
|
1333
1371
|
declare function completeRemediationProposal(db: SqlDb, projectId: string, proposalId: string, options: {
|
|
1334
1372
|
environment?: string;
|
|
1373
|
+
runnerId?: string;
|
|
1335
1374
|
resultingChangeId?: string | null;
|
|
1336
1375
|
remediationAgentRunId?: string | null;
|
|
1337
1376
|
baselineRequestRatePerMin?: number | null;
|
|
@@ -1339,6 +1378,7 @@ declare function completeRemediationProposal(db: SqlDb, projectId: string, propo
|
|
|
1339
1378
|
}): Promise<RemediationProposal>;
|
|
1340
1379
|
declare function failRemediationProposal(db: SqlDb, projectId: string, proposalId: string, options: {
|
|
1341
1380
|
environment?: string;
|
|
1381
|
+
runnerId?: string;
|
|
1342
1382
|
failureReason: string;
|
|
1343
1383
|
nowIso?: string;
|
|
1344
1384
|
}): Promise<RemediationProposal>;
|
|
@@ -1349,6 +1389,8 @@ interface WatchdogEvaluationSummary {
|
|
|
1349
1389
|
stillDegraded: number;
|
|
1350
1390
|
timedOutClaims: number;
|
|
1351
1391
|
expiredGrants: number;
|
|
1392
|
+
/** Findings whose evaluation threw; logged and retried on the next tick. */
|
|
1393
|
+
failed: number;
|
|
1352
1394
|
}
|
|
1353
1395
|
/**
|
|
1354
1396
|
* Post-Remediation Watchdog & Lease/Claim Timeout Evaluator (RFC 0013 § 5.B, § 6.B & P1 #3).
|
|
@@ -1357,10 +1399,18 @@ interface WatchdogEvaluationSummary {
|
|
|
1357
1399
|
* - `recovery_status`: whether the service recovered under comparable traffic (`N >= minComparableRequests`)
|
|
1358
1400
|
* - `causal_verification_status`: `"operationally_corroborated"` (never promoted to `"counterfactual_verified"`
|
|
1359
1401
|
* by telemetry recovery alone!).
|
|
1402
|
+
*
|
|
1403
|
+
* Checkpoints are scheduled at +2m/+5m/+15m measured from the remediation's
|
|
1404
|
+
* completion time (not from whenever a tick happened to run), and a finding
|
|
1405
|
+
* only becomes `recovered` after two consecutive healthy checkpoints that each
|
|
1406
|
+
* had sufficient traffic. Pass `projectId` to scope the sweep to one tenant
|
|
1407
|
+
* (HTTP path); the cron path omits it and sweeps every project.
|
|
1360
1408
|
*/
|
|
1361
1409
|
declare function evaluateRemediationWatchdogs(db: SqlDb, options?: {
|
|
1362
1410
|
nowIso?: string;
|
|
1363
1411
|
minComparableRequests?: number;
|
|
1412
|
+
projectId?: string;
|
|
1413
|
+
logger?: Logger;
|
|
1364
1414
|
}): Promise<WatchdogEvaluationSummary>;
|
|
1365
1415
|
|
|
1366
1416
|
/**
|