Monday, April 27, 2026
28 changes · saas-19.2
Enhancements to existing features
This update enhances the reporting features within the Enterprise edition by making return type menu options consistently available, regardless of whether debug mode is enabled. This change expands user access to critical reporting configurations, streamlining the process for financial analysis and reporting.
Original PR description
Before, the menu return types in configuration was only available in debug mode. Now it is available for the group `account.group_account_readonly` task-5912751 Forward-Port-Of: odoo/enterprise#114830
This update enhances the user experience for Dutch SBR tax returns by providing clearer status tracking within the Odoo interface. It automatically updates the return's status and hides the 'Pay' button until the return is fully accepted, streamlining the process and reducing potential errors. This improves reporting accuracy and compliance.
Original PR description
…workflow This commit integrates the Dutch SBR tax reporting process into the `account.return` workflow to provide better visibility, UI feedback, and tracking for users. Main changes: * Added a new…
…workflow This commit integrates the Dutch SBR tax reporting process into the `account.return` workflow to provide better visibility, UI feedback, and tracking for users. Main changes: * Added a new `l10n_nl_sbr_status` field (Pending, Accepted, Error) to `account.return` to track the submission status for Kanban UI color coding. * Updated the Kanban view to dynamically apply custom CSS classes (`nl-sbr-error`, `nl-sbr-pending`) to the state bubble based on the SBR status. * Introduced an `action_refresh_sbr_status` method and a corresponding "Refresh" button in the Kanban view to manually trigger the status check cron. * Consolidated Chatter messages so that status updates, errors, and submission success notifications log directly on the `account.return` record rather than the closing entry. * Added an `action_reset_tax_return_common` override to prevent resetting or modifying a tax return once it has been accepted by Digipoort. * Modified the UI to hide the "Pay" button unless the SBR return has been fully accepted. * Updated `_on_post_submission_event` to block further processing of the return until the SBR report is accepted. task-6034675 Forward-Port-Of: odoo/enterprise#110516
Resolved issues and error corrections
This update corrects a calculation error in the HK payroll reports (IR56B/F/G) by adding adjustments for global reimbursements and deductions. This ensures that tax calculations accurately reflect the employee's taxable income, aligning with Hong Kong's tax regulations. It's a critical fix for accurate financial reporting.
Original PR description
Added GLOBAL_REIMBURSEMENT and GLOBAL_DEDUCTION to the AmtOfSalary calculation for IR56B/F/G reports. This ensures adjustments are properly reflected in taxable income totals. task-6126661 Forward-Port-Of: odoo/enterprise#115108 Forward-Port-Of: odoo/enterprise#114041
This update resolves an issue that prevented users from grouping depreciation schedules by analytic plans. The problem stemmed from an incorrect formatting of data within the database query, specifically surrounding analytic account IDs. Removing unnecessary parentheses corrected this, allowing users to successfully group by analytic plans.
Original PR description
Currently, an error occurs when user tries to group by an analytic plan on depreciation schedule. Steps to replicate: - Install `accountant` with demo, turn on `Analytic Accounting` from settings. -…
Currently, an error occurs when user tries to group by an analytic plan on depreciation schedule.
Steps to replicate:
- Install `accountant` with demo, turn on `Analytic Accounting` from settings.
- Open `Accounting > Review > Depreciation Schedule`.
- Click `Analytic` > Add a `Plan`.
Error:
```
psycopg2.errors.UndefinedFunction: operator does not exist: text = record
LINE 12: WHERE key IN (('7', '16', '8', '15', '6', '9', '...
^
HINT: No operator matches the given name and argument types. You might need to add explicit type casts.
```
Cause:
- At line [1], we pass a tuple of `analytic_account_ids`, which is then wrapped again in parentheses at line [2].
- This results in the IDs being enclosed in double parentheses, e.g. `(('7', '16', '8', '15', '6'))`.
- When the `IN` clause is used with this double-parenthesized tuple, PostgreSQL treats it as a list containing a single record. It then tries to compare `key` (a text value) with that record `('7', '16', '8', '15', '6')`, effectively resulting in a `text = record` comparison, which is invalid and causes error.
Solution:
- Removed the extra parentheses from the query.
[1]: https://github.com/odoo/enterprise/blob/847b5be291adbfa315f8f74ab7a6dd3d1fb7d518/account_asset/models/account_assets_report.py#L124
[2]: https://github.com/odoo/enterprise/blob/847b5be291adbfa315f8f74ab7a6dd3d1fb7d518/account_asset/models/account_assets_report.py#L121
sentry-7423121981
Forward-Port-Of: odoo/enterprise#114334This update resolves an issue where the 'print' function for bills exports only the records visible on the current page. Now, when you select all bills, including those not displayed on the current page, they will be included in the exported print file. This ensures a complete and accurate export of all selected bills.
Original PR description
Right now when selecting all the records in the current page from bills list view and there are some other records not displayed in this page then click on "select all X" where X is all the records either displayed in the current page or not it shows "selected X", however when trying to export them through the print button it only exports the ones that are in the current page, this PR fixes this bug. opw-6129628 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#261058
This update fixes a misclassification of accounts 657 and 757 in Odoo's French reporting, aligning with the new PCG 2025 accounting standards. Previously, these accounts were incorrectly categorized as 'exceptional items,' leading to inaccurate profit and loss statements. This change ensures compliance with French regulations and provides accurate financial reporting.
Original PR description
…tions As part of the PCG 2025 reform in France, accounts 657 and 757 were introduced to handle capital gains and losses on the disposal of tangible and intangible assets related to normal, current activities. Previously, Odoo incorrectly categorized these under exceptional items which led to mismatches in the P&L. Source: https://www.anc.gouv.fr/files/anc/files/1_Normes_fran%C3%A7aises/Plans%20comptables/PCG--1er-janvier-2025.pdf Relevant excerpts: <img width="630" height="372" alt="image" src="https://github.com/user-attachments/assets/88a66dac-1cc0-4a33-a902-edb6b626f18f" /> <img width="631" height="318" alt="image" src="https://github.com/user-attachments/assets/403b65dc-20ba-447e-937d-20575f1f45ab" /> opw-6105764 Forward-Port-Of: odoo/enterprise#115054 Forward-Port-Of: odoo/enterprise#114837
This update corrects a problem where spaces in French SIRET numbers were causing invoices to be rejected by Chorus Pro. The fix ensures SIRET values are exactly 14 characters long, resolving compatibility issues with the Peppol system and enabling accurate invoice transmission. This prevents delays and errors in invoice processing.
Original PR description
### Issue: When sending invoices to Chorus Pro via Peppol in France, SIRET numbers may contain spaces, causing the document to be silently rejected ### Cause: SIRET values must be exactly 14…
### Issue: When sending invoices to Chorus Pro via Peppol in France, SIRET numbers may contain spaces, causing the document to be silently rejected ### Cause: SIRET values must be exactly 14 characters long However, spaces were not removed when generating the XML, leading to invalid values in: `<cbc:ID schemeID="0009">` and `<cbc:CompanyID schemeID="0009">` This issue can occur for both the company and the customer SIRET, as both rely on `company_registry` As a result, Chorus Pro rejects the document due to invalid SIRET length ### Steps to reproduce: - Install `l10n_fr_facturx_chorus_pro` and switch to `FR Company` - Enable and Activate Peppol in Settings - Go in Settings > Users & Companies > Companies and open the `FR Company` - Add spaces in the Company ID: 968 515 7590 5808 - Create a Customer (Country: France, VAT: FR23334175221, Company ID/Siret: 123 456 7890 1234) - In the customer's Invoicing Tab (Invoice sending: by Peppol, eInvoice format: EU Standard (Peppol Bis 3.0), France SIRET: 11000201100044) - Create and Send an invoice via Peppol (Your Customer, any line with a tax) - Open the XML - Check the IDs and CompanyIDs in the document Before the fix, there is missing spaces opw-6047840 Forward-Port-Of: odoo/odoo#260578
This update fixes an issue where Google Reserve slots incorrectly showed resources as available due to missing leave information. The team also removed unnecessary code related to scheduling offsets, streamlining the process as Google Reserve slots are pre-defined. This ensures accurate availability for bookings.
Original PR description
Resources on leave were still showing as available in BatchAvailabilityLookup responses because unavailabilities were not checked. Also remove the min_schedule_hours offset copied from the frontend logic. It is not relevant for Google Reserve as slots are pre-built in the feeds. Task-6150788 Forward-Port-Of: odoo/enterprise#114793
This update fixes an issue where menu items with spaces in their URLs wouldn't automatically link to newly created pages. The fix ensures that menus with and without leading slashes are correctly linked, and a warning is displayed in the menu editor to prevent confusion when users enter spaceful URLs. This improves the user experience and ensures accurate navigation.
Original PR description
When a menu item URL contains a space and has no leading slash (e.g., "some url"), creating a page from its 404 screen does not link the menu to the newly created page. The menu keeps pointing to a…
When a menu item URL contains a space and has no leading slash (e.g., "some url"), creating a page from its 404 screen does not link the menu to the newly created page. The menu keeps pointing to a 404. **Steps to reproduce**: 1. Create a menu item with a URL containing spaces and no leading slash (e.g., "some url"). 2. Click the menu item -> a 404 page is displayed (expected). 3. Click "Create Page" -> the page is created and saved. 4. Click the menu item again -> it still returns a 404 (unexpected). **Issue**: During page creation, the path is slugified (e.g., "some url" -> "/some-url"). The controller then tries to link the menu to the new page by setting `page_id`. However, `pagenew()` only searches for menu URLs with a leading slash, so a menu saved as "some url" is not found when searching for "/some url". As a result, `page_id` is never set, and `_clean_url()` keeps resolving the menu to "/some url" instead of the page's actual URL "/some-url". Menus without spaces (e.g., "mypage") have the same issue where `page_id` is not set, but since `_clean_url()` prepends "/" and renders "/mypage", which matches the new page URL, the menu still resolves correctly. **Fix**: Match both URL formats (with and without leading slash) when linking a menu to a newly created page. Additionally, a warning is now shown in the menu editor when a URL contains spaces, since spaces are slugified during page creation, which could cause confusion. (Note: this is only a warning - URLs with spaces are still allowed.) task-[5095646](https://www.odoo.com/odoo/project/974/tasks/5095646) --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#261208 Forward-Port-Of: odoo/odoo#248967
This update resolves a problem where mobile money transactions using DPO Pay were frequently declined due to an error in the transaction ID (sourceId). The fix ensures that the sourceId adheres to DPO Pay's length restrictions, preventing these transaction failures and improving the reliability of mobile money payments.
Original PR description
Steps to reproduce: = - Configure a payment method with DPO Pay (Mobile Money). - Open POS. - Add a product and initiate a transaction using the DPO Pay mobile money method. - Process the transaction on the terminal device. Issue: = - Transaction is declined with error: - "Data mismatch in one of the fields - OriginatorSourceID exceeds maximum length of 15 characters." Fix: = - Updated `sourceId` generation logic for mobile money transactions. - Ensured `sourceId` complies with DPO Pay constraints (maximum 15 alphanumeric characters), as enforced in recent DPO Pay updates. - Prevented transaction failures caused by oversized `sourceId`. task-6143491 Forward-Port-Of: odoo/odoo#260553
This update fixes an issue where DIAN invoices were incorrectly marked as 'rejected' due to expected status update failures. The system now correctly handles multiple DIAN document updates, ensuring invoices are accurately reflected as 'accepted' by DIAN, which is crucial for generating correct QR codes and printing.
Original PR description
Before this commit, the logic that computes the invoice's DIAN state would rely solely on the state of the most recent document. The problem with that approach is that we will regularly send status…
Before this commit, the logic that computes the invoice's DIAN state would rely solely on the state of the most recent document. The problem with that approach is that we will regularly send status updates to DIAN after the invoice was successfully submitted via the status cron here: https://github.com/odoo/enterprise/blob/19.0/l10n_co_dian/models/account_move.py#L484 Those status updates are expected to fail a certain number of times (typically when no commercial status information is available, or in other terms when `l10n_co_dian_commercial_state` is still in `'pending'`). As a result, an invoice successfully transmitted to DIAN could still end up with a `l10n_co_dian_state` not set to `'invoice_accepted'`. This leads, among other things to a QR code that cannot be reprinted as the logic here: https://github.com/odoo/enterprise/blob/19.0/l10n_co_dian/models/account_move.py#L225 determines which template to render based on that state. The issue cannot be easily reproduced or tested as `l10n_co_dian.document` are generated almost only in prod scenarios. The most common setup where the error happens is for invoices that have 2 DIAN documents: 1. the first (oldest, bottom-most) one reflects acceptance of the invoice sending by DIAN (`state = 'invoice_accepted'`) 2. the second one (most recent, top-most), which reflects the latest query for commercial status update by the cron and which failed (`state = 'invoice_rejected'` and the error message reflects the lack of commercial events) opw-6108318 opw-5931442 opw-6034035 Forward-Port-Of: odoo/enterprise#113929
This update resolves an issue where CFDI generation for payroll payslips failed due to rounding discrepancies between the company's currency settings and the XML formatting requirements. The fix explicitly rounds payroll amounts to 2 decimal places, ensuring compliance with CFDI standards and preventing errors.
Original PR description
Currently, if the company is configured with a 4-decimal currency, the CFDI generation for payslips might fail with NOM111 and CFDI40119 errors. This occurs because the calculation of totals and subtotals uses the raw unrounded floats, which can cause penny differences when the XML template formats the individual lines to 2 decimal places. This commit forces all payroll concept amounts to be explicitly rounded to 2 decimal places before accumulating the totals. This ensures that the sum of the formatted XML nodes precisely matches the total and subtotal values reported in the CFDI. Accounting might require a higher decimal precision for the company's currency (e.g., 4 decimals for inventory). However, payroll CFDI stamping strictly requires 2 decimal precision. This fix isolates the payroll CFDI calculations from the company's currency settings. Forward-Port-Of: odoo/enterprise#114936
This update fixes an issue where MyInvois consolidation documents incorrectly combined invoices with gaps in their sequence numbers. The change now accurately splits the batch into multiple XML lines when invoices are missing, ensuring correct invoice generation and reducing potential errors. This improves the reliability of the MyInvois document creation process.
Original PR description
When generating a consolidated MyInvois document, the system must split the batch into multiple XML lines if there are gaps in the sequence (e.g., if an invoice in the middle of the range was already sent individually) The previous logic attempted to detect these gaps by searching the database(`account.move`) for any invoices that fell within the sequence range and lacked a EDI document. Because this search would find the "missing" invoices, it would fill the gap and fail to detect it and produce a single consolidated line. This commit replaces the search and relies only on the selected recordset, along with the addition of sorted `sequence_number` for gap detection and adds test for handling consolidation of broken sequences. Task: [6057214](https://www.odoo.com/odoo/project.task/6057214) --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#261150
This update fixes an issue where IoT events were missed due to a failure in the longpolling fallback mechanism. Now, if longpolling fails, the system automatically switches to websocket, ensuring that critical events, such as Worldline payment confirmations, are reliably received. This improves the stability and functionality of our IoT integrations.
Original PR description
Community PR: https://github.com/odoo/odoo/pull/260931 Before this commit, if `onMessage` in `iot_http_service` was called directly, it would fail to fallback to websocket if the longpolling request failed, causing events to be missed. One symptom of this is Worldline payments failing to confirm when using websocket. After this commit, the `_longpolling` method will now throw an error in this case, causing the fallback mechanism to attempt websocket instead. Forward-Port-Of: odoo/enterprise#114882 Forward-Port-Of: odoo/enterprise#114779
This update resolves a problem where users received duplicate notifications when submitting the email reminder form for events. The fix ensures notifications are displayed correctly and prevents unwanted redirects to talk pages, improving the user experience when adding events to their agenda.
Original PR description
This PR fixes the email reminder form with multiple commits: - Commit 1 fixes the notifications displayed when the email form is submitted as the messages of those notifications are redundant. - Commit 2 inserts the form inside the HTML body instead of the interaction's HTML since the surrounding HTML of this last one may cause display issues as with the <a> tag redirecting the users on the talks page when they click on the form which should not happen. Task-5347538 Forward-Port-Of: odoo/odoo#251468
This update fixes an issue where group payments weren't accurately calculating installment amounts. Previously, the full bill amount was included, even for subsequent installments. Now, payments correctly reflect the full amount of the initial bill and only the next installment payment for multi-installment bills, ensuring accurate financial reporting.
Original PR description
Steps to reproduce: 1- Install Accounting and make sure "Batch Payments" is enabled in settings 2- Go to [Accounting -> Vendors -> Bills] 3- Create two bills for the same vendor, ensuring one of them has multiple installments (i.e payment term with 3 installments) 4- Confirm the bills 5- In list view, select both bills and another bill from a different vendor and click on Pay 6- Select "Group Payments" and confirm the payment Description of issue: The batch payment of the first vendor has the full amount for both bills Expected behavior: The payment should consider the full amount of the first bill and the first installment only of the second bill opw-5969972 Forward-Port-Of: odoo/odoo#260933 Forward-Port-Of: odoo/odoo#257871
This update resolves an issue where changing the account on bank reconciliation lines with analytic distributions would cause errors and data inconsistencies. The fix ensures accurate account updates by properly managing analytic line links during editing, preventing orphaned analytic lines and improving the bank reconciliation process.
Original PR description
Before this commit, editing a line with an analytic distribution caused inconsistent behavior when changing the account. When an analytic distribution was present, editing the line created analytic…
Before this commit, editing a line with an analytic distribution caused inconsistent behavior when changing the account. When an analytic distribution was present, editing the line created analytic lines linked to the move line. However, changing the account from the form view in the bank reconciliation widget triggered _inverse_account_id, which in turn called _inverse_analytic_distribution. This resulted in unlinking the analytic_line_ids from the move line, preventing the account change from being applied. On a second attempt, the account could be modified because there were no longer any analytic lines to unlink. This led to orphaned analytic lines not linked to any journal item. To fix this, the inverse method is now disabled while editing the line in the form view. Upon saving, the analytic_line_ids are explicitly unlinked, and _create_analytic_lines is triggered during the update to correctly recreate the analytic lines. opw-6107329 Forward-Port-Of: odoo/enterprise#114863
This update fixes an error in how holiday leave time off is calculated. Previously, public holidays were incorrectly included in the time off duration, leading to inaccurate hours reported. The fix ensures that approved time off aligns with the expected 8-hour workday, even when public holidays are present.
Original PR description
# Setup You'll need a User with : - An active contract (for easiness of testing, a contract that started long ago with 8hrs/day) # How to reproduce - Create a new Time Off type with "Ignore Public…
# Setup
You'll need a User with :
- An active contract (for easiness of testing, a contract that started long ago with 8hrs/day)
# How to reproduce
- Create a new Time Off type with "Ignore Public Holidays" enabled
- Create a Public Holiday for Period X
- Create A Time Off request for the User for a Period Y that contains Period X
- Go to the Time Off Ledger
- Remove the Missing Hours filter and search for the dates in Period Y
Exemple of periods :
- Period X => Feb 10 2026 - Feb 10 2026
- Period Y => Feb 9 2026 - Feb 11 2026
# The problem
The "Approved Time Off" and "Difference" values are wrong.
With the given exemples, we'll see Feb 9 and Feb 11 with "Approved Time Off" values of 12hrs, which is wrong since the employee is supposed to work 8hrs a day, so he should have a time off of also 8hrs.
# Cause
The calculation for "Approved Time Off" is the following :
Divide the `number_of_hours` of a hr_leave
By the number of working days during the period of the leave
Using our exemple, we get :
`number_of_hours` = 24hrs
number of working days = 2
Approved Time Off = 24hrs / 2 => 12hrs, but we expect 8hrs
The `number_of_hours` is correct since we checked "Ignore Public Holidays" (which actually means : include the public holidays in the number of hours of a leave)
The problem is that the aggregation for the number of working days excludes automatically
public holidays, without paying attention to the value of "Ignore Public Holidays" :
https://github.com/odoo/odoo/blob/5e623af55fba64e812db6bcaf06d8f7c5d08f055/addons/hr_holidays_attendance/report/hr_leave_attendance_report.py#L193-L202
Explanation for this part of the query : we only keep days where there is no record in
resource_calendar_leaves (`WHERE rcl2.id IS NULL`) that contains that day
and that are considered public (`AND rcl2.resource_id IS NULL`)
# Proposed Solution
We add a `JOIN hr_leave_type` to be able to get the value for
`include_public_holidays_in_duration` ("Ignore Public Holidays").
Then, we make it so we exclude the Public Holidays only if that value is
false (`AND NOT lvt.include_public_holidays_in_duration`)
opw-6082422
---
I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr
Forward-Port-Of: odoo/odoo#258963This update fixes an issue where stock wasn't being properly reserved for delivery orders when stock arrived at a child location within the warehouse system. Previously, the system didn't recognize the connection between the parent and child locations, leading to incorrect stock availability. This ensures accurate stock reservations and prevents over-delivery issues.
Original PR description
Steps to reproduce: - Create a storable product with no stock on hand - Create a delivery order from WH/Stock → state is "Waiting for Availability" - Create a receipt with destination WH/Stock/Shelf1 and validate it Problem: The incoming quantity is not reserved against the waiting delivery, even though WH/Stock/Shelf1 is a child of WH/Stock. opw-6124879 Forward-Port-Of: odoo/odoo#261072
This update enhances the ticket printing experience in Point of Sale and Loyalty modules, addressing alignment issues and improving the display of point values. It also fixes a printing error related to company details and prevents potential errors for specific locales, ensuring a more reliable and professional customer experience.
Original PR description
In this commit: = - `Next Order Coupon` code below bardcode is displayed. - Displayed correct string for won and balance points. - Logo size increased. - Company details not shown if not available while printing from terminal. - Next order coupon Barcode alignment fixed. - Fixed Lot and Serial number alignment. - Prevented traceback for l10n-specific company (e.g. CL, SE). - Removed extra padding from around "Need an invoice ?" text task-5499545
This update resolves a problem where portal users creating tickets via email triggered a system crash due to incorrect access permissions to employee calendars. The fix ensures that the system correctly handles multi-company user scenarios, preventing access errors and allowing ticket creation to proceed smoothly. This improves the reliability of the Helpdesk portal.
Original PR description
Problem: Portal email with auto-assignment crashes ticket creation due to calendar access. When a helpdesk ticket is created via email from a portal user and automatic assignment is enabled, the…
Problem: Portal email with auto-assignment crashes ticket creation due to calendar access. When a helpdesk ticket is created via email from a portal user and automatic assignment is enabled, the system computes working intervals for users to determine assignment. This computation goes into resource logic, where resource.calendar fields (flexible_hours) are read. If the assigned user is linked to multiple employees across companies, multiple resource.resource records are evaluated. The helpdesk email flow starts in sudo, but the employee calendar lookup explicitly drops sudo before returning the calendar. Then, the calendar is accessed in the portal context, which does not have permission to read the other company's resource.calendar, leading to an AccessError and preventing ticket creation. Although the failure is triggered from Enterprise helpdesk, the actual crash occurs in Odoo (resource.calendar), meaning the fix must be applied there. Fix: Preserve sudo when fetching employee calendars to ensure that scheduling logic does not depend on the access rights of the email sender. A test is added in helpdesk_holidays, as the issue requires both helpdesk (auto-assignment) and hr (employees/resources) to reproduce. The test simulates a portal email flow with a multi-company user linked to multiple employees and ensures ticket creation succeeds. Steps to Reproduce: 1. Install Helpdesk, Employees, and enable multi-company 2. Create two companies (e.g., Company A and Company B) 3. Create one internal user (User X) with access to both companies 4. Create two employees linked to the same user: - Employee 1 in Company A - Employee 2 in Company B Make sure they are set with a start date, but no end date. Needs to be active employee. 5. Create a Helpdesk team in Company A 6. Add Agent X as a team member 7. Enable automatic assignment 8. Configure an email alias for the helpdesk team 9. Create a portal user 10. Send an email from the portal user to the alias Related Ticket: opw-6035099 Forward-Port-Of: odoo/odoo#257720
This update resolves an issue where portal email auto-assignment was failing due to permission problems accessing employee calendars across different companies. The fix ensures the system correctly accesses calendar data, allowing ticket assignments to proceed smoothly. This improves the reliability of the helpdesk system for portal users.
Original PR description
Problem: Portal email with auto-assignment crashes ticket creation due to calendar access. When a helpdesk ticket is created via email from a portal user and automatic assignment is enabled, the…
Problem: Portal email with auto-assignment crashes ticket creation due to calendar access. When a helpdesk ticket is created via email from a portal user and automatic assignment is enabled, the system computes working intervals for users to determine assignment. This computation goes into resource logic, where resource.calendar fields (flexible_hours) are read. If the assigned user is linked to multiple employees across companies, multiple resource.resource records are evaluated. The helpdesk email flow starts in sudo, but the employee calendar lookup explicitly drops sudo before returning the calendar. Then, the calendar is accessed in the portal context, which does not have permission to read the other company's resource.calendar, leading to an AccessError and preventing ticket creation. Although the failure is triggered from Enterprise helpdesk, the actual crash occurs in Odoo (resource.calendar), meaning the fix must be applied there. Fix: Preserve sudo when fetching employee calendars to ensure that scheduling logic does not depend on the access rights of the email sender. A test is added in helpdesk_holidays, as the issue requires both helpdesk (auto-assignment) and hr (employees/resources) to reproduce. The test simulates a portal email flow with a multi-company user linked to multiple employees and ensures ticket creation succeeds. Steps to Reproduce: 1. Install Helpdesk, Employees, and enable multi-company 2. Create two companies (e.g., Company A and Company B) 3. Create one internal user (User X) with access to both companies 4. Create two employees linked to the same user: - Employee 1 in Company A - Employee 2 in Company B Make sure they are set with a start date, but no end date. Needs to be active employee. 5. Create a Helpdesk team in Company A 6. Add Agent X as a team member 7. Enable automatic assignment 8. Configure an email alias for the helpdesk team 9. Create a portal user 10. Send an email from the portal user to the alias Related Ticket: opw-6035099 Forward-Port-Of: odoo/enterprise#114699 Forward-Port-Of: odoo/enterprise#113047
This update fixes an issue where the 'Configuration' menu was hidden for users with 'All Timesheets' access, preventing them from managing billing targets. The fix ensures that menu visibility updates correctly after changes to billing settings, providing consistent access for all approvers. This improves usability and accuracy of timesheet reporting.
Original PR description
Steps to reproduce Bug 1: 1. Login as a user with "All Timesheets" (Approver) access. 2. Disable the "Timesheet Assistant" feature for this user. 3. Ensure "Billing Rate Indicators" is enabled in…
Steps to reproduce Bug 1:
1. Login as a user with "All Timesheets" (Approver) access.
2. Disable the "Timesheet Assistant" feature for this user.
3. Ensure "Billing Rate Indicators" is enabled in settings.
Steps to reproduce Bug 2:
1. Login as a user with "All Timesheets" (Approver) access.
2. Disable the "Billing Rate Indicators" setting in company settings.
3. Ensure "Timesheet Assistant" is enabled in settings.
Steps to reproduce Bug 3:
1. Only install 'sale_timesheet_enterprise'.
2. Go to Timesheets > Configuration > Settings.
3. Toggle "Billing Rate Indicators" (timesheet_show_rates) or change the encoding unit (timesheet_encode_uom_id), then save and check the menus.
Issue:
1. The "Configuration" menu is hidden, preventing access to billing targets even if the user has "All Timesheets" access.
2. The "Billing Time Targets" menu is still visible inside Configuration even if the "Billing Rate Indicators" feature is disabled in the settings.
3. Menu visibility does not update immediately after saving the settings. Menus that should appear (e.g., "Employee Billing Time Targets" or "Timesheets Assistant") remain hidden, or vice versa, until the cache is cleared or the server is restarted.
Cause:
1. The `hr_timesheet_enterprise_menu_configuration` was restricted in XML to groups that excluded "All Timesheets" users.
2. The `_load_menus_blacklist` logic in Python only blacklisted billing menus for users who were both Managers and System Admins, leaving them visible to regular Approvers even when the feature was disabled.
3. The load_menus method is decorated with @ormcache and stored in the Registry LRU cache. Menu visibility depends on timesheet_show_rates and timesheet_encode_uom_id through _load_menus_blacklist. When this field is updated, the ORM does not automatically invalidate the cached load_menus result because these specific fields are not part of the configuration fields. As a result, the stale old menu remains in memory.
Fix:
- Updated XML to include `hr_timesheet.group_hr_timesheet_approver` in the Enterprise Configuration menu permissions.
- Refactored `_load_menus_blacklist` to:
- Hide all billing-related menus for all users when the feature is disabled.
- Hide the parent Configuration menu if it would otherwise be empty.
- Override the write method in res.company in both modules and explicitly call env.registry.clear_cache() when the relevant configuration fields are modified.
task-5428010
Forward-Port-Of: odoo/enterprise#106464This update fixes inaccuracies in tax calculations for Argentina (l10n_ar) by modernizing the underlying tax calculation methods. The changes ensure more accurate VAT calculations and prepare the system for future adjustments to Argentina's specific tax regulations. This improves the reliability of financial reporting for Argentinian businesses.
Original PR description
This commit refactors the tax amount calculations on the `_get_vat` and `_l10n_ar_get_amounts` method so that it uses the tax computation engine helpers properly, to prepare for any future fixes done on how Argentina tax calculations differs from all other localizations. This replaces all move line queries with the proper `base_line` calculation, with the proper aggregating methods. related-enterprise-PR: https://github.com/odoo/enterprise/pull/92639 task-4891206 Forward-Port-Of: odoo/odoo#260171 Forward-Port-Of: odoo/odoo#223393
This update fixes inaccuracies in how tax amounts are calculated for Arabic VAT transactions within the Odoo Enterprise system. By utilizing the system's tax computation engine, the changes ensure more precise and reliable tax calculations, particularly for sales and invoices. This improves financial reporting accuracy.
Original PR description
- Rewrite all tax amounts calculations on `_get_tributes` and `_get_line_details` to properly use the tax computation engine helpers (`base_line`, and aggregating methods) - Ensure that all final amounts from the calculation are formatted with `float_repr` with appropriate precision. related-community-PR: https://github.com/odoo/odoo/pull/223393 task-4891206 Forward-Port-Of: odoo/enterprise#114379 Forward-Port-Of: odoo/enterprise#92639
This update resolves an issue where the 'is_company' field in several Latin American localization modules (AR, BR, EC) was incorrectly calculated. The change ensures accurate identification of companies, improving data integrity and functionality for users in these regions. This fix primarily impacts the l10n_latam_base module and related localization modules.
Original PR description
*: l10n_{ar,br,ec}
In 19.1 we changed the `is_company` field to a computed
stored field.
This change needs to be reflected correctly in many localisations
where the default computed value is too naive.
This commit is introducing a generic fix for most l10n that depends
on the module `l10n_latam_base`.
Improve the test coverage for the computation.
Note: This is not strictly necessary for this fix
on Enterprise side, since we removed the invisibility
condition but in case of some customization relying
on it it's safer if we can deduce it correctly.
Enterprise: https://github.com/odoo/enterprise/pull/114403
Related: https://github.com/odoo/odoo/pull/211043
task-6141307
Forward-Port-Of: odoo/odoo#260224This update corrects a visibility problem with Peruvian identifiers (like driver licenses) that arose after a change in the Odoo 19.1 system. The fix removes a restrictive condition, ensuring these identifiers are always displayed correctly. This ensures accurate reporting and data management for Peruvian businesses.
Original PR description
In 19.1 we changed the `is_company` field to a computed stored field. That change broke the visibility for some Peruvian identifiers (driver license, etc). This commit removes the visibility condition on those fields to be displayed all the time. Note: we still add the correct compute on related Community commit for sake of correctness and completeness. Community: https://github.com/odoo/odoo/pull/260224 Related: https://github.com/odoo/odoo/pull/211043 task-6141307 Forward-Port-Of: odoo/enterprise#114403
This update resolves an issue preventing AI chat functionality on Safari iOS devices. The fix addresses a compatibility problem with older Safari versions that don't fully support a key streaming technology. By switching to a more basic reading method, the AI chat now works reliably on Safari, ensuring a smooth user experience for all customers.
Original PR description
Steps: - Install ai - Open ai chat - Try to send a message - Traceback The AI chat was failing on iOS with a traceback when trying to process the stream response. Even though MDN suggests…
Steps: - Install ai - Open ai chat - Try to send a message - Traceback The AI chat was failing on iOS with a traceback when trying to process the stream response. Even though MDN suggests compatibility, Safari (WebKit) versions prior to 26.4 do not implement the AsyncIterator protocol on ReadableStream. This makes `for await (const chunk of response.body)` throw a TypeError as `[Symbol.asyncIterator]` is undefined. https://developer.mozilla.org/en-US/docs/Web/API/ReadableStream This commit replaces the async iteration with a manual reader loop (`getReader().read()`). This is the low-level primitive supported by all versions of Safari and ensures the stream is properly consumed and unlocked even if the connection is interrupted. Steps to reproduce: 1. Open Discuss/AI Chat on an iPad or iPhone (eg. 26.4). 2. Send a message. 3. The response triggers a JS error. ```js Uncaught Promise > undefined is not a function (near '...chunk of asyncStream...') ``` opw-6054307 Forward-Port-Of: odoo/enterprise#113926