[FIX] base: call dedicated method for regenerating assets bundles

__Current behavior before commit:__
The logic to regenerate assets bundles is located in the frontend (i.e.
the JS is making the calls to retrieve and unlink them) which is not
very clean.

Furthermore, when doing so, the old assets might still be included on
cached views that called them with `t-call-assets`.

Therefore, regenerating assets bundles can break the CSS or the JS as
long as the view cache is not cleared.

__Description of the fix:__
A new backend method is implemented for regenerating asset bundles.
This provides a dedicated and maintainable approach. Additionally, the
cache is explicitly cleared during the regeneration process.

__Example of steps to reproduce the issue on runbot:__
1. Check `Disable cache` in chrome dev tools.
1. Little bug icon > Regenerate Assets Bundles

closes odoo/odoo#145279

X-original-commit: b8e1f9f880e4723ddbe595043d22b565ad735832
Signed-off-by: Xavier Dollé (xdo) <xdo@odoo.com>
Signed-off-by: Julien Launois (jula) <jula@odoo.com>
This commit is contained in:
Julien (jula)
2023-12-07 10:07:58 +00:00
parent c569a0d41b
commit ad702c20b1
3 changed files with 19 additions and 17 deletions
@@ -32,15 +32,10 @@ export function regenerateAssets({ env }) {
type: "item",
description: _t("Regenerate Assets Bundles"),
callback: async () => {
const domain = [
"&",
["res_model", "=", "ir.ui.view"],
"|",
["name", "=like", "%.assets_%.css"],
["name", "=like", "%.assets_%.js"],
];
const ids = await env.services.orm.search("ir.attachment", domain);
await env.services.orm.unlink("ir.attachment", ids);
await env.services.orm.call(
"ir.attachment",
"regenerate_assets_bundles",
);
browser.location.reload();
},
sequence: 430,
@@ -270,12 +270,8 @@ QUnit.module("DebugMenu", (hooks) => {
if (args.method === "check_access_rights") {
return Promise.resolve(true);
}
if (route === "/web/dataset/call_kw/ir.attachment/search") {
assert.step("ir.attachment/search");
return [1, 2, 3];
}
if (route === "/web/dataset/call_kw/ir.attachment/unlink") {
assert.step("ir.attachment/unlink");
if (route === "/web/dataset/call_kw/ir.attachment/regenerate_assets_bundles") {
assert.step("ir.attachment/regenerate_assets_bundles");
return Promise.resolve(true);
}
};
@@ -293,7 +289,7 @@ QUnit.module("DebugMenu", (hooks) => {
const item = target.querySelector(".dropdown-menu .dropdown-item");
assert.strictEqual(item.textContent, "Regenerate Assets Bundles");
await click(item);
assert.verifySteps(["ir.attachment/search", "ir.attachment/unlink", "reloadPage"]);
assert.verifySteps(["ir.attachment/regenerate_assets_bundles", "reloadPage"]);
});
QUnit.test("can open a view", async (assert) => {
+12 -1
View File
@@ -16,7 +16,7 @@ import uuid
from collections import defaultdict
from PIL import Image
from odoo import api, fields, models, tools, _
from odoo import api, fields, models, SUPERUSER_ID, tools, _
from odoo.exceptions import AccessError, ValidationError, UserError
from odoo.tools import config, human_size, ImageProcess, str2bool, consteq
from odoo.tools.mimetypes import guess_mimetype
@@ -729,3 +729,14 @@ class IrAttachment(models.Model):
def _get_serve_attachment(self, url, extra_domain=None, order=None):
domain = [('type', '=', 'binary'), ('url', '=', url)] + (extra_domain or [])
return self.search(domain, order=order, limit=1)
@api.model
def regenerate_assets_bundles(self):
self.search([
('public', '=', True),
("url", "=like", "/web/assets/%"),
('res_model', '=', 'ir.ui.view'),
('res_id', '=', 0),
('create_uid', '=', SUPERUSER_ID),
]).unlink()
self.clear_caches()