Repository: OCA/server-tools

Issue:
[9.0][database_cleanup] model purge broken
I think purging models not longer works, because of this : https://github.com/OCA/OCB/blob/9.0/openerp/addons/base/ir/ir_model.py#L147

Any ideas on how we could have it fix?
@hbrunn 




Discussion:
you might want to elaborate on what the actual problem is

The models we want to delete are old ones and are not declared in the current available modules, so they are not loaded.
In the _prepare_update method, Odoo tries to access the model with `self.env[record.model]` which fails.

So we get an error of this kind : 

  File "/opt/ostore/odoo/parts/server-tools/database_cleanup/models/purge_models.py", line 94, in purge
    .with_context(*_context_flags).unlink()
  File "/opt/ostore/odoo/parts/odoo/openerp/api.py", line 248, in wrapper
    return new_api(self, *args, *_kwargs)
  File "/opt/ostore/odoo/parts/odoo/openerp/api.py", line 574, in new_api
    result = method(self._model, cr, uid, self.ids, _args, *_old_kwargs)
  File "/opt/ostore/odoo/parts/odoo/openerp/addons/base/ir/ir_model.py", line 147, in unlink
    model.field_id._prepare_update()
  File "/opt/ostore/odoo/parts/odoo/openerp/api.py", line 248, in wrapper
    return new_api(self, _args, *_kwargs)
  File "/opt/ostore/odoo/parts/odoo/openerp/addons/base/ir/ir_model.py", line 445, in _prepare_update
    model = self.env[record.model]
  File "/opt/ostore/odoo/parts/odoo/openerp/api.py", line 768, in __getitem__
    return self.registry[model_name]._browse(self, ())
  File "/opt/ostore/odoo/parts/odoo/openerp/modules/registry.py", line 84, in __getitem__
    return self.models[model_name]
ValueError: "res.partner.address" while evaluating
u"self.purge(cr, uid, context.get('active_ids', []), context)"

now this is a message to work with. I'd suggest to override https://github.com/OCA/OCB/blob/9.0/openerp/addons/base/ir/ir_model.py#L439 in a way such that it does nothing if the model in question isn't available. Repeat for succeeding functions with similar behavior, and comment lavishly


Resolving patch:
diff --git a/database_cleanup/models/__init__.py b/database_cleanup/models/__init__.py
--- a/database_cleanup/models/__init__.py
+++ b/database_cleanup/models/__init__.py
@@ -5,3 +5,4 @@
 from . import purge_tables
 from . import purge_data
 from . import purge_menus
+from . import ir_model_fields
diff --git a/database_cleanup/models/ir_model_fields.py b/database_cleanup/models/ir_model_fields.py
new file mode 100644
--- /dev/null
+++ b/database_cleanup/models/ir_model_fields.py
@@ -0,0 +1,17 @@
+# -*- coding: utf-8 -*-
+# © 2014-2016 Therp BV <http://therp.nl>
+# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).
+from openerp import api, models
+
+
+class IrModelFields(models.Model):
+    _inherit = 'ir.model.fields'
+
+    # In case of purging it means the model does not exist anymore in
+    # installed module. In this specific case, we need to avoid to check
+    # if fields can be removed as it would fail.
+    @api.multi
+    def _prepare_update(self):
+        if self.env.context.get('purge'):
+            self -= self.filtered(lambda x: x.model not in self.env.registry)
+        return super(IrModelFields, self)._prepare_update()
diff --git a/database_cleanup/models/purge_models.py b/database_cleanup/models/purge_models.py
--- a/database_cleanup/models/purge_models.py
+++ b/database_cleanup/models/purge_models.py
@@ -54,6 +54,7 @@ def purge(self):
         context_flags = {
             MODULE_UNINSTALL_FLAG: True,
             'no_drop_table': True,
+            'purge': True,
         }
 
         for line in self:


Test patch: