Thursday, March 5, 2026
28 changes · saas-19.1
New functionality added to Odoo
This update incorporates the Central Bank of Uzbekistan as a source for real-time currency rates. This change ensures Odoo Enterprise complies with local regulations and provides more accurate currency conversions for transactions involving Uzbekistan.
Original PR description
## Description of the issue/feature this PR addresses: This PR adds the Central Bank of Uzbekistan as a provider for currency update task-id - 5917344 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/enterprise#108059
Enhancements to existing features
This update expands the 'Unpaid' filter in the vendor bill section to now display draft bills alongside posted bills. This allows users to see all outstanding bills, regardless of their payment status, improving visibility and streamlining payment management. A technical update ensures journal entries are correctly filtered, maintaining data accuracy.
Original PR description
In this commit: - Updated the `Unpaid` filter to show draft bills in addition to posted bills. The filter now includes all non-cancelled bills with payment status `Not Paid` or `Partially Paid`. - Backported the logic from 18.0 to ensure journal entries are filtered out by checking that type is not equal to `journal_entry`. task-5900283 Forward-Port-Of: odoo/odoo#251208 Forward-Port-Of: odoo/odoo#247179
Resolved issues and error corrections
A test was failing due to a time zone discrepancy in the planning module. The fix corrects a calculation that incorrectly shifted dates based on the server's time zone setting, ensuring consistent test results. This prevents disruptions to the planning functionality.
Original PR description
__ ## Error description The test fails when it is launched at 23h. We obtain an assertion error: `AssertionError: datetime.datetime(2026, 2, 26, 11, 0) != datetime.datetime(2026, 2, 25, 11, 0)` ## Origin of the issue In the `_default_start_datetime()` method of planning, we return `return datetime.combine(fields.Date.context_today(self), time.min)`. So, we call context_today. which is implemented this way: https://github.com/odoo/odoo/blob/f3ec2aa4514c03874aae96ae975e2617e8260c72/odoo/orm/fields_temporal.py#L154-L158 Let's say the hour of the test is 23h50 in GMT+0. The slot will be created at 23h50 in GMT+0. But if the time zone of the environment is set at GMT+1, at the moment of the `_compute_datetime`, we will call this piece of code, where we will translate 23h50 to GMT+1, we will obtain 00h50, then only return the day, which offsets the result of one day in the future. X-original-commit: d91c53869842f65a60088ffa101f67404af6e58e
This update enables cashiers to record multiple payments for a single order in Point of Sale. Previously, users were limited to one cash payment line, causing issues when multiple people paid at different times. This change improves the user experience and accurately reflects payments made in a group setting.
Original PR description
Before this commit: ============ - The user is not able to process multiple cash payment lines. An error pop-up appears saying `There is already a cash payment line.` After this commit: ============ - The user can process multiple cash payment lines. Use Case: ----------- - If a group of people goes to a restaurant and one person leaves earlier, he decides to pay $10 at the cashier and leave. When the others pay later, the cashier will see that $10 has already been paid and can add another cash payment line for the remaining amount. Task-5969853 Forward-Port-Of: odoo/odoo#250639
This update adjusts the Romanian tax reporting (l10n_ro_saft) to align with recent changes in the core Enterprise version (CE). The update removes outdated tax codes and adds new ones, ensuring accurate reporting for Romanian businesses. This ensures compliance with current tax regulations.
Original PR description
Some taxes were no longer needed in CE, so they needed to be removed task-5411745 Forward-Port-Of: odoo/enterprise#109507 Forward-Port-Of: odoo/enterprise#106127
This update adjusts the salary scale parameters used in the Odoo Enterprise’s Belgian payroll module (l10n_be_hr_payroll). Specifically, the base salary figures for the first year of employment and overall salary scale values have been updated to reflect the latest regulations as of January 1st, 2026. This ensures accurate payroll calculations for Belgian employees.
Original PR description
. Update cp200_salary_scale_first_year values for 01/01/2026 . Update cp200_salary_scale values for 01/01/2026 task-5485636 Forward-Port-Of: odoo/enterprise#107473
This update enhances the point-of-sale (POS) system by allowing for easier customization of the ticket screen. The changes enable developers to add specific styling classes to the ticket screen, providing greater flexibility for tailoring the user interface. This improves the system's adaptability to different business needs and branding requirements.
Original PR description
See odoo/enterprise#94390 Forward-Port-Of: odoo/odoo#226447
This update refines the payroll schedule wizard for Belgian companies, restricting its use to only employees within Belgium. It removes a redundant field and improves the user interface with added spacing, resulting in a cleaner and more intuitive experience for HR staff managing Belgian employee schedules.
Original PR description
- Show the “Working Schedule Change” wizard only for employees belonging to Belgian companies. - Remove the “Post Change Contract Creation” field from the working schedule change wizard. - Add extra right padding to the warning alert in the time-off section for improved UI spacing. task-5367812 Forward-Port-Of: odoo/enterprise#101013
This update resolves an issue where filtering by 'Analytic Distribution' in Journal Entries and Purchase Orders was returning incorrect results. The fix ensures that 'is set' and 'is not set' filters work as expected, accurately displaying records with and without an analytic distribution. This improves data accuracy and reporting.
Original PR description
**Problem:** When filtering by "Analytic Distribution" in views, using "is set" or "is not set" filters (or searching for False) returns incorrect results. When the filter is 'set' it returns all…
**Problem:** When filtering by "Analytic Distribution" in views, using "is set" or "is not set" filters (or searching for False) returns incorrect results. When the filter is 'set' it returns all records (even the ones without an analytic distribution) and when the filter is 'not set' it returns no records (even the ones without an analytic distribution). **Steps to reproduce:** 1) Go to Accounting > Journal Entries. 2) Apply a filter for Invoice lines > Distribution Analytic Account. 3) Select "is set" or "is not set". 4) Check records. Issue is also reproduceable on Purchase Orders. **Cause:** The `_search_analytic_distribution` method did not correctly handle the case when the value is [False], so it results in an invalid Query. **Solution:** - We need to handle the case when we have False in the value on it's own. opw-5478688 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#251816 Forward-Port-Of: odoo/odoo#247777
A test failure related to invoice data formatting was resolved. The fix ensures the correct invoice data is used in a key export process, preventing potential errors and ensuring consistent invoice generation for Turkish VAT invoices. This improves the reliability of the e-invoice export functionality.
Original PR description
In the `test_which_service_to_call` test, we are calling `_call_web_service_before_invoice_pdf_render` with invoice_data. But invoice_data is just a dict with `invoice.read()` and the extra key extra_edis. Instead of manually building invoice_data, we should call `_get_default_sending_settings`, which is meant to be used in the base `account.move.send` flow. Why this fix? Because by not calling `_get_default_sending_settings`, we risk changing the expected invoice_data format used in `_call_web_service_before_invoice_pdf_render`, which could lead to KeyErrors. Spotted while developing https://github.com/odoo/enterprise/pull/80590, the test failed, raising the ['invoice_edi_format'] key error. no-task Forward-Port-Of: odoo/odoo#251885 Forward-Port-Of: odoo/odoo#232105
This update resolves a problem preventing the correct generation of CSV reports for Peru-specific accounting. The fix addresses an incompatibility with a recent Python update, ensuring reports are now created without errors. The change also streamlines the CSV configuration process for improved efficiency.
Original PR description
Revealed when l10n modules got enabled on the "distro builds" nightly: on Trixie, `delimiter="|", lineterminator='|\n'` raises ValueError: bad delimiter or lineterminator value This is due to…
Revealed when l10n modules got enabled on the "distro builds" nightly: on Trixie, `delimiter="|", lineterminator='|\n'` raises
ValueError: bad delimiter or lineterminator value
This is due to python/cpython#113797 which added new validations to dialect definitions. For this issue, that the delimiter can not be in the line terminator. This can be fixed via a different trick, which is documented:
> The optional `restval` parameter specifies the value to be written
> if the dictionary is missing a key in `fieldnames`.
so if we add a trailing fieldname which *can not* be found in the row dicts, then `DictWriter` will always write out an empty trailing cell (the default `restval` is an empty string), which should result in the same output.
Also remove the `csv.register_dialect` calls, that's so subsequent CSV calls can easily refer to a common configuration but here two different dialects are being registered under the same name, and each one is only used for the following `DictWriter` call, so at best this is a complete waste of time and at worst this is a race condition in threaded configurations. Just pass the formatting parameters directly to the `DictWriter`.
https://runbot.odoo.com/odoo/error/240950
Forward-Port-Of: odoo/enterprise#109437
Forward-Port-Of: odoo/enterprise#109081This update expands the color field options within the Odoo Gantt editor to include all integer fields from the underlying model. Previously, only fields directly visible in the view could be selected. This change improves the editor's flexibility and allows for more comprehensive visualization of task data.
Original PR description
Before this commit, only fields already present in the view were selectable for the color field in the gantt editor. After this commit, all int fields of the model are available task-5981029 Forward-Port-Of: odoo/enterprise#109189
This update fixes an issue where VIES validation errors caused errors in the system. The team has broadened the exception handling to catch all `zeep` errors, preventing tracebacks and ensuring accurate VAT number checks. This resolves a previous problem impacting OCR invoice updates.
Original PR description
Catch all `zeep` exceptions instead of only `zeep.Fault`. On 14th of February 2026, the VIES service wasn't working properly, they were returning invalid XML in their response. This caused the `check_vies` call to raise a `zeep.XMLSyntaxError` which wasn't caught, causing a traceback every time VIES was used to validate a VAT number. opw-5938723 (OCR couldn't be refreshed on an invoice because it tried to create a partner from its VAT number and it couldn't be checked with VIES). Forward-Port-Of: odoo/odoo#250123 Forward-Port-Of: odoo/odoo#249853
This update ensures the Odoo command-line interface consistently uses the correct data directory, regardless of user configuration. While the preferred method is using the odoorc configuration file, this change enforces the use of the data directory for the odoo-bin module, providing a more reliable setup.
Original PR description
The prefered way is to use the odoorc config file, but some plateforms let their users configure their config file, but --data-dir should be enforced by the plateform. Forward-Port-Of: odoo/odoo#251937
This update fixes an issue where large company logos on customer documents were overlapping with important address information. By adding a maximum width constraint to the small company logo, the document layout is now cleaner and more professional, ensuring key customer details are always visible. This improves the overall presentation of customer documents.
Original PR description
**Description of the issue/feature this PR addresses:** Similar issue described in: https://github.com/odoo/odoo/pull/249432 Since there is no `max-width` defined for `o_company_logo_small`, if a user uploads a large logo, the customer address overlaps with the company details. This can be tested by previewing the document with a large logo. <img width="684" height="449" alt="image" src="https://github.com/user-attachments/assets/aa2ac10b-cb0f-448a-ade3-6e7bb8b1fcff" /> **Current behavior before PR:** <img width="681" height="383" alt="image" src="https://github.com/user-attachments/assets/cf7d5740-db51-43e3-b8f6-70325e9e28c0" /> **Desired behavior after PR is merged:** <img width="505" height="307" alt="image" src="https://github.com/user-attachments/assets/b175a06a-cde0-4808-a1fb-276fd96272c3" /> --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr cc @ForgeFlow Forward-Port-Of: odoo/odoo#251976
This update fixes a technical issue within the mass mailing module that prevented certain elements from being correctly displayed. The change ensures that a key method is interpreted correctly, improving the overall reliability and accuracy of the mass mailing process. This ensures consistent and accurate email campaigns.
Original PR description
Description of the issue/feature this PR addresses: This PR makes sure `isSelectionInEditable` is correctly checked in `EmptyNotEditableElementsPlugin`. `isSelectionInEditable` is a shared method previous code interpreted it as property. --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#251744
This update fixes an issue where duplicate Dimona activities were being created in the payroll system, particularly when updating employee versions. The change ensures that Dimona activities are only created once, streamlining payroll processing and preventing potential data inconsistencies. This improves the reliability of the Belgian payroll calculations.
Original PR description
This pr restores the previous behaviour of the dimona and part-time activities creation when the cron is ran or when a version or employee is updated. The original bug was: create an instance on…
This pr restores the previous behaviour of the dimona and part-time activities creation when the cron is ran or when a version or employee is updated. The original bug was: create an instance on saas-18.4 with l10n_be_hr_payroll settings > company > my company > update infos > country: Belgium employee > new > payroll > contract > start_date: any date (this should create a first dimona activity) settings > technical > automation > scheduled actions > "HR Employee: Update Current Version" > run manually `_trigger_l10n_be_next_activities` in `hr.version` of `l10n_be_hr_payroll` is duplicating Dimona activities on records that already have one. We check if a dimona activity already exists for a given `hr.employee` before creating the new activity. Same is done for dimona declaration of part times. The activity now redirects to the employee form (instead of the version form) and appears in it. [tasks-5134380](https://www.odoo.com/odoo/project/1251/tasks/5134380) Forward-Port-Of: odoo/enterprise#109304 Forward-Port-Of: odoo/enterprise#96423
This update resolves a problem where Odoo couldn't send email templates without a linked record. A recent change in the Odoo codebase caused this to fail. This fix ensures email templates can now be sent correctly, regardless of whether a record is associated with them.
Original PR description
Add explicit support for sending an email template with no actual record, i.e., calling `template.send_mail(False)`. This used to work but now fails since https://github.com/odoo/odoo/pull/227477. task-6000637
A technical issue causing the Activity Logs report to appear incorrectly in the Sign Template list view has been resolved. The fix corrects a misconfiguration in the report's model, ensuring it now displays within the Sign Request view and prevents errors.
Original PR description
Version: - saas-18.2 Issue: - The "Activity Logs" report was showing in the Sign Template list view. When clicking it, a traceback occurred because the report tried to read a `sign.request` record from a `sign.template` context. Cause: - The report model was set to `sign.request`, but the`binding_model_id` was set to `model_sign_template`. - This mismatch caused the report to appear in the wrong place. Solution: - Updated the `binding_model_id` to `model_sign_request` so the report now appears in the Sign Request view, which matches the report model and prevents the error. task-5984137 Forward-Port-Of: odoo/enterprise#109171
This update fixes an issue where the system was incorrectly returning multiple bank records when a company contact had the same account number on multiple child contacts. This ensured accurate bank information is displayed and used within the Odoo system, preventing potential data inconsistencies.
Original PR description
The function `_find_or_create_bank_account` is expected to return one or no record at all. In the case of child contacts, it is possible that the same account number was set on multiple records, leading the function to return multiple banks. Forward-Port-Of: odoo/odoo#251733
A bug was causing the task list to display duplicate 'New' and 'Create New' buttons, leading to confusion and potential duplicate task creations. This fix removes the duplicate buttons by preventing the ProjectTaskTemplateDropdown component from rendering in dialog contexts. This ensures a cleaner and more intuitive task creation experience.
Original PR description
Steps to Reproduce --- 1. Enable Task Dependencies in Project settings 2. Create project with no task templates 3. Open task form -> Blocked By tab -> Add a line 4. Observe duplicate "New" and "Create New" buttons Issue --- - The task list view displays both “New” and “Create New” buttons, resulting in duplicated creation actions. Current Behaviour --- - Two different creation buttons are displayed simultaneously Expected Behaviour --- - Only a single “New” button should be displayed Root cause --- - ControlPanel refactoring removed props.showButtons without adding !env.inDialog check to task views. Fix --- - Add !env.inDialog check , this prevents the ProjectTaskTemplateDropdown component from rendering in dialog contexts, eliminating the duplicate button issue. Related - https://github.com/odoo/odoo/pull/220325 task - 5403917
A minor bug causing test failures in the stock module has been resolved. The fix ensures the database is fully updated before deleting zero inventory quantities, preventing unpredictable test results. This improves the reliability of our stock management testing.
Original PR description
In Signal app, the test `test_set_inventory_quant_to_zero` was failing randomly when asserting that the quant no longer exists after calling `_unlink_zero_quants()`. All required conditions for deletion were met: - inventory_quantity == 0 - user_id is False - quantity == 0 - reserved_quantity == 0 The method `_unlink_zero_quants()` performs a raw SQL query to select zero quants. Since raw SQL does not trigger an automatic ORM flush, the quant state could be out-of-sync with the database at the time of the query, making the deletion non-deterministic. Add an explicit `flush_all()` before calling `_unlink_zero_quants()` in the test to ensure the database reflects the latest ORM state and avoid random failures. Runbot-241210 Forward-Port-Of: odoo/odoo#252006
A previous bug prevented users from correctly updating both the last month and last day of their fiscal year when managing multiple companies. This update corrects the underlying code to ensure constraints are checked after all changes have been applied, resolving the validation error and allowing for accurate fiscal year settings.
Original PR description
Having a parent company and a chid company selected, and changing both the last day and the last month of the fiscal year as the same time raises a ValidationError. This is because in this case, in the write we successively modify each changed delegated fields from root company to the branches. Then, when checking the constrains we loop through all delegated fields and check if the value of the branches are the same as the root company. This check triggers the error as all values are not set yet. By using a write on branches for all changed delegated fields instead of a simple assignation, the constrains check occurs once all the value have been updated. Steps: - Have a root company and a branch - Select both in company selector - Go to Accounting configuration - Change fiscalyear last month AND ast day at the same time - Save -> ValidationError in `_check_root_delegated_fields` opw-5431145 Forward-Port-Of: odoo/odoo#251941 Forward-Port-Of: odoo/odoo#241413
This update resolves a technical error that prevented users from correctly ordering stock when using the replenishment multiple feature. The fix corrects a calculation error within the stock management system, ensuring accurate order quantities are generated for replenishment rules. This improves the reliability of stock ordering processes.
Original PR description
Backport of: https://github.com/odoo/odoo/commit/fe806166968d55a70f5bf335dcb3633e18d8ecc7 Steps to reproduce: - Create a storable product “P1”: - UoM: Unit and Pack of 6 - Purchase tab: add any vendor - Go to Replenishment and create a new rule: - Product: P1 - Min: 10 - Max: 100 - Replenishment Multiple: Pack of 6 - Select the line and click “Replenish” → “Order to Max” Issue: A traceback is raised: “TypeError: unsupported operand types in: uom.uom(2,) - 4.0” In `_get_qty_to_order`, we compute the quantity to order and then adjust it according to the replenishment multiple, but we try to Subtract the rounded remainder from the uom (which is a recordset) instead of the quantity (which is a float). opw-5947919 Forward-Port-Of: odoo/odoo#251338 Forward-Port-Of: odoo/odoo#250608
This update resolves a technical issue preventing the holiday tour from functioning correctly within the calendar view. The fix ensures the tour consistently displays and operates as intended, improving the user experience. This change was identified and addressed through automated testing.
Original PR description
This fix adjusts the tour in `test_hours_time_off_request_calendar_view` as it was failing in some cases. runbot error 237682 Forward-Port-Of: odoo/odoo#249458 Forward-Port-Of: odoo/odoo#249267
This update fixes an issue where payslips weren't generating correct work entries for employees with no recorded working hours. The change ensures that all employees, including those with flexible work arrangements, receive accurate payslips. This improves payroll accuracy and reporting.
Original PR description
**Version:** - 19.0 **Steps to reproduce:** - Create an employee. - Leave the Working Hours field empty. - Set the contract dates and a wage. - Create a payslip using the smart button. **Issue:** - Worked day lines are empty for flexible employees when the payslip is created from the smart button. **Cause:** - Flexible employees were being skipped because their working hours were empty, which results in work entries not being generated. **Solution:** - Updated the condition to also generate work entries for flexible employees. Task-5431870 Forward-Port-Of: odoo/enterprise#103101
This update corrects a visual issue where the 'invalid locators' alert was appearing incorrectly within a form due to an outdated website view. The fix ensures the alert is displayed correctly after the 'Be aware' alert, resolving a potential user experience problem. This change improves the clarity and usability of the application.
Original PR description
The XPath `//div[hasclass('alert-info')]` used to insert the invalid locators warning matches multiple elements since the website module has another `alert-info` div inside the visibility field:…
The XPath `//div[hasclass('alert-info')]` used to insert the invalid locators warning matches multiple elements since the website module has another `alert-info` div inside the visibility field: https://github.com/odoo/odoo/blob/31c199f3d19b8f9c54d582b6a5c4684e1ed38d0a/addons/website/views/website_pages_views.xml#L221
<img width="1065" height="633" alt="image" src="https://github.com/user-attachments/assets/dab8955c-d01b-4682-871a-b7499ed99297" />
<img width="1427" height="986" alt="image" src="https://github.com/user-attachments/assets/a05efb5d-254b-4e3a-ad14-530ae6718be6" />
On databases created before the invalid locators feature was added, the website inherited view has a lower ID than the web one, so it is applied first. This causes the XPath to match the wrong element and places the warning in the middle of the form fields instead of after the "Be aware" alert. This is not reproducible on runbot since fresh databases always have the correct ID ordering.
<img width="2291" height="956" alt="image" src="https://github.com/user-attachments/assets/fc7eee11-c66e-4d84-b827-f2ed61c76a97" />
We now target the correct alert div that is a direct child of the sheet element. Hence, the inheriting order no longer affect the location of the warning.
---
I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr
Forward-Port-Of: odoo/odoo#251631This update resolves a rare issue in the Gantt view that could cause it to crash when users interact with search filters. The fix prevents a race condition that occurred when a search dropdown closed while a pill was being hovered, ensuring smoother operation and preventing unexpected errors.
Original PR description
This commit fixes a traceback in the Gantt view caused by a race condition during search operations. If a user clicks a search dropdown item located directly above a task pill, and that search filters out the underlying pill, a `pointerenter` event can fire on the pill just as the dropdown closes. Because the search amy already be applied, the renderer could lose track of the pill, causing the handler to crash when trying to access it. This commit adds a safety check to the event handler to exit early if the hovered pill is no longer found in the renderer. Forward-Port-Of: odoo/enterprise#109545