Преглед: v_customer_loyalty_full_v2
| Датотека | views/06_customer_loyalty_view_v2.sql
|
|---|
| Шема | kbnteam
|
|---|
| Категорија | Договори, Фактурирање и Верност
|
|---|
| Поврзани индекси | indexes/v_customer_loyalty_full_v2_index.sql
|
|---|
| Статус | Канонска верзија — препорачана за употреба наместо v_customer_loyalty_full
|
|---|
Опис
Прикажува статус на верност, податоци за ниво и статистика на нарачки на купувачи. Користи CTE order_stats за агрегирање на вкупен приход, број на нарачки и последна нарачка по купувач. V2 верзијата е почиста и поефикасна од v_customer_loyalty_full бидејќи CTE-то е поделено наместо вградено подпрашање.
Зависности
| Табела | Тип на употреба
|
|---|
kbnteam.customer_loyalty | Главна табела
|
kbnteam.customer | JOIN — купувач
|
kbnteam.company | JOIN — компанија
|
kbnteam.api_user | JOIN — детали за корисник
|
kbnteam.customer_loyalty_status | JOIN — статус на верност
|
kbnteam.loyalty_tier | JOIN — ниво на верност
|
kbnteam.customer_order | LEFT JOIN (CTE) — статистика на нарачки
|
SQL Дефиниција
CREATE OR REPLACE VIEW kbnteam.v_customer_loyalty_full_v2 AS
WITH order_stats AS (
SELECT
o.customer_user_id,
COUNT(*) AS order_count,
COALESCE(SUM(o.order_total), 0)::numeric(14,2) AS total_spent,
MAX(o.order_datetime) AS last_order_at
FROM kbnteam.customer_order o
GROUP BY o.customer_user_id
)
SELECT
cl.cus_loyalty_id,
cl.user_id AS customer_user_id,
cu.company_id,
cmp.company_name,
au.user_first_name,
au.user_last_name,
au.user_email,
au.user_phone_no,
cl.cus_loyalty_curr_points,
cl.cus_loyalty_joined_at,
cls.cus_loyalty_status_id,
cls.cus_loyalty_status_name,
lt.tier_id,
lt.tier_name,
lt.tier_discount_percentage,
lt.tier_free_delivery_eligibility,
lt.tier_priority_support,
COALESCE(os.order_count, 0) AS order_count,
COALESCE(os.total_spent, 0)::numeric(14,2) AS total_spent,
os.last_order_at
FROM kbnteam.customer_loyalty cl
JOIN kbnteam.customer cu
ON cu.user_id = cl.user_id
JOIN kbnteam.company cmp
ON cmp.company_id = cu.company_id
JOIN kbnteam.api_user au
ON au.user_id = cl.user_id
JOIN kbnteam.customer_loyalty_status cls
ON cls.cus_loyalty_status_id = cl.cus_loyalty_status_id
JOIN kbnteam.loyalty_tier lt
ON lt.tier_id = cl.tier_id
LEFT JOIN order_stats os
ON os.customer_user_id = cl.user_id;
Тестирање на перформанси
Препорачано тест прашање
SET search_path TO kbnteam;
SET statement_timeout = '60s';
-- Тест 1: по компанија
EXPLAIN (ANALYZE, BUFFERS, VERBOSE)
SELECT * FROM kbnteam.v_customer_loyalty_full_v2
WHERE company_id = 1;
-- Тест 2: по ниво на верност
EXPLAIN (ANALYZE, BUFFERS, VERBOSE)
SELECT * FROM kbnteam.v_customer_loyalty_full_v2
WHERE tier_id = 1;
-- Тест 3: по купувач (директна точка пристап)
EXPLAIN (ANALYZE, BUFFERS, VERBOSE)
SELECT * FROM kbnteam.v_customer_loyalty_full_v2
WHERE customer_user_id = 1;
Резултати пред индексирање
| Метрика | Тест 1 (company) | Тест 2 (tier) | Тест 3 (customer)
|
|---|
| Planning Time | _ ms | _ ms | _ ms
|
| Execution Time | _ ms | _ ms | _ ms
|
| Rows Returned | _ | _ | _
|
| customer_order scan | _ | _ | _
|
-- Излезот од EXPLAIN ANALYZE овде (пред индексирање)
Применети индекси
-- indexes/v_customer_loyalty_full_v2_index.sql
CREATE INDEX IF NOT EXISTS idx_customer_order_customer_user_id_order_datetime
ON kbnteam.customer_order (customer_user_id, order_datetime DESC);
Резултати по индексирање
| Метрика | Тест 1 (company) | Тест 2 (tier) | Тест 3 (customer)
|
|---|
| Planning Time | _ ms | _ ms | _ ms
|
| Execution Time | _ ms | _ ms | _ ms
|
| Rows Returned | _ | _ | _
|
| customer_order scan | _ | _ | _
|
-- Излезот од EXPLAIN ANALYZE овде (по индексирање)
Анализа на подобрување
| Индекс | Помага на | Очекувана промена
|
|---|
idx_customer_order_customer_user_id_order_datetime | CTE order_stats GROUP BY + MAX(order_datetime) | Seq Scan → Index Scan
|
| Метрика | Пред | По | Δ Подобрување
|
|---|
| Execution Time (Тест 3) | _ ms | _ ms | _ %
|
Напомена: Индексот е особено ефективен при Тест 3 (по купувач) бидејќи CTE-то order_stats може директно да го скенира по customer_user_id. При целосен скен (Тест 1 или 2), подобрувањето зависи од бројот на редови.