Changes between Version 1 and Version 2 of DriverDeliveriesView
- Timestamp:
- 09/14/26 00:40:31 (13 days ago)
Legend:
- Unmodified
- Added
- Removed
- Modified
-
DriverDeliveriesView
v1 v2 1 1 = Преглед: v_driver_deliveries = 2 2 3 ||= Датотека ||= `views/04_driver_deliveries_view.sql` || 4 ||= Шема ||= `kbnteam` || 5 ||= Категорија ||= Нарачки и Достави || 6 ||= Поврзани индекси ||= `indexes/v_driver_deliveries_index.sql` || 7 ||= Сложеност ||= Висока — 2 CTE + 13 табели || 3 ||= Својство ||= Вредност || 4 || Шема || `kbnteam` || 5 || Категорија || Нарачки и достави || 6 || Поврзани индекси || [wiki:DriverDeliveriesIndex Индекси за нарачки и достави] || 8 7 9 8 == Опис == 10 Прикажува доделување на достави и поврзаниот содржај на нарачките наменет за возачите. Го следи истиот шаблон за агрегирање на ставки (CTE `order_meals` и `order_drinks`) како `v_orders_full`, но е ориентиран кон доставата наместо кон нарачката. Корисен за екранот на возачот во мобилната/веб апликација. 9 10 Ги прикажува доставите, доставувачите, рестораните, компаниите и поврзаните нарачки. 11 12 Го користи прегледот на нарачки за деталите за клиентот и нарачаните производи. Се прикажуваат и доставите без назначен доставувач или поврзани нарачки. 13 14 Еден ред за секоја клиентска нарачка во доставата. Достава без клиентски нарачки останува прикажана со NULL податоци за нарачката. 15 16 Податоците за нарачките се добиваат преку [wiki:OrdersFullView v_orders_full]. Овој преглед е зависност на прегледот за достави. 11 17 12 18 == Зависности == 13 ||= Табела ||= Тип на употреба || 14 || `kbnteam.delivery` || Главна табела || 15 || `kbnteam.delivery_status` || JOIN — статус на достава || 16 || `kbnteam.driver` || LEFT JOIN — возач || 17 || `kbnteam.api_user` || LEFT JOIN (×2) — детали за возач и купувач || 18 || `kbnteam.restaurant` || LEFT JOIN — ресторан на возачот || 19 || `kbnteam.company_order` || LEFT JOIN — компаниска нарачка || 20 || `kbnteam.company` || LEFT JOIN — компанија || 21 || `kbnteam.customer_order` || LEFT JOIN — нарачка || 22 || `kbnteam.customer` || LEFT JOIN — купувач || 23 || `kbnteam.order_meal` || LEFT JOIN (CTE) — оброци || 24 || `kbnteam.meal` || JOIN (CTE) — назив на оброк || 25 || `kbnteam.order_drink` || LEFT JOIN (CTE) — пијачи || 26 || `kbnteam.drink` || JOIN (CTE) — назив на пијач || 27 28 == SQL Дефиниција == 19 20 ||= Табела / преглед ||= Употреба || 21 || `kbnteam.delivery` || Достави, датуми, забелешки и назначени доставувачи. || 22 || `kbnteam.delivery_status` || Називи на статусите на доставите. || 23 || `kbnteam.driver` || Доставувачи и нивните ресторани. || 24 || `kbnteam.api_user` || Лични и контактни податоци за корисниците. || 25 || `kbnteam.restaurant` || Податоци за рестораните. || 26 || `kbnteam.company_order` || Поврзување на компаниските нарачки со компанијата и доставата. || 27 || `kbnteam.company` || Податоци за компаниите. || 28 || [wiki:OrdersFullView v_orders_full] || Преглед со детали за клиентските нарачки и листи со производи. || 29 30 == Излезни колони == 31 32 ||= Колона ||= Извор / пресметка ||= Опис || 33 || `delivery_id` || `delivery.delivery_id` || Идентификатор на доставата. || 34 || `delivery_date` || `delivery.delivery_date` || Датум на доставата. || 35 || `delivery_notes` || `delivery.delivery_notes` || Забелешки за доставата. || 36 || `d_status_name` || `delivery_status.d_status_name` || Статус на доставата. || 37 || `driver_user_id` || `driver.user_id` || Идентификатор на доставувачот. || 38 || `driver_first_name` || `api_user.user_first_name` || Име на доставувачот. || 39 || `driver_last_name` || `api_user.user_last_name` || Презиме на доставувачот. || 40 || `driver_phone` || `api_user.user_phone_no` || Телефон на доставувачот. || 41 || `rest_id` || `restaurant.rest_id` || Идентификатор на ресторанот. || 42 || `rest_name` || `restaurant.rest_name` || Назив на ресторанот. || 43 || `comp_order_id` || `company_order.comp_order_id` || Идентификатор на компаниската нарачка. || 44 || `company_id` || `company.company_id` || Идентификатор на компанијата. || 45 || `company_name` || `company.company_name` || Назив на компанијата. || 46 || `order_id` || `v_orders_full.order_id` || Идентификатор на клиентската нарачка. || 47 || `order_datetime` || `v_orders_full.order_datetime` || Датум и време на нарачката. || 48 || `order_total` || `v_orders_full.order_total` || Вкупен износ на нарачката. || 49 || `customer_user_id` || `v_orders_full.customer_user_id` || Идентификатор на клиентот. || 50 || `customer_first_name` || `v_orders_full.customer_first_name` || Име на клиентот. || 51 || `customer_last_name` || `v_orders_full.customer_last_name` || Презиме на клиентот. || 52 || `customer_email` || `v_orders_full.customer_email` || Е-пошта на клиентот. || 53 || `meals` || `COALESCE(v_orders_full.meals, '')` || Подредена листа со називи на нарачаните јадења. || 54 || `drinks` || `COALESCE(v_orders_full.drinks, '')` || Подредена листа со називи на нарачаните пијалоци. || 55 56 == SQL дефиниција == 57 29 58 {{{ 30 59 #!sql 31 60 CREATE OR REPLACE VIEW kbnteam.v_driver_deliveries AS 32 WITH order_meals AS (33 SELECT34 x.order_id,35 string_agg(x.meal_name, ', ' ORDER BY x.meal_name) AS meals36 FROM (37 SELECT DISTINCT38 om.order_id,39 m.meal_name40 FROM kbnteam.order_meal om41 JOIN kbnteam.meal m ON m.meal_id = om.meal_id42 ) x43 GROUP BY x.order_id44 ),45 order_drinks AS (46 SELECT47 x.order_id,48 string_agg(x.drink_name, ', ' ORDER BY x.drink_name) AS drinks49 FROM (50 SELECT DISTINCT51 od.order_id,52 d.drink_name53 FROM kbnteam.order_drink od54 JOIN kbnteam.drink d ON d.drink_id = od.drink_id55 ) x56 GROUP BY x.order_id57 )58 61 SELECT 59 62 d.delivery_id, … … 73 76 o.order_datetime, 74 77 o.order_total, 75 cu.user_id AScustomer_user_id,76 au.user_first_name AScustomer_first_name,77 au.user_last_name AScustomer_last_name,78 au.user_email AScustomer_email,79 COALESCE(o m.meals, '') AS meals,80 COALESCE(o d.drinks, '') AS drinks78 o.customer_user_id, 79 o.customer_first_name, 80 o.customer_last_name, 81 o.customer_email, 82 COALESCE(o.meals, '') AS meals, 83 COALESCE(o.drinks, '') AS drinks 81 84 FROM kbnteam.delivery d 82 85 JOIN kbnteam.delivery_status ds ON ds.d_status_id = d.d_status_id … … 86 89 LEFT JOIN kbnteam.company_order co ON co.delivery_id = d.delivery_id 87 90 LEFT JOIN kbnteam.company cmp ON cmp.company_id = co.company_id 88 LEFT JOIN kbnteam.customer_order o ON o.comp_order_id = co.comp_order_id 89 LEFT JOIN kbnteam.customer cu ON cu.user_id = o.customer_user_id 90 LEFT JOIN kbnteam.api_user au ON au.user_id = cu.user_id 91 LEFT JOIN order_meals om ON om.order_id = o.order_id 92 LEFT JOIN order_drinks od ON od.order_id = o.order_id; 91 LEFT JOIN kbnteam.v_orders_full o ON o.comp_order_id = co.comp_order_id; 93 92 }}} 94 93 95 94 == Тестирање на перформанси == 96 95 97 === Препорачано тест прашање === 98 {{{ 99 #!sql 100 SET search_path TO kbnteam; 101 SET statement_timeout = '60s'; 102 103 -- Тест 1: по возач и датум на достава 96 Примерите користат илустративни идентификатори и датуми. За споредливи мерења се избираат вредности што постојат во базата и се задржуваат истите податоци, филтри, услови за кеширање и број на повторувања. Статистиките за табелите треба да бидат ажурирани во двете состојби. 97 98 === Тест прашалници === 99 100 {{{ 101 #!sql 102 BEGIN READ ONLY; 103 SET LOCAL statement_timeout = '60s'; 104 105 -- Тест 1: по доставувач и датум 104 106 EXPLAIN (ANALYZE, BUFFERS, VERBOSE) 105 107 SELECT * FROM kbnteam.v_driver_deliveries 106 108 WHERE driver_user_id = 1 107 AND delivery_date >= CURRENT_DATE - INTERVAL '30 days'; 109 AND delivery_date >= DATE '2026-09-01' 110 AND delivery_date < DATE '2026-10-01'; 108 111 109 112 -- Тест 2: по компаниска нарачка … … 111 114 SELECT * FROM kbnteam.v_driver_deliveries 112 115 WHERE comp_order_id = 1; 116 117 ROLLBACK; 113 118 }}} 114 119 115 120 === Резултати пред индексирање === 116 ||= Метрика ||= Тест 1 (возач + датум) ||= Тест 2 (comp_order) || 121 122 Основната состојба ги задржува индексите на примарните клучеви и уникатните ограничувања. Останатите присутни индекси се евидентираат одделно. При споредба на заеднички индекси се користи истата почетна состојба за секој преглед. 123 124 ||= Метрика ||= Тест 1 (по доставувач и датум) ||= Тест 2 (по компаниска нарачка) || 117 125 || Planning Time || ___ ms || ___ ms || 118 126 || Execution Time || ___ ms || ___ ms || 119 127 || Rows Returned || ___ || ___ || 120 || delivery scan || ___ || ___ || 121 || order_meal scan || ___ || ___ || 122 123 {{{ 124 -- Излезот од EXPLAIN ANALYZE овде (пред индексирање) 125 }}} 126 127 === Применети индекси === 128 {{{ 129 #!sql 130 -- indexes/v_driver_deliveries_index.sql 128 || Начин на читање по табела || ___ || ___ || 129 || Shared Hit Blocks || ___ || ___ || 130 || Shared Read Blocks || ___ || ___ || 131 132 {{{ 133 -- Планови и резултати пред дополнителното индексирање: 134 135 }}} 136 137 === Дополнителни и заеднички индекси === 138 139 `company_order(delivery_id)` има уникатен индекс. Прегледот ги користи и индексите за нарачките преку `v_orders_full`. 140 141 ||= Индекс ||= Табела и колони ||= Намена || 142 || `idx_company_order_company_id` || `company_order(company_id)` || Пронаоѓање компаниски нарачки по компанија. || 143 || `idx_customer_order_comp_order_id` || `customer_order(comp_order_id)` || Пронаоѓање клиентски нарачки по компаниска нарачка. || 144 || `idx_order_meal_order_id_meal_id` || `order_meal(order_id, meal_id)` || Пристап до јадењата на нарачката и групирање по order_id. || 145 || `idx_order_drink_order_id_drink_id` || `order_drink(order_id, drink_id)` || Пристап до пијалоците на нарачката и групирање по order_id. || 146 || `idx_delivery_driver_user_id_delivery_date` || `delivery(driver_user_id, delivery_date)` || Пронаоѓање достави по доставувач; во прегледите за нарачки и достави и по датум. || 147 || `idx_driver_rest_id` || `driver(rest_id)` || Пронаоѓање доставувачи по ресторан. || 148 149 {{{ 150 #!sql 151 CREATE INDEX IF NOT EXISTS idx_company_order_company_id 152 ON kbnteam.company_order (company_id); 153 154 CREATE INDEX IF NOT EXISTS idx_customer_order_comp_order_id 155 ON kbnteam.customer_order (comp_order_id); 156 157 CREATE INDEX IF NOT EXISTS idx_order_meal_order_id_meal_id 158 ON kbnteam.order_meal (order_id, meal_id); 159 160 CREATE INDEX IF NOT EXISTS idx_order_drink_order_id_drink_id 161 ON kbnteam.order_drink (order_id, drink_id); 162 131 163 CREATE INDEX IF NOT EXISTS idx_delivery_driver_user_id_delivery_date 132 164 ON kbnteam.delivery (driver_user_id, delivery_date); 133 165 134 CREATE INDEX IF NOT EXISTS idx_order_meal_order_id_meal_id 135 ON kbnteam.order_meal (order_id, meal_id); 136 137 CREATE INDEX IF NOT EXISTS idx_order_drink_order_id_drink_id 138 ON kbnteam.order_drink (order_id, drink_id); 139 140 CREATE INDEX IF NOT EXISTS idx_customer_order_comp_order_id 141 ON kbnteam.customer_order (comp_order_id); 166 CREATE INDEX IF NOT EXISTS idx_driver_rest_id 167 ON kbnteam.driver (rest_id); 168 }}} 169 170 === Проверка на индексите === 171 172 {{{ 173 #!sql 174 SELECT tablename, indexname, indexdef 175 FROM pg_indexes 176 WHERE schemaname = 'kbnteam' 177 AND indexname IN ( 178 'idx_company_order_company_id', 179 'idx_customer_order_comp_order_id', 180 'idx_order_meal_order_id_meal_id', 181 'idx_order_drink_order_id_drink_id', 182 'idx_delivery_driver_user_id_delivery_date', 183 'idx_driver_rest_id' 184 ) 185 ORDER BY tablename, indexname; 142 186 }}} 143 187 144 188 === Резултати по индексирање === 145 ||= Метрика ||= Тест 1 (возач + датум) ||= Тест 2 (comp_order) || 189 190 Мерењето ги користи истите тест прашалници и услови како почетното мерење. 191 192 ||= Метрика ||= Тест 1 (по доставувач и датум) ||= Тест 2 (по компаниска нарачка) || 146 193 || Planning Time || ___ ms || ___ ms || 147 194 || Execution Time || ___ ms || ___ ms || 148 195 || Rows Returned || ___ || ___ || 149 || delivery scan || ___ || ___ || 150 || order_meal scan || ___ || ___ || 151 152 {{{ 153 -- Излезот од EXPLAIN ANALYZE овде (по индексирање) 196 || Начин на читање по табела || ___ || ___ || 197 || Shared Hit Blocks || ___ || ___ || 198 || Shared Read Blocks || ___ || ___ || 199 200 {{{ 201 -- Планови и резултати по дополнителното индексирање: 202 154 203 }}} 155 204 156 205 === Анализа на подобрување === 157 ||= Индекс ||= Помага на ||= Очекувана промена || 158 || `idx_delivery_driver_user_id_delivery_date` || Тест 1 — филтрирање по возач и датум || Seq Scan → Index Scan || 159 || `idx_customer_order_comp_order_id` || Тест 2 и JOIN со `company_order` || Seq Scan → Index Scan || 160 || `idx_order_meal_order_id_meal_id` || CTE агрегација || Seq Scan → Index Scan || 161 || `idx_order_drink_order_id_drink_id` || CTE агрегација || Seq Scan → Index Scan || 162 163 ||= Метрика ||= Пред ||= По ||= Δ Подобрување || 206 207 ||= Метрика ||= Пред ||= По ||= Промена (%) || 164 208 || Execution Time (Тест 1) || ___ ms || ___ ms || ___ % || 165 209 || Execution Time (Тест 2) || ___ ms || ___ ms || ___ % || 210 211 Промената се пресметува како 100 × (време пред − време по) / време пред, кога почетното време е поголемо од нула. Негативна вредност означува побавно извршување. 212 213 Изборот меѓу секвенцијално читање, индексно читање и други планови зависи од обемот на податоците, селективноста на филтрите и статистиките. Индексите не гарантираат забрзување или отстранување на сортирањата и спојувањата. Плановите и времињата се утврдуваат со мерење.
