You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

124 lines
4.2 KiB

8 years ago
  1. # Copyright 2014-2016 Therp BV <http://therp.nl>
  2. # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).
  3. # pylint: disable=consider-merging-classes-inherited
  4. from odoo import _, api, models, fields
  5. from odoo.exceptions import UserError
  6. from odoo.addons.base.models.ir_model import MODULE_UNINSTALL_FLAG
  7. class IrModel(models.Model):
  8. _inherit = 'ir.model'
  9. def _drop_table(self):
  10. """this function crashes for undefined models"""
  11. existing_model_ids = self.filtered(lambda x: x.model in self.env)
  12. return super(IrModel, existing_model_ids)._drop_table()
  13. @api.depends()
  14. def _inherited_models(self):
  15. """this function crashes for undefined models"""
  16. existing_model_ids = self.filtered(lambda x: x.model in self.env)
  17. super(IrModel, existing_model_ids)._inherited_models()
  18. class IrModelFields(models.Model):
  19. _inherit = 'ir.model.fields'
  20. @api.multi
  21. def _prepare_update(self):
  22. """this function crashes for undefined models"""
  23. existing = self.filtered(lambda x: x.model in self.env)
  24. return super(IrModelFields, existing)._prepare_update()
  25. class CleanupPurgeLineModel(models.TransientModel):
  26. _inherit = 'cleanup.purge.line'
  27. _name = 'cleanup.purge.line.model'
  28. _description = 'Purge models'
  29. wizard_id = fields.Many2one(
  30. 'cleanup.purge.wizard.model', 'Purge Wizard', readonly=True)
  31. @api.multi
  32. def purge(self):
  33. """
  34. Unlink models upon manual confirmation.
  35. """
  36. context_flags = {
  37. MODULE_UNINSTALL_FLAG: True,
  38. 'purge': True,
  39. }
  40. if self:
  41. objs = self
  42. else:
  43. objs = self.env['cleanup.purge.line.model']\
  44. .browse(self._context.get('active_ids'))
  45. for line in objs:
  46. self.env.cr.execute(
  47. "SELECT id, model from ir_model WHERE model = %s",
  48. (line.name,))
  49. row = self.env.cr.fetchone()
  50. if not row:
  51. continue
  52. self.logger.info('Purging model %s', row[1])
  53. attachments = self.env['ir.attachment'].search([
  54. ('res_model', '=', line.name)
  55. ])
  56. if attachments:
  57. self.env.cr.execute(
  58. "UPDATE ir_attachment SET res_model = NULL "
  59. "WHERE id in %s",
  60. (tuple(attachments.ids), ))
  61. self.env['ir.model.constraint'].search([
  62. ('model', '=', line.name),
  63. ]).unlink()
  64. cronjobs = self.env['ir.cron'].with_context(
  65. active_test=False
  66. ).search([
  67. ('model_id.model', '=', line.name),
  68. ])
  69. if cronjobs:
  70. cronjobs.unlink()
  71. relations = self.env['ir.model.fields'].search([
  72. ('relation', '=', row[1]),
  73. ]).with_context(**context_flags)
  74. for relation in relations:
  75. try:
  76. # Fails if the model on the target side
  77. # cannot be instantiated
  78. relation.unlink()
  79. except KeyError:
  80. pass
  81. except AttributeError:
  82. pass
  83. self.env['ir.model.relation'].search([
  84. ('model', '=', line.name)
  85. ]).with_context(**context_flags).unlink()
  86. self.env['ir.model'].browse([row[0]])\
  87. .with_context(**context_flags).unlink()
  88. line.write({'purged': True})
  89. return True
  90. class CleanupPurgeWizardModel(models.TransientModel):
  91. _inherit = 'cleanup.purge.wizard'
  92. _name = 'cleanup.purge.wizard.model'
  93. _description = 'Purge models'
  94. @api.model
  95. def find(self):
  96. """
  97. Search for models that cannot be instantiated.
  98. """
  99. res = []
  100. self.env.cr.execute("SELECT model from ir_model")
  101. for model, in self.env.cr.fetchall():
  102. if model not in self.env:
  103. res.append((0, 0, {'name': model}))
  104. if not res:
  105. raise UserError(_('No orphaned models found'))
  106. return res
  107. purge_line_ids = fields.One2many(
  108. 'cleanup.purge.line.model', 'wizard_id', 'Models to purge')