mirror of
https://github.com/MBombeck/HealthLog.git
synced 2026-11-15 15:02:04 +00:00
style: apply prettier across the tree
One-shot prettier pass so the new format:check gate starts from a clean baseline. Formatting only — no behaviour change. Generator-owned and vendored artifacts stay untouched via .prettierignore.
This commit is contained in:
1 parent
b3fea2ef59
commit
1f4ba5939d
1000 files changed
+12130
-8385
No files matched your search
@@ -90,9 +90,9 @@ describe("isTolerableRequestProbeError — narrow-catch classifier", () => {
|
||||
expect(isTolerableRequestProbeError(new Error("private member #x"))).toBe(
|
||||
false,
|
||||
);
|
||||
expect(
|
||||
isTolerableRequestProbeError(new RangeError("private member")),
|
||||
).toBe(false);
|
||||
expect(isTolerableRequestProbeError(new RangeError("private member"))).toBe(
|
||||
false,
|
||||
);
|
||||
expect(isTolerableRequestProbeError("private member string")).toBe(false);
|
||||
expect(isTolerableRequestProbeError(null)).toBe(false);
|
||||
expect(isTolerableRequestProbeError(undefined)).toBe(false);
|
||||
|
||||
@@ -1,9 +1,6 @@
|
||||
import { describe, it, expect } from "vitest";
|
||||
import { z } from "zod/v4";
|
||||
import {
|
||||
returnAllZodIssues,
|
||||
sanitiseZodIssues,
|
||||
} from "../api-response";
|
||||
import { returnAllZodIssues, sanitiseZodIssues } from "../api-response";
|
||||
|
||||
// v1.4.42 W2 — every Zod-validated route historically returned
|
||||
// `parsed.error.issues[0].message`, dropping every issue past the first.
|
||||
@@ -28,7 +25,9 @@ describe("returnAllZodIssues", () => {
|
||||
const body = (await response.json()) as {
|
||||
data: null;
|
||||
error: string;
|
||||
details: { issues: Array<{ path: string; code: string; message: string }> };
|
||||
details: {
|
||||
issues: Array<{ path: string; code: string; message: string }>;
|
||||
};
|
||||
};
|
||||
expect(body.data).toBeNull();
|
||||
expect(body.error).toBe("Validation failed");
|
||||
|
||||
@@ -15,14 +15,41 @@ const PNG_1X1 = Buffer.from(
|
||||
|
||||
/** Minimal JPEG: SOI + APP0 + SOF0(1×1) + EOI. */
|
||||
const JPEG_1X1 = Buffer.from([
|
||||
0xff, 0xd8, // SOI
|
||||
0xff, 0xe0, 0x00, 0x10, 0x4a, 0x46, 0x49, 0x46, 0x00, 0x01, 0x01, 0x00, 0x00,
|
||||
0x01, 0x00, 0x01, 0x00, 0x00,
|
||||
0xff, 0xc0, 0x00, 0x0b, 0x08,
|
||||
0x00, 0x01, // height = 1
|
||||
0x00, 0x01, // width = 1
|
||||
0x01, 0x01, 0x11, 0x00,
|
||||
0xff, 0xd9, // EOI
|
||||
0xff,
|
||||
0xd8, // SOI
|
||||
0xff,
|
||||
0xe0,
|
||||
0x00,
|
||||
0x10,
|
||||
0x4a,
|
||||
0x46,
|
||||
0x49,
|
||||
0x46,
|
||||
0x00,
|
||||
0x01,
|
||||
0x01,
|
||||
0x00,
|
||||
0x00,
|
||||
0x01,
|
||||
0x00,
|
||||
0x01,
|
||||
0x00,
|
||||
0x00,
|
||||
0xff,
|
||||
0xc0,
|
||||
0x00,
|
||||
0x0b,
|
||||
0x08,
|
||||
0x00,
|
||||
0x01, // height = 1
|
||||
0x00,
|
||||
0x01, // width = 1
|
||||
0x01,
|
||||
0x01,
|
||||
0x11,
|
||||
0x00,
|
||||
0xff,
|
||||
0xd9, // EOI
|
||||
]);
|
||||
|
||||
/**
|
||||
|
||||
Binary file not shown.
@@ -10,14 +10,7 @@
|
||||
* `window` shape the helper actually reads, so the test runs under
|
||||
* the default node environment without pulling in `jsdom`.
|
||||
*/
|
||||
import {
|
||||
afterEach,
|
||||
beforeEach,
|
||||
describe,
|
||||
expect,
|
||||
it,
|
||||
vi,
|
||||
} from "vitest";
|
||||
import { afterEach, beforeEach, describe, expect, it, vi } from "vitest";
|
||||
|
||||
interface Globals {
|
||||
document?: { cookie: string };
|
||||
|
||||
@@ -106,9 +106,9 @@ describe("formatDateOrRelative", () => {
|
||||
});
|
||||
|
||||
it("accepts a Date instance as well as ISO string", () => {
|
||||
expect(
|
||||
formatDateOrRelative(new Date(NOW - 30 * MINUTE), fakeT, NOW),
|
||||
).toBe("insights.relativeMinutesAgoOther:count=30");
|
||||
expect(formatDateOrRelative(new Date(NOW - 30 * MINUTE), fakeT, NOW)).toBe(
|
||||
"insights.relativeMinutesAgoOther:count=30",
|
||||
);
|
||||
});
|
||||
|
||||
// v1.4.49.2 — regression guard. The helper's `t()` calls must dispatch
|
||||
@@ -121,16 +121,39 @@ describe("formatDateOrRelative", () => {
|
||||
it("emits only keys that exist in the translation bundle", async () => {
|
||||
const en = await import("../../../messages/en.json");
|
||||
const bundleKeysCalled = new Set<string>();
|
||||
const collectingT = (key: string, params?: Record<string, string | number>) => {
|
||||
const collectingT = (
|
||||
key: string,
|
||||
params?: Record<string, string | number>,
|
||||
) => {
|
||||
bundleKeysCalled.add(key);
|
||||
return params ? `${key}:${JSON.stringify(params)}` : key;
|
||||
};
|
||||
// Drive every relative bucket so we hit `t()` on each branch.
|
||||
formatDateOrRelative(new Date(NOW - 30 * SECOND).toISOString(), collectingT, NOW);
|
||||
formatDateOrRelative(new Date(NOW - 1 * MINUTE).toISOString(), collectingT, NOW);
|
||||
formatDateOrRelative(new Date(NOW - 30 * MINUTE).toISOString(), collectingT, NOW);
|
||||
formatDateOrRelative(new Date(NOW - 1 * HOUR).toISOString(), collectingT, NOW);
|
||||
formatDateOrRelative(new Date(NOW - 12 * HOUR).toISOString(), collectingT, NOW);
|
||||
formatDateOrRelative(
|
||||
new Date(NOW - 30 * SECOND).toISOString(),
|
||||
collectingT,
|
||||
NOW,
|
||||
);
|
||||
formatDateOrRelative(
|
||||
new Date(NOW - 1 * MINUTE).toISOString(),
|
||||
collectingT,
|
||||
NOW,
|
||||
);
|
||||
formatDateOrRelative(
|
||||
new Date(NOW - 30 * MINUTE).toISOString(),
|
||||
collectingT,
|
||||
NOW,
|
||||
);
|
||||
formatDateOrRelative(
|
||||
new Date(NOW - 1 * HOUR).toISOString(),
|
||||
collectingT,
|
||||
NOW,
|
||||
);
|
||||
formatDateOrRelative(
|
||||
new Date(NOW - 12 * HOUR).toISOString(),
|
||||
collectingT,
|
||||
NOW,
|
||||
);
|
||||
expect(bundleKeysCalled.size).toBeGreaterThan(0);
|
||||
// `insights.*` carries a mix of string and nested-object children
|
||||
// (e.g. `personalRecord: { badge, tooltip }`), so the bundle type
|
||||
|
||||
@@ -75,10 +75,8 @@ vi.mock("node:fs", async () => {
|
||||
return false;
|
||||
};
|
||||
const readFileSync = (p: string) => {
|
||||
if (p.endsWith("GeoLite2-City.mmdb"))
|
||||
return Buffer.from("city-mmdb-stub");
|
||||
if (p.endsWith("GeoLite2-ASN.mmdb"))
|
||||
return Buffer.from("asn-mmdb-stub");
|
||||
if (p.endsWith("GeoLite2-City.mmdb")) return Buffer.from("city-mmdb-stub");
|
||||
if (p.endsWith("GeoLite2-ASN.mmdb")) return Buffer.from("asn-mmdb-stub");
|
||||
throw new Error(`unexpected read ${p}`);
|
||||
};
|
||||
return {
|
||||
@@ -219,7 +217,11 @@ describe("lookupIpLocation — offline-first city resolver (v1.4.27 B3)", () =>
|
||||
const fetchSpy = vi.fn().mockResolvedValue(
|
||||
new Response(
|
||||
new TextEncoder().encode(
|
||||
JSON.stringify({ success: true, city: "Hamburg", country_code: "DE" }),
|
||||
JSON.stringify({
|
||||
success: true,
|
||||
city: "Hamburg",
|
||||
country_code: "DE",
|
||||
}),
|
||||
).buffer as ArrayBuffer,
|
||||
{
|
||||
status: 200,
|
||||
|
||||
@@ -98,7 +98,10 @@ describe("offline-geo runtime detection (v1.4.27 R5)", () => {
|
||||
});
|
||||
|
||||
it("offlineGeoReady() is true when the City MMDB is present and no marker", async () => {
|
||||
writeFileSync(join(tmpRoot, "GeoLite2-City.mmdb"), Buffer.from("city-stub"));
|
||||
writeFileSync(
|
||||
join(tmpRoot, "GeoLite2-City.mmdb"),
|
||||
Buffer.from("city-stub"),
|
||||
);
|
||||
const { offlineGeoReady } = await import("../geo");
|
||||
expect(offlineGeoReady()).toBe(true);
|
||||
});
|
||||
@@ -130,7 +133,10 @@ describe("offline-geo runtime detection (v1.4.27 R5)", () => {
|
||||
});
|
||||
|
||||
it("does NOT fire the notification when the City MMDB is present", async () => {
|
||||
writeFileSync(join(tmpRoot, "GeoLite2-City.mmdb"), Buffer.from("city-stub"));
|
||||
writeFileSync(
|
||||
join(tmpRoot, "GeoLite2-City.mmdb"),
|
||||
Buffer.from("city-stub"),
|
||||
);
|
||||
// The stubbed reader returns null for every IP, which is fine — the
|
||||
// lookup will still go through the online path, but the offline
|
||||
// check sees a healthy directory so the notification stays silent.
|
||||
|
||||
@@ -107,16 +107,12 @@ describe("getClientIp trusted-proxy semantics (V3 audit)", () => {
|
||||
// pollute the rate-limit / audit log with non-IP strings; they are
|
||||
// now rejected at the helper.
|
||||
it("rejects structurally invalid IPv4 candidates (1.2)", () => {
|
||||
const ip = getClientIp(
|
||||
makeRequest({ "x-forwarded-for": "1.2, 5.6.7.8" }),
|
||||
);
|
||||
const ip = getClientIp(makeRequest({ "x-forwarded-for": "1.2, 5.6.7.8" }));
|
||||
expect(ip).toBe("5.6.7.8");
|
||||
});
|
||||
|
||||
it("rejects structurally invalid IPv6 candidates (:::)", () => {
|
||||
const ip = getClientIp(
|
||||
makeRequest({ "x-forwarded-for": ":::, 5.6.7.8" }),
|
||||
);
|
||||
const ip = getClientIp(makeRequest({ "x-forwarded-for": ":::, 5.6.7.8" }));
|
||||
expect(ip).toBe("5.6.7.8");
|
||||
});
|
||||
|
||||
@@ -129,9 +125,7 @@ describe("getClientIp trusted-proxy semantics (V3 audit)", () => {
|
||||
|
||||
it("accepts well-formed IPv6 addresses", () => {
|
||||
process.env.TRUST_PROXY_HOPS = "1";
|
||||
const ip = getClientIp(
|
||||
makeRequest({ "x-forwarded-for": "2001:db8::1" }),
|
||||
);
|
||||
const ip = getClientIp(makeRequest({ "x-forwarded-for": "2001:db8::1" }));
|
||||
expect(ip).toBe("2001:db8::1");
|
||||
});
|
||||
|
||||
@@ -294,12 +288,8 @@ describe("getClientIpOrTrustWarning shape (F-6, 2026-05-16)", () => {
|
||||
process.env.TRUST_PROXY_HOPS = "2";
|
||||
const warn = vi.spyOn(console, "warn").mockImplementation(() => {});
|
||||
try {
|
||||
getClientIpOrTrustWarning(
|
||||
makeRequest({ "x-forwarded-for": "5.6.7.8" }),
|
||||
);
|
||||
getClientIpOrTrustWarning(
|
||||
makeRequest({ "x-forwarded-for": "5.6.7.8" }),
|
||||
);
|
||||
getClientIpOrTrustWarning(makeRequest({ "x-forwarded-for": "5.6.7.8" }));
|
||||
getClientIpOrTrustWarning(makeRequest({ "x-forwarded-for": "5.6.7.8" }));
|
||||
expect(warn).toHaveBeenCalledTimes(1);
|
||||
} finally {
|
||||
warn.mockRestore();
|
||||
|
||||
@@ -189,7 +189,9 @@ describe("serializeInsightsLayout — defaults + dense order", () => {
|
||||
tiles: [{ id: "overview", visible: true, order: 0 }],
|
||||
});
|
||||
// Sorted by input order, then re-numbered 0,1,2.
|
||||
expect(serialized.sections.map((s) => ({ id: s.id, order: s.order }))).toEqual([
|
||||
expect(
|
||||
serialized.sections.map((s) => ({ id: s.id, order: s.order })),
|
||||
).toEqual([
|
||||
{ id: "trends", order: 0 },
|
||||
{ id: "vitals", order: 1 },
|
||||
{ id: "signals", order: 2 },
|
||||
@@ -333,7 +335,11 @@ describe("orderedVisibleSectionIds — W2 render-order helper", () => {
|
||||
const visible = orderedVisibleSectionIds(layout);
|
||||
// The three explicit sections lead in their saved order; the rest
|
||||
// auto-merge invisible (new-id semantics), so they do NOT appear.
|
||||
expect(visible.slice(0, 3)).toEqual(["trends", "vitals", "wellness-scores"]);
|
||||
expect(visible.slice(0, 3)).toEqual([
|
||||
"trends",
|
||||
"vitals",
|
||||
"wellness-scores",
|
||||
]);
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -33,7 +33,10 @@ describe("queryKeys factory", () => {
|
||||
});
|
||||
|
||||
it("threads the slim slice through queryKeys.analytics", () => {
|
||||
expect(queryKeys.analytics("summaries")).toEqual(["analytics", "summaries"]);
|
||||
expect(queryKeys.analytics("summaries")).toEqual([
|
||||
"analytics",
|
||||
"summaries",
|
||||
]);
|
||||
});
|
||||
|
||||
it("keeps the no-arg call byte-identical to the legacy literal", () => {
|
||||
@@ -238,7 +241,9 @@ describe("dependent-key bundles", () => {
|
||||
// (audit-L4).
|
||||
it("medicationDependentKeys bundles the dashboard-medication-compliance prefix (v1.4.40)", () => {
|
||||
const keyStrings = medicationDependentKeys.map((k) => JSON.stringify(k));
|
||||
expect(keyStrings).toContain(JSON.stringify(["dashboard-medication-compliance"]));
|
||||
expect(keyStrings).toContain(
|
||||
JSON.stringify(["dashboard-medication-compliance"]),
|
||||
);
|
||||
});
|
||||
|
||||
// v1.5.5 D-3 §10 invariant 20 — the per-medication inline compliance
|
||||
@@ -334,7 +339,8 @@ describe("queryKey factory enforcement", () => {
|
||||
}
|
||||
|
||||
it("no guarded file declares a bare-literal `queryKey:` (factory enforcement)", () => {
|
||||
const offenders: Array<{ file: string; line: number; snippet: string }> = [];
|
||||
const offenders: Array<{ file: string; line: number; snippet: string }> =
|
||||
[];
|
||||
const files = collect();
|
||||
for (const file of files) {
|
||||
const text = readFileSync(file, "utf8");
|
||||
|
||||
@@ -17,13 +17,22 @@ describe("reference-ranges backbone", () => {
|
||||
it("every band + conflict + headline resolves a real citation", () => {
|
||||
for (const metric of REFERENCE_METRICS) {
|
||||
const range = REFERENCE_RANGES[metric];
|
||||
expect(CITATIONS[range.referenceId], `${metric} referenceId`).toBeTruthy();
|
||||
expect(
|
||||
CITATIONS[range.referenceId],
|
||||
`${metric} referenceId`,
|
||||
).toBeTruthy();
|
||||
expect(range.unit, `${metric} unit`).toBeTruthy();
|
||||
expect(range.guidanceCaveat, `${metric} guidanceCaveat`).toBeTruthy();
|
||||
for (const band of range.bands) {
|
||||
expect(CITATIONS[band.citation], `${metric} band ${band.label}`).toBeTruthy();
|
||||
expect(
|
||||
CITATIONS[band.citation],
|
||||
`${metric} band ${band.label}`,
|
||||
).toBeTruthy();
|
||||
// A band must pin at least one bound.
|
||||
expect(band.low != null || band.high != null, `${metric} ${band.label}`).toBe(true);
|
||||
expect(
|
||||
band.low != null || band.high != null,
|
||||
`${metric} ${band.label}`,
|
||||
).toBe(true);
|
||||
}
|
||||
for (const conflict of range.conflicts ?? []) {
|
||||
expect(CITATIONS[conflict.citation], `${metric} conflict`).toBeTruthy();
|
||||
@@ -62,14 +71,18 @@ describe("reference-ranges backbone", () => {
|
||||
const marked = bands.filter((b) => b.normal === true);
|
||||
expect(marked, `${metric} normal-band count`).toHaveLength(1);
|
||||
// `normalBandIndex` points at that marked band.
|
||||
expect(bands[normalBandIndex(metric)].normal, `${metric} index`).toBe(true);
|
||||
expect(bands[normalBandIndex(metric)].normal, `${metric} index`).toBe(
|
||||
true,
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
it("resolves the normal band by marker, not by index 0", () => {
|
||||
// BMI authors Underweight FIRST; the normal band is the 18.5–24.9 entry.
|
||||
expect(REFERENCE_RANGES.BMI.bands[0].label).toBe("Underweight");
|
||||
expect(REFERENCE_RANGES.BMI.bands[normalBandIndex("BMI")].label).toBe("Normal");
|
||||
expect(REFERENCE_RANGES.BMI.bands[normalBandIndex("BMI")].label).toBe(
|
||||
"Normal",
|
||||
);
|
||||
// BMI 22 is healthy → within (the index-0 bug reported it slightly-outside).
|
||||
expect(classifyReference("BMI", 22)).toBe("within");
|
||||
// BMI 17 is underweight → one band below normal → slightly-outside
|
||||
@@ -93,10 +106,14 @@ describe("reference-ranges backbone", () => {
|
||||
|
||||
it("returns insufficient for absent values and band-less metrics", () => {
|
||||
expect(classifyReference("RESTING_HEART_RATE", null)).toBe("insufficient");
|
||||
expect(classifyReference("RESTING_HEART_RATE", Number.NaN)).toBe("insufficient");
|
||||
expect(classifyReference("RESTING_HEART_RATE", Number.NaN)).toBe(
|
||||
"insufficient",
|
||||
);
|
||||
// HRV carries no fixed population band — baseline-only.
|
||||
expect(REFERENCE_RANGES.HEART_RATE_VARIABILITY.bands).toHaveLength(0);
|
||||
expect(classifyReference("HEART_RATE_VARIABILITY", 42)).toBe("insufficient");
|
||||
expect(classifyReference("HEART_RATE_VARIABILITY", 42)).toBe(
|
||||
"insufficient",
|
||||
);
|
||||
});
|
||||
|
||||
it("steps backbone uses the canonical 8,000 green floor", () => {
|
||||
|
||||
@@ -67,18 +67,16 @@ describe("pinnedPublicDispatcher", () => {
|
||||
it("refuses a hostname that resolves to a private IP", async () => {
|
||||
// Mock dns.lookup to return 169.254.169.254 (cloud metadata).
|
||||
const lookupSpy = vi.spyOn(dns, "lookup");
|
||||
lookupSpy.mockImplementation(
|
||||
((
|
||||
_hostname: string,
|
||||
_opts: dns.LookupAllOptions,
|
||||
callback: (
|
||||
err: NodeJS.ErrnoException | null,
|
||||
addresses: dns.LookupAddress[],
|
||||
) => void,
|
||||
) => {
|
||||
callback(null, [{ address: "169.254.169.254", family: 4 }]);
|
||||
}) as unknown as typeof dns.lookup,
|
||||
);
|
||||
lookupSpy.mockImplementation(((
|
||||
_hostname: string,
|
||||
_opts: dns.LookupAllOptions,
|
||||
callback: (
|
||||
err: NodeJS.ErrnoException | null,
|
||||
addresses: dns.LookupAddress[],
|
||||
) => void,
|
||||
) => {
|
||||
callback(null, [{ address: "169.254.169.254", family: 4 }]);
|
||||
}) as unknown as typeof dns.lookup);
|
||||
|
||||
const dispatcher = getPinnedPublicDispatcher();
|
||||
// Drive the dispatcher through `fetch` so the integration mirrors
|
||||
@@ -100,18 +98,16 @@ describe("pinnedPublicDispatcher", () => {
|
||||
// The expected outcome is therefore NOT ENOTFOUND but a connect
|
||||
// failure further down the stack (the IP refuses or times out).
|
||||
const lookupSpy = vi.spyOn(dns, "lookup");
|
||||
lookupSpy.mockImplementation(
|
||||
((
|
||||
_hostname: string,
|
||||
_opts: dns.LookupAllOptions,
|
||||
callback: (
|
||||
err: NodeJS.ErrnoException | null,
|
||||
addresses: dns.LookupAddress[],
|
||||
) => void,
|
||||
) => {
|
||||
callback(null, [{ address: "192.0.2.1", family: 4 }]);
|
||||
}) as unknown as typeof dns.lookup,
|
||||
);
|
||||
lookupSpy.mockImplementation(((
|
||||
_hostname: string,
|
||||
_opts: dns.LookupAllOptions,
|
||||
callback: (
|
||||
err: NodeJS.ErrnoException | null,
|
||||
addresses: dns.LookupAddress[],
|
||||
) => void,
|
||||
) => {
|
||||
callback(null, [{ address: "192.0.2.1", family: 4 }]);
|
||||
}) as unknown as typeof dns.lookup);
|
||||
|
||||
const dispatcher = getPinnedPublicDispatcher();
|
||||
let caught: unknown;
|
||||
@@ -135,21 +131,19 @@ describe("pinnedPublicDispatcher", () => {
|
||||
// Mock dns.lookup to return one private + one public address. The
|
||||
// dispatcher must drop the private one and pin to the public one.
|
||||
const lookupSpy = vi.spyOn(dns, "lookup");
|
||||
lookupSpy.mockImplementation(
|
||||
((
|
||||
_hostname: string,
|
||||
_opts: dns.LookupAllOptions,
|
||||
callback: (
|
||||
err: NodeJS.ErrnoException | null,
|
||||
addresses: dns.LookupAddress[],
|
||||
) => void,
|
||||
) => {
|
||||
callback(null, [
|
||||
{ address: "10.0.0.5", family: 4 },
|
||||
{ address: "192.0.2.1", family: 4 },
|
||||
]);
|
||||
}) as unknown as typeof dns.lookup,
|
||||
);
|
||||
lookupSpy.mockImplementation(((
|
||||
_hostname: string,
|
||||
_opts: dns.LookupAllOptions,
|
||||
callback: (
|
||||
err: NodeJS.ErrnoException | null,
|
||||
addresses: dns.LookupAddress[],
|
||||
) => void,
|
||||
) => {
|
||||
callback(null, [
|
||||
{ address: "10.0.0.5", family: 4 },
|
||||
{ address: "192.0.2.1", family: 4 },
|
||||
]);
|
||||
}) as unknown as typeof dns.lookup);
|
||||
|
||||
const dispatcher = getPinnedPublicDispatcher();
|
||||
let caught: unknown;
|
||||
|
||||
Reference in new issue
Block a user