Merge lp:~openerp-dev/openobject-server/6.0-opw-4630-jvo into lp:openobject-server/6.0

Proposed by Jay Vora (Serpent Consulting Services)
Status: Merged
Merged at revision: 3376
Proposed branch: lp:~openerp-dev/openobject-server/6.0-opw-4630-jvo
Merge into: lp:openobject-server/6.0
Diff against target: 61 lines (+24/-1)
2 files modified
bin/addons/base/ir/ir_model.py (+6/-1)
bin/osv/orm.py (+18/-0)
To merge this branch: bzr merge lp:~openerp-dev/openobject-server/6.0-opw-4630-jvo
Reviewer Review Type Date Requested Status
Olivier Dony (Odoo) Approve
Jay Vora (Serpent Consulting Services) final review Pending
Review via email: mp+54355@code.launchpad.net
To post a comment you must log in.
Revision history for this message
Olivier Dony (Odoo) (odo-openerp) wrote :

Something I missed in my first look: the search on ir.values should instead rely on the 'value' column, which will hold the reference in the form 'ir.actions.act_window,42', while the 'model' column is in fact related to the object to which that ir.values entry related too.

Here's an illustration:
=> select id,key2,model,value from ir_values where model = 'res.partner' limit 1;
 id | key2 | model | value
----+--------------------+-------------+--------------------------
 49 | client_print_multi | res.partner | ir.actions.report.xml,56

So we'll want to do something like:

ir_value_ids = pool_ir_values.search(cr, uid,
           [('value','in',['%s,%s' % (self._name,sid) for sid in sub_ids])],
           context=context)
pool_ir_values.unlink(cr, uid, ir_value_ids, context=context)

review: Needs Fixing
Revision history for this message
Olivier Dony (Odoo) (odo-openerp) wrote :

Another thing I noticed is that we don't check whether the browse_record that is returned in get_object() actually corresponds to a valid record. Indeed you can create a browse_record for an ID that does not exist, and it will only raise errors when you really access its data.

To be consistent, we need to check this as well and raise a ValueError in that case.

I'm going to add a little patch for that.

review: Needs Fixing
Revision history for this message
Olivier Dony (Odoo) (odo-openerp) wrote :

Jay, would you please double-check this branch after the latest patches?
To me it looks ok now, but I'll let you merge it after a last check.

review: Approve
Revision history for this message
Jay Vora (Serpent Consulting Services) (jayvora) wrote :

Olivier, Sure I will do some tests and will end this proposal into a commit :).

Revision history for this message
Jay Vora (Serpent Consulting Services) (jayvora) wrote :

Olivier,

Thanks for the peer review and discussion over this topic which has ended into an exemplary commit.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'bin/addons/base/ir/ir_model.py'
2--- bin/addons/base/ir/ir_model.py 2011-01-20 16:27:06 +0000
3+++ bin/addons/base/ir/ir_model.py 2011-03-23 19:21:36 +0000
4@@ -608,12 +608,17 @@
5 """Returns (model, res_id) corresponding to a given module and xml_id (cached) or raise ValueError if not found"""
6 data_id = self._get_id(cr, uid, module, xml_id)
7 res = self.read(cr, uid, data_id, ['model', 'res_id'])
8+ if not res['res_id']:
9+ raise ValueError('No references to %s.%s' % (module, xml_id))
10 return (res['model'], res['res_id'])
11
12 def get_object(self, cr, uid, module, xml_id, context=None):
13 """Returns a browsable record for the given module name and xml_id or raise ValueError if not found"""
14 res_model, res_id = self.get_object_reference(cr, uid, module, xml_id)
15- return self.pool.get(res_model).browse(cr, uid, res_id, context=context)
16+ result = self.pool.get(res_model).browse(cr, uid, res_id, context=context)
17+ if not result.exists():
18+ raise ValueError('No record found for unique ID %s.%s. It may have been deleted.' % (module, xml_id))
19+ return result
20
21 def _update_dummy(self,cr, uid, model, module, xml_id=False, store=True):
22 if not xml_id:
23
24=== modified file 'bin/osv/orm.py'
25--- bin/osv/orm.py 2011-03-11 08:27:20 +0000
26+++ bin/osv/orm.py 2011-03-23 19:21:36 +0000
27@@ -3227,9 +3227,26 @@
28
29
30 self.check_access_rule(cr, uid, ids, 'unlink', context=context)
31+ pool_model_data = self.pool.get('ir.model.data')
32+ pool_ir_values = self.pool.get('ir.values')
33 for sub_ids in cr.split_for_in_conditions(ids):
34 cr.execute('delete from ' + self._table + ' ' \
35 'where id IN %s', (sub_ids,))
36+
37+ # Removing the ir_model_data reference if the record being deleted is a record created by xml/csv file,
38+ # as these are not connected with real database foreign keys, and would be dangling references.
39+ # Step 1. Calling unlink of ir_model_data only for the affected IDS.
40+ referenced_ids = pool_model_data.search(cr, uid, [('res_id','in',list(sub_ids)),('model','=',self._name)], context=context)
41+ # Step 2. Marching towards the real deletion of referenced records
42+ pool_model_data.unlink(cr, uid, referenced_ids, context=context)
43+
44+ # For the same reason, removing the record relevant to ir_values
45+ ir_value_ids = pool_ir_values.search(cr, uid,
46+ ['|',('value','in',['%s,%s' % (self._name, sid) for sid in sub_ids]),'&',('res_id','in',list(sub_ids)),('model','=',self._name)],
47+ context=context)
48+ if ir_value_ids:
49+ pool_ir_values.unlink(cr, uid, ir_value_ids, context=context)
50+
51 for order, object, store_ids, fields in result_store:
52 if object != self._name:
53 obj = self.pool.get(object)
54@@ -3237,6 +3254,7 @@
55 rids = map(lambda x: x[0], cr.fetchall())
56 if rids:
57 obj._store_set_values(cr, uid, rids, fields, context)
58+
59 return True
60
61 #