Skip to content

GitLab

  • Projects
  • Groups
  • Snippets
  • Help
    • Loading...
  • Help
    • Help
    • Support
    • Community forum
    • Submit feedback
    • Contribute to GitLab
  • Sign in / Register
erp5 erp5
  • Project overview
    • Project overview
    • Details
    • Activity
    • Releases
  • Repository
    • Repository
    • Files
    • Commits
    • Branches
    • Tags
    • Contributors
    • Graph
    • Compare
  • Labels
    • Labels
  • Merge requests 139
    • Merge requests 139
  • CI/CD
    • CI/CD
    • Pipelines
    • Jobs
    • Schedules
  • Operations
    • Operations
    • Environments
  • Analytics
    • Analytics
    • CI/CD
    • Repository
    • Value Stream
  • Wiki
    • Wiki
  • Snippets
    • Snippets
  • Members
    • Members
  • Activity
  • Graph
  • Jobs
  • Commits
Collapse sidebar
  • nexedi
  • erp5erp5
  • Merge requests
  • !2017

Merged
Created Nov 13, 2024 by Nicolas Wavrant@NicolasMaintainer

Stock view optimization

  • Overview 6
  • Commits 1
  • Changes 2

The "Stock" view of Products can become very slow when the user selects a section or a node, and takes dozens of seconds, or more. This happened on 2 of my projects.

This is what the "WHERE" statement of the query looks like, and how Mariadb's ordonancer plans it:

WHERE
  stock.uid = catalog.uid
  AND ((stock.ledger_uid = 2809240927
  AND `related_stock_node_category_uid_1_category`.`category_uid` = 1833756305
  AND stock.resource_uid = 84476002
  AND stock.simulation_state IN ('ordered', 'planned', 'started', 'ready', 'confirmed', 'assigned', 'delivered', 'stopped', 'acknowledged')
  AND `related_stock_section_category_uid_1_category`.`category_uid` = 33761)
  AND (`stock`.`uid` = `catalog`.`uid`)
  AND (related_stock_node_category_uid_1_category.uid = stock.node_uid)
  AND (related_stock_section_category_uid_1_category.uid = stock.section_uid))
+------+-------------+-----------------------------------------------+--------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+-------------------+---------+---------------------------------------------------------------------+------+----------------------------------------------+
| id   | select_type | table                                         | type   | possible_keys                                                                                                                                                                         | key               | key_len | ref                                                                 | rows | Extra                                        |
+------+-------------+-----------------------------------------------+--------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+-------------------+---------+---------------------------------------------------------------------+------+----------------------------------------------+
|    1 | SIMPLE      | related_stock_node_category_uid_1_category    | ref    | PRIMARY,Membership                                                                                                                                                                    | Membership        | 8       | const                                                               |   26 | Using index; Using temporary; Using filesort |
|    1 | SIMPLE      | stock                                         | ref    | PRIMARY,node_uid,resource_node_uid,resource_section_node_uid,state_section_increase_node_date,section_uid_portal_type_mirror_section_uid,ledger_uid,ledger_section_grouping_date_node | resource_node_uid | 18      | const,erp5.related_stock_node_category_uid_1_category.uid           |   40 | Using where                                  |
|    1 | SIMPLE      | related_stock_section_category_uid_1_category | ref    | PRIMARY,Membership                                                                                                                                                                    | PRIMARY           | 16      | erp5.stock.section_uid,const                                        |    1 | Using index                                  |
|    1 | SIMPLE      | catalog                                       | eq_ref | PRIMARY                                                                                                                                                                               | PRIMARY           | 8       | erp5.stock.uid                                                      |    1 |                                              |
+------+-------------+-----------------------------------------------+--------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+-------------------+---------+---------------------------------------------------------------------+------+----------------------------------------------+

There are 4 steps, the 1st one being on a join table, so it can't make good use of the index. Which is sad as resource_section_node_uid looks perfect for us.

As this hints to joins making the query slow, I wrote this patch (and re-edited for submission to generic) to query first the UIDs that are searched by joins (iow: entities used as node or source of stock entries), and inject them directly in the stock query.

WHERE
  stock.uid = catalog.uid
  AND ((stock.ledger_uid = 2809240927
  AND stock.simulation_state IN ('ordered', 'planned', 'started', 'ready', 'confirmed', 'assigned', 'delivered', 'stopped', 'acknowledged')
  AND stock.resource_uid = 84476002
  AND stock.node_uid = 33883
  AND stock.section_uid IN (33883, 11452967, 11452968, 11452969, 11452970, 11452971, 11452972, 11452973, 11452974, 11452975, 11452976, 11452977, 11452978, 11452979, 11452983, 12896399, 475678011, 475678012, 475678013, 475678014, 860163658, 860163659, 860163660, 860163661, 860163662, 860163663, 860163664, 860163665, 860163666, 860163667, 860163668, 1424009821, 1491920240, 1493437626, 1567513548, 1754246652, 2136977055, 2230443736, 2244740712, 2589384676, 2621144387, 2762595449))
  AND (`stock`.`uid` = `catalog`.`uid`))
+------+-------------+---------+--------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+------------+---------+--------------------------+------+---------------------------------------------------------------------+
| id   | select_type | table   | type   | possible_keys                                                                                                                                                                         | key        | key_len | ref                      | rows | Extra                                                               |
+------+-------------+---------+--------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+------------+---------+--------------------------+------+---------------------------------------------------------------------+
|    1 | SIMPLE      | stock   | range  | PRIMARY,node_uid,resource_node_uid,resource_section_node_uid,state_section_increase_node_date,section_uid_portal_type_mirror_section_uid,ledger_uid,ledger_section_grouping_date_node | ledger_uid | 18      | NULL                     | 7495 | Using index condition; Using where; Using temporary; Using filesort |
|    1 | SIMPLE      | catalog | eq_ref | PRIMARY                                                                                                                                                                               | PRIMARY    | 8       | erp5.stock.uid           |    1 |                                                                     |
+------+-------------+---------+--------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+------------+---------+--------------------------+------+---------------------------------------------------------------------+

In my case, this query becomes instant on production.

The main drawback I see is that if the list of nodes or sections is too long, which isn't the case in my projects as they represent the physical warehouse & shops of my customer, it would probably impact the query.

Edited Nov 15, 2024 by Nicolas Wavrant
Assignee
Assign to
Reviewer
Request review from
None
Milestone
None
Assign milestone
Time tracking
Source branch: stock-view-optimization
GitLab Nexedi Edition | About GitLab | About Nexedi | 沪ICP备2021021310号-2 | 沪ICP备2021021310号-7