Files
HealthLog/src/lib/analytics/__tests__/effective-range.test.ts
T
Marc-André BombeckandClaude Opus 4.7 02b99553b9 chore(style): repo-wide prettier sweep before v1.4.6 tag
Long-overdue prettier sweep; prettier had drifted vs. checked-in code
across ~130 files (mostly long-argument line-break wrapping in TS and
table-padding in markdown). Pure formatting — no semantic changes —
and required to clear the v1.4.6 release gate's `pnpm format:check`.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-09 02:27:17 +02:00

204 lines
7.0 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { describe, it, expect } from "vitest";
import {
getEffectiveRange,
getAllEffectiveRanges,
METRIC_BOUNDS,
type UserProfileForRange,
type ThresholdOverridesJson,
} from "../effective-range";
const baseProfile: UserProfileForRange = {
heightCm: 180,
dateOfBirth: new Date("1985-01-01"),
gender: "MALE",
};
describe("getEffectiveRange", () => {
it("returns computed default when no override is set", () => {
const result = getEffectiveRange("WEIGHT", baseProfile, null);
expect(result.isOverride).toBe(false);
expect(result.range).not.toBeNull();
// BMI 18.5..24.9 at 1.80m ≈ 59.94..80.68
expect(result.range!.greenMin).toBeCloseTo(59.94, 1);
expect(result.range!.greenMax).toBeCloseTo(80.68, 1);
});
it("returns null range when a prerequisite profile field is missing", () => {
const result = getEffectiveRange(
"WEIGHT",
{ heightCm: null, dateOfBirth: null, gender: null },
null,
);
expect(result.range).toBeNull();
expect(result.default).toBeNull();
});
it("uses override when present", () => {
const overrides: ThresholdOverridesJson = {
WEIGHT: { min: 70, max: 85 },
};
const result = getEffectiveRange("WEIGHT", baseProfile, overrides);
expect(result.isOverride).toBe(true);
expect(result.range!.greenMin).toBe(70);
expect(result.range!.greenMax).toBe(85);
// Orange wings should be non-degenerate
expect(result.range!.orangeMin).toBeLessThan(70);
expect(result.range!.orangeMax).toBeGreaterThan(85);
});
it("returns the pristine default alongside the override", () => {
const overrides: ThresholdOverridesJson = {
WEIGHT: { min: 70, max: 85 },
};
const result = getEffectiveRange("WEIGHT", baseProfile, overrides);
expect(result.default).not.toBeNull();
expect(result.default!.greenMin).toBeCloseTo(59.94, 1);
});
it("has bounds for every supported metric", () => {
for (const metric of Object.keys(METRIC_BOUNDS) as Array<
keyof typeof METRIC_BOUNDS
>) {
const result = getEffectiveRange(metric, baseProfile, null);
expect(result.bounds).toEqual(METRIC_BOUNDS[metric]);
}
});
it("has sensible blood glucose defaults in fasting context", () => {
const result = getEffectiveRange(
"BLOOD_GLUCOSE_FASTING",
baseProfile,
null,
);
expect(result.range!.greenMin).toBe(70);
expect(result.range!.greenMax).toBe(99);
expect(result.range!.orangeMax).toBe(125); // pre-diabetes upper
});
it("has different defaults for postprandial vs fasting", () => {
const fasting = getEffectiveRange(
"BLOOD_GLUCOSE_FASTING",
baseProfile,
null,
);
const post = getEffectiveRange(
"BLOOD_GLUCOSE_POSTPRANDIAL",
baseProfile,
null,
);
expect(post.range!.greenMax).toBeGreaterThan(fasting.range!.greenMax);
});
});
describe("getAllEffectiveRanges", () => {
it("returns an entry for every metric", () => {
const ranges = getAllEffectiveRanges(baseProfile, null);
const keys = Object.keys(ranges);
expect(keys).toContain("WEIGHT");
expect(keys).toContain("BLOOD_GLUCOSE_FASTING");
expect(keys).toContain("TOTAL_BODY_WATER");
expect(keys).toContain("BONE_MASS");
expect(keys).toContain("OXYGEN_SATURATION");
expect(keys.length).toBeGreaterThanOrEqual(14);
});
});
// Audit-2026-05-07 / phase P0 / closes audit C-15: TOTAL_BODY_WATER and
// BONE_MASS lacked threshold definitions. Severity logic returned `nominal`
// for any value, so users would see "all healthy" regardless of input.
describe("body composition thresholds", () => {
it("TOTAL_BODY_WATER has a sensible non-null green band", () => {
const result = getEffectiveRange("TOTAL_BODY_WATER", baseProfile, null);
expect(result.range).not.toBeNull();
expect(result.range!.greenMin).toBeGreaterThan(0);
expect(result.range!.greenMax).toBeGreaterThan(result.range!.greenMin);
expect(result.range!.orangeMin).toBeLessThan(result.range!.greenMin);
expect(result.range!.orangeMax).toBeGreaterThan(result.range!.greenMax);
});
it("BONE_MASS has a sensible non-null green band", () => {
const result = getEffectiveRange("BONE_MASS", baseProfile, null);
expect(result.range).not.toBeNull();
expect(result.range!.greenMin).toBeGreaterThan(0);
expect(result.range!.greenMax).toBeGreaterThan(result.range!.greenMin);
});
it("respects user override for body water", () => {
const overrides: ThresholdOverridesJson = {
TOTAL_BODY_WATER: { min: 30, max: 45 },
};
const result = getEffectiveRange(
"TOTAL_BODY_WATER",
baseProfile,
overrides,
);
expect(result.isOverride).toBe(true);
expect(result.range!.greenMin).toBe(30);
expect(result.range!.greenMax).toBe(45);
});
it("METRIC_BOUNDS for body composition match VALUE_RANGES in validation", () => {
expect(METRIC_BOUNDS.TOTAL_BODY_WATER).toEqual({
min: 5,
max: 100,
unit: "kg",
});
expect(METRIC_BOUNDS.BONE_MASS).toEqual({ min: 0.5, max: 8, unit: "kg" });
});
});
// Audit-2026-05-07 / v1.3.3: SpO2 (pulse oximetry) added as a single-value
// metric with lower-only severity (saturation cannot exceed 100% by definition).
// Defaults follow BTS Guideline 2017 (target 94–98%) and ATS clinical practice
// (≥95% at rest is healthy). Below 92% triggers orange band; below 88% in
// real-world clinical literature is the ER threshold.
describe("OXYGEN_SATURATION thresholds", () => {
it("has a non-null green band centred on the BTS healthy range", () => {
const result = getEffectiveRange("OXYGEN_SATURATION", baseProfile, null);
expect(result.range).not.toBeNull();
expect(result.range!.greenMin).toBe(95);
expect(result.range!.greenMax).toBe(100);
});
it("collapses upper orange wing to greenMax (no upper concern)", () => {
const result = getEffectiveRange("OXYGEN_SATURATION", baseProfile, null);
expect(result.range!.orangeMax).toBe(result.range!.greenMax);
});
it("respects user override (e.g. COPD baseline 88-92)", () => {
const overrides: ThresholdOverridesJson = {
OXYGEN_SATURATION: { min: 88, max: 92 },
};
const result = getEffectiveRange(
"OXYGEN_SATURATION",
baseProfile,
overrides,
);
expect(result.isOverride).toBe(true);
expect(result.range!.greenMin).toBe(88);
expect(result.range!.greenMax).toBe(92);
});
it("clamps override orangeMax to physiological 100% (no impossible saturations)", () => {
// Without the bounds clamp this used to emit orangeMax = 100.75.
const overrides: ThresholdOverridesJson = {
OXYGEN_SATURATION: { min: 95, max: 100 },
};
const result = getEffectiveRange(
"OXYGEN_SATURATION",
baseProfile,
overrides,
);
expect(result.range!.orangeMax).toBeLessThanOrEqual(100);
expect(result.range!.orangeMin).toBeGreaterThanOrEqual(50);
});
it("METRIC_BOUNDS plausibility floor is 50% (incompatible-with-life below)", () => {
expect(METRIC_BOUNDS.OXYGEN_SATURATION).toEqual({
min: 50,
max: 100,
unit: "%",
});
});
});