Improve threshold between rebuild and update MPTT

Indeed we should count the number of nodes updated instead of the number of
queries.

rebuild: 1 write and 1 select on each node
update: (1 write + 3 select + 2 write on average ½ all nodes + 1 write on child
of id) on each ids

So the threshold is:

2 * count < (4 + 2 * count / 2 + 1 * x) * len(ids)
2 * count < (4 + count + x) * len(ids)

which can be approximated to

2 * count < count * len(ids)
2 < len(ids)

issue5399
review20861002
This commit is contained in:
Cédric Krier committed 2016-03-21 23:43:22 +01:00
1 parent c19f93cd9b
commit 792d623c7b
2 files changed
+6 -9

No files matched your search

+1 -6
View File
@@ -1291,7 +1291,6 @@ class ModelSQL(ModelStorage):
@classmethod
def _update_mptt(cls, field_names, list_ids, values=None):
cursor = Transaction().connection.cursor()
count = None
for field_name, ids in zip(field_names, list_ids):
field = cls._fields[field_name]
if (isinstance(field, fields.Many2One)
@@ -1315,11 +1314,7 @@ class ModelSQL(ModelStorage):
& (Column(parent, field.right) == 0)))
nested_create = cursor.fetchone()
if count is None:
cursor.execute(*table.select(Count(Literal(1))))
count, = cursor.fetchone()
if not nested_create and len(ids) < count / 4:
if not nested_create and len(ids) < 2:
for id_ in ids:
cls._update_tree(id_, field_name,
field.left, field.right)
+5 -3
View File
@@ -175,16 +175,18 @@ class MPTTTestCase(unittest.TestCase):
records = Mptt.search([
('parent', '=', None),
])
with patch.object(Mptt, '_update_tree') as mock:
with patch.object(Mptt, '_update_tree') as update, \
patch.object(Mptt, '_rebuild_tree') as rebuild:
Mptt.write(records, {'name': 'Parent Records'})
self.assertFalse(mock.called)
self.assertFalse(update.called)
self.assertFalse(rebuild.called)
first_parent, second_parent = records[:2]
Mptt.write(list(first_parent.childs), {
'parent': second_parent.id,
})
self.assertTrue(mock.called)
self.assertTrue(update.called or rebuild.called)
@with_transaction()
def test_nested_create(self):