Wednesday, March 25, 2026
19 changes · saas-18.4
Enhancements to existing features
Invoice-related attachment updates for Serbian and Polish electronic invoicing are now saved together with the corresponding accounting document updates. This reduces the risk of mismatched records if part of the process fails, helping keep invoice data consistent.
Original PR description
Was committing the move fields update, then updating the attachment. This might create an issue were the move update commits successfully, but setting the attachment fails and we end up with an inconsistency. Set attachment in the same transaction as the move update. task-6035727 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#255440 Forward-Port-Of: odoo/odoo#255262
Resolved issues and error corrections
This fix prevents an error when users try to react to certain messages in Discuss or related apps. The reaction option is now hidden for message types that do not support it, improving stability and avoiding confusing failures.
Original PR description
*= im_livechat, portal, test_discuss_full **Steps to reproduce:** • Install the mail_group module • Open Discuss • Go to the History tab • Add a reaction on a message that has model `mail.group` •…
*= im_livechat, portal, test_discuss_full **Steps to reproduce:** • Install the mail_group module • Open Discuss • Go to the History tab • Add a reaction on a message that has model `mail.group` • Throws an error The error occurs because the `mail.group` model does not implement the `_get_allowed_access_params()` method, which is invoked during the process here. Actually, the "add reaction" button should not be shown on messages whose model does not inherit from mail.thread. https://github.com/odoo/odoo/blob/d12c1e07727f9b04cd2be2e7dac1ec3af49cb637/addons/mail/models/mail_message.py#L579 Desired behavior after PR is merged: This PR fixes the issue by hiding the "add reaction" button on messages with models that don’t inherit from mail.thread, such as mail.group. enterprise: https://github.com/odoo/enterprise/pull/111271 Task-5098050 [Reference](https://github.com/user-attachments/assets/aa2c4251-fd1f-4734-a62c-9fc80dd5f587) --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#255369 Forward-Port-Of: odoo/odoo#218615
Employees with recorded extra hours will now see them correctly on their Time Off dashboard. This helps employees and managers get an accurate view of available time balances without missing overtime-related allocations.
Original PR description
### Issue: When an employee has Extra Hours, they are not shown in the dashboard. ### Steps to reproduce: - Install Attendance and Time off apps - Create some attendance with extra hours for the employee - Go to the employee's time off dashboard - Notice Extra Hours allocation is not shown ## Cause: The extra hours are added in [`get_allocation_data()`](https://github.com/odoo/odoo/blob/5c3deb11627f4d6762c4994207bd582afb96f064/addons/hr_holidays_attendance/models/hr_leave_type.py#L35-L66), but then they are removed in [`get_allocation_data_request()`](https://github.com/odoo/odoo/blob/5c3deb11627f4d6762c4994207bd582afb96f064/addons/hr_holidays/models/hr_leave_type.py#L489) just before returning because `max_leaves` is zero. ### Solution: We also set `max_leaves` to `employee.total_overtime`. If the employee doesn't have any extra hours, then it will not display. opw-5925258 Forward-Port-Of: odoo/odoo#255504 Forward-Port-Of: odoo/odoo#253655
This fixes an issue in the HTML editor where replacing an image with a caption created an extra undo step. Users can now press Undo once to correctly restore the previous image, making editing content more predictable.
Original PR description
Problem: Undo does not work as expected when an image has a caption. Cause: When replacing an image that has a caption, two history steps are added. As a result, the first undo does not revert the image replacement. Solution: Remove the unnecessary history step so the image replacement is correctly reverted on the first undo. Steps to reproduce: - Go to To-do → Create New. - Upload an image and add a caption. - Replace the image with another one. - Press Undo (Ctrl + Z). - Observe that nothing happens on the first undo. task-6014046 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr
This update adjusts the required cbor2 library version to one that aligns with common Linux distributions and includes a ready-to-install package. This reduces installation issues and makes deployments smoother without changing business features.
Original PR description
This commit sets the cbor2 library's version to match more closely the Debian Bookworm/Ubuntu Jammy packaged versions and to match the ones with a prebuild wheel. Note: while the 5.4.2 already matched the one from Jammy, it didn't provided a corresponding wheel, which the 5.4.2.post1 did fix (cf. https://github.com/agronholm/cbor2/releases/tag/5.4.2.post1). runbot-238903 Forward-Port-Of: odoo/odoo#254638
Italian electronic invoices with an incorrect ENASARCO withholding reason can now still be imported when a matching withholding type exists. This reduces import failures and manual corrections for affected Italian invoicing workflows.
Original PR description
Some invoice come in with a wrong ENASARCO withholding reason. We now broaden the search to allow taxes with the same withholding type to be used during import even if the withholding reason doesn't match. In the test, I change the Enasarco tax to reason Q to check that it gets correctly assigned. Ticket [link](https://www.odoo.com/odoo/project.task/5175587), [link](https://www.odoo.com/odoo/project.task/5933699) opw-5175587 opw-5933699 Forward-Port-Of: odoo/odoo#251734 Forward-Port-Of: odoo/odoo#236251
This fixes how website snippet previews handle dynamic content so custom snippets with sample data are not accidentally cleared. It helps users see a more accurate preview when choosing or configuring website building blocks.
Original PR description
The commit 0327a6d37fe3274d59c158eaacb153a43121df0f added the interaction to fetch content of dynamic snippet in the iframe of the dialog to preview snippets. To avoid emptying dynamic snippets filled with fake data, it skipped rendering in certain condition. This commit changes that condition to better match the intent to not remove preview data. task-5427353
This fix ensures that web assets loaded later in the process are prepared before tests run. It helps avoid delays or unexpected asset generation during testing, making test results more stable and predictable.
Original PR description
tl;dr: look for lazy loaded bundles and add them to the bundles' list to pregenerate before running tests to avoid generation on the fly. Forward-Port-Of: odoo/odoo#248256
This update resolves an issue where fields weren't being created correctly within Odoo. The fix ensures that fields are properly populated during the creation process, improving data accuracy and reliability. This primarily impacts HR and reporting modules.
Original PR description
See https://github.com/odoo/odoo/pull/199647. Forward-Port-Of: odoo/enterprise#109725
This update resolves an issue where users couldn't add reactions to messages within the Discuss module, specifically when using the mail_group model. The fix ensures that the 'add reaction' button isn't displayed for message types that don't properly support reactions, improving the overall stability and usability of the Discuss feature.
Original PR description
Steps to reproduce: - Install the mail_group module - Open Discuss - Go to the History tab - Add a reaction on a message that has model mail.group - Throws an error The error occurs because the mail.group model does not implement the `_get_allowed_access_params()` method, which is invoked during the process here. Actually, the "add reaction" button should not be shown on messages whose model does not inherit from mail.thread. This commit fixes the issue by hiding the "add reaction" button on messages with models that don’t inherit from mail.thread, such as `mail.group`. community: https://github.com/odoo/odoo/pull/218615 Task-5098050 Forward-Port-Of: odoo/enterprise#111673 Forward-Port-Of: odoo/enterprise#111271
This update ensures that all contract sign-off and validation steps are completed before the applicant's process ends. This prevents inconsistencies in the system's state and improves the reliability of our HR processes. It’s a small fix to enhance data accuracy and process repeatability.
Original PR description
This commit adds final steps after the applicant contract being signed to let the actual sign & validate fully finish before ending the tour to avoid unconsistent state and be more reproducible. runbot-241162
This update resolves an issue in Odoo's Web Studio where field visibility settings (based on user groups) were not consistently applied. Previously, toggling the 'Show invisible Elements' checkbox didn't always retain the intended hidden state. This fix ensures that fields remain invisible when a user lacks the necessary access permissions, improving the consistency and usability of the Web Studio interface.
Original PR description
Steps to reproduce ================== - Install contacts,web_studio - Login as admin - Go to contacts - Open any record - Open studio - Click on any field - Add the "Role / Portal" group - Toggle the…
Steps to reproduce ================== - Install contacts,web_studio - Login as admin - Go to contacts - Open any record - Open studio - Click on any field - Add the "Role / Portal" group - Toggle the "Show invisible Elements" checkbox - Click on the same field => The field is marked as invisible - Add an invisible condition => The invisible condition is lost (but still applied on the view) Cause of the issue ================== In studio, when fetching the view, the invisible attribute is set to True when the user does not have access to the field (when he is not part of the groups). The goal is to make the field invisible in studio unless the "Show invisible Elements" is toggled. But this causes the actual value of the invisible attribute to be lost. Note that this also applies to the column_invisible attribute. Solution ======== If an invisible/column_invisible attribute is present on the nodes with missing access, we copy the actual value to the `actual_invisible` attribute. We then use that value in the editor, when present. opw-6026971 Forward-Port-Of: odoo/enterprise#111751 Forward-Port-Of: odoo/enterprise#111299
A recent update caused Studio Approval Rules to be unexpectedly deleted from the database during updates. This fix prevents the ORM from removing these rules, ensuring they remain active. The issue was triggered during an upgrade from 18.0 to 19.0 and is now resolved.
Original PR description
Server and automated actions created by the ORM for the purpose of revoking approval rights are created without `noupdate=True` which leads to said records being removed by the ORM becuase of not being found in the source. Such records created on the fly should have `noupdate=True` to prevent that from happening. This bug can be reproduced by going to Settings > Technical > User Interface > Studio Approval Rules and creating a new record from there and updating `web_studio`. The update will drop the record from the database. Issue originally detected in the upgrade process from 18.0 to 19.0. This fix will be complemented by an upgrade script that fixes erronous records. Forward-Port-Of: odoo/enterprise#110065
This update ensures that document creation times are displayed accurately for users, regardless of their location. Previously, times were inconsistent due to a failure to convert dates from UTC to the user's local timezone. Now, all times are correctly formatted for each user, improving the overall user experience.
Original PR description
Step to reproduce: 1. Install `documents` 2. Upload a document and open the tree view 3. Compare the field `Created On` and the time from the `Manage Versions` action Issue: - The displayed time is inconsistent between the tree view and the dialog Cause: - The datetime used in Manage Versions is formatted without converting it from UTC to the user’s timezone Solution: - Use timezone-aware datetime helpers so values are converted from UTC to the user’s timezone. Before: <img width="1328" height="81" alt="image" src="https://github.com/user-attachments/assets/2a02f03c-714d-417d-a805-fd0dd7c52753" /> <img width="636" height="297" alt="image" src="https://github.com/user-attachments/assets/c4514469-2f51-493f-8991-32371fb7f338" /> After: <img width="641" height="312" alt="image" src="https://github.com/user-attachments/assets/3979ece8-635a-4b54-9b53-d8b28b3336ec" /> opw-5467782 Forward-Port-Of: odoo/enterprise#104443
This update prevents data merge operations from silently failing due to timeouts. Instead, a warning notification is displayed, suggesting users reduce the number of records merged and reloading the model upon successful completion. This enhances the reliability and user experience of the data cleaning process.
Original PR description
Display a warning notification when the merge operation times out instead of failing silently. Suggest merging fewer records and reload the model on success. task-5912855 Forward-Port-Of: odoo/enterprise#110763
This update resolves a recurring issue where the Italian POS printer would generate errors when the system was offline. The fix adds a safety mechanism to gracefully handle offline scenarios, preventing tracebacks and ensuring smoother operation for users with intermittent internet connections. This improves the reliability of the Italian POS system.
Original PR description
When loosing internet connexion a lot of tracebacks appear is the pos if we use the italian fiscal printer. Steps to reproduce: ------------------- * Setup italian fiscal printer for a shop * Open shop * Turn wi-fi off * Add items to cart * Go to payment screen > Traceback * Add a payment and validate > Traceback Why the fix: ------------ Don't try to reach the printer if we're offline regarding the price to pay. We add a try catch block around the call for printing the receipt. If the try block fails when the network is offline we assume it's just because of the offline mode. If it failed while online we raise the error. opw-5432090 Forward-Port-Of: odoo/enterprise#110326 Forward-Port-Of: odoo/enterprise#105515
This update resolves an issue where only administrators could delete work entry types within the payroll module. Now, users with SUPERUSER permissions can delete these types, streamlining payroll configuration and reducing reliance on technical support. This change improves operational efficiency for HR and payroll teams.
Original PR description
Forward-Port-Of: odoo/enterprise#111967
This update resolves a problem where translations were not appearing correctly in the Chilean E-Invoicing module, specifically on Ubuntu Jammy and Debian Bookworm operating systems. The change converts a complex list comprehension to a standard for loop, ensuring accurate translation lookup and functionality.
Original PR description
This commit transforms the list comprehension into a regular for loop to avoid the translation missing context when looking up for lang. Note: the issue appeared more specifically on Ubuntu Jammy and Debian Bookworm. runbot-240951 Forward-Port-Of: odoo/enterprise#111147
This update addresses a potential issue where automated email verification services (Mail Defender) could inadvertently trigger appointment cancellations. The system has been updated to replace direct links with a form, preventing these bots from interacting with the appointment functionality. This ensures appointments are handled correctly and reliably.
Original PR description
…ointments Mail defender services may click URLs in emails to verify their contents. Additionally they may sometimes interact with the page and visit related pages. For this reason URLs sent in emails should not trigger any action directly nor contain any simple link that could trigger an action. The "cancel/reschedule" anchor URL is replaced with a form which bots should not click. We also port the fix done in appointment to the view in appointment as it replaces the original view in this module. task-4555579 Forward-Port-Of: odoo/enterprise#111879 Forward-Port-Of: odoo/enterprise#79831