[FIX] web: x2many with non inline form: don't share active fields
Before this commit, the StaticList and its Records shared the same reference to the activeFields. When an x2many record was opened in form view (and that form view wasn't inline), we altered the active fields to add the information coming from the form, and we loaded the corresponding data for the record we open. However, by doing so, we also altered the active fields of all the other records, for which we didn't load the corresponding data. From that point, a rendering of those kanban records could lead to a crash, because we iterate over active fields and make the assumption that there's an entry for each of them in data, which isn't the case. For instance, this happened in a dev branch in project, in mobile: after opening a sub task in form view, if we switched to another notebook tab and then switched back, there was a crash. This commit fixes the issue by creating a copy of activeFields for each Record, s.t. when a record is opened in a dialog, only its activeFields (and those of the StaticList) are altered. Note that activeFields of the StaticList must be altered in this case to ensure that the onchange spec is properly generated, with the fields of the form view. closes odoo/odoo#148351 Signed-off-by: Francois Georis (fge) <fge@odoo.com>
This commit is contained in:
@@ -716,7 +716,7 @@ export class StaticList extends DataPoint {
|
||||
const id = resId || params.virtualId;
|
||||
const config = {
|
||||
context: this.context,
|
||||
activeFields: params.activeFields || this.activeFields,
|
||||
activeFields: Object.assign({}, params.activeFields || this.activeFields),
|
||||
resModel: this.resModel,
|
||||
fields: params.fields || this.fields,
|
||||
relationField: this.config.relationField,
|
||||
|
||||
@@ -14445,4 +14445,68 @@ QUnit.module("Fields", (hooks) => {
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
QUnit.test(
|
||||
"x2many kanban with float field in form (non inline) but not in kanban",
|
||||
async function (assert) {
|
||||
// In this test, the form view contains an extra float field and isn't inline. When we open
|
||||
// a record, we add the form fields to the list of activeFields, and we load the
|
||||
// corresponding data (for that record only). Afterwards, we force a re-rendering of the
|
||||
// x2many kanban to ensure that the other record can still be rendered. Before the fix coming
|
||||
// with this test, it wasn't the case, because those records had extra activeFields, but no
|
||||
// entry in data for those fields.
|
||||
serverData.models.partner.records[0].turtles = [2, 3];
|
||||
serverData.views = {
|
||||
"turtle,false,form": `
|
||||
<form>
|
||||
<field name="display_name"/>
|
||||
<field name="turtle_qux"/>
|
||||
</form>`,
|
||||
};
|
||||
|
||||
await makeView({
|
||||
type: "form",
|
||||
resModel: "partner",
|
||||
serverData,
|
||||
arch: `
|
||||
<form>
|
||||
<field name="bar"/>
|
||||
<field name="turtles" invisible="not bar">
|
||||
<kanban>
|
||||
<field name="display_name"/>
|
||||
<templates>
|
||||
<t t-name="kanban-box">
|
||||
<div class="oe_kanban_global_click">
|
||||
<t t-esc="record.display_name.raw_value"/>
|
||||
</div>
|
||||
</t>
|
||||
</templates>
|
||||
</kanban>
|
||||
</field>
|
||||
</form>`,
|
||||
resId: 1,
|
||||
});
|
||||
|
||||
assert.containsOnce(target, ".o_field_widget[name=turtles]");
|
||||
assert.containsN(target, ".o_kanban_record:not(.o_kanban_ghost)", 2);
|
||||
|
||||
// open the first record
|
||||
await click(target.querySelector(".o_kanban_record"));
|
||||
assert.containsOnce(target, ".o_dialog");
|
||||
assert.containsOnce(target, ".o_dialog .o_field_widget[name=turtle_qux]");
|
||||
|
||||
// close the dialog
|
||||
await click(target.querySelector(".o_dialog .o_form_button_save"));
|
||||
assert.containsNone(target, ".o_dialog");
|
||||
|
||||
// toggle bar to make the x2many invisible
|
||||
await click(target, ".o_field_widget[name=bar] input");
|
||||
assert.containsNone(target, ".o_field_widget[name=turtles]");
|
||||
|
||||
// toggle bar again to make the x2many visible and force kanban cards to re-render
|
||||
await click(target, ".o_field_widget[name=bar] input");
|
||||
assert.containsOnce(target, ".o_field_widget[name=turtles]");
|
||||
assert.containsN(target, ".o_kanban_record:not(.o_kanban_ghost)", 2);
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user