From 47f0eafe9ab2b979690763a639d07bee392ec258 Mon Sep 17 00:00:00 2001 From: Thomas Rehn Date: Thu, 25 Aug 2016 08:02:46 +0200 Subject: [PATCH] [IMP] rewrite get_binary_extension so that it uses a first pass to determine the extension from the filename only --- attachment_preview/__openerp__.py | 2 +- attachment_preview/model/ir_attachment.py | 68 +++++++++++++---------- 2 files changed, 40 insertions(+), 30 deletions(-) diff --git a/attachment_preview/__openerp__.py b/attachment_preview/__openerp__.py index fa62e146..62eda094 100644 --- a/attachment_preview/__openerp__.py +++ b/attachment_preview/__openerp__.py @@ -20,7 +20,7 @@ ############################################################################## { "name": "Preview attachments", - "version": "8.0.1.1.0", + "version": "8.0.1.2.0", "author": "Therp BV,Odoo Community Association (OCA)", "license": "AGPL-3", "complexity": "normal", diff --git a/attachment_preview/model/ir_attachment.py b/attachment_preview/model/ir_attachment.py index b00d3474..da8c86d7 100644 --- a/attachment_preview/model/ir_attachment.py +++ b/attachment_preview/model/ir_attachment.py @@ -32,35 +32,45 @@ class IrAttachment(Model): self, cr, uid, model, ids, binary_field, filename_field=None, context=None): result = {} - for this in self.pool[model].browse( - cr, uid, - ids if isinstance(ids, collections.Iterable) else [ids], - context=context): - if not this.id: - result[this.id] = False - continue - extension = '' - if filename_field and this[filename_field]: - filename, extension = os.path.splitext(this[filename_field]) - if not this[binary_field]: - result[this.id] = False - continue - if not extension: - try: - import magic - ms = magic.open( - hasattr(magic, 'MAGIC_MIME_TYPE') and - magic.MAGIC_MIME_TYPE or magic.MAGIC_MIME) - ms.load() - mimetype = ms.buffer( - base64.b64decode(this[binary_field])) - except ImportError: - (mimetype, encoding) = mimetypes.guess_type( - 'data:;base64,' + this[binary_field], strict=False) - extension = mimetypes.guess_extension( - mimetype.split(';')[0], strict=False) - - result[this.id] = (extension or '').lstrip('.').lower() + context_bin_size = dict(context or {}) + context_bin_size['bin_size'] = True + ids_to_browse = ids if isinstance(ids, collections.Iterable) \ + else [ids] + # First pass: load fields in bin_size mode to avoid loading big files + # unnecessarily. + if filename_field: + for this in self.pool[model].browse(cr, uid, ids_to_browse, + context=context_bin_size): + if not this.id: + result[this.id] = False + continue + extension = '' + if this[filename_field]: + filename, extension = os.path.splitext( + this[filename_field]) + if this[binary_field] and extension: + result[this.id] = extension + # Second pass for all attachments which have to be loaded fully + # to get the extension from the content + ids_to_browse = [_id for _id in ids_to_browse if _id not in result] + for this in self.pool[model].browse(cr, uid, ids_to_browse, + context=context): + try: + import magic + ms = magic.open( + hasattr(magic, 'MAGIC_MIME_TYPE') and + magic.MAGIC_MIME_TYPE or magic.MAGIC_MIME) + ms.load() + mimetype = ms.buffer( + base64.b64decode(this[binary_field])) + except ImportError: + (mimetype, encoding) = mimetypes.guess_type( + 'data:;base64,' + this[binary_field], strict=False) + extension = mimetypes.guess_extension( + mimetype.split(';')[0], strict=False) + result[this.id] = extension + for _id in result: + result[_id] = (extension or '').lstrip('.').lower() return result if isinstance(ids, collections.Iterable) else result[ids] def get_attachment_extension(self, cr, uid, ids, context=None):