diff --git a/odoo/addons/base/models/ir_actions_report.py b/odoo/addons/base/models/ir_actions_report.py index 4c4a5610a06..dd2aef301c3 100644 --- a/odoo/addons/base/models/ir_actions_report.py +++ b/odoo/addons/base/models/ir_actions_report.py @@ -794,6 +794,7 @@ class IrActionsReport(models.Model): if (tools.config['test_enable'] or tools.config['test_file']) and not self.env.context.get('force_report_rendering'): return self._render_qweb_html(report_ref, res_ids, data=data) + self = self.with_context(webp_as_jpg=True) collected_streams = self._render_qweb_pdf_prepare_streams(report_ref, data, res_ids=res_ids) # access the report details with sudo() but keep evaluation context as current user diff --git a/odoo/addons/base/models/ir_qweb.py b/odoo/addons/base/models/ir_qweb.py index 71a17884eec..f19f77f6132 100644 --- a/odoo/addons/base/models/ir_qweb.py +++ b/odoo/addons/base/models/ir_qweb.py @@ -359,6 +359,7 @@ structure. """ +import base64 import fnmatch import io import logging @@ -384,7 +385,7 @@ from odoo.tools.constants import SUPPORTED_DEBUGGER, EXTERNAL_ASSET from odoo.tools.safe_eval import assert_valid_codeobj, _BUILTINS, to_opcodes, _EXPR_OPCODES, _BLACKLIST from odoo.tools.json import scriptsafe from odoo.tools.misc import str2bool -from odoo.tools.image import image_data_uri +from odoo.tools.image import image_data_uri, FILETYPE_BASE64_MAGICWORD from odoo.http import request from odoo.tools.profiler import QwebTracker from odoo.exceptions import UserError, AccessDenied, AccessError, MissingError, ValidationError @@ -861,6 +862,24 @@ class IrQWeb(models.AbstractModel): # values for running time + def _get_converted_image_data_uri(self, base64_source): + if self.env.context.get('webp_as_jpg'): + mimetype = FILETYPE_BASE64_MAGICWORD.get(base64_source[:1], 'png') + if 'webp' in mimetype: + # Use converted image so that is recognized by wkhtmltopdf. + bin_source = base64.b64decode(base64_source) + Attachment = self.env['ir.attachment'] + checksum = Attachment._compute_checksum(bin_source) + origins = Attachment.search([['res_field', '!=', None], ['checksum', '=', checksum]]) + if origins: + converted = Attachment.search([ + ['res_model', '=', 'ir.attachment'], + ['res_id', 'in', origins.ids], + ], limit=1) + if converted: + base64_source = converted.datas + return image_data_uri(base64_source) + def _prepare_environment(self, values): """ Prepare the values and context that will sent to the compiled and evaluated function. @@ -878,7 +897,6 @@ class IrQWeb(models.AbstractModel): values.setdefault('debug', debug) values.setdefault('user_id', self.env.user.with_env(self.env)) values.setdefault('res_company', self.env.company.sudo()) - values.update( request=request, # might be unbound if we're not in an httprequest context test_mode_enabled=bool(config['test_enable'] or config['test_file']), @@ -887,7 +905,7 @@ class IrQWeb(models.AbstractModel): time=safe_eval.time, datetime=safe_eval.datetime, relativedelta=relativedelta, - image_data_uri=image_data_uri, + image_data_uri=self._get_converted_image_data_uri, # specific 'math' functions to ease rounding in templates and lessen controller marshmalling floor=math.floor, ceil=math.ceil,