summaryrefslogtreecommitdiff
path: root/odoo/addons/test_new_api
diff options
context:
space:
mode:
authorRaphael Collet <rco@odoo.com>2020-03-10 16:33:05 +0000
committerRaphael Collet <rco@odoo.com>2020-03-23 09:04:59 +0000
commitfd50ba9fb838067fab0b920470cf79b9c94d785c (patch)
tree4e7ebd1736c4584fbcb168282ca49e1cf9e6c730 /odoo/addons/test_new_api
parent8978b0bc8f335a4339e7868343a2767980d29f97 (diff)
[IMP] core: do not recompute stored field on new record
The use case is a cache miss of a stored field with compute on a new record with origin. The field should be computed only when explicitly triggered, i.e., when a dependency has been modified. Otherwise it should be fetched from the origin record. closes odoo/odoo#47353 Signed-off-by: Raphael Collet (rco) <rco@openerp.com>
Diffstat (limited to 'odoo/addons/test_new_api')
-rw-r--r--odoo/addons/test_new_api/models/test_new_api.py12
-rw-r--r--odoo/addons/test_new_api/tests/test_new_fields.py46
-rw-r--r--odoo/addons/test_new_api/tests/test_onchange.py28
-rw-r--r--odoo/addons/test_new_api/views/test_new_api_views.xml23
4 files changed, 109 insertions, 0 deletions
diff --git a/odoo/addons/test_new_api/models/test_new_api.py b/odoo/addons/test_new_api/models/test_new_api.py
index 14a981b3b0c..9331f6eedee 100644
--- a/odoo/addons/test_new_api/models/test_new_api.py
+++ b/odoo/addons/test_new_api/models/test_new_api.py
@@ -796,6 +796,7 @@ class ModelChildM2o(models.Model):
parent_id = fields.Many2one('test_new_api.model_parent_m2o', ondelete='cascade')
size1 = fields.Integer(compute='_compute_sizes', store=True)
size2 = fields.Integer(compute='_compute_sizes', store=True)
+ cost = fields.Integer(compute='_compute_cost', store=True, readonly=False)
@api.depends('parent_id.name')
def _compute_sizes(self):
@@ -803,6 +804,11 @@ class ModelChildM2o(models.Model):
record.size1 = len(self.parent_id.name)
record.size2 = len(self.parent_id.name)
+ @api.depends('name')
+ def _compute_cost(self):
+ for record in self:
+ record.cost = len(record.name)
+
def write(self, vals):
res = super(ModelChildM2o, self).write(vals)
if self.name == 'A':
@@ -816,6 +822,12 @@ class ModelParentM2o(models.Model):
name = fields.Char('Name')
child_ids = fields.One2many('test_new_api.model_child_m2o', 'parent_id', string="Children")
+ cost = fields.Integer(compute='_compute_cost', store=True)
+
+ @api.depends('child_ids.cost')
+ def _compute_cost(self):
+ for record in self:
+ record.cost = sum(child.cost for child in record.child_ids)
class Country(models.Model):
diff --git a/odoo/addons/test_new_api/tests/test_new_fields.py b/odoo/addons/test_new_api/tests/test_new_fields.py
index c27704a47d9..7aa9b3c5a74 100644
--- a/odoo/addons/test_new_api/tests/test_new_fields.py
+++ b/odoo/addons/test_new_api/tests/test_new_fields.py
@@ -1090,6 +1090,52 @@ class TestFields(TransactionCaseWithUserDemo):
with self.assertRaises(AccessError):
cat1.name
+ def test_40_real_vs_new(self):
+ """ test field access on new records vs real records. """
+ Model = self.env['test_new_api.category']
+ real_record = Model.create({'name': 'Foo'})
+ self.env.cache.invalidate()
+ new_origin = Model.new({'name': 'Bar'}, origin=real_record)
+ new_record = Model.new({'name': 'Baz'})
+
+ # non-computed non-stored field: default value
+ real_record = real_record.with_context(default_dummy='WTF')
+ new_origin = new_origin.with_context(default_dummy='WTF')
+ new_record = new_record.with_context(default_dummy='WTF')
+ self.assertEqual(real_record.dummy, 'WTF')
+ self.assertEqual(new_origin.dummy, 'WTF')
+ self.assertEqual(new_record.dummy, 'WTF')
+
+ # non-computed stored field: origin or default if no origin
+ real_record = real_record.with_context(default_color=42)
+ new_origin = new_origin.with_context(default_color=42)
+ new_record = new_record.with_context(default_color=42)
+ self.assertEqual(real_record.color, 0)
+ self.assertEqual(new_origin.color, 0)
+ self.assertEqual(new_record.color, 42)
+
+ # computed non-stored field: always computed
+ self.assertEqual(real_record.display_name, 'Foo')
+ self.assertEqual(new_origin.display_name, 'Bar')
+ self.assertEqual(new_record.display_name, 'Baz')
+
+ # computed stored field: origin or computed if no origin
+ Model = self.env['test_new_api.recursive']
+ real_record = Model.create({'name': 'Foo'})
+ new_origin = Model.new({'name': 'Bar'}, origin=real_record)
+ new_record = Model.new({'name': 'Baz'})
+ self.assertEqual(real_record.display_name, 'Foo')
+ self.assertEqual(new_origin.display_name, 'Foo')
+ self.assertEqual(new_record.display_name, 'Baz')
+
+ # computed stored field with recomputation: always computed
+ real_record.name = 'Fool'
+ new_origin.name = 'Barr'
+ new_record.name = 'Bazz'
+ self.assertEqual(real_record.display_name, 'Fool')
+ self.assertEqual(new_origin.display_name, 'Barr')
+ self.assertEqual(new_record.display_name, 'Bazz')
+
def test_40_new_defaults(self):
""" Test new records with defaults. """
user = self.env.user
diff --git a/odoo/addons/test_new_api/tests/test_onchange.py b/odoo/addons/test_new_api/tests/test_onchange.py
index 5d544bd2875..398bd537bbd 100644
--- a/odoo/addons/test_new_api/tests/test_onchange.py
+++ b/odoo/addons/test_new_api/tests/test_onchange.py
@@ -678,3 +678,31 @@ class TestComputeOnchange(common.TransactionCase):
form.foo = "foo6"
self.assertEqual(form.bar, "foo6")
self.assertEqual(form.baz, "baz5")
+
+ def test_onchange_one2many(self):
+ record = self.env['test_new_api.model_parent_m2o'].create({
+ 'name': 'Family',
+ 'child_ids': [
+ (0, 0, {'name': 'W', 'cost': 10}),
+ (0, 0, {'name': 'X', 'cost': 10}),
+ (0, 0, {'name': 'Y'}),
+ (0, 0, {'name': 'Z'}),
+ ],
+ })
+ record.flush()
+ self.assertEqual(record.child_ids.mapped('name'), list('WXYZ'))
+ self.assertEqual(record.cost, 22)
+
+ # modifying a line should not recompute the cost on other lines
+ with common.Form(record) as form:
+ with form.child_ids.edit(1) as line:
+ line.name = 'XXX'
+ self.assertEqual(form.cost, 15)
+
+ with form.child_ids.edit(1) as line:
+ line.cost = 20
+ self.assertEqual(form.cost, 32)
+
+ with form.child_ids.edit(2) as line:
+ line.cost = 30
+ self.assertEqual(form.cost, 61)
diff --git a/odoo/addons/test_new_api/views/test_new_api_views.xml b/odoo/addons/test_new_api/views/test_new_api_views.xml
index 830210c4d87..c0ed0a7baa7 100644
--- a/odoo/addons/test_new_api/views/test_new_api_views.xml
+++ b/odoo/addons/test_new_api/views/test_new_api_views.xml
@@ -296,5 +296,28 @@
</form>
</field>
</record>
+
+ <!-- Multi form view -->
+ <record id="model_parent_form" model="ir.ui.view">
+ <field name="name">model parent form view</field>
+ <field name="model">test_new_api.model_parent_m2o</field>
+ <field name="arch" type="xml">
+ <form string="Model Parent">
+ <sheet>
+ <group>
+ <field name="name"/>
+ <field name="cost"/>
+ </group>
+ <label for="child_ids"/>
+ <field name="child_ids">
+ <tree string="Children" editable="bottom">
+ <field name="name"/>
+ <field name="cost"/>
+ </tree>
+ </field>
+ </sheet>
+ </form>
+ </field>
+ </record>
</data>
</odoo>