From 326a44c3f7f754160c78649f7c6c69dc0c030d92 Mon Sep 17 00:00:00 2001 From: Romain Derie Date: Fri, 25 Jan 2019 10:35:22 +0000 Subject: [PATCH] [FIX] web_editor, website: consider COW view when loading view Before this commit: 1. If we were editing a template with no xml_id, typically the case when editing a specific view (COW'd), the 'Template ID' label would be left empty as the view does not have an xml_id but only a key. 2. If we were editing a generic view, the template would be COW'd and replaced by the specific one created during the save. After the save, the page would be reload and will try to reopen the edited template (stored in url `res=123`). But as this template would be replaced by the COW'd view, the JS would crash trying to access an inexisting view. The HTML editor would then open in a very thin modal, barely editable. Now: 1. Display the template's key instead of its xml_id. The key is basically a duplicate of the xml_id, mainly used in website. 2. If we are saving a generic view, we search for its newly created specific view to upload the URL hash before reloading. task-1934279 Fix #30447 --- addons/web_editor/controllers/main.py | 5 ++- .../web_editor/static/src/js/widgets/ace.js | 2 +- addons/website/controllers/web_editor.py | 5 +++ .../website/static/src/js/html_editor.test.js | 1 + addons/website/static/src/js/widgets/ace.js | 32 ++++++++++++++++--- 5 files changed, 38 insertions(+), 7 deletions(-) diff --git a/addons/web_editor/controllers/main.py b/addons/web_editor/controllers/main.py index 5c7b5316d44..d6d39817d7f 100644 --- a/addons/web_editor/controllers/main.py +++ b/addons/web_editor/controllers/main.py @@ -271,6 +271,9 @@ class Web_Editor(http.Controller): result['originalSrc'] = record.url return result + def _get_view_fields_to_read(self): + return ['name', 'id', 'key', 'xml_id', 'arch', 'active', 'inherit_id'] + ## The get_assets_editor_resources route is in charge of transmitting the resources the assets ## editor needs to work. ## @param key - the xml_id or id of the view the resources are related to @@ -283,7 +286,7 @@ class Web_Editor(http.Controller): def get_assets_editor_resources(self, key, get_views=True, get_scss=True, bundles=False, bundles_restriction=[]): # Related views must be fetched if the user wants the views and/or the style views = request.env["ir.ui.view"].get_related_views(key, bundles=bundles) - views = views.read(['name', 'id', 'key', 'xml_id', 'arch', 'active', 'inherit_id']) + views = views.read(self._get_view_fields_to_read()) scss_files_data_by_bundle = [] diff --git a/addons/web_editor/static/src/js/widgets/ace.js b/addons/web_editor/static/src/js/widgets/ace.js index 507779a8917..37c21f2aa36 100644 --- a/addons/web_editor/static/src/js/widgets/ace.js +++ b/addons/web_editor/static/src/js/widgets/ace.js @@ -360,7 +360,7 @@ var ViewEditor = Widget.extend({ this.aceEditor.setSession(editingSession); if (this.currentType === 'xml') { - this.$viewID.text(_.str.sprintf(_t("Template ID: %s"), this.views[resID].xml_id)); + this.$viewID.text(_.str.sprintf(_t("Template ID: %s"), this.views[resID].key)); } else { this.$viewID.text(_.str.sprintf(_t("SCSS file: %s"), resID)); } diff --git a/addons/website/controllers/web_editor.py b/addons/website/controllers/web_editor.py index 93c3aa46007..530c9ef2b10 100644 --- a/addons/website/controllers/web_editor.py +++ b/addons/website/controllers/web_editor.py @@ -6,6 +6,11 @@ from odoo.http import request class Web_Editor(Web_Editor): + def _get_view_fields_to_read(self): + res = super(Web_Editor, self)._get_view_fields_to_read() + res.append('website_id') + return res + def save_scss_view_hook(self): res = super(Web_Editor, self).save_scss_view_hook() diff --git a/addons/website/static/src/js/html_editor.test.js b/addons/website/static/src/js/html_editor.test.js index a57e7d4ea22..6c7633cf7aa 100644 --- a/addons/website/static/src/js/html_editor.test.js +++ b/addons/website/static/src/js/html_editor.test.js @@ -54,6 +54,7 @@ tour.register('html_editor_multiple_templates', { }, { content: "add something in the oe_structure specific view", + extra_trigger: '#ace-view-id:contains("website.aboutus_oe_structure_test_ui")', // If no xml_id it should show key trigger: 'div.ace_line .ace_xml:contains("s_cover")', run: function () { ace.edit('ace-view-editor').getSession().insert({row: 2, column: 1}, '

anothernewcontent

\n'); diff --git a/addons/website/static/src/js/widgets/ace.js b/addons/website/static/src/js/widgets/ace.js index 22a1755bd82..f4fe74ddd38 100644 --- a/addons/website/static/src/js/widgets/ace.js +++ b/addons/website/static/src/js/widgets/ace.js @@ -2,6 +2,7 @@ odoo.define("website.ace", function (require) { "use strict"; var AceEditor = require('web_editor.ace'); +var weContext = require('web_editor.context'); /** * Extends the default view editor so that the URL hash is updated with view ID @@ -37,9 +38,30 @@ var WebsiteAceEditor = AceEditor.extend({ */ _saveResources: function () { return this._super.apply(this, arguments).then((function () { - this._updateHash(); - window.location.reload(); - return $.Deferred(); + var defs = []; + if (this.currentType === 'xml') { + var selectedView = _.findWhere(this.views, {id: this._getSelectedResource()}); + if (!selectedView.website_id[0]) { + // When saving a generic view, the view will be COW'd and + // replace by the specific view after the reload. Thus the id in + // URL won't exist anymore. We need to find the specific ID. + var context = weContext.get(); + defs.push(this._rpc({ + model: 'ir.ui.view', + method: 'search_read', + fields: ['id'], + domain: [['key', '=', selectedView.key], ['website_id', '=', context.website_id]], + }).then((function (view) { + if (view[0]) { + this._updateHash(view[0].id); + } + }).bind(this))); + } + } + return $.when.apply($, defs).then((function () { + window.location.reload(); + return $.Deferred(); + })); }).bind(this)); }, /** @@ -56,8 +78,8 @@ var WebsiteAceEditor = AceEditor.extend({ * * @private */ - _updateHash: function () { - window.location.hash = this.hash + "?res=" + this._getSelectedResource(); + _updateHash: function (resID) { + window.location.hash = this.hash + "?res=" + (resID || this._getSelectedResource()); }, });