fix(rectification): share decideFromDossier across projections and treat a sole candidate as a close, not a tie
Independent Staging Quality Gate / validate (push) Successful in 11m43s
Independent Staging Quality Gate / publish (push) Successful in 40m51s

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
Jesse_Chen
2026-08-28 19:21:28 +08:00
co-authored by Cursor
parent 30d8c78d19
commit 69c3e94920
10 changed files with 271 additions and 300 deletions
@@ -14,6 +14,7 @@ import {
} from "../src/lib/rectification-agentic/v9/varga-observations.ts";
import { WINDOW_SCAN_DISPLAY_LAYER_ORDER } from "../src/lib/rectification-agentic/v9/refinement-packet.ts";
import { RECTIFICATION_SKILL_VERSION } from "../src/lib/rectification-agentic/v9/case-status.ts";
import { decideRectification } from "../src/lib/rectification-agentic/core/rectification-decision.ts";
import { readVedastroMinuteSensitiveStatus } from "../src/lib/rectification-agentic/v9/confirmation-gate.ts";
import { authoritativeCandidateProjection } from "../src/lib/rectification-agentic/v9/inference-adapter.ts";
import { createRectificationV9Tools, latestResultToolProjection } from "../src/mastra/rectification-v9-tools.ts";
@@ -49,6 +50,14 @@ const FAMILY_ID = "44444444-4444-4444-8444-444444444443";
const CAREER_ID = "44444444-4444-4444-8444-444444444444";
const UNIQUE_MINUTE_COPY = /±5 分钟确定性/;
function collectDecision(candidates: readonly { time: string; relativeSupport?: number }[]) {
return decideRectification({
methodCoverageAll: false,
trainingGateOpen: false,
candidateScores: candidates.map((item) => ({ time: item.time, score: item.relativeSupport ?? 0 })),
});
}
const DYNAMIC_STYLE_OPTIONS = [
{ label: "明确发生且时间吻合", answer_class: "yes" as const },
{ label: "发生过但程度较弱", answer_class: "weak_yes" as const },
@@ -864,7 +873,7 @@ test("read-case follows method plan and keeps D9/D10 type tables when SQL missin
confirmation_allowed: boolean;
indistinguishable_width_minutes: number;
window_scan: { d9_candidates_differ: boolean } | null;
session_outcome: { kind: string };
session_outcome: string;
};
}>;
}).execute({ caseId: CASE_ID, projection: "full_diagnostics" });
@@ -881,7 +890,7 @@ test("read-case follows method plan and keeps D9/D10 type tables when SQL missin
(projection as { next_user_action?: { on_user_stop?: { id?: string } } }).next_user_action?.on_user_stop?.id,
"offer_provisional_range",
);
assert.equal(projection.latest_result.session_outcome.kind, "collect_evidence");
assert.equal(projection.latest_result.session_outcome, "collect_evidence");
assert.equal(projection.internal_observations.find((item) => item.layer === "d9")?.ask_theme, "relationship_style");
assert.equal(projection.latest_result.confirmation_allowed, false);
assert.ok(projection.latest_result.indistinguishable_width_minutes >= 25);
@@ -1316,26 +1325,27 @@ test("public tool surface stays at 14 and new cases bind 10.0.13", () => {
"8d7aa2d4bea0414e9a89ef908ccbc8c708c98f79f5b78ae4f7dc229b5f7dbb30",
);
assert.equal(deprecated.status, "deprecated");
const plateau = latestResultToolProjection({
resultId: RESULT_ID,
candidates: [
const plateauCandidates = [
{ candidateId: CANDIDATE_ID, time: "04:45", rank: 1, relativeSupport: 40, tiedMinuteCount: 25 },
{ candidateId: SECOND_CANDIDATE_ID, time: "04:46", rank: 2, relativeSupport: 35, tiedMinuteCount: 25 },
{ candidateId: THIRD_CANDIDATE_ID, time: "04:47", rank: 3, relativeSupport: 25, tiedMinuteCount: 25 },
],
];
const plateau = latestResultToolProjection({
resultId: RESULT_ID,
candidates: plateauCandidates,
selectionAllowed: true,
confirmationAllowed: true,
representativeTime: "04:45",
selectedTime: null,
selectionKind: null,
algorithmVersion: "rectification-v5",
});
}, collectDecision(plateauCandidates));
assert.equal(plateau.confirmation_allowed, false);
assert.equal(plateau.unique_minute_claim, false);
assert.match(String(plateau.skill_verification_report), /Dasha \+ Gochara/);
assert.match(String(plateau.skill_verification_report), /candidate_range_not_birth_time_truth/);
assert.doesNotMatch(String(plateau.skill_verification_report), UNIQUE_MINUTE_COPY);
assert.equal((plateau.session_outcome as { kind: string }).kind, "collect_evidence");
assert.equal(plateau.session_outcome, "collect_evidence");
const skill = readFileSync(new URL("../../skills/jyotish-birth-time-rectification/SKILL.md", import.meta.url), "utf8");
assert.match(skill, /method_followup_plan/);
assert.match(skill, /感情 → 事业 → 家人 → 职业 → 占问/);
@@ -1383,14 +1393,14 @@ test("Mastra hides active candidates when the receipt range excludes one of them
algorithmVersion: "rectification-v5",
decisionReceipt: { inference_state: inferenceState },
};
const session = {
methods: buildMethodFollowupPlan({ evidence: CLASSIC_COVERAGE }).methods,
const session = decideRectification({
methodCoverageAll: true,
userStopped: true,
candidateScores: candidates.map((item) => ({ time: item.time, score: item.relativeSupport })),
holdoutValidation: "passed" as const,
holdoutValidation: "passed",
snapshotCurrent: true,
trainingGateOpen: true,
};
});
const valid = latestResultToolProjection(latest, session);
assert.deepEqual((valid.candidates as typeof candidates).map((item) => item.time), ["05:00", "05:07"]);
assert.equal(valid.selection_allowed, true);
@@ -2836,9 +2846,9 @@ test("paused case with selection_allowed may offer the escape hatch", async () =
accounting: accounting.client as never,
});
const projection = await (tools["rectification-offer-candidates"] as unknown as {
execute(input: unknown): Promise<{ session_outcome: { kind: string } }>;
execute(input: unknown): Promise<{ session_outcome: string }>;
}).execute({ caseId: CASE_ID });
assert.equal(projection.session_outcome.kind, "provisional_range_user_stopped");
assert.equal(projection.session_outcome, "provisional_range_user_stopped");
assert.equal(
accounting.calls.some((call) =>
call.fn === "transition_agentic_rectification_case_status"
@@ -2949,9 +2959,9 @@ test("offer-candidates allows a 34/33/33 tie after method coverage when remainin
accounting: accounting.client as never,
});
const projection = await (tools["rectification-offer-candidates"] as unknown as {
execute(input: unknown): Promise<{ session_outcome: { kind: string } }>;
execute(input: unknown): Promise<{ session_outcome: string }>;
}).execute({ caseId: CASE_ID });
assert.equal(projection.session_outcome.kind, "provisional_range");
assert.equal(projection.session_outcome, "provisional_range");
assert.equal(
accounting.calls.some((call) =>
call.fn === "transition_agentic_rectification_case_status"