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.

104 lines
3.7 KiB

  1. # coding: utf-8
  2. # @ 2015 Florian DA COSTA @ Akretion
  3. # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).
  4. from openerp import models, fields, api, _
  5. from openerp.exceptions import Warning as UserError
  6. import openerp
  7. import hashlib
  8. from base64 import b64decode
  9. import logging
  10. _logger = logging.getLogger(__name__)
  11. class IrAttachmentMetadata(models.Model):
  12. _name = 'ir.attachment.metadata'
  13. _inherits = {'ir.attachment': 'attachment_id'}
  14. _inherit = ['mail.thread']
  15. internal_hash = fields.Char(
  16. store=True, compute='_compute_hash',
  17. help="File hash computed with file data to be compared "
  18. "to external hash when provided.")
  19. external_hash = fields.Char(
  20. help="File hash comes from the external owner of the file.\n"
  21. "If provided allow to check than downloaded file "
  22. "is the exact copy of the original file.")
  23. attachment_id = fields.Many2one(
  24. 'ir.attachment', required=True, ondelete='cascade',
  25. help="Link to ir.attachment model ")
  26. file_type = fields.Selection(
  27. selection=[],
  28. string="File type",
  29. help="The file type determines an import method to be used "
  30. "to parse and transform data before their import in ERP or an export")
  31. sync_date = fields.Datetime()
  32. state = fields.Selection([
  33. ('pending', 'Pending'),
  34. ('failed', 'Failed'),
  35. ('done', 'Done'),
  36. ], readonly=False, required=True, default='pending')
  37. state_message = fields.Text()
  38. @api.depends('datas', 'external_hash')
  39. def _compute_hash(self):
  40. for attachment in self:
  41. if attachment.datas:
  42. attachment.internal_hash = hashlib.md5(
  43. b64decode(attachment.datas)).hexdigest()
  44. if attachment.external_hash and\
  45. attachment.internal_hash != attachment.external_hash:
  46. raise UserError(
  47. _("File corrupted: Something was wrong with "
  48. "the retrieved file, please relaunch the task."))
  49. @api.model
  50. def run_attachment_metadata_scheduler(self, domain=None):
  51. if domain is None:
  52. domain = []
  53. domain.append(('state', '=', 'pending'))
  54. attachments = self.search(domain)
  55. if attachments:
  56. return attachments.run()
  57. return True
  58. @api.multi
  59. def run(self):
  60. """
  61. Run the process for each attachment metadata
  62. """
  63. for attachment in self:
  64. with api.Environment.manage():
  65. with openerp.registry(self.env.cr.dbname).cursor() as new_cr:
  66. new_env = api.Environment(
  67. new_cr, self.env.uid, self.env.context)
  68. attach = attachment.with_env(new_env)
  69. try:
  70. attach._run()
  71. except Exception, e:
  72. attach.env.cr.rollback()
  73. _logger.exception(e)
  74. attach.write(
  75. {
  76. 'state': 'failed',
  77. 'state_message': e,
  78. })
  79. attach.env.cr.commit()
  80. else:
  81. attach.write({'state': 'done'})
  82. attach.env.cr.commit()
  83. return True
  84. @api.multi
  85. def _run(self):
  86. self.ensure_one()
  87. _logger.info('Start to process attachment metadata id %s' % self.id)
  88. @api.multi
  89. def set_done(self):
  90. """
  91. Manually set to done
  92. """
  93. message = "Manually set to done by %s" % self.env.user.name
  94. self.write({'state_message': message, 'state': 'done'})