fix(velocity): cross-stack contract + NULL safety per pre-push review

3 pre-push code-reviewer findings fixed:

1. TS union extended ('objective'|'sale_graph'|'rosreestr_fallback')
   + UI conditions handle both objective и sale_graph как valid sources.
2. COALESCE(deals_total_vol_m2, deals_total_count * 45.0) — NULL safety
   for DKP-only rows (vol_m2 nullable, count > 0).
3. room_bucket parking filter — verified false positive (все 5 buckets
   apartments: студия/1/2/3/4+).

Refs: PR #157 pre-push code-reviewer
This commit is contained in:
lekss361 2026-05-15 09:20:51 +03:00
parent a21f440dcf
commit cc03ffa32d
3 changed files with 14 additions and 8 deletions

View file

@ -178,7 +178,8 @@ def compute_velocity(
)
SELECT
m.obj_id,
SUM(crm.deals_total_vol_m2) AS total_sqm,
SUM(COALESCE(crm.deals_total_vol_m2,
crm.deals_total_count * 45.0)) AS total_sqm,
COUNT(DISTINCT crm.report_month) AS months_with_data,
MIN(crm.report_month) AS period_start,
MAX(crm.report_month) AS period_end
@ -294,7 +295,8 @@ def _get_ekb_median(db: Session, months_window: int = 6) -> float | None:
WITH per_project AS (
SELECT
project_name,
SUM(deals_total_vol_m2) AS total_sqm,
SUM(COALESCE(deals_total_vol_m2,
deals_total_count * 45.0)) AS total_sqm,
COUNT(DISTINCT report_month) AS months_data
FROM objective_corpus_room_month
WHERE report_month >= (CURRENT_DATE - :window_interval::interval)

View file

@ -260,16 +260,19 @@ export default function RecommendPage() {
}
/>
<KpiCard
label="Sale_graph покрытие"
label="Покрытие velocity"
value={
data.scope.velocity_source === "objective" ||
data.scope.velocity_source === "sale_graph"
? `${data.scope.velocity_objects} ЖК`
: "fallback"
}
hint={
data.scope.velocity_source === "sale_graph"
? `${data.scope.velocity_observations} точек`
: "rosreestr city-wide"
data.scope.velocity_source === "objective"
? `${data.scope.velocity_observations} точек · objective (свежее)`
: data.scope.velocity_source === "sale_graph"
? `${data.scope.velocity_observations} точек · sale_graph`
: "rosreestr city-wide"
}
/>
<KpiCard

View file

@ -461,8 +461,9 @@ export function RecommendVelocityPanel({
. Базовый темп{" "}
<strong>{scope.market_velocity_per_month?.toFixed(1) ?? "—"}</strong>{" "}
кв/мес (
{scope.velocity_source === "sale_graph"
? `sale_graph: ${scope.velocity_objects} ЖК / ${scope.velocity_observations} точек`
{scope.velocity_source === "objective" ||
scope.velocity_source === "sale_graph"
? `${scope.velocity_source}: ${scope.velocity_objects} ЖК / ${scope.velocity_observations} точек`
: "fallback на rosreestr-сделки"}
),{" "}
{scope.competitors_radius_n != null &&