Skip to content

[FIX] account_operating_unit: use sudo() in OU onchange#835

Open
IJOL wants to merge 1 commit intoOCA:18.0from
BITVAX:18.0-fix-journal-access-denied
Open

[FIX] account_operating_unit: use sudo() in OU onchange#835
IJOL wants to merge 1 commit intoOCA:18.0from
BITVAX:18.0-fix-journal-access-denied

Conversation

@IJOL
Copy link
Copy Markdown

@IJOL IJOL commented Apr 5, 2026

Summary

  • Add .sudo() when reading journal_id.operating_unit_id and journal_id.type in _onchange_operating_unit to prevent AccessError for users without journal read permission.

Test plan

  • Create a user with OU Manager group but without Accounting Manager group
  • Open a vendor bill and change the operating unit
  • Verify no AccessError is raised when the journal onchange triggers

Users without journal read permission get AccessError when the
_onchange_operating_unit triggers. Use sudo() to safely read
journal.operating_unit_id and journal.type.

Port of BITVAX fix from 16.0-fix-journal-access-denied branch.
@AaronHForgeFlow
Copy link
Copy Markdown
Contributor

can you explain how to reproduce the issue?

@IJOL
Copy link
Copy Markdown
Author

IJOL commented Apr 9, 2026

@AaronHForgeFlow Sure, here's how to reproduce:

Steps to reproduce

  1. Create two Operating Units: OU_A and OU_B, each with its own bank/cash journal
  2. Create a user with:
    • Group: OU Manager (operating_unit.group_manager_operating_unit)
    • Group: Account User (account.group_account_user) — but NOT Account Manager
    • Operating Units: both OU_A and OU_B
    • The ir.rule "Journals from allowed operating units" restricts journal visibility by OU
  3. Log in as that user
  4. Create a vendor bill assigned to OU_A
  5. Change the Operating Unit field from OU_A to OU_B

Expected behavior

The _onchange_operating_unit method switches the journal to one matching OU_B.

Actual behavior (without this fix)

AccessError is raised because the method reads self.journal_id.operating_unit_id and self.journal_id.type — but the current journal (from OU_A) may not be readable by the user due to the ir.rule filtering. Adding .sudo() on these two reads prevents the AccessError while still respecting the rule when searching for the replacement journal.

This was originally fixed in our 16.0 fork (BITVAX/operating-unit 16.0-fix-journal-access-denied) and ported to 18.0.

Copy link
Copy Markdown
Contributor

@AaronHForgeFlow AaronHForgeFlow left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe we can achieve the same result by deriving the journal type from the move_type (which is always accessible) and moving the OU logic directly into the search domain (code not tested)

def _onchange_operating_unit(self):
    if not self.operating_unit_id:
        return
    j_type = 'sale' if self.move_type in ('out_invoice', 'out_refund') else 'purchase'
    if self.move_type == 'entry':
        j_type = 'general'
    new_journal = self.env["account.journal"].search([
        ("type", "=", j_type),
        ("operating_unit_id", "=", self.operating_unit_id.id)
    ], limit=1)
    if new_journal:
        self.journal_id = new_journal
    if self.line_ids:
        self.line_ids.operating_unit_id = self.operating_unit_id

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants