feat(lab): separate RAVNOVES transfer from public benchmark

This commit is contained in:
DCCONSTRUCTIONS
2026-07-31 14:35:51 +03:00
parent 55b7821a5c
commit c1b0f6f8a3
15 changed files with 1018 additions and 61 deletions
@@ -14,9 +14,11 @@ import { fetchE34TemporalLayerResult } from "./e34TemporalLayer";
import { fetchE35DegradationRecoveryResult } from "./e35DegradationRecovery";
import { fetchE40ProductGateResult } from "./e40ProductGate";
import { fetchL3PointPillarsVisualAudit } from "./l3PointPillarsVisualAudit";
import { fetchL31PointPillarsRavnoves } from "./l31PointPillarsRavnoves";
export type AdvancedLaboratoryWorkId =
| "l3-pointpillars-visual-audit"
| "l31-pointpillars-ravnoves"
| "e31-source-binding"
| "e32-track-geometry"
| "e33-worker-shadow"
@@ -35,6 +37,7 @@ export interface AdvancedLaboratoryIndexItem {
const WORK_IDS: readonly AdvancedLaboratoryWorkId[] = [
"l3-pointpillars-visual-audit",
"l31-pointpillars-ravnoves",
"e31-source-binding",
"e32-track-geometry",
"e33-worker-shadow",
@@ -48,6 +51,7 @@ const WORK_IDS: readonly AdvancedLaboratoryWorkId[] = [
const RESULT_PREFIX: Readonly<Record<AdvancedLaboratoryWorkId, string>> = {
"l3-pointpillars-visual-audit": "l3-pointpillars-visual-audit",
"l31-pointpillars-ravnoves": "l31-pointpillars-ravnoves",
"e31-source-binding": "e31-source-qualification",
"e32-track-geometry": "e32-track-geometry",
"e33-worker-shadow": "e33-worker-shadow",
@@ -68,6 +72,7 @@ export function isAdvancedLaboratoryWorkId(
export function emptyAdvancedLaboratoryResults(): AdvancedLaboratoryResults {
return {
l3: null,
l31: null,
e31: null,
e32: null,
e33: null,
@@ -169,6 +174,7 @@ export function advancedLaboratoryResultAvailable(
results: AdvancedLaboratoryResults,
): boolean {
return workId === "l3-pointpillars-visual-audit" ? results.l3 !== null
: workId === "l31-pointpillars-ravnoves" ? results.l31 !== null
: workId === "e31-source-binding" ? results.e31 !== null
: workId === "e32-track-geometry" ? results.e32 !== null
: workId === "e33-worker-shadow" ? results.e33 !== null
@@ -193,6 +199,8 @@ export async function fetchAdvancedLaboratoryResult(
const results = emptyAdvancedLaboratoryResults();
if (workId === "l3-pointpillars-visual-audit") {
results.l3 = await fetchL3PointPillarsVisualAudit({ fetcher, signal });
} else if (workId === "l31-pointpillars-ravnoves") {
results.l31 = await fetchL31PointPillarsRavnoves({ fetcher, signal });
} else if (workId === "e31-source-binding") {
results.e31 = await fetchOne(
"/api/v1/laboratory/e31/results?limit=1",
@@ -0,0 +1,27 @@
import type {
E31LaboratoryResult,
E32LaboratoryResult,
E33LaboratoryResult,
E37AcceptanceContractResult,
E38PerceptionBaselineResult,
E39PerceptionRefinementResult,
} from "./advancedResults";
import type { E34TemporalLayerResult } from "./e34TemporalLayer";
import type { E35DegradationRecoveryResult } from "./e35DegradationRecovery";
import type { E40PerceptionProductGateResult } from "./e40ProductGate";
import type { L3PointPillarsVisualAuditResult } from "./l3PointPillarsVisualAudit";
import type { L31PointPillarsRavnovesResult } from "./l31PointPillarsRavnoves";
export interface AdvancedLaboratoryResults {
l3: L3PointPillarsVisualAuditResult | null;
l31: L31PointPillarsRavnovesResult | null;
e31: E31LaboratoryResult | null;
e32: E32LaboratoryResult | null;
e33: E33LaboratoryResult | null;
e34: E34TemporalLayerResult | null;
e35: E35DegradationRecoveryResult | null;
e37: E37AcceptanceContractResult | null;
e38: E38PerceptionBaselineResult | null;
e39: E39PerceptionRefinementResult | null;
e40: E40PerceptionProductGateResult | null;
}
@@ -1,17 +1,15 @@
import {
fetchE34TemporalLayerResult,
type E34TemporalLayerResult,
} from "./e34TemporalLayer";
import {
fetchE35DegradationRecoveryResult,
type E35DegradationRecoveryResult,
} from "./e35DegradationRecovery";
import {
fetchE40ProductGateResult,
type E40PerceptionProductGateResult,
} from "./e40ProductGate";
import { settledCatalogValue } from "./catalogTransport";
import type { L3PointPillarsVisualAuditResult } from "./l3PointPillarsVisualAudit";
import type { AdvancedLaboratoryResults } from "./advancedLaboratoryResults";
export type { AdvancedLaboratoryResults } from "./advancedLaboratoryResults";
export interface E31LaboratoryResult {
resultId: string;
@@ -238,19 +236,6 @@ export interface E39PerceptionRefinementResult {
access: "read-only";
}
export interface AdvancedLaboratoryResults {
l3: L3PointPillarsVisualAuditResult | null;
e31: E31LaboratoryResult | null;
e32: E32LaboratoryResult | null;
e33: E33LaboratoryResult | null;
e34: E34TemporalLayerResult | null;
e35: E35DegradationRecoveryResult | null;
e37: E37AcceptanceContractResult | null;
e38: E38PerceptionBaselineResult | null;
e39: E39PerceptionRefinementResult | null;
e40: E40PerceptionProductGateResult | null;
}
export class AdvancedLaboratoryContractError extends Error {
constructor(message: string) {
super(message);
@@ -990,5 +975,17 @@ export async function fetchAdvancedLaboratoryResults({
const e38 = settledCatalogValue(settled[6]);
const e39 = settledCatalogValue(settled[7]);
const e40 = settledCatalogValue(settled[8]);
return { l3: null, e31, e32, e33, e34, e35, e37, e38, e39, e40 };
return {
l3: null,
l31: null,
e31,
e32,
e33,
e34,
e35,
e37,
e38,
e39,
e40,
};
}
@@ -0,0 +1,475 @@
import {
AdvancedLaboratoryContractError,
type LaboratoryFetch,
} from "./advancedResults";
import type { L3VisualBox } from "./l3PointPillarsVisualAudit";
export interface L31ClassCounts {
Vehicle: number;
Pedestrian: number;
Cyclist: number;
}
export interface L31VisualFrameSummary {
frameId: string;
frameIndex: number;
sessionSeconds: number;
sourcePointCount: number;
predictionCount: number;
classCounts: L31ClassCounts;
inferenceMs: number;
}
export interface L31PointPillarsRavnovesResult {
resultId: string;
createdAtUtc: string;
status: "cross-domain-transfer-measured-visual-review-required";
sourceSessionId: string;
sourcePackId: string;
sourceLogicalContentSha256: string;
model: {
name: "pointpillars";
sourceModelSha256: string;
engineSha256: string;
embeddedScoreThreshold: number;
};
execution: {
workerHostId: "worker-006";
sequential: true;
parallelWorkers: 1;
sourcePaced: false;
existingTritonOnly: true;
};
metrics: {
frameCount: number;
inputAdmissionFraction: number;
outputSchemaValidFraction: number;
framesWithPredictions: number;
framesWithVehiclePredictions: number;
predictionCount: number;
classCounts: L31ClassCounts;
inferenceLatencyMs: { p50: number; p95: number; maximum: number };
poseBindingAgeMs: { p50: number; p95: number; maximum: number };
deterministicReplayFraction: number;
deterministicReplayFrames: number;
};
frames: readonly L31VisualFrameSummary[];
limitations: readonly string[];
}
export interface L31VisualFrame {
frameId: string;
summary: L31VisualFrameSummary & {
deterministicReplay: boolean;
replayInferenceMs: number;
visualBoxCount: number;
visualBoxTruncated: boolean;
};
sourcePointCount: number;
modelRangePointCount: number;
sampledPointCount: number;
pointsXyzi: readonly number[];
truthBoxes: readonly L3VisualBox[];
predictionBoxes: readonly L3VisualBox[];
}
const RESULT_ID = /^l31-pointpillars-ravnoves-[a-f0-9]{64}$/;
const PACK_ID = /^lidar-replay-pack-[a-f0-9]{64}$/;
const SHA256 = /^[a-f0-9]{64}$/;
const FRAME_ID = /^[0-9]{6}$/;
function record(value: unknown, label: string): Record<string, unknown> {
if (!value || typeof value !== "object" || Array.isArray(value)) {
throw new AdvancedLaboratoryContractError(`${label}: ожидался объект.`);
}
return value as Record<string, unknown>;
}
function array(value: unknown, label: string): readonly unknown[] {
if (!Array.isArray(value)) {
throw new AdvancedLaboratoryContractError(`${label}: ожидался массив.`);
}
return value;
}
function string(value: unknown, label: string): string {
if (typeof value !== "string" || !value.trim()) {
throw new AdvancedLaboratoryContractError(`${label}: ожидалась строка.`);
}
return value;
}
function exact<T extends string>(value: unknown, expected: T, label: string): T {
if (value !== expected) {
throw new AdvancedLaboratoryContractError(`${label}: нарушен контракт.`);
}
return expected;
}
function number(value: unknown, label: string, minimum = 0): number {
if (
typeof value !== "number"
|| !Number.isFinite(value)
|| value < minimum
) {
throw new AdvancedLaboratoryContractError(`${label}: неверное число.`);
}
return value;
}
function integer(value: unknown, label: string): number {
const parsed = number(value, label);
if (!Number.isInteger(parsed)) {
throw new AdvancedLaboratoryContractError(`${label}: ожидалось целое.`);
}
return parsed;
}
function boolean(value: unknown, label: string): boolean {
if (typeof value !== "boolean") {
throw new AdvancedLaboratoryContractError(`${label}: ожидался boolean.`);
}
return value;
}
function exactBoolean(
value: unknown,
expected: boolean,
label: string,
): boolean {
const parsed = boolean(value, label);
if (parsed !== expected) {
throw new AdvancedLaboratoryContractError(`${label}: нарушен контракт.`);
}
return parsed;
}
function classCounts(value: unknown, label: string): L31ClassCounts {
const counts = record(value, label);
if (
Object.keys(counts).sort().join(",") !== "Cyclist,Pedestrian,Vehicle"
) {
throw new AdvancedLaboratoryContractError(`${label}: классы изменились.`);
}
return {
Vehicle: integer(counts.Vehicle, `${label}.Vehicle`),
Pedestrian: integer(counts.Pedestrian, `${label}.Pedestrian`),
Cyclist: integer(counts.Cyclist, `${label}.Cyclist`),
};
}
function distribution(
value: unknown,
label: string,
): { p50: number; p95: number; maximum: number } {
const item = record(value, label);
return {
p50: number(item.p50, `${label}.p50`),
p95: number(item.p95, `${label}.p95`),
maximum: number(item.maximum, `${label}.maximum`),
};
}
function parseSummary(value: unknown): L31VisualFrameSummary {
const item = record(value, "L3.1 frame");
const frameId = string(item.frame_id, "L3.1 frame_id");
if (!FRAME_ID.test(frameId)) {
throw new AdvancedLaboratoryContractError("L3.1 frame_id: неверный формат.");
}
return {
frameId,
frameIndex: integer(item.frame_index, "L3.1 frame_index"),
sessionSeconds: number(item.session_seconds, "L3.1 session_seconds"),
sourcePointCount: integer(
item.source_point_count,
"L3.1 source_point_count",
),
predictionCount: integer(
item.prediction_count,
"L3.1 prediction_count",
),
classCounts: classCounts(item.class_counts, "L3.1 class_counts"),
inferenceMs: number(
item.inference_ms,
"L3.1 inference_ms",
Number.MIN_VALUE,
),
};
}
function parseResult(value: unknown): L31PointPillarsRavnovesResult {
const item = record(value, "L3.1 result");
exact(
item.schema_version,
"missioncore.l31-pointpillars-ravnoves-result/v1",
"L3.1 schema_version",
);
exact(item.access, "read-only", "L3.1 access");
const resultId = string(item.result_id, "L3.1 result_id");
const sourcePackId = string(item.source_pack_id, "L3.1 source_pack_id");
const logicalSha = string(
item.source_logical_content_sha256,
"L3.1 logical content",
);
if (
!RESULT_ID.test(resultId)
|| !PACK_ID.test(sourcePackId)
|| !SHA256.test(logicalSha)
) {
throw new AdvancedLaboratoryContractError(
"L3.1: нарушена идентичность результата.",
);
}
const model = record(item.model, "L3.1 model");
const execution = record(item.execution, "L3.1 execution");
const metrics = record(item.metrics, "L3.1 metrics");
const frames = array(item.frames, "L3.1 frames").map(parseSummary);
if (
!frames.length
|| frames.length > 18
|| new Set(frames.map(({ frameId }) => frameId)).size !== frames.length
) {
throw new AdvancedLaboratoryContractError("L3.1 frames: неверный каталог.");
}
return {
resultId,
createdAtUtc: string(item.created_at_utc, "L3.1 created_at_utc"),
status: exact(
item.status,
"cross-domain-transfer-measured-visual-review-required",
"L3.1 status",
),
sourceSessionId: exact(
item.source_session_id,
"20260720T065719Z_viewer_live",
"L3.1 source_session_id",
),
sourcePackId,
sourceLogicalContentSha256: logicalSha,
model: {
name: exact(model.name, "pointpillars", "L3.1 model.name"),
sourceModelSha256: string(
model.source_model_sha256,
"L3.1 model sha",
),
engineSha256: string(model.engine_sha256, "L3.1 engine sha"),
embeddedScoreThreshold: number(
model.embedded_score_threshold,
"L3.1 score threshold",
),
},
execution: {
workerHostId: exact(
execution.worker_host_id,
"worker-006",
"L3.1 worker",
),
sequential: exactBoolean(
execution.sequential,
true,
"L3.1 sequential",
) as true,
parallelWorkers: (
integer(execution.parallel_workers, "L3.1 parallel workers") === 1
? 1
: (() => {
throw new AdvancedLaboratoryContractError(
"L3.1 parallel workers: нарушен контракт.",
);
})()
),
sourcePaced: exactBoolean(
execution.source_paced,
false,
"L3.1 source paced",
) as false,
existingTritonOnly: exactBoolean(
execution.existing_triton_only,
true,
"L3.1 Triton",
) as true,
},
metrics: {
frameCount: integer(metrics.frame_count, "L3.1 frame count"),
inputAdmissionFraction: number(
metrics.input_admission_fraction,
"L3.1 admission",
),
outputSchemaValidFraction: number(
metrics.output_schema_valid_fraction,
"L3.1 schema valid",
),
framesWithPredictions: integer(
metrics.frames_with_predictions,
"L3.1 frames with predictions",
),
framesWithVehiclePredictions: integer(
metrics.frames_with_vehicle_predictions,
"L3.1 frames with vehicles",
),
predictionCount: integer(
metrics.prediction_count,
"L3.1 predictions",
),
classCounts: classCounts(metrics.class_counts, "L3.1 metric classes"),
inferenceLatencyMs: distribution(
metrics.inference_latency_ms,
"L3.1 latency",
),
poseBindingAgeMs: distribution(
metrics.pose_binding_age_ms,
"L3.1 pose age",
),
deterministicReplayFraction: number(
metrics.deterministic_replay_fraction,
"L3.1 determinism",
),
deterministicReplayFrames: integer(
metrics.deterministic_replay_frames,
"L3.1 determinism frames",
),
},
frames,
limitations: array(item.limitations, "L3.1 limitations").map(
(entry) => string(entry, "L3.1 limitation"),
),
};
}
function parseBox(value: unknown): L3VisualBox {
const box = record(value, "L3.1 box");
const center = [
number(box.x_m, "L3.1 box.x", -Infinity),
number(box.y_m, "L3.1 box.y", -Infinity),
number(box.z_m, "L3.1 box.z", -Infinity),
] as const;
const size = [
number(box.length_m, "L3.1 box.length", Number.MIN_VALUE),
number(box.width_m, "L3.1 box.width", Number.MIN_VALUE),
number(box.height_m, "L3.1 box.height", Number.MIN_VALUE),
] as const;
const modelClass = string(box.model_class, "L3.1 box.class");
if (!["Vehicle", "Pedestrian", "Cyclist"].includes(modelClass)) {
throw new AdvancedLaboratoryContractError("L3.1 box.class: неизвестен.");
}
return {
benchmarkClass: modelClass,
centerXyzM: center,
sizeLwhM: size,
yawRad: number(box.yaw_rad, "L3.1 box.yaw", -Infinity),
status: "model-prediction",
score: number(box.score, "L3.1 box.score"),
};
}
export async function fetchL31PointPillarsRavnoves({
fetcher = fetch,
signal,
}: {
fetcher?: LaboratoryFetch;
signal?: AbortSignal;
} = {}): Promise<L31PointPillarsRavnovesResult | null> {
const response = await fetcher(
"/api/v1/laboratory/l31/pointpillars-ravnoves/results?limit=1",
{ method: "GET", headers: { Accept: "application/json" }, signal },
);
if (!response.ok) {
throw new AdvancedLaboratoryContractError(
`L3.1 RAVNOVES недоступен: HTTP ${response.status}.`,
);
}
const catalog = record(await response.json(), "L3.1 catalog");
exact(
catalog.schema_version,
"missioncore.l31-pointpillars-ravnoves-catalog-results/v1",
"L3.1 catalog schema",
);
const items = array(catalog.items, "L3.1 catalog.items");
if (items.length > 1) {
throw new AdvancedLaboratoryContractError("L3.1 catalog: лишние результаты.");
}
return items.length ? parseResult(items[0]) : null;
}
export async function fetchL31PointPillarsRavnovesFrame(
resultId: string,
frameId: string,
{
fetcher = fetch,
signal,
}: {
fetcher?: LaboratoryFetch;
signal?: AbortSignal;
} = {},
): Promise<L31VisualFrame> {
if (!RESULT_ID.test(resultId) || !FRAME_ID.test(frameId)) {
throw new AdvancedLaboratoryContractError("L3.1 frame: неверная identity.");
}
const response = await fetcher(
`/api/v1/laboratory/l31/pointpillars-ravnoves/${resultId}/frames/${frameId}`,
{ method: "GET", headers: { Accept: "application/json" }, signal },
);
if (!response.ok) {
throw new AdvancedLaboratoryContractError(
`L3.1 frame недоступен: HTTP ${response.status}.`,
);
}
const payload = record(await response.json(), "L3.1 visual frame");
exact(
payload.schema_version,
"missioncore.l31-pointpillars-ravnoves-visual-frame/v1",
"L3.1 visual schema",
);
exact(payload.frame_id, frameId, "L3.1 visual frame_id");
const summaryRaw = record(payload.summary, "L3.1 visual summary");
const summary = parseSummary(summaryRaw);
const points = record(payload.points, "L3.1 points");
exact(points.layout, "flat-xyzi", "L3.1 points.layout");
const pointValues = array(points.values, "L3.1 points.values").map(
(entry, index) => number(entry, `L3.1 points[${index}]`, -Infinity),
);
const sampledPointCount = integer(
points.sampled_point_count,
"L3.1 sampled points",
);
if (sampledPointCount > 12_000 || pointValues.length !== sampledPointCount * 4) {
throw new AdvancedLaboratoryContractError("L3.1 points: нарушен bound.");
}
return {
frameId,
summary: {
...summary,
deterministicReplay: boolean(
summaryRaw.deterministic_replay,
"L3.1 deterministic replay",
),
replayInferenceMs: number(
summaryRaw.replay_inference_ms,
"L3.1 replay latency",
),
visualBoxCount: integer(
summaryRaw.visual_box_count,
"L3.1 visual box count",
),
visualBoxTruncated: boolean(
summaryRaw.visual_box_truncated,
"L3.1 visual box truncated",
),
},
sourcePointCount: integer(
points.source_point_count,
"L3.1 source points",
),
modelRangePointCount: integer(
points.model_range_point_count,
"L3.1 model range points",
),
sampledPointCount,
pointsXyzi: pointValues,
truthBoxes: [],
predictionBoxes: array(
payload.prediction_boxes,
"L3.1 prediction boxes",
).map(parseBox),
};
}
@@ -21,7 +21,12 @@ export interface L3VisualBox {
centerXyzM: readonly [number, number, number];
sizeLwhM: readonly [number, number, number];
yawRad: number;
status: "matched" | "false-negative" | "true-positive" | "false-positive";
status:
| "matched"
| "false-negative"
| "true-positive"
| "false-positive"
| "model-prediction";
score: number | null;
}