From 09453314b391a654d3d2801ccb91aa497a755a4b Mon Sep 17 00:00:00 2001 From: Suherdy Yacob Date: Tue, 19 May 2026 18:18:01 +0700 Subject: [PATCH] fix: add sudo() calls to cross-company journal and account access to ensure record visibility in payments, POS sessions, and payment registration --- models/account_payment.py | 41 ++++++++++++++++-------------- models/pos_session.py | 9 ++++--- wizard/account_payment_register.py | 6 ++--- 3 files changed, 30 insertions(+), 26 deletions(-) diff --git a/models/account_payment.py b/models/account_payment.py index aafe950..a129dc8 100644 --- a/models/account_payment.py +++ b/models/account_payment.py @@ -7,12 +7,12 @@ class AccountPayment(models.Model): def action_post(self): # 1. Capture info before super() because we might need to create extra moves - centralized_payments = self.filtered(lambda p: p.journal_id.is_centralized and p.company_id != p.journal_id.parent_company_id) + centralized_payments = self.filtered(lambda p: p.journal_id.sudo().is_centralized and p.company_id != p.journal_id.sudo().parent_company_id) # 2. Call super() to post the original payment(s) # We need to make sure the original payment uses the RK account instead of Bank account if it's centralized for payment in centralized_payments: - if not payment.journal_id.branch_intercompany_account_id: + if not payment.journal_id.sudo().branch_intercompany_account_id: raise UserError(_("Please configure the Branch Inter-company Account on journal %s", payment.journal_id.name)) # We override the journal's account temporarily for the liquidity line @@ -20,22 +20,24 @@ class AccountPayment(models.Model): # 3. Handle Centralized entries in Parent for payment in centralized_payments: - parent_company = payment.journal_id.parent_company_id - parent_journal = payment.journal_id.parent_journal_id - parent_rk_account = payment.journal_id.parent_intercompany_account_id + journal_sudo = payment.journal_id.sudo() + parent_company = journal_sudo.parent_company_id + parent_journal = journal_sudo.parent_journal_id + parent_rk_account = journal_sudo.parent_intercompany_account_id - print(f">>> DEBUG: Centralized Payment for {payment.name}") - print(f" Company: {payment.company_id.id}, Parent Co: {parent_company.id}") - print(f" Parent Journal: {parent_journal.name} (ID: {parent_journal.id})") - print(f" Parent RK: {parent_rk_account.code} (ID: {parent_rk_account.id})") - if not parent_journal or not parent_rk_account: raise UserError(_("Please configure the Parent Journal and RK Account on journal %s", payment.journal_id.name)) - # Create the mirroring entry in Parent - # Debit: Parent RK (Receivable from Branch) - # Credit: Bank - parent_move = self.env['account.move'].with_company(parent_company).create({ + parent_journal_sudo = parent_journal.sudo() + parent_rk_account_sudo = parent_rk_account.sudo() + + print(f">>> DEBUG: Centralized Payment for {payment.name}") + print(f" Company: {payment.company_id.id}, Parent Co: {parent_company.id}") + print(f" Parent Journal: {parent_journal_sudo.name} (ID: {parent_journal_sudo.id})") + print(f" Parent RK: {parent_rk_account_sudo.code} (ID: {parent_rk_account_sudo.id})") + + # Create the mirroring entry in Parent using sudo + parent_move = self.env['account.move'].sudo().with_company(parent_company).create({ 'move_type': 'entry', 'date': payment.date, 'company_id': parent_company.id, @@ -52,7 +54,7 @@ class AccountPayment(models.Model): }), (0, 0, { 'name': payment.memo or f"Centralized Payment: {payment.name}", - 'account_id': parent_journal.default_account_id.id, + 'account_id': parent_journal_sudo.default_account_id.id, 'credit': payment.amount, 'partner_id': payment.partner_id.id, 'company_id': parent_company.id, @@ -60,7 +62,7 @@ class AccountPayment(models.Model): }), ] }) - parent_move.action_post() + parent_move.sudo().action_post() print(f" Parent Move Posted: {parent_move.name}") return res @@ -71,11 +73,12 @@ class AccountPayment(models.Model): when the payment is centralized. """ res = super()._prepare_move_line_default_vals(write_off_line_vals, force_balance) - if self.journal_id.is_centralized and self.company_id != self.journal_id.parent_company_id: + journal_sudo = self.journal_id.sudo() + if journal_sudo.is_centralized and self.company_id != journal_sudo.parent_company_id: # The first line is usually the liquidity line in outbound payments # or the counterpart line. Odoo 17+ uses _seek_for_lines to identify them. # But here we can just update the account if it matches the journal's default. for line_vals in res: - if line_vals.get('account_id') == self.journal_id.default_account_id.id: - line_vals['account_id'] = self.journal_id.branch_intercompany_account_id.id + if line_vals.get('account_id') == journal_sudo.default_account_id.id: + line_vals['account_id'] = journal_sudo.branch_intercompany_account_id.id return res diff --git a/models/pos_session.py b/models/pos_session.py index 4f83f9f..13a3853 100644 --- a/models/pos_session.py +++ b/models/pos_session.py @@ -65,7 +65,8 @@ class PosSession(models.Model): for order in orders: for payment in order.payment_ids: - pm = payment.payment_method_id + pm_id = payment.payment_method_id.id + pm = self.env['pos.payment.method'].sudo().browse(pm_id) if pm.intercompany_clearing_account_id and pm.intercompany_clearing_journal_id: if pm not in clearing_amounts: clearing_amounts[pm] = 0.0 @@ -158,7 +159,7 @@ class PosSession(models.Model): try: clearing_move = self.env['account.move'].sudo().with_company(session.company_id).create(move_vals) - clearing_move._post() + clearing_move.sudo()._post() # 1. Reconcile aggregated lines with session move for key, data in aggregated_data.items(): @@ -224,7 +225,7 @@ class PosSession(models.Model): continue outstanding_receipt_account = None - for pml in parent_bank_journal.inbound_payment_method_line_ids: + for pml in parent_bank_journal.sudo().inbound_payment_method_line_ids: if pml.payment_account_id: outstanding_receipt_account = pml.payment_account_id break @@ -301,7 +302,7 @@ class PosSession(models.Model): try: parent_move = self.env['account.move'].sudo().with_company(parent_company).create(parent_move_vals) - parent_move._post() + parent_move.sudo()._post() _logger.info( "Created aggregated parent mirror entry %s in company %s for session %s (Lines: %s)", parent_move.name, parent_company.name, session.name, len(line_ids) diff --git a/wizard/account_payment_register.py b/wizard/account_payment_register.py index 87f2699..060f599 100644 --- a/wizard/account_payment_register.py +++ b/wizard/account_payment_register.py @@ -67,7 +67,7 @@ class AccountPaymentRegister(models.TransientModel): 'amount_currency': amount_currency if self.payment_type == 'outbound' else -amount_currency, }), (0, 0, { - 'name': _("Due to Parent (%s)") % parent_company.name, + 'name': _("Due to Parent (%s)") % parent_company.sudo().name, 'partner_id': False, 'account_id': journal.branch_intercompany_account_id.id, 'debit': amount_company_curr if self.payment_type == 'inbound' else 0.0, @@ -101,8 +101,8 @@ class AccountPaymentRegister(models.TransientModel): } # Create payment in parent company context - parent_payment = self.env['account.payment'].with_company(parent_company).sudo().create(payment_vals) - parent_payment.action_post() + parent_payment = self.env['account.payment'].sudo().with_company(parent_company).create(payment_vals) + parent_payment.sudo().action_post() payments |= parent_payment