From f54b9a4a0cbdd5bb6088b15218e73d5b4a9731c8 Mon Sep 17 00:00:00 2001 From: Ivan Yelizariev Date: Wed, 2 Dec 2020 15:18:02 +0100 Subject: [PATCH] [FIX] properly translate terms surrounded by spaces This reimplements logic from Odoo v13 [1], i.e. if we have a text that follows by space e.g. "This database will expire in " [2], then we want get translation for the term without that space and add the space manually. This way we can export trimmed terms for translations and don't miss the space, when atranslator forget to add it at the end of translation [1] https://github.com/odoo/odoo/blob/26927417e2957acba6fb79446c2520107daa7eea/addons/web/static/src/js/core/qweb.js#L46 [2] https://github.com/odoo/enterprise/blob/ab0e893493f909ec3033e8a1cf6c141ea9375587/web_enterprise/static/src/xml/base.xml#L21 --- opw-2410708 --- src/qweb/qweb.ts | 4 +++- tests/qweb/__snapshots__/qweb.test.ts.snap | 12 ++++++++++++ tests/qweb/qweb.test.ts | 11 +++++++++++ 3 files changed, 26 insertions(+), 1 deletion(-) diff --git a/src/qweb/qweb.ts b/src/qweb/qweb.ts index f6b7c830..cf6cce9c 100644 --- a/src/qweb/qweb.ts +++ b/src/qweb/qweb.ts @@ -70,6 +70,7 @@ const TRANSLATABLE_ATTRS = ["label", "title", "placeholder", "alt"]; const lineBreakRE = /[\r\n]/; const whitespaceRE = /\s+/g; +const translationRE = /^(\s*)([\s\S]+?)(\s*)$/; const NODE_HOOKS_PARAMS = { create: "(_, n)", @@ -496,7 +497,8 @@ export class QWeb extends EventBus { } if (this.translateFn) { if ((node.parentNode as any).getAttribute("t-translation") !== "off") { - text = this.translateFn(text); + const match = translationRE.exec(text); + text = match[1] + this.translateFn(match[2]) + match[3]; } } if (ctx.parentNode) { diff --git a/tests/qweb/__snapshots__/qweb.test.ts.snap b/tests/qweb/__snapshots__/qweb.test.ts.snap index 9f9a0b75..8016dd76 100644 --- a/tests/qweb/__snapshots__/qweb.test.ts.snap +++ b/tests/qweb/__snapshots__/qweb.test.ts.snap @@ -3924,6 +3924,18 @@ exports[`translation support some attributes are translated 1`] = ` }" `; +exports[`translation support translation is done on the trimmed text, with extra spaces readded after 1`] = ` +"function anonymous(context, extra +) { + // Template name: \\"test\\" + let h = this.h; + let c1 = [], p1 = {key:1}; + let vn1 = h('div', p1, c1); + c1.push({text: \` mot \`}); + return vn1; +}" +`; + exports[`whitespace handling consecutives whitespaces are condensed into a single space 1`] = ` "function anonymous(context, extra ) { diff --git a/tests/qweb/qweb.test.ts b/tests/qweb/qweb.test.ts index 80976074..f624b808 100644 --- a/tests/qweb/qweb.test.ts +++ b/tests/qweb/qweb.test.ts @@ -2154,6 +2154,17 @@ describe("translation support", () => { '

mot

mot

mot

mot

mot

' ); }); + + test("translation is done on the trimmed text, with extra spaces readded after", () => { + const translations = { + word: "mot", + }; + const translateFn = jest.fn((expr) => translations[expr] || expr); + const qweb = new QWeb({ translateFn }); + qweb.addTemplate("test", "
word
"); + expect(renderToString(qweb, "test")).toBe("
mot
"); + expect(translateFn).toHaveBeenCalledWith("word"); + }); }); describe("t-key tests", () => {