[FIX] web: prevent traceback during calendar popover processing
Before this commit, a traceback would occurs in sale_management calendar view when the user would try to display the popover of a sale_order.
```js
basic_model.js:2399 Uncaught (in promise) Error: for modifier "readonly": Unknown field state in domain
at Class._evalModifiers (basic_model.js:2399)
at calendar_popover.js:203
at Function._.each._.forEach (underscore.js:145)
at calendar_popover.js:180
at async Promise.all (index 1)
_evalModifiers @ basic_model.js:2399
(anonymous) @ calendar_popover.js:203
_.each._.forEach @ underscore.js:145
(anonymous) @ calendar_popover.js:180
Promise.then (async)
_renderEventPopover @ calendar_renderer.js:861
eventClick @ calendar_renderer.js:416
Calendar.publiclyTrigger @ main.js:6981
EventClicking._this.handleSegClick @ main.js:6462
realHandler @ main.js:385
```
It would happen because the domain of the partner_id is ["state", "not in", ['draft', 'sent']] but the state field is invisible="1" in the view.
state was absent during of the evalContext in the _evalModifiers function.
closes odoo/odoo#72617
Taskid: 2524993
X-original-commit: 0d636c0f8dbcfb4b7adda26c0edc02a12b0c7e44
Signed-off-by: Michaël Mattiello <mcm-odoo@users.noreply.github.com>
Signed-off-by: Arnaud Joset <arj-odoo@users.noreply.github.com>
This commit is contained in:
@@ -31,6 +31,7 @@ var CalendarPopover = Widget.extend(WidgetAdapterMixin, StandaloneFieldManagerMi
|
||||
this.event = eventInfo.event;
|
||||
this.modelName = eventInfo.modelName;
|
||||
this._canDelete = eventInfo.canDelete;
|
||||
this.popoverFields = eventInfo.popoverFields;
|
||||
},
|
||||
/**
|
||||
* @override
|
||||
@@ -126,7 +127,7 @@ var CalendarPopover = Widget.extend(WidgetAdapterMixin, StandaloneFieldManagerMi
|
||||
var self = this;
|
||||
var fieldsToGenerate = [];
|
||||
const fieldInformation = {};
|
||||
var fields = _.keys(this.displayFields);
|
||||
var fields = _.keys(this.popoverFields);
|
||||
for (var i=0; i<fields.length; i++) {
|
||||
var fieldName = fields[i];
|
||||
var displayFieldInfo = self.displayFields[fieldName] || {attrs: {invisible: 1}};
|
||||
@@ -139,6 +140,7 @@ var CalendarPopover = Widget.extend(WidgetAdapterMixin, StandaloneFieldManagerMi
|
||||
string: displayFieldInfo.attrs.string || fieldInfo.string,
|
||||
value: self.event.extendedProps.record[fieldName],
|
||||
type: fieldInfo.type,
|
||||
invisible: displayFieldInfo.attrs.invisible,
|
||||
};
|
||||
if (field.type === 'selection') {
|
||||
field.selection = fieldInfo.selection;
|
||||
@@ -200,7 +202,7 @@ var CalendarPopover = Widget.extend(WidgetAdapterMixin, StandaloneFieldManagerMi
|
||||
// Only display the fields whose attributes does not make them invisible
|
||||
let fieldClass = "list-group-item flex-shrink-0 d-flex flex-wrap";
|
||||
if (fieldWidget.attrs && fieldWidget.attrs.modifiers) {
|
||||
const fieldModifier = record.evalModifiers(fieldWidget.attrs.modifiers);
|
||||
const fieldModifier = record.evalModifiers(_.pick(fieldWidget.attrs.modifiers, 'invisible'));
|
||||
fieldClass += fieldModifier.invisible ? ' o_invisible_modifier' : '';
|
||||
}
|
||||
|
||||
|
||||
@@ -180,6 +180,7 @@ return AbstractRenderer.extend({
|
||||
init: function (parent, state, params) {
|
||||
this._super.apply(this, arguments);
|
||||
this.displayFields = params.displayFields;
|
||||
this.popoverFields = params.popoverFields;
|
||||
this.model = params.model;
|
||||
this.filters = [];
|
||||
this.color_map = {};
|
||||
@@ -807,6 +808,7 @@ return AbstractRenderer.extend({
|
||||
event: eventData,
|
||||
modelName: this.model,
|
||||
canDelete: this.canDelete,
|
||||
popoverFields: this.popoverFields,
|
||||
};
|
||||
|
||||
var start = moment((eventData.extendedProps && eventData.extendedProps.r_start) || eventData.start);
|
||||
|
||||
@@ -69,6 +69,7 @@ var CalendarView = AbstractView.extend({
|
||||
var mapping = {};
|
||||
var fieldNames = fields.display_name ? ['display_name'] : [];
|
||||
var displayFields = {};
|
||||
let popoverFields = {};
|
||||
|
||||
_.each(fieldsToGather, function (field) {
|
||||
if (arch.attrs[field]) {
|
||||
@@ -87,6 +88,7 @@ var CalendarView = AbstractView.extend({
|
||||
if (child.tag !== 'field') return;
|
||||
var fieldName = child.attrs.name;
|
||||
fieldNames.push(fieldName);
|
||||
popoverFields[fieldName] = {attrs: child.attrs};
|
||||
if (!child.attrs.invisible || child.attrs.filters) {
|
||||
child.attrs.options = child.attrs.options ? pyUtils.py_eval(child.attrs.options) : {};
|
||||
if (!child.attrs.invisible) {
|
||||
@@ -177,6 +179,7 @@ var CalendarView = AbstractView.extend({
|
||||
this.controllerParams.scales = scales;
|
||||
|
||||
this.rendererParams.displayFields = displayFields;
|
||||
this.rendererParams.popoverFields = popoverFields;
|
||||
this.rendererParams.model = viewInfo.model;
|
||||
this.rendererParams.hideDate = utils.toBoolElse(attrs.hide_date || '', false);
|
||||
this.rendererParams.hideTime = utils.toBoolElse(attrs.hide_time || '', false);
|
||||
|
||||
@@ -938,7 +938,7 @@ QUnit.module('Views', {
|
||||
});
|
||||
|
||||
QUnit.test('render popover with modifiers', async function (assert) {
|
||||
assert.expect(3);
|
||||
assert.expect(5);
|
||||
|
||||
this.data.event.fields.priority = {string: "Priority", type: "selection", selection: [['0', 'Normal'], ['1', 'Important']],};
|
||||
|
||||
@@ -953,6 +953,10 @@ QUnit.module('Views', {
|
||||
'all_day="allday" '+
|
||||
'mode="week">'+
|
||||
'<field name="priority" widget="priority" readonly="1"/>'+
|
||||
'<field name="is_hatched" invisible="1"/>'+
|
||||
'<field name="partner_id" attrs=\'{"invisible": [["is_hatched","=",False]]}\'/>'+
|
||||
'<field name="start" attrs=\'{"invisible": [["is_hatched","=",True]]}\'/>'+
|
||||
|
||||
'</calendar>',
|
||||
archs: archs,
|
||||
viewOptions: {
|
||||
@@ -964,7 +968,8 @@ QUnit.module('Views', {
|
||||
|
||||
assert.containsOnce(calendar, '.o_cw_popover', "should open a popover clicking on event");
|
||||
assert.containsOnce(calendar, '.o_cw_popover .o_priority span.o_priority_star', "priority field should not be editable");
|
||||
|
||||
assert.strictEqual(calendar.$('.o_cw_popover li.o_invisible_modifier').text(), 'user : partner 1', "partner_id field should be invisible");
|
||||
assert.containsOnce(calendar, '.o_cw_popover span.o_field_date', "The start date should be visible");
|
||||
await testUtils.dom.click($('.o_cw_popover .o_cw_popover_close'));
|
||||
assert.containsNone(calendar, '.o_cw_popover', "should close a popover");
|
||||
|
||||
|
||||
Reference in New Issue
Block a user