From 90ca3fd1a73f58aaf9db047da2219809476e0f30 Mon Sep 17 00:00:00 2001 From: Hubert Van De Walle Date: Wed, 28 Feb 2024 12:45:14 +0100 Subject: [PATCH] [FIX] hr: many2one_avatar field uses wrong model Steps to reproduce ================== - Install Timesheets - Login as Admin - Edit the access rights of Mark Demo: * Timesheets: "User: all timesheets" * Employees: "None" - Logout and login as Demo - Go to a project task - Switch to the Timesheets notebook - Add a new line - Click on the employee field > Search More => An error occurred Cause of the issue ================== The hr.employee.public model is an SQL view of the hr.employee table with differents permissions. Since the user doesn't have the hr.group_hr_user group, the model hr.employee.public should be used and not hr.employee. Since [0], the model is switched depending on whether the user has the appropriate group. The EmployeeFieldRelationMixin is used and defines a getter for the relation. That relation was not propagated to the Many2OneField. Solution ======== Pass the relation to the many2OneProps. --- [0]: https://github.com/odoo/odoo/pull/136786 opw-3765393 closes odoo/odoo#155743 Signed-off-by: Sofie Gvaladze (sgv) --- .../many2one_avatar_employee_field.js | 18 +++++- .../static/tests/m2x_avatar_employee_tests.js | 59 +++++++++++++++++++ 2 files changed, 75 insertions(+), 2 deletions(-) diff --git a/addons/hr/static/src/views/fields/many2one_avatar_employee_field/many2one_avatar_employee_field.js b/addons/hr/static/src/views/fields/many2one_avatar_employee_field/many2one_avatar_employee_field.js index aa475f05bb0..fb3f520e758 100644 --- a/addons/hr/static/src/views/fields/many2one_avatar_employee_field/many2one_avatar_employee_field.js +++ b/addons/hr/static/src/views/fields/many2one_avatar_employee_field/many2one_avatar_employee_field.js @@ -11,7 +11,14 @@ import { EmployeeFieldRelationMixin } from "@hr/views/fields/employee_field_rela export class Many2OneAvatarEmployeeField extends EmployeeFieldRelationMixin( Many2OneAvatarUserField -) {} +) { + get many2OneProps() { + return { + ...super.many2OneProps, + relation: this.relation, + }; + } +} export const many2OneAvatarEmployeeField = { ...many2OneAvatarUserField, @@ -31,7 +38,14 @@ registry.category("fields").add("many2one_avatar_employee", many2OneAvatarEmploy export class KanbanMany2OneAvatarEmployeeField extends EmployeeFieldRelationMixin( KanbanMany2OneAvatarUserField -) {} +) { + get many2OneProps() { + return { + ...super.many2OneProps, + relation: this.relation, + }; + } +} export const kanbanMany2OneAvatarEmployeeField = { ...kanbanMany2OneAvatarUserField, diff --git a/addons/hr/static/tests/m2x_avatar_employee_tests.js b/addons/hr/static/tests/m2x_avatar_employee_tests.js index 24fe8c75122..697c423b8db 100644 --- a/addons/hr/static/tests/m2x_avatar_employee_tests.js +++ b/addons/hr/static/tests/m2x_avatar_employee_tests.js @@ -8,6 +8,8 @@ import { dom } from "@web/../tests/legacy/helpers/test_utils"; import { contains } from "@web/../tests/utils"; import { registry } from "@web/core/registry"; import { makeFakeUserService } from "@web/../tests/helpers/mock_services"; +import { selectDropdownItem } from "@web/../tests/helpers/utils"; +import { makeView, setupViewRegistries } from "@web/../tests/views/helpers"; const serviceRegistry = registry.category("services"); @@ -217,6 +219,63 @@ QUnit.test("many2one_avatar_employee with relation set in options", async functi ); }); +QUnit.test("many2one_avatar_employee without hr.group_hr_user", async function (assert) { + assert.expect(2); + + setupViewRegistries(); + serviceRegistry.add( + "user", + makeFakeUserService((group) => group !== "hr.group_hr_user"), + { force: true } + ); + + await makeView({ + type: "form", + resModel: "m2x.avatar.employee", + serverData: { + models: { + "m2x.avatar.employee": { + fields: { + employee_id: { + string: "employee", type: "one2many", relation: "hr.employee" + }, + }, + records: [], + }, + "hr.employee": { + fields: { + display_name: { string: "Displayed name", type: "char" }, + }, + records: [ + { display_name: "babar" }, + ], + }, + "hr.employee.public": { + fields: { + display_name: { string: "Displayed name", type: "char" }, + }, + records: [ + { display_name: "babar" }, + ], + }, + }, + views: { + "hr.employee.public,false,list": ``, + "hr.employee.public,false,search": ``, + "hr.employee,false,list": ``, + "hr.employee,false,search": ``, + } + }, + arch: `
`, + mockRPC: function (_, { model, method }) { + if (method === "name_search" || method === "web_search_read") { + assert.strictEqual(model, "hr.employee.public"); + } + } + }); + await selectDropdownItem(document, "employee_id", "Search More..."); +}); + QUnit.test( "many2one_avatar_employee: click on an employee not associated with a user", async function (assert) {