See discussions on https://github.com/odoo/odoo/pull/85494/. TLDR: webp image format needs to be supported, but we should avoid going through the Pillow library as it is largely unsafe for that format. jpg attachment are created in JS at upload time. Wkhtmltopdf doesn't support webp, so, in reports, we should display one of those jpg copies. This work is handled by `ir.qweb: _get_converted_image_data_uri` which is used as: ```xml <img src="image_data_uri(some_b64value)" /> ``` The mentioned PR did not however adapt the ir.qweb.field.image that, when passed the option `qweb_img_raw_data` should return a base64 url such as `data:[mimetype],base64,[datas]`. usage: ```xml <span t-field="object.image_field" t-options-widget="'image'" t-options-qweb_img_raw_data="1" /> ``` Hence, before this commit, there was a crash as we tried to pass that value to PIL. After this commit, there is no crash, and the image displays correctly as JPG in the PDF opw-3859423 closes odoo/odoo#163003 X-original-commit: 9056a4b1f28e820c0444f28367cc30abebd5ea30 Signed-off-by: Benoit Socias (bso) <bso@odoo.com> Signed-off-by: Lucas Perais (lpe) <lpe@odoo.com>
75 lines
3.3 KiB
Python
75 lines
3.3 KiB
Python
import base64
|
|
from lxml import etree
|
|
|
|
from odoo.tests.common import TransactionCase
|
|
from odoo.tools.mimetypes import guess_mimetype
|
|
|
|
class TestIrQweb(TransactionCase):
|
|
def test_image_field(self):
|
|
view = self.env["ir.ui.view"].create({
|
|
"key": "web.test_qweb",
|
|
"type": "qweb",
|
|
"arch": """<t t-name="test_qweb">
|
|
<span t-field="record.avatar_128" t-options-widget="'image'" t-options-qweb_img_raw_data="is_raw_image" />
|
|
</t>"""
|
|
})
|
|
partner = self.env["res.partner"].create({
|
|
"name": "test image partner",
|
|
"image_128": "iVBORw0KGgoAAAANSUhEUgAAAAIAAAACCAIAAAD91JpzAAAAF0lEQVR4nGJxKFrEwMDAxAAGgAAAAP//D+IBWx9K7TUAAAAASUVORK5CYII=",
|
|
})
|
|
|
|
html = view._render_template(view.id, {"is_raw_image": True, "record": partner})
|
|
tree = etree.fromstring(html)
|
|
img = tree.find("img")
|
|
self.assertTrue(img.get("src").startswith("data:image/png;base64"))
|
|
self.assertEqual(img.get("class"), "img img-fluid")
|
|
self.assertEqual(img.get("alt"), "test image partner")
|
|
|
|
html = view._render_template(view.id, {"is_raw_image": False, "record": partner})
|
|
tree = etree.fromstring(html)
|
|
img = tree.find("img")
|
|
self.assertTrue(img.get("src").startswith("/web/image"))
|
|
self.assertEqual(img.get("class"), "img img-fluid")
|
|
self.assertEqual(img.get("alt"), "test image partner")
|
|
|
|
def test_image_field_webp(self):
|
|
webp = "UklGRsCpAQBXRUJQVlA4WAoAAAAQAAAAGAQA/wMAQUxQSMywAAAdNANp22T779/0RUREkvqLOTPesG1T21jatpLTSbpXQzTMEw3zWMM81jCPnWG2fTM7vpndvpkd38y2758Y+6a/Ld/Mt3zzT/XwzCKlV0Ooo61UpZIsKLjKc98R"
|
|
webp_decoded = base64.b64decode(webp)
|
|
self.assertEqual(guess_mimetype(webp_decoded), "image/webp")
|
|
|
|
view = self.env["ir.ui.view"].create({
|
|
"key": "web.test_qweb",
|
|
"type": "qweb",
|
|
"arch": """<t t-name="test_qweb">
|
|
<span t-field="record.flag_image" t-options-widget="'image'" t-options-qweb_img_raw_data="is_raw_image" />
|
|
</t>"""
|
|
})
|
|
lang_record = self.env["res.lang"].create({
|
|
"name": "test lang",
|
|
"flag_image": webp,
|
|
"code": "TEST"
|
|
})
|
|
attachment = self.env["ir.attachment"].search([
|
|
("res_model", "=", "res.lang"),
|
|
("res_id", '=', lang_record.id),
|
|
("res_field", "=", "flag_image")
|
|
])
|
|
|
|
jpeg_attach = self.env["ir.attachment"].create({
|
|
"name": "webpcopy.jpg",
|
|
"res_model": "ir.attachment",
|
|
"res_id": attachment.id,
|
|
"datas": "iVBORw0KGgoAAAANSUhEUgAAAAIAAAACCAIAAAD91JpzAAAAF0lEQVR4nGJxKFrEwMDAxAAGgAAAAP//D+IBWx9K7TUAAAAASUVORK5CYII="
|
|
})
|
|
jpeg_datas = jpeg_attach.datas
|
|
|
|
html = view.with_context(webp_as_jpg=False)._render_template(view.id, {"is_raw_image": True, "record": lang_record})
|
|
tree = etree.fromstring(html)
|
|
img = tree.find("img")
|
|
self.assertEqual(img.get("src"), "data:image/webp;base64,%s" % webp)
|
|
|
|
html = view.with_context(webp_as_jpg=True)._render_template(view.id, {"is_raw_image": True, "record": lang_record})
|
|
tree = etree.fromstring(html)
|
|
img = tree.find("img")
|
|
self.assertEqual(img.get("src"), "data:image/png;base64,%s" % jpeg_datas.decode())
|