Files
OmniRoute/tests/unit/httpClientAbortGuard-default-logger.test.mjs
Bob.Hou e7999c477b fix(db): bound health scans and isolate native diagnostics (#13717)
Merged after a maintainer rework that kept every one of @HouMinXi's commits intact.

**What the rework added on top of the contribution:** the new DB health-check behaviour is gated behind a default-off feature flag (`src/shared/constants/featureFlagDefinitions.ts`, `defaultValue: "false"`), documented in `docs/reference/FEATURE_FLAGS.md` with the description key carried into all 66 locales, so the release default is unchanged and the new bounds only apply when an operator opts in. The optional-FTS5 migration set was reconciled by hand with the "180" entry that landed meanwhile (`src/lib/db/migrationRunner/constants.ts`).

**Carried from your rebased head:** the `/api/db/health` local-only classification in `src/server/authz/routeGuard.ts` plus its `routeGuard` assertion — `runManagedDbHealthCheck()` forks native diagnostics into a child process, so Hard Rules #15/#17 apply. Re-verified here: 37 pass / 0 fail.

Validated as a combined board first (this PR merged with the 21 siblings of the same wave on the release tip): eslint with the frozen suppressions, typecheck:core, check:open-sse-typecheck, complexity, cognitive-complexity, changelog-integrity, i18n new-key coverage, docs-counts, docs-sync, migration-numbering, provider-consistency and a duplicate-identifier audit all green, plus 176 passing / 0 failing focused node:test cases across the 25 test files the wave touches and the dashboard test under Vitest (2/0). Then re-validated alone on the fresh tip before this merge: conflicts re-resolved, file sizes rebaselined for this PR's own growth, eslint and this PR's focused tests re-run.

Thank you for the depth of this one — the resource-bounds suite and the sql.js startup/backup coverage are the kind of tests that keep a database layer honest.
2026-09-16 12:59:45 -03:00

34 lines
1.6 KiB
JavaScript

"use strict";
import assert from "node:assert";
import { test } from "node:test";
// Production calls installProcessCrashGuard() with NO argument in
// apiBridgeServer.ts / liveServer.ts / embedWsProxy.ts. The default logger
// must be callable; this file runs in its own node:test process, so the
// module-level installed flag starts unset and the no-arg path is exercised
// for real. Emitting "uncaughtException" through process.emit would trip the
// test runner's own listener, so the guard handler is invoked directly.
import { installProcessCrashGuard } from "../../src/shared/utils/httpClientAbortGuard.mjs";
test("installProcessCrashGuard() with no argument swallows a client abort without throwing", () => {
const warnings = [];
const originalWarn = console.warn;
console.warn = (...args) => warnings.push(args);
try {
installProcessCrashGuard();
const handlers = process
.listeners("uncaughtException")
.filter((fn) => fn.toString().includes("swallowed client-abort"));
assert.ok(handlers.length > 0, "guard handler must be registered");
const abortErr = Object.assign(new Error("aborted"), { code: "ECONNRESET" });
// A broken default logger (console is an object, not a function) throws
// TypeError here — that is what took the production process down.
assert.doesNotThrow(() => handlers[0](abortErr, "uncaughtException"));
assert.equal(warnings.length, 1, "the swallowed abort must be logged once");
assert.ok(String(warnings[0][1]).includes("swallowed client-abort"));
} finally {
console.warn = originalWarn;
}
});