[FIX] fields: read unstored one2many field without search function

> The bug is not present in 16.2+, but we keep the test

To Reproduce:
=============

- on a contact add a one2many field using studio
- in related field choose a field that is not stored and doesn't have a search function implemented
- close studio and notice all the lines of the selected field are listed on the contact even if are not linked to it

Problem:
========
- when searching a field that is not stored and doesn't have a search function, all the lines are returned

Solution:
=========
in this usecase filter the returned lines and only keep the ones linked to the record

opw-3265982

closes odoo/odoo#123563

X-original-commit: 7b29e9dff1d5ef97c5fb2a2ae0709bb21fd3fa3a
Signed-off-by: Rémy Voet <ryv@odoo.com>
Signed-off-by: abla001 <abla@odoo.com>
This commit is contained in:
Abdelouahab (abla)
2023-06-05 14:50:03 +02:00
parent f85a4366b0
commit d10a40b14d
3 changed files with 62 additions and 0 deletions
@@ -1803,3 +1803,18 @@ class TeamMember(models.Model):
name = fields.Char('Name')
team_id = fields.Many2one('test_new_api.team')
parent_id = fields.Many2one('test_new_api.team', related='team_id.parent_id')
class UnsearchableO2M(models.Model):
_name = 'test_new_api.unsearchable.o2m'
_description = 'Test non-stored unsearchable o2m'
name = fields.Char('Name')
stored_parent_id = fields.Many2one('test_new_api.unsearchable.o2m', store=True)
parent_id = fields.Many2one('test_new_api.unsearchable.o2m', store=False, compute="_compute_parent_id")
child_ids = fields.One2many('test_new_api.unsearchable.o2m', 'parent_id')
@api.depends('stored_parent_id')
def _compute_parent_id(self):
for r in self:
r.parent_id = r.stored_parent_id
@@ -110,3 +110,4 @@ access_test_new_api_employer,access_test_new_api_employer,model_test_new_api_emp
public_access_test_new_api_course,access_test_new_api_course,model_test_new_api_course,base.group_public,1,0,0,0
access_test_new_api_team,access_test_new_api_team,model_test_new_api_team,base.group_user,1,0,0,0
access_test_new_api_team_member,access_test_new_api_team_member,model_test_new_api_team_member,base.group_user,1,0,0,0
access_test_new_api_unsearchable_o2m,access_test_new_api_unsearchable_o2m,model_test_new_api_unsearchable_o2m,,1,1,1,1
1 id name model_id:id group_id:id perm_read perm_write perm_create perm_unlink
110 public_access_test_new_api_course access_test_new_api_course model_test_new_api_course base.group_public 1 0 0 0
111 access_test_new_api_team access_test_new_api_team model_test_new_api_team base.group_user 1 0 0 0
112 access_test_new_api_team_member access_test_new_api_team_member model_test_new_api_team_member base.group_user 1 0 0 0
113 access_test_new_api_unsearchable_o2m access_test_new_api_unsearchable_o2m model_test_new_api_unsearchable_o2m 1 1 1 1
@@ -2,6 +2,7 @@
from odoo.tests.common import TransactionCase
from odoo.exceptions import MissingError
from odoo import Command
from odoo.tools import mute_logger
class One2manyCase(TransactionCase):
@@ -434,3 +435,48 @@ class One2manyCase(TransactionCase):
# Check that the search is not stuck in the loop
Team.search([('id', 'parent_of', team1.id)])
Team.search([('id', 'child_of', team1.id)])
@mute_logger('odoo.osv.expression')
def test_create_one2many_with_unsearchable_field(self):
# odoo.osv.expression is muted as reading a non-stored and unsearchable field will log an error and makes the runbot red
unsearchableO2M = self.env['test_new_api.unsearchable.o2m']
# Create a parent record
parent_record1 = unsearchableO2M.create({
'name': 'Parent 1',
})
# Create another parent record
parent_record2 = unsearchableO2M.create({
'name': 'Parent 2',
})
children = {parent_record1.id : [], parent_record2.id : []}
# Create child records linked to parent_record1
for i in range(5):
child = unsearchableO2M.create({
'name': f'Child {i}',
'stored_parent_id': parent_record1.id,
'parent_id': parent_record1.id,
})
self.assertEqual(child.parent_id, parent_record1)
children[parent_record1.id].append(child.id)
# Create child records linked to parent_record2
for i in range(5, 10):
child = unsearchableO2M.create({
'name': f'Child {i}',
'stored_parent_id': parent_record2.id,
'parent_id': parent_record2.id,
})
self.assertEqual(child.parent_id, parent_record2)
children[parent_record2.id].append(child.id)
# invalidating the cache to force reading one2many again
self.env.invalidate_all()
# Make sure the parent_record1 only has its own child records
self.assertEqual(parent_record1.child_ids.ids, children[parent_record1.id])
# Make sure the parent_record2 only has its own child records
self.assertEqual(parent_record2.child_ids.ids, children[parent_record2.id])