From 2847262953fae2b3139e60494d084fad3c832389 Mon Sep 17 00:00:00 2001 From: lekss361 Date: Mon, 11 May 2026 17:30:09 +0300 Subject: [PATCH] feat(analytics): extend recommend comparables with cad_quarter, lat/lon, buildings_n --- backend/app/schemas/recommend.py | 4 ++++ backend/app/services/analytics_queries.py | 22 +++++++++++++++++++++- 2 files changed, 25 insertions(+), 1 deletion(-) diff --git a/backend/app/schemas/recommend.py b/backend/app/schemas/recommend.py index 81236116..e66af731 100644 --- a/backend/app/schemas/recommend.py +++ b/backend/app/schemas/recommend.py @@ -48,6 +48,10 @@ class RecommendComparable(BaseModel): obj_class: str | None = None flat_count: int | None = None sold_perc: float | None = None + cad_quarter: str | None = None + lat: float | None = None + lon: float | None = None + buildings_n: int | None = None class RecommendMixOutput(BaseModel): diff --git a/backend/app/services/analytics_queries.py b/backend/app/services/analytics_queries.py index e39d439e..ff2361b9 100644 --- a/backend/app/services/analytics_queries.py +++ b/backend/app/services/analytics_queries.py @@ -2077,15 +2077,31 @@ def recommend_mix( FROM domrf_kn_sales_agg WHERE type = 'apartments' GROUP BY obj_id + ), + vcf_dedup AS ( + -- один ряд на canonical_name: берём с наибольшим cad_buildings_n + SELECT DISTINCT ON (lower(canonical_name)) + lower(canonical_name) AS name_key, + cad_quarter, + latitude, + longitude, + cad_buildings_n + FROM v_complex_full + ORDER BY lower(canonical_name), cad_buildings_n DESC NULLS LAST ) SELECT o.obj_id, o.comm_name, o.dev_name, o.obj_class, o.flat_count, - a.perc AS sold_perc + a.perc AS sold_perc, + c.cad_quarter, + c.latitude AS lat, + c.longitude AS lon, + c.cad_buildings_n AS buildings_n FROM domrf_kn_objects o LEFT JOIN latest_agg la ON la.obj_id = o.obj_id LEFT JOIN domrf_kn_sales_agg a ON a.obj_id = la.obj_id AND a.snapshot_date = la.snap AND a.type = 'apartments' + LEFT JOIN vcf_dedup c ON c.name_key = lower(o.comm_name) WHERE o.region_cd = :rc AND o.district_name = :dn AND (CAST(:cls AS TEXT) IS NULL OR o.obj_class = :cls) @@ -2212,6 +2228,10 @@ def recommend_mix( "obj_class": r["obj_class"], "flat_count": r["flat_count"], "sold_perc": _f(r["sold_perc"]), + "cad_quarter": r["cad_quarter"], + "lat": _f(r["lat"]), + "lon": _f(r["lon"]), + "buildings_n": r["buildings_n"], } for r in cmp_rows ],