Daily updates from Odoo
Navigate
Branch
Monday, June 15, 2026
233 changes
18 changes
Resolved issues and error corrections
This update clarifies bank statements for transactions split into multiple lines. Previously, all split lines received the same message, making it difficult to understand each charge. Now, transaction details are added to the label, aligning with CodaBox's breakdown and improving user clarity.
Original PR description
Currently, when global transaction is split into multiple lines, Odoo assigns the exact same communication text to every single split line. This makes it difficult for users to identify what each specific charge is for. To fix this, this commit introduces the transaction category data. Using this data to append specific transaction details to the end of the communication label. As a result, each split line now has a clear, descriptive label that closely matches the detailed breakdown provided by CodaBox. task-6059709 Forward-Port-Of: odoo/enterprise#113811
This update resolves a crash issue that occurred during pivot table autofill operations, specifically with formulas like `=PIVOT(1)`. By adding a check for simple `=PIVOT(...)` formulas, the system now consistently prevents crashes and maintains predictable behavior, ensuring a smoother user experience.
Original PR description
Current behavior before PR: - Autofill on formulas like `=PIVOT(1)` could crash after the refactor in e34c0a3, the new logic tried to process all pivot formulas. - However, simple `=PIVOT(...)` cases do not require any change in formula during autofill. Desired behavior after PR is merged: - Add an early return for pivot formulas that are not `PIVOT.VALUE` or `PIVOT.HEADER`, avoiding unnecessary processing. - Ensure `=PIVOT(...)` formulas remain unchanged during autofill, preventing crashes and keeping behavior consistent. Task: [6158888](https://www.odoo.com/odoo/project/2328/tasks/6158888) Forward-Port-Of: odoo/enterprise#119390
This update resolves an issue where duplicating a Time Off type with a Payroll Code would trigger an error due to a uniqueness constraint. The fix automatically appends a suffix to the code field during duplication, allowing for multiple time off types with the same code but different names.
Original PR description
Steps to reproduce: ------------------------------------------ 1. Install Time Off module 2. Create a new Time Off type with Payroll Code (e.g, TEST) 3. Duplicate the Time Off type Observation:…
Steps to reproduce: ------------------------------------------ 1. Install Time Off module 2. Create a new Time Off type with Payroll Code (e.g, TEST) 3. Duplicate the Time Off type Observation: ------------------------------------------ User Error raised: ``` Cannot insert 'Test (copy)': Work entry type 'Test' of code 'TEST', with no country assigned, already exists. ``` Issue: ------------------------------------------ When you duplicate a Time off type, Odoo's default `copy()` method doesn't modify the code field. The `_check_code_unicity` constraint enforces that each combination of `code` and `country_id` must be unique. Since your duplicated record has the same `code`, the same `country_id` and a different `name`. The constraint correctly raises an error. Solution: ------------------------------------------ Override the `copy()` method to automatically append a suffix to the code field when duplicating, similar to how the name field gets '(copy)' appended. opw-6225931 Forward-Port-Of: odoo/odoo#265144
This update enhances the accuracy of partner searches within Odoo by using exact name matches instead of partial matches. This prevents incorrect partner identification and ensures more reliable data retrieval, particularly important for UBL import processes. The system now also uses bank account details to further refine partner identification.
Original PR description
Before this commit: * Partner was searched using contains on the name, which could match unrelated partners with similar names (e.g. 'Global Tech' matching 'Global Technologies Ltd'). After this commit: - Partner retrieval now uses an exact name match to avoid incorrect matches caused by partial name search. - The search limit is set to 1 to ensure a consistent result when multiple partners are found. Technical: - Replaced `ilike` with `=ilike` in the name search domain. task-5485563 Forward-Port-Of: odoo/odoo#269525 Forward-Port-Of: odoo/odoo#250309
This update fixes an issue where URLs using forward slashes were incorrectly simplifying into single words. Previously, `/` characters were silently removed, leading to unexpected URL formatting. This change restores the original behavior, ensuring URLs with forward slashes are correctly converted to hyphens, improving URL consistency and reliability.
Original PR description
After Unicode slug support was introduced in https://github.com/odoo/odoo/commit/926e45aa93ffc3f74fe9bf4ae8f06642976c2ae5, `/`
characters started being silently removed instead of treated as
slug boundaries.
As a result:
"foo/bar" -> "foobar"
while it should instead generate:
"foo/bar" -> "foo-bar"
This restores the previous behavior by treating each non word character
as separators normalized to `-`.
task-6219984
Forward-Port-Of: odoo/odoo#269621
Forward-Port-Of: odoo/odoo#264557This update fixes an issue where the Odoo tour system would throw an error if a tour was only stored in the user's browser but not in the database. Now, the system gracefully handles this situation by displaying a notification and clearing the tour data, ensuring a smoother user experience.
Original PR description
Before this commit if there was a tour in the localStorage but no more in the DB, an error was threw. Now, instead, there is a notification when starting a tour that doesn't exist in the DB, but no more error when trying to resume a tour that is no more in the DB. The localStorage is cleaned instead. TASK-6229383 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr
This update fixes an error in the vehicle contract report that was incorrectly adding recurring costs. The issue stemmed from overlapping database queries, leading to inflated totals. The fix replaces multiple joins with a single, more efficient query, ensuring accurate cost reporting for vehicles.
Original PR description
Steps to reproduce: ------------------- 1. Install Fleet with demo data. 2. Create a contract for a vehicle (A) with a recurring cost of 1000 and "Monthly" frequency. 3. Go to Reporting > Costs and…
Steps to reproduce: ------------------- 1. Install Fleet with demo data. 2. Create a contract for a vehicle (A) with a recurring cost of 1000 and "Monthly" frequency. 3. Go to Reporting > Costs and verify the monthly cost (it shows 1000). 4. Create another contract for the same vehicle (A) with a recurring cost of 50 and "Monthly" frequency. 5. Check the monthly cost again. Issue: ------ The reported cost is incorrect. Instead of 1050 (1000 + 50), it shows 2100. Cause: ------ The query uses multiple LEFT JOINs on the contract table, including: https://github.com/odoo/odoo/blob/9ca36dbe53692309bac84329de3b54a1c510cce0/addons/fleet/report/fleet_report.py#L103 These joins overlap and produce duplicate rows for the same vehicle and month, which results in inflated cost totals. Solution: --------- Replace the multiple LEFT JOINs with a single LATERAL join. This ensures the contract table is processed once per vehicle per month and avoids duplication, resulting in correct totals. **Before:** <img width="940" height="609" alt="image" src="https://github.com/user-attachments/assets/e5b3e747-1135-4674-97c9-4e4fd9986dfd" /> **After:** <img width="1053" height="590" alt="image" src="https://github.com/user-attachments/assets/f0df3819-07fb-4de5-aab3-5b4c6f10d213" /> opw-6024132 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#256051
This update resolves an error that occurred when users removed the date field in the Accrued Expense Entry wizard. The fix adds a check to ensure the date field has a valid value before performing comparisons, preventing a type error. This ensures the feature continues to function correctly.
Original PR description
Currently, error occurs when user removes date on Accrued Expense Entry wizard. Steps to replicate: - Install `purchase` and `accountant` with demo. - Open any Purchase Order > Click on cog menu >…
Currently, error occurs when user removes date on Accrued Expense Entry wizard.
Steps to replicate:
- Install `purchase` and `accountant` with demo.
- Open any Purchase Order > Click on cog menu > Accrued Expense Entry.
- Remove value from `date` and click else where.
Error:
```
File '/home/odoo/odoo19/community/addons/account/wizard/accrued_orders.py', line 67, in _compute_reversal_date
if not record.reversal_date or record.reversal_date <= record.date:
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
TypeError: '<=' not supported between instances of 'datetime.date' and 'bool'
```
Cause:
- As the user removed value from `date`, [here] `record.date` is received as False.
- As a result the comparison `record.reversal_date <= record.date` causes this error to occur.
Solution:
- Added a conditional check for `date` before the date comparison.
[here]: https://github.com/odoo/odoo/blob/8791cdcd89ea3cb56b1fac63b3e2ffbd2956a912/addons/account/wizard/accrued_orders.py#L67
No ID
---
I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr
Forward-Port-Of: odoo/odoo#269418
Forward-Port-Of: odoo/odoo#262568This update fixes an issue where the VAT books report was incorrectly including withholding tax in the total VAT calculation for Spanish companies. The fix excludes 'retencion' (withholding tax) from the VAT calculation, ensuring accurate reporting of VAT liabilities. This ensures compliance and reliable financial reporting.
Original PR description
Step to reproduce - install `l10n_es_reports` and switch to ES company - create a invoice, add a product, set price = 100 - add two taxes (one should be withholding tax) ex: 21%G and 19%whi - confirm it, total payable is now 100 + 21 - 19 = 102 - open vat Books report for ES, see line for this invoice Observation: - for this invoice, in total vat column, we get 102 value - it should be 100+ 21 i.e 121 as we do not include withholding taxes in total vat Cause: - the query for report used to sum up all the taxes for calculating vat Fix: - excluded tax of type "retencion" in tax summation opw-6082329 Forward-Port-Of: odoo/enterprise#120270 Forward-Port-Of: odoo/enterprise#114137
This update resolves an issue preventing users from selecting contacts with VAT numbers as feedback recipients within appraisals. The previous system incorrectly identified VAT-enabled contacts as 'companies,' limiting recipient options. Removing a restrictive domain allows for full recipient selection, streamlining the feedback process.
Original PR description
Issue: ---------------------------------------- We cannot add a contact with a VAT as a feedback recipient. Steps to reproduce: ---------------------------------------- - Have a contact with a VAT - Go to a confirmed appraisal and select 'Ask Feedback' - We cannot add the contact as recipient. Cause: ---------------------------------------- There is a domain on the field to only accept non company contacts. The idea of the domain was to restrict the field to persons only. But since f2965048f60fe6c815b3e50fa714c97a93dfb5d3 the field `is_company` is computed based on the VAT presence. So a contact with a VAT specified is considered a company. Solution: ---------------------------------------- Remove the domain. We allow to select all contacts, the users will have to do the sort. opw-6280689 Forward-Port-Of: odoo/enterprise#120236
This update resolves an issue where closing and reopening records with x2many fields would cause a crash. The fix ensures that all related lists and records share the same 'fields' object, correctly updating the display of property fields within those lists. This improves stability and user experience when working with complex data structures.
Original PR description
Have an x2many field displayed as a list in a form view. In the arch, the x2many form view **isn't** inlined. In that x2many form view, there's a properties field. When a record is clicked,…
Have an x2many field displayed as a list in a form view. In the arch, the x2many form view **isn't** inlined. In that x2many form view, there's a properties field. When a record is clicked, `extendRecord` is called to add the new fields (those of the form) into `this.fields` and those fields are fetched. If there're properties in the property definition, fake fields are created to represent them (see `_processProperties`). However, because of extendRecord, the static list and the record don't share the same reference to the `fields` object. As a consequence, the `fields` object of the static list isn't updated with the fake property fields. If the user closes the record, and opens/closes it again, there's a crash, because the record is re-updated with the fields of the static list, and thus doesn't know about those property fields anymore. This commit fixes the issue by ensuring that we keep the same `fields` object when extending a record, s.t. the list and all its records always share the same object. Bug originally reported here: https://github.com/odoo/odoo/pull/268312 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269717
This update fixes a display issue where employee holiday availability dates in the internal chat (Discuss) were incorrectly showing the previous day when users were in negative timezones. The fix ensures dates are displayed accurately regardless of the user's timezone, improving communication and reducing confusion.
Original PR description
Issue: ---------------------------------------- When in a negative timezone, the "Out of Office until..." text in discuss shows the day before. Steps to reproduce:…
Issue: ---------------------------------------- When in a negative timezone, the "Out of Office until..." text in discuss shows the day before. Steps to reproduce: ---------------------------------------- - Change the timezone of the user to "America/Toronto" for example - Have an employee currently on leave until tomorrow - Open discuss to chat with this employee - The "Out of Office until..." shows today's date Cause: ---------------------------------------- When calling `toLocaleString()` without a timezone specified in the options, the date is converted to local time (in the browser's timezone). Here `persona.out_of_office_date_end` is just a date, `deserializeDateTime()` converts it to a timestamp, so the same day at 0am. Then if the timezone is negative, the timestamp becomes an hour the previous day when calling `toLocaleString()`. The format we give `DateTime.DATE_MED` doesn't include hours, so we just display the previous date. Solution: ---------------------------------------- Add `timeZone:"UTC"` in the options to avoid the timezone conversion. opw-6252040 Forward-Port-Of: odoo/odoo#268886 Forward-Port-Of: odoo/odoo#267479
This update fixes a bug where purchase order line prices were incorrectly set to zero when using reordering rules with expired vendor price lists. The fix ensures the system uses the correct product cost or a valid fallback price, preventing inaccurate purchase order pricing. This improves the reliability of purchase order generation.
Original PR description
Version: ---------- - 18.0+ Steps to reproduce: ----------------------- 1 - Install the `purchase` and `stock` modules. 2 - Create a storable product with tracking enabled. Set the Cost (standard…
Version: ---------- - 18.0+ Steps to reproduce: ----------------------- 1 - Install the `purchase` and `stock` modules. 2 - Create a storable product with tracking enabled. Set the Cost (standard price) to 50. 3 - Open the product form and go to the Purchase tab. * Add a vendor with: * Quantity: 2 * Price: 10 4 - Create a Reordering Rule for this product: * Route: Buy * Trigger: Manual * To Order Quantity: 2 5 - Click on the Order button to generate a purchase order. 6 - Open the generated Purchase Order and verify the Unit Price on the purchase order line. 7 - Open the same product and go to the Purchase tab. In the existing vendor line, add an End Date lower than today so the vendor pricelist becomes expired. 8 - Reopen the same reordering rule. Change To Order Quantity to 1. 9 - Click on the Order button again Issue: ----- The generated purchase order line gets a Unit Price of 0 instead of keeping the product cost or a valid fallback price. Root Cause: -------------- - When clicking on `Order`, it triggers `action_replenish`, which calls the procurement flow: `_procure_orderpoint_confirm` → `run` → `run` → `_run_buy`. - Inside `_run_buy`, the system checks whether a `purchase.order.line` already exists. In this case, the PO line exists, so it calls `_update_purchase_order_line`. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/purchase_stock/models/stock_rule.py#L137 - In `_update_purchase_order_line`, the system tries to fetch a seller using `_select_seller`, - which internally calls `_get_filtered_sellers`. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/product/models/product_product.py#L759 - However, if the seller's `end_date` is less than `today`, `_get_filtered_sellers` skips that seller and returns no valid seller. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/product/models/product_product.py#L731-L733 - As a result, `_update_purchase_order_line` does not find any seller and falls back to setting `price_unit` to `0`, causing the purchase order line price to be updated incorrectly. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/purchase_stock/models/stock_rule.py#L259 --- opw-6117461 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269971 Forward-Port-Of: odoo/odoo#262396
This update ensures that non-mandatory text fields in sign documents appear with a transparent background when using dark mode in browsers. A recent update to PDF.js caused a color mismatch, and this fix corrects the styling to match the overall page aesthetic, improving the user experience.
Original PR description
## Issue When using the browser's dark mode, non-mandatory text fields in sign documents appear with a dark background, which does not match the aesthetic of the rest of the page. ## Steps to…
## Issue
When using the browser's dark mode, non-mandatory text fields in sign documents appear with a dark background, which does not match the aesthetic of the rest of the page.
## Steps to reproduce
1. Set your browser's theme to a dark theme (in Chrome, go to Settings > Appearance > Theme, chose a theme from the dark options)
2. Install Sign (`sign`)
3. Open a Sign template and add 3 Text fields:
- Mandatory
- Non-mandatory
- Read-only (for comparison)
4. Click *Sign Now*
5. **The non-mandatory text field has a dark background.**
## Cause
Since a [PDF.js update](https://github.com/mozilla/pdf.js/commit/ae1cbc6a9ecc738d6777830488ad5481b97338bc), the `light dark` color-theme was added to `:root`. This means that the element will react to the settings of the browser and adapt its background and text color. In this case, there's no other `background-color` provided to mandatory fields, resulting in them using the dark color of the browser theme.
## Fix
We make the default background of text fields transparent then we update the selector of `.o_sign_sign_item_required` to prevent their `background-color` from being overwritten by that new transparent background.
| | Before | After |
|------------|--------|-------|
| **Light mode** | <img width="211" height="99" alt="6213059-before-light" src="https://github.com/user-attachments/assets/c4c70394-c7c2-4dbf-92b9-c1362d1cf9c8" /> | <img width="207" height="89" alt="6213059-after-light" src="https://github.com/user-attachments/assets/63142be5-9f7d-4d5d-94e8-ef9428e1b778" /> |
| **Dark mode** | <img width="220" height="95" alt="6213059-before-dark" src="https://github.com/user-attachments/assets/19149c3d-511e-407c-821e-f318f373368a" /> | <img width="210" height="103" alt="6213059-after-dark" src="https://github.com/user-attachments/assets/0b412d4f-061f-41b3-aae9-569b9a8219dc" /> |
opw-6213059
Forward-Port-Of: odoo/enterprise#117589This update fixes an issue where new timesheet entries created from the systray menu were always added to the bottom of the list, making it difficult to see the most recent entries. The fix reorders entries to display the newest timesheet entry at the top, improving usability. This change ensures a more intuitive experience for users managing their timesheets.
Original PR description
## Issues When creating a new timesheet entry from the systray menu, that entry is added at the end of the list, which is inconvenient when the list gets long, as it requires to scroll through the…
## Issues When creating a new timesheet entry from the systray menu, that entry is added at the end of the list, which is inconvenient when the list gets long, as it requires to scroll through the entirety of it to see the most recent entry. ## Steps to reproduce 1. Install Timesheets (`timesheet_grid`) 2. Open the systray menu 3. Create two timesheet entries 4. The second (= most recent) entry appears below the first (= oldest) entry ## Cause Since https://github.com/odoo/enterprise/commit/5901619141c81085111f2ee65b54492abf1e324f the entries are sorted based on the create date in ascending orer. This means that the oldest entries appear at the top, and the most recent at the bottom. On top of that, new entries were added at the end of the list instead of the start. ## Test The existing test `Creating a new timesheet places it at the top of the list` was only adding one entry to the list, thus was not properly testing **where** the new entries were added. opw-6284059 Forward-Port-Of: odoo/enterprise#120258
This update resolves an issue where HR users without payroll access couldn't view employee type counts due to conflicting access restrictions in the system's data. The fix uses a system-level bypass to allow HR users to correctly calculate these counts, ensuring accurate reporting.
Original PR description
**Steps to Reproduce** 1. Create a database on v19.3. 2. Install `hr` and `hr_payroll`. 3. Create or log in as a user who only has access rights for the Employee app (`hr`) and no Payroll access. 4.…
**Steps to Reproduce**
1. Create a database on v19.3.
2. Install `hr` and `hr_payroll`.
3. Create or log in as a user who only has access rights for the Employee app (`hr`) and no Payroll access.
4. Go to **Employees → Configuration → Employee → Employee Types**. Opening the Employee Types menu raises the following error:
```python
You do not have enough rights to access the field "employee_type_id" on
Employee Contract (hr.version). Please contact your system administrator.
Operation: read
User: 2
Groups: allowed for groups 'Payroll / Assistant'
```
**Issue Description:**
The field `employee_type_id` is defined in both modules with different group restrictions:
* In `hr/models/hr_version.py`, the [field](https://github.com/odoo/odoo/blob/f7e87637d5c47047ebffda0f3c929c25022c3f27/addons/hr/models/hr_version.py#L184) is restricted to **HR Managers**.
* In `hr_payroll/models/hr_version.py`, the [field](https://github.com/odoo/enterprise/blob/acd831acd0f59f7b8c15bccfb6da0c3969fc3f6d/hr_payroll/models/hr_version.py#L41 ) is extended with the **Payroll / Assistant** group.
When both modules are installed, access to `hr.version.employee_type_id` requires Payroll permissions.
In v19.3, [PR #241780](https://github.com/odoo/odoo/pull/241780/changes) introduced the `employee_count` [computation](https://github.com/odoo/odoo/blob/f7e87637d5c47047ebffda0f3c929c25022c3f27/addons/hr/models/hr_employee_type.py#L25 ) on `hr.employee.type`. During this computation, `_read_group()` is executed on `hr.employee` using the domain.
HR-only users (without hr_payroll.group_hr_payroll_user) cannot read the field, causing below traceback.
**Solution:**
Use `.sudo()` to bypass access control for the system-level computation. This allows:
- HR users without payroll rights to view employee type counts
- The computation to complete without access errors
**Traceback:**
```python
File "/home/odoo/src/odoo/saas-19.3/addons/hr/models/hr_employee_type.py"
line 25, in _compute_employee_count
employee_count_by_employee_type = dict(self.env['hr.employee']._read_group(
...
File "/home/odoo/src/odoo/saas-19.3/odoo/orm/models.py", line 2732, in
check_field_access
raise AccessError(error_msg)
odoo.exceptions.AccessError: You do not have enough rights to access the field
"employee_type_id" on Employee Contract (hr.version).
Operation: read
User: 8
Groups: allowed for groups 'Payroll / Assistant'
```
opw-6246367
upg- 4302826
tbg- 2751
Description of the issue/feature this PR addresses:
Current behavior before PR:
Desired behavior after PR is merged:
---
I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-prThis update corrects a bug that prevented new online account connections for Canadian bank accounts (without IBANs). The fix skips unnecessary journal checks when an account number is missing, preventing misleading error messages and ensuring proper connection creation. Users with Canadian bank accounts should now experience a smoother connection process.
Original PR description
…unt number When a provider returns an account without `account_number` (typical for Canadian banks, which do not use IBANs), the existing-journal search ran with `bank_account_number = False`.…
…unt number When a provider returns an account without `account_number` (typical for Canadian banks, which do not use IBANs), the existing-journal search ran with `bank_account_number = False`. Because `bank_account_number` is a related field on `bank_account_id.account_number`, that search matched every bank journal in the user's allowed companies whose `bank_account_id` was unset. If any of those journals was tied to a connected online link, the new sync was blocked with the misleading error "There's already a synchronized journal linked to this IBAN", even though no IBAN was involved. Skip the search entirely when `account_number` is falsy: without an identifier there is nothing meaningful to dedup against, and the downstream code already handles `existing_journals` being empty by creating a fresh journal. Note: when the provider omits `account_number`, a delete-and-recreate of the connection will now create a fresh journal rather than coincidentally reusing an unlinked empty-`bank_account_number` journal. That reuse path already failed (with a spurious "IBAN already connected" error) as soon as the user had more than one such journal, so the prior behavior was not reliable. The supported recovery path remains the reconnect button on the existing journal, which uses the `active_id` branch and is unchanged. opw-6253563 Forward-Port-Of: odoo/enterprise#119848
This update fixes an issue where Latin American invoices weren't correctly displaying company-specific document layouts (like 'Bubble') in the header. The change ensures that custom headers are displayed alongside the layout image, providing accurate and branded invoice presentation for LATAM clients. This improves the professional appearance of invoices.
Original PR description
Problem: When printing an invoice for a Latin American (LATAM) company, the company's document layout is not used in the header of the invoice. For example, if an Argentinian company has set up a…
Problem: When printing an invoice for a Latin American (LATAM) company, the company's document layout is not used in the header of the invoice. For example, if an Argentinian company has set up a Bubble layout as its document layout, the header of the invoice will not have the bubble. Steps to reproduce: 1. Install l10n_ar 2. Create an invoice using Electronic Sales Journal 3. Set document layout to Bubble in the company settings 4. Print the invoice 5. Notice that the header of the invoice does not have the bubble Cause: Most LATAM localizations use custom headers for their reports. In report_templates of l10n_latam_invoice_document, it checks if custom_header is set to decide whether to display the custom header. If custom_header is set, the div with class "header" will be hidden, and the custom header will be displayed after the div with class "header". Since the div with class "header" contains the background image that corresponds to the document layout, the background image will not be displayed when div with class "header" is hidden. Solution: Instead of hiding the entire div with class "header" when custom_header is set, only hide the table inside the header. This way, the background image of the document layout will still be displayed even when a custom header is used. opw-6204062 Forward-Port-Of: odoo/odoo#267164
17 changes
Enhancements to existing features
This update significantly improves the speed of searching for partners within the Point of Sale module, especially when dealing with large customer databases. By optimizing the search process and removing unnecessary sorting, the system responds more quickly, leading to a better user experience. This change focuses on internal performance improvements.
Original PR description
Improve partner search response time on large databases (1M+ rows): - Implement smart field selection based on input type (phone, email, text). - Use prefix search (=ilike) for identifiers and exact match for barcodes. - Remove expensive sorting by complete_name in the backend. - Increase search limit to 500 to reduce network round-trips. task-id: 6143737 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#265943 Forward-Port-Of: odoo/odoo#260347
This update improves the timesheet timer by prioritizing recently used projects, tasks, and helpdesk tickets. This reduces the time users spend searching for relevant records and streamlines the timesheet entry process. The change preserves existing prefill functionality for a seamless experience.
Original PR description
Before this PR --- The systray timer used the default search ordering, making users repeatedly search for projects, tasks, and helpdesk tickets they had recently tracked time on. After this PR --- The systray timer now ranks projects, tasks, and helpdesk tickets according to recent timesheet activity. Frequently used records are surfaced first while preserving the existing prefill behavior, making timer selection faster and requiring fewer manual searches. task - 6216535
This update enhances the Point of Sale system by allowing flexible formatting and parsing of orderline quantities within the decrease quantity popup. This change enables other modules to enforce quantity constraints, such as preventing negative values, improving overall order accuracy and data integrity.
Original PR description
We now allow formatting and parsing quantity on an orderline when using the decrease quantity popup. This allows overriding from other modules to add contraints (e.g. `pos_blackbox_be` prevents from setting negative quantities). see odoo/enterprise#119702 task-5942777 Forward-Port-Of: odoo/odoo#269487
Resolved issues and error corrections
This update clarifies bank statement communications for split transactions. Previously, all lines of a split transaction received the same message, making it difficult to understand each charge. Now, transaction categories are used to add specific details to each line, aligning with CodaBox's breakdown and improving user clarity.
Original PR description
Currently, when global transaction is split into multiple lines, Odoo assigns the exact same communication text to every single split line. This makes it difficult for users to identify what each specific charge is for. To fix this, this commit introduces the transaction category data. Using this data to append specific transaction details to the end of the communication label. As a result, each split line now has a clear, descriptive label that closely matches the detailed breakdown provided by CodaBox. task-6059709 Forward-Port-Of: odoo/enterprise#113811
This update fixes an issue where the vehicle contract report was incorrectly calculating total costs due to overlapping data joins. The change replaces multiple joins with a single, more efficient join, ensuring accurate reporting of recurring costs for vehicles. This improves the reliability of financial reporting within the Fleet module.
Original PR description
Steps to reproduce: ------------------- 1. Install Fleet with demo data. 2. Create a contract for a vehicle (A) with a recurring cost of 1000 and "Monthly" frequency. 3. Go to Reporting > Costs and…
Steps to reproduce: ------------------- 1. Install Fleet with demo data. 2. Create a contract for a vehicle (A) with a recurring cost of 1000 and "Monthly" frequency. 3. Go to Reporting > Costs and verify the monthly cost (it shows 1000). 4. Create another contract for the same vehicle (A) with a recurring cost of 50 and "Monthly" frequency. 5. Check the monthly cost again. Issue: ------ The reported cost is incorrect. Instead of 1050 (1000 + 50), it shows 2100. Cause: ------ The query uses multiple LEFT JOINs on the contract table, including: https://github.com/odoo/odoo/blob/9ca36dbe53692309bac84329de3b54a1c510cce0/addons/fleet/report/fleet_report.py#L103 These joins overlap and produce duplicate rows for the same vehicle and month, which results in inflated cost totals. Solution: --------- Replace the multiple LEFT JOINs with a single LATERAL join. This ensures the contract table is processed once per vehicle per month and avoids duplication, resulting in correct totals. **Before:** <img width="940" height="609" alt="image" src="https://github.com/user-attachments/assets/e5b3e747-1135-4674-97c9-4e4fd9986dfd" /> **After:** <img width="1053" height="590" alt="image" src="https://github.com/user-attachments/assets/f0df3819-07fb-4de5-aab3-5b4c6f10d213" /> opw-6024132 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#256051
This update corrects a technical issue within the HR module that was causing inaccurate reporting related to employee contract overlaps. The fix ensures that contract overlap calculations are now more precise, leading to more reliable data for HR and management decisions. This improves the accuracy of our reporting on employee contracts.
This update resolves a bug that caused crashes when editing records with x2many fields containing properties. The fix ensures that all related data consistently shares the same object, preventing data inconsistencies and improving overall stability. This enhances the reliability of the system when working with complex data structures.
Original PR description
Have an x2many field displayed as a list in a form view. In the arch, the x2many form view **isn't** inlined. In that x2many form view, there's a properties field. When a record is clicked,…
Have an x2many field displayed as a list in a form view. In the arch, the x2many form view **isn't** inlined. In that x2many form view, there's a properties field. When a record is clicked, `extendRecord` is called to add the new fields (those of the form) into `this.fields` and those fields are fetched. If there're properties in the property definition, fake fields are created to represent them (see `_processProperties`). However, because of extendRecord, the static list and the record don't share the same reference to the `fields` object. As a consequence, the `fields` object of the static list isn't updated with the fake property fields. If the user closes the record, and opens/closes it again, there's a crash, because the record is re-updated with the fields of the static list, and thus doesn't know about those property fields anymore. This commit fixes the issue by ensuring that we keep the same `fields` object when extending a record, s.t. the list and all its records always share the same object. Bug originally reported here: https://github.com/odoo/odoo/pull/268312 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269717
This update fixes an issue where purchase order line prices were incorrectly set to zero when using reordering rules with expired vendor pricelists. The fix ensures that the product's original cost or a valid fallback price is used, preventing inaccurate pricing on purchase orders. This improves the reliability of purchase order generation.
Original PR description
Version: ---------- - 18.0+ Steps to reproduce: ----------------------- 1 - Install the `purchase` and `stock` modules. 2 - Create a storable product with tracking enabled. Set the Cost (standard…
Version: ---------- - 18.0+ Steps to reproduce: ----------------------- 1 - Install the `purchase` and `stock` modules. 2 - Create a storable product with tracking enabled. Set the Cost (standard price) to 50. 3 - Open the product form and go to the Purchase tab. * Add a vendor with: * Quantity: 2 * Price: 10 4 - Create a Reordering Rule for this product: * Route: Buy * Trigger: Manual * To Order Quantity: 2 5 - Click on the Order button to generate a purchase order. 6 - Open the generated Purchase Order and verify the Unit Price on the purchase order line. 7 - Open the same product and go to the Purchase tab. In the existing vendor line, add an End Date lower than today so the vendor pricelist becomes expired. 8 - Reopen the same reordering rule. Change To Order Quantity to 1. 9 - Click on the Order button again Issue: ----- The generated purchase order line gets a Unit Price of 0 instead of keeping the product cost or a valid fallback price. Root Cause: -------------- - When clicking on `Order`, it triggers `action_replenish`, which calls the procurement flow: `_procure_orderpoint_confirm` → `run` → `run` → `_run_buy`. - Inside `_run_buy`, the system checks whether a `purchase.order.line` already exists. In this case, the PO line exists, so it calls `_update_purchase_order_line`. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/purchase_stock/models/stock_rule.py#L137 - In `_update_purchase_order_line`, the system tries to fetch a seller using `_select_seller`, - which internally calls `_get_filtered_sellers`. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/product/models/product_product.py#L759 - However, if the seller's `end_date` is less than `today`, `_get_filtered_sellers` skips that seller and returns no valid seller. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/product/models/product_product.py#L731-L733 - As a result, `_update_purchase_order_line` does not find any seller and falls back to setting `price_unit` to `0`, causing the purchase order line price to be updated incorrectly. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/purchase_stock/models/stock_rule.py#L259 --- opw-6117461 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269971 Forward-Port-Of: odoo/odoo#262396
This update ensures that non-mandatory text fields in sign documents appear with a transparent background when using dark mode in a web browser. A recent update to PDF.js automatically adjusted background colors based on the browser theme, causing a visual inconsistency. This fix corrects this issue, maintaining a consistent and professional appearance across all sign documents.
Original PR description
## Issue When using the browser's dark mode, non-mandatory text fields in sign documents appear with a dark background, which does not match the aesthetic of the rest of the page. ## Steps to…
## Issue
When using the browser's dark mode, non-mandatory text fields in sign documents appear with a dark background, which does not match the aesthetic of the rest of the page.
## Steps to reproduce
1. Set your browser's theme to a dark theme (in Chrome, go to Settings > Appearance > Theme, chose a theme from the dark options)
2. Install Sign (`sign`)
3. Open a Sign template and add 3 Text fields:
- Mandatory
- Non-mandatory
- Read-only (for comparison)
4. Click *Sign Now*
5. **The non-mandatory text field has a dark background.**
## Cause
Since a [PDF.js update](https://github.com/mozilla/pdf.js/commit/ae1cbc6a9ecc738d6777830488ad5481b97338bc), the `light dark` color-theme was added to `:root`. This means that the element will react to the settings of the browser and adapt its background and text color. In this case, there's no other `background-color` provided to mandatory fields, resulting in them using the dark color of the browser theme.
## Fix
We make the default background of text fields transparent then we update the selector of `.o_sign_sign_item_required` to prevent their `background-color` from being overwritten by that new transparent background.
| | Before | After |
|------------|--------|-------|
| **Light mode** | <img width="211" height="99" alt="6213059-before-light" src="https://github.com/user-attachments/assets/c4c70394-c7c2-4dbf-92b9-c1362d1cf9c8" /> | <img width="207" height="89" alt="6213059-after-light" src="https://github.com/user-attachments/assets/63142be5-9f7d-4d5d-94e8-ef9428e1b778" /> |
| **Dark mode** | <img width="220" height="95" alt="6213059-before-dark" src="https://github.com/user-attachments/assets/19149c3d-511e-407c-821e-f318f373368a" /> | <img width="210" height="103" alt="6213059-after-dark" src="https://github.com/user-attachments/assets/0b412d4f-061f-41b3-aae9-569b9a8219dc" /> |
opw-6213059
Forward-Port-Of: odoo/enterprise#117589This update fixes an issue where the Datev export incorrectly displayed currency amounts due to using the company currency instead of the invoice's currency. The change ensures accurate reporting of tax and currency rates when exporting ledger data to Datev, improving financial reporting accuracy.
Original PR description
There is an issue in the Datev export functionality. In the current functionality, the code calculates a delta between the taxes in the `tax_totals` and the ones on the journal items. Issue is, the tax amounts from tax_totals were always in company currency, while the entry itself can use a foreign one. This replaces the use of company currency with the use of the invoice's currency and appropriately adjusts the test featuring foreign currency. Steps: Create a foreign currency. Create an invoice with a taxed product using the currency. Export the ledger to Datev. Inspect the resulting csv. Note that neither the final listed price, nor the rate listed for the currency align with the ones in the db. opw-6275889 Forward-Port-Of: odoo/enterprise#120293
This update ensures that inventory counts accurately reflect products without lot numbers. Previously, scanning these products caused incorrect updates to inventory quantities, leading to discrepancies. The fix correctly handles lotless products during inventory adjustments, ensuring accurate tracking.
Original PR description
### Steps to reproduce: 1. Create a product tracked by lot 2. Put 10 units in WH/Stock without lot 3. Inventory > Operations > Adjustments > Physical Inventory 4. Select the line referring to your…
### Steps to reproduce: 1. Create a product tracked by lot 2. Put 10 units in WH/Stock without lot 3. Inventory > Operations > Adjustments > Physical Inventory 4. Select the line referring to your product and request an inventory count + Show Expected Quantity 5. Open the barcode app > Count Inventory 6. Scan your product #### > The line is not selected, in particular, next scans will be re-interpreted as product scans rather than new serial creation for your product. ### Cause of the issue: Scanning your product search a line to select if any: https://github.com/odoo/enterprise/blob/bce04ce24b66fb1a2481274eb3aebdc30a62766e/stock_barcode/static/src/models/barcode_model.js#L1432-L1435 https://github.com/odoo/enterprise/blob/bce04ce24b66fb1a2481274eb3aebdc30a62766e/stock_barcode/static/src/models/barcode_model.js#L1630-L1632 However, the `findLine` will fail since this method calls the `_canOverrideTrackingNumber` to determine if the lot of the barcodData matches the one of the line: https://github.com/odoo/enterprise/blob/bce04ce24b66fb1a2481274eb3aebdc30a62766e/stock_barcode/static/src/models/barcode_model.js#L1859-L1863 But, the override of the `_canOverrideTrackingNumber` method for the `BarcodeQuantModel` does not handle the absence of lotName in the barcodeData correctly as it does not consider that a line without lot can be overridden by an empty lotName: https://github.com/odoo/enterprise/blob/bce04ce24b66fb1a2481274eb3aebdc30a62766e/stock_barcode/static/src/models/barcode_quant_model.js#L729-L731 Note however that the super call does: https://github.com/odoo/enterprise/blob/bce04ce24b66fb1a2481274eb3aebdc30a62766e/stock_barcode/static/src/models/barcode_model.js#L795-L798 ### Issue 2: ### Steps to reproduce: - Steps 1 -> 5 - Click on your product line to select it - Scan a new lot to add one new unit referring to that lot - Confirm (1) - Apply Now #### > User Error: Quant's editing is restricted, you can't do this operation Since the line is selected, you have a currentLine during the `processBarcode` and hence the existing line will be updated using the `lotName``: https://github.com/odoo/enterprise/blob/cf3c2fce8a6b7b2d7547d44a0e4423f887986d52/stock_barcode/static/src/models/barcode_model.js#L1560-L1584 However, writing on the line will then try to write on the related quant during the validation process which will be forbiden since we are not allowed to change the lot of an existing quant: https://github.com/odoo/odoo/blob/e3b0ca11d99b2ef819cdad68b169112cd73668b6/addons/stock/models/stock_quant.py#L351-L360 Now, the issue is that actually due to the nature of the line and of the barcode data, the line lot is not expected to be updated but rather a new line is expected to be created: https://github.com/odoo/enterprise/blob/cf3c2fce8a6b7b2d7547d44a0e4423f887986d52/stock_barcode/static/src/models/barcode_model.js#L795-L798 Additional issue: Fixing issue 1 and 2 highlight and other issue of the validation process: - Steps 1 -> 6 > The line gets selected - Scan a newlot > a new subline is added referring to 1 unit of your new quant - Confirm (1) > Some serials where not counted, set them as missing #### > Check your quants: the 10 unit lotless quant was not updated but a new quant for 1 units was created for your newlot ### Cause of the issue: Applying all quantities is expecting to toggle them as counted before applying to update the existing quants: https://github.com/odoo/enterprise/blob/c8535a7a0e2eae811048a34a0bae187a1fa45311/stock_barcode/static/src/models/barcode_quant_model.js#L72-L82 https://github.com/odoo/enterprise/blob/c8535a7a0e2eae811048a34a0bae187a1fa45311/stock_barcode/static/src/models/barcode_quant_model.js#L287-L296 However, only line tracked by serial numbers are set as counted: https://github.com/odoo/enterprise/blob/c8535a7a0e2eae811048a34a0bae187a1fa45311/stock_barcode/static/src/models/barcode_quant_model.js#L60-L63 opw-6212923 Forward-Port-Of: odoo/enterprise#118373
This update fixes a potential issue in the knowledge article tour process. It ensures the system correctly identifies the target article before allowing users to share, favorite, or edit it. This improves the user experience and prevents errors during these common actions.
Original PR description
With this commit, We ensure we're in the correct article before making any changes (share, add to favorites, edit) using `waitUntil`. We've added a `checkArticle` function to ensure the article is in the correct place in the menu. runbot-error-id~234645 Forward-Port-Of: odoo/enterprise#110123
This update ensures that Latin American invoices correctly display the company's chosen document layout (e.g., Bubble) in the invoice header. Previously, custom layouts weren't being applied, leading to a standard header. This change improves the visual consistency and branding of invoices for LATAM clients.
Original PR description
Problem: When printing an invoice for a Latin American (LATAM) company, the company's document layout is not used in the header of the invoice. For example, if an Argentinian company has set up a…
Problem: When printing an invoice for a Latin American (LATAM) company, the company's document layout is not used in the header of the invoice. For example, if an Argentinian company has set up a Bubble layout as its document layout, the header of the invoice will not have the bubble. Steps to reproduce: 1. Install l10n_ar 2. Create an invoice using Electronic Sales Journal 3. Set document layout to Bubble in the company settings 4. Print the invoice 5. Notice that the header of the invoice does not have the bubble Cause: Most LATAM localizations use custom headers for their reports. In report_templates of l10n_latam_invoice_document, it checks if custom_header is set to decide whether to display the custom header. If custom_header is set, the div with class "header" will be hidden, and the custom header will be displayed after the div with class "header". Since the div with class "header" contains the background image that corresponds to the document layout, the background image will not be displayed when div with class "header" is hidden. Solution: Instead of hiding the entire div with class "header" when custom_header is set, only hide the table inside the header. This way, the background image of the document layout will still be displayed even when a custom header is used. opw-6204062 Forward-Port-Of: odoo/odoo#267164
This update fixes a potential issue where certified point-of-sale configurations could allow users to enter negative quantities on order lines. This has now been resolved across both the backend and frontend of the Odoo system, ensuring accurate order tracking and reporting. This change improves data integrity and prevents errors related to negative stock levels.
Original PR description
Certified pos configs should not allow to set negative quantities on order lines. We now prevent it from both backend and frontend. see odoo/odoo#269487 task-5942777 Forward-Port-Of: odoo/enterprise#119702
This update corrects a potential issue in the Swiss payroll module where users could incorrectly request refunds on payslips. Swiss payroll regulations limit payments to one per month, so the system now directs users to cancel and re-create the payslip for accurate corrections. This ensures compliance with Swiss tax laws.
Original PR description
Prevent refunds for CH payslips since only one payslip per month is allowed for Swiss payroll. Users should cancel the payslip and create a new one to apply corrections. task-5951981 Forward-Port-Of: odoo/enterprise#107943
This update corrects an issue where sale order references were incorrectly linked to the user's company instead of the order's company. This fix ensures accurate reference processing, particularly in multi-company environments, by using the correct company context for journal lookups. This improves the reliability of sale order referencing and payment processing.
Original PR description
Description of the issue/feature this PR addresses: Fixes an issue where the sale order reference computation was fetching the invoice journal based on the logged-in user's current company instead of…
Description of the issue/feature this PR addresses: Fixes an issue where the sale order reference computation was fetching the invoice journal based on the logged-in user's current company instead of the company associated with the specific payment provider or transaction context. This caused incorrect reference processing or errors in multi-company environments when a user was logged into one company but processing an order from another. Current behavior before PR: The function searches for the account.journal using self.company_id.id. Since self in this context (likely a payment provider or transaction record) might be evaluated under the active user's environment context, it fetched the journal from the user's currently active company (allowed_company_ids), disregarding the actual company related to the sale order or the transaction. Desired behavior after PR is merged: The invoice journal search uses the correct company context (e.g., order.company_id.id or the specific company linked to the payment record), ensuring that the sale order reference is processed using the appropriate journal from the correct company, regardless of which company the logged-in user is currently switched into. --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269558
Code cleanup and technical improvements
This update simplifies the bank reconciliation process within Odoo Enterprise. The code has been reorganized to enhance readability and maintainability, making it easier for developers to understand and update. This change improves the overall stability and efficiency of the reconciliation feature.
Original PR description
Reworked the try_auto_reconcile function to make it more readable by creating helper functions and splitting the function into multiple smaller ones. task-6171727 Forward-Port-Of: odoo/enterprise#120430 Forward-Port-Of: odoo/enterprise#116958
22 changes
Enhancements to existing features
This update enhances the synchronization of point-of-sale (POS) transactions with Fiskaly, our payment processing partner. It separates flows for retail and restaurant orders, ensuring more accurate and timely updates are sent, particularly during kitchen synchronization for restaurants. This improves the reliability of financial reporting.
Original PR description
In this commit: ------------------ - Maintain separate Fiskaly transaction flows for retail (short tx) and restaurant (long tx) orders as discussed with the Fiskaly team. - `Initialize order…
In this commit: ------------------ - Maintain separate Fiskaly transaction flows for retail (short tx) and restaurant (long tx) orders as discussed with the Fiskaly team. - `Initialize order transactions` with an empty payload when the `first product` is added. - Start `receipt transactions` with an empty payload when the `first payment line` is added. - For retail flows, no intermediate order updates are sent to Fiskaly before finalization. - For restaurant flows, create additional transaction updates during kitchen synchronization. Ensure already synchronized products are not resent, and only newly added or updated quantities are included in the payload. - `Finalize order and receipt transactions` with complete order lines and payment details when we validate the order. task: 6208963 Reference: <img width="1863" height="1285" alt="de_tss_flow" src="https://github.com/user-attachments/assets/9140788e-7948-4a08-9f11-27197b22ca8b" /> Forward-Port-Of: odoo/enterprise#119912 Forward-Port-Of: odoo/enterprise#117526
This update enhances the Point of Sale system by allowing more flexible formatting and parsing of order quantities within the decrease quantity popup. This change enables other modules to enforce quantity constraints, like preventing negative values, improving overall order accuracy and data integrity.
Original PR description
We now allow formatting and parsing quantity on an orderline when using the decrease quantity popup. This allows overriding from other modules to add contraints (e.g. `pos_blackbox_be` prevents from setting negative quantities). see odoo/enterprise#119702 task-5942777 Forward-Port-Of: odoo/odoo#269487
This update enhances the visual appearance of both customer receipts and preparation tickets within the Point of Sale system. Specifically, font styling has been improved and floor information is now displayed alongside table numbers on preparation tickets, providing clearer details for staff.
Original PR description
In this commit - --------------- Enhanced font styling for receipt and preparation ticket Added floor information next to table number on preparation ticket Task - 6125322 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#260559
Resolved issues and error corrections
This update clarifies bank statements for transactions split into multiple lines. Previously, all split lines received the same message, making it difficult to understand each charge. Now, transaction category data is used to add specific details to each line, aligning with CodaBox's reporting and improving user clarity.
Original PR description
Currently, when global transaction is split into multiple lines, Odoo assigns the exact same communication text to every single split line. This makes it difficult for users to identify what each specific charge is for. To fix this, this commit introduces the transaction category data. Using this data to append specific transaction details to the end of the communication label. As a result, each split line now has a clear, descriptive label that closely matches the detailed breakdown provided by CodaBox. task-6059709 Forward-Port-Of: odoo/enterprise#113811
This update resolves an issue where attendees received duplicate emails when rescheduling meetings. The fix prevents a nested calendar event write, which was causing the duplicate notifications. This ensures attendees only receive one email notification for meeting date changes.
Original PR description
Steps to reproduce: 1. Install CRM, Calendar, and Contacts. 2. Create a contact with an email address you can receive emails on. 3. Configure an outgoing email server. 4. Open a CRM lead and create a…
Steps to reproduce: 1. Install CRM, Calendar, and Contacts. 2. Create a contact with an email address you can receive emails on. 3. Configure an outgoing email server. 4. Open a CRM lead and create a meeting activity using the calendar. 5. Add the created contact as an attendee of the meeting. 6. Return to the lead and click the Reschedule button on the activity. 7. Select the same meeting and change its start date to a future date. Issue: - Attendees receive the meeting date-change email twice. Root cause: - When a calendar event linked to an activity is rescheduled, the event write syncs the new start date to the related activity through `_sync_activities`. That activity write was not marked as calendar-originated after commit https://github.com/odoo/odoo/commit/bc090486bd7810b1b0af1bae398255a2d6615f09, so `mail.activity.write` treated the updated deadline as an activity-originated change and wrote back to the same calendar event. https://github.com/odoo/odoo/blob/8cbb0fe91a35fcdb4a7e4e1a7e8afe40b1691f11/addons/calendar/models/calendar_event.py#L779 https://github.com/odoo/odoo/blob/8cbb0fe91a35fcdb4a7e4e1a7e8afe40b1691f11/addons/calendar/models/mail_activity.py#L24-L33 - This created a nested calendar event write. Both the nested write and the original write then triggered attendee date-change notifications, resulting in duplicate emails. Solution: - Pass the existing `calendar_event_meeting_update` context flag when syncing calendar event changes to linked activities. This prevents the activity sync from writing back to the event while preserving activity-to-event rescheduling. opw-6209956 Forward-Port-Of: odoo/odoo#266675
This update resolves an issue where closing and reopening x2many fields with properties in Odoo caused a crash. The fix ensures that the shared 'fields' object is maintained when extending records, allowing the list and its records to consistently reflect property changes. This improves stability and prevents unexpected errors when working with complex data structures.
Original PR description
Have an x2many field displayed as a list in a form view. In the arch, the x2many form view **isn't** inlined. In that x2many form view, there's a properties field. When a record is clicked,…
Have an x2many field displayed as a list in a form view. In the arch, the x2many form view **isn't** inlined. In that x2many form view, there's a properties field. When a record is clicked, `extendRecord` is called to add the new fields (those of the form) into `this.fields` and those fields are fetched. If there're properties in the property definition, fake fields are created to represent them (see `_processProperties`). However, because of extendRecord, the static list and the record don't share the same reference to the `fields` object. As a consequence, the `fields` object of the static list isn't updated with the fake property fields. If the user closes the record, and opens/closes it again, there's a crash, because the record is re-updated with the fields of the static list, and thus doesn't know about those property fields anymore. This commit fixes the issue by ensuring that we keep the same `fields` object when extending a record, s.t. the list and all its records always share the same object. Bug originally reported here: https://github.com/odoo/odoo/pull/268312 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269717
This update addresses a misleading message appearing in self-order takeout/delivery emails. Due to recent code changes, emails were being sent before payment processing, leading to the incorrect 'Attached you will find you receipt' mention. To avoid confusion, this fix removes the mention until the receipt can be reliably rendered.
Original PR description
Currently, when takeout and delivery mails are sent out to clients the mention "Attached you will find you receipt" can be seen. Since this commit https://github.com/odoo/odoo/commit/a0b567508ffeb572a3c36bf28ae085d766d95f18 we now send the email only from the backend but the receipt cannot be rendered from the backend so we're never able to send it. We were aware of this limitation at the time and decided to go forward with it. It was better than havin no mail sent. At that time the mail was sent prior to the order being paid so we wouldn't see the "Attached you will find you receipt" message anyway. Recently the code has been update to send the mail after the payment was processed so the mention appears. Since it can be misleading we'll remove the mention for now. opw-6197985 Forward-Port-Of: odoo/odoo#266004
This update fixes an issue where purchase order line prices were incorrectly set to zero when using reordering rules. The fix addresses a problem where the system failed to find a valid vendor price when a vendor's pricing had expired, leading to inaccurate pricing on purchase orders. This ensures purchase order prices accurately reflect product costs or valid fallback prices.
Original PR description
Version: ---------- - 18.0+ Steps to reproduce: ----------------------- 1 - Install the `purchase` and `stock` modules. 2 - Create a storable product with tracking enabled. Set the Cost (standard…
Version: ---------- - 18.0+ Steps to reproduce: ----------------------- 1 - Install the `purchase` and `stock` modules. 2 - Create a storable product with tracking enabled. Set the Cost (standard price) to 50. 3 - Open the product form and go to the Purchase tab. * Add a vendor with: * Quantity: 2 * Price: 10 4 - Create a Reordering Rule for this product: * Route: Buy * Trigger: Manual * To Order Quantity: 2 5 - Click on the Order button to generate a purchase order. 6 - Open the generated Purchase Order and verify the Unit Price on the purchase order line. 7 - Open the same product and go to the Purchase tab. In the existing vendor line, add an End Date lower than today so the vendor pricelist becomes expired. 8 - Reopen the same reordering rule. Change To Order Quantity to 1. 9 - Click on the Order button again Issue: ----- The generated purchase order line gets a Unit Price of 0 instead of keeping the product cost or a valid fallback price. Root Cause: -------------- - When clicking on `Order`, it triggers `action_replenish`, which calls the procurement flow: `_procure_orderpoint_confirm` → `run` → `run` → `_run_buy`. - Inside `_run_buy`, the system checks whether a `purchase.order.line` already exists. In this case, the PO line exists, so it calls `_update_purchase_order_line`. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/purchase_stock/models/stock_rule.py#L137 - In `_update_purchase_order_line`, the system tries to fetch a seller using `_select_seller`, - which internally calls `_get_filtered_sellers`. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/product/models/product_product.py#L759 - However, if the seller's `end_date` is less than `today`, `_get_filtered_sellers` skips that seller and returns no valid seller. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/product/models/product_product.py#L731-L733 - As a result, `_update_purchase_order_line` does not find any seller and falls back to setting `price_unit` to `0`, causing the purchase order line price to be updated incorrectly. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/purchase_stock/models/stock_rule.py#L259 --- opw-6117461 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269971 Forward-Port-Of: odoo/odoo#262396
This update fixes an issue where the system wasn't accurately tracking component usage when creating backorders for manufacturing orders. Specifically, the system wasn't correctly deducting the required component quantity from the available stock. This ensures that the correct amount of components is used during the manufacturing process, preventing shortages and improving inventory accuracy. The fix addresses a reported problem (opw-6128575) related to multi-step routes and tracked components.
Original PR description
### Steps to reproduce: - In the settings enable: Multi-Steps Routes - Set your warehouse to manufacture in 2 steps (pick then manufacture). - Create a final product (FP) with a BOM in flexible…
### Steps to reproduce: - In the settings enable: Multi-Steps Routes - Set your warehouse to manufacture in 2 steps (pick then manufacture). - Create a final product (FP) with a BOM in flexible consumption: - 2 x COMP (lot tracked) - Put a lot for 6 units in of COMP in stock - Create and confirm an MO for 5 units of FP - Set the quantity producing on the MO to 1, requiring 2 of the 6 available units of COMP - Validate the MO and create a backorder for the remaining quantity. #### > The consumed qty on the main MO is of 0 units rather than 2. ### Cause of the issue: Since the component is tracked, and since the pbm move was backordered, the move quantity will not be automatically set when setting the `qty_producing`: https://github.com/odoo/odoo/blob/a1bcd917846493d08dd02b63e6110078ff5156a3/addons/mrp/models/mrp_production.py#L1405-L1411 And in particular, the move is not picked as it would if the product was untracked or if the pbm move was not backordered: https://github.com/odoo/odoo/blob/a1bcd917846493d08dd02b63e6110078ff5156a3/addons/mrp/models/mrp_production.py#L1421-L1427 And, since the move will not be picked at any other point in this flow, the move will be unreserved during the `button_mark_done`: https://github.com/odoo/odoo/blob/7c35e183d6cc33a6e5d20e5e97ffef79e03b49d4/addons/mrp/models/mrp_production.py#L2216 https://github.com/odoo/odoo/blob/7c35e183d6cc33a6e5d20e5e97ffef79e03b49d4/addons/mrp/models/mrp_production.py#L1895-L1896 https://github.com/odoo/odoo/blob/7c35e183d6cc33a6e5d20e5e97ffef79e03b49d4/addons/mrp/models/mrp_production.py#L1901 opw-6128575 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269235
This update ensures that prettified links in portal chatter messages remain functional after a page refresh. Previously, a refresh would break these links. The fix involves sending the correct thread name to ensure the links are properly formatted and displayed to users.
Original PR description
Before this commit, a message link posted on a portal chatter would lose it's prettified link (introduced in [1]) upon page refresh. This happens because `prepareMessageBody` needs the thread's `displayName` to create the prettified message link, which is not sent on portal chatter init. This commit fixes the issue by sending the thread's `display_name`. [1] https://github.com/odoo/odoo/pull/221069 task-6204819 Forward-Port-Of: odoo/odoo#263488
This update resolves an issue where the 'Download' button for EDI documents was failing to provide the correct XML file when Carvajal encountered an error. The fix adds a necessary callback to generate the XML content, ensuring users can now successfully download the required EDI documents.
Original PR description
When Carvajal returns an error, the EDI document is created with the XML attachment correctly stored in attachment_id. However, the Download button in the EDI Documents tab uses the computed field edi_content, which internally looks for an 'edi_content' callback in _get_move_applicability(). Since l10n_co_edi never provided this key, the computed field always returned empty bytes, resulting in an empty file download. Add the edi_content callback pointing to _l10n_co_edi_generate_xml so the Download button serves the actual generated XML. The "Download" button returns an empty file instead of the generated XML sent to Carvajal. <img width="1376" height="765" alt="Captura de pantalla 2026-06-11 a la(s) 12 21 55 p m" src="https://github.com/user-attachments/assets/ac1b6e85-e67d-4021-8d9c-07a03a390245" /> Forward-Port-Of: odoo/enterprise#120320
This update fixes a bug where the Assistant wasn't displaying suggestion icons for certain activities like 'Working on task'. The fix ensures the Assistant correctly identifies activity types, allowing the icons to appear and provide users with helpful suggestions. This improves the Assistant's usability and functionality.
Original PR description
- When the Assistant detected activities such as 'Working on task', the suggestion icon was not displayed because the event type was not assigned. Unlike `aw.rule` matches, the Odoo URL resolver only set the label and related record information, but did not set the activity type required by `getIcon()`. - Expose the activity type through `get_assistant_data` and assign the activity type when resolving model URLs in extractWatcherActivity. task-6259793
This update corrects an issue in the Datev ledger export where currency calculations were incorrect. The fix ensures that tax amounts are now accurately reflected in the invoice's currency, resolving discrepancies in the exported data and improving the reliability of Datev reports. This impacts German-specific financial reporting.
Original PR description
There is an issue in the Datev export functionality. In the current functionality, the code calculates a delta between the taxes in the `tax_totals` and the ones on the journal items. Issue is, the tax amounts from tax_totals were always in company currency, while the entry itself can use a foreign one. This replaces the use of company currency with the use of the invoice's currency and appropriately adjusts the test featuring foreign currency. Steps: Create a foreign currency. Create an invoice with a taxed product using the currency. Export the ledger to Datev. Inspect the resulting csv. Note that neither the final listed price, nor the rate listed for the currency align with the ones in the db. opw-6275889 Forward-Port-Of: odoo/enterprise#120293
This update fixes a potential issue where certified point-of-sale configurations could allow users to enter negative quantities on order lines. This has now been resolved across both the backend and frontend of the Odoo system, ensuring data accuracy and preventing incorrect order processing. This change improves the reliability of our POS functionality.
Original PR description
Certified pos configs should not allow to set negative quantities on order lines. We now prevent it from both backend and frontend. see odoo/odoo#269487 task-5942777 Forward-Port-Of: odoo/enterprise#119702
This update resolves an issue where inventory counts weren't accurately recording products without lot numbers. The fix ensures that new units without lots are correctly added to inventory counts, preventing miscounts and improving data accuracy. It addresses a validation error related to how the system handles lotless products during inventory adjustments.
Original PR description
### Steps to reproduce: 1. Create a product tracked by lot 2. Put 10 units in WH/Stock without lot 3. Inventory > Operations > Adjustments > Physical Inventory 4. Select the line referring to your…
### Steps to reproduce: 1. Create a product tracked by lot 2. Put 10 units in WH/Stock without lot 3. Inventory > Operations > Adjustments > Physical Inventory 4. Select the line referring to your product and request an inventory count + Show Expected Quantity 5. Open the barcode app > Count Inventory 6. Scan your product #### > The line is not selected, in particular, next scans will be re-interpreted as product scans rather than new serial creation for your product. ### Cause of the issue: Scanning your product search a line to select if any: https://github.com/odoo/enterprise/blob/bce04ce24b66fb1a2481274eb3aebdc30a62766e/stock_barcode/static/src/models/barcode_model.js#L1432-L1435 https://github.com/odoo/enterprise/blob/bce04ce24b66fb1a2481274eb3aebdc30a62766e/stock_barcode/static/src/models/barcode_model.js#L1630-L1632 However, the `findLine` will fail since this method calls the `_canOverrideTrackingNumber` to determine if the lot of the barcodData matches the one of the line: https://github.com/odoo/enterprise/blob/bce04ce24b66fb1a2481274eb3aebdc30a62766e/stock_barcode/static/src/models/barcode_model.js#L1859-L1863 But, the override of the `_canOverrideTrackingNumber` method for the `BarcodeQuantModel` does not handle the absence of lotName in the barcodeData correctly as it does not consider that a line without lot can be overridden by an empty lotName: https://github.com/odoo/enterprise/blob/bce04ce24b66fb1a2481274eb3aebdc30a62766e/stock_barcode/static/src/models/barcode_quant_model.js#L729-L731 Note however that the super call does: https://github.com/odoo/enterprise/blob/bce04ce24b66fb1a2481274eb3aebdc30a62766e/stock_barcode/static/src/models/barcode_model.js#L795-L798 ### Issue 2: ### Steps to reproduce: - Steps 1 -> 5 - Click on your product line to select it - Scan a new lot to add one new unit referring to that lot - Confirm (1) - Apply Now #### > User Error: Quant's editing is restricted, you can't do this operation Since the line is selected, you have a currentLine during the `processBarcode` and hence the existing line will be updated using the `lotName``: https://github.com/odoo/enterprise/blob/cf3c2fce8a6b7b2d7547d44a0e4423f887986d52/stock_barcode/static/src/models/barcode_model.js#L1560-L1584 However, writing on the line will then try to write on the related quant during the validation process which will be forbiden since we are not allowed to change the lot of an existing quant: https://github.com/odoo/odoo/blob/e3b0ca11d99b2ef819cdad68b169112cd73668b6/addons/stock/models/stock_quant.py#L351-L360 Now, the issue is that actually due to the nature of the line and of the barcode data, the line lot is not expected to be updated but rather a new line is expected to be created: https://github.com/odoo/enterprise/blob/cf3c2fce8a6b7b2d7547d44a0e4423f887986d52/stock_barcode/static/src/models/barcode_model.js#L795-L798 Additional issue: Fixing issue 1 and 2 highlight and other issue of the validation process: - Steps 1 -> 6 > The line gets selected - Scan a newlot > a new subline is added referring to 1 unit of your new quant - Confirm (1) > Some serials where not counted, set them as missing #### > Check your quants: the 10 unit lotless quant was not updated but a new quant for 1 units was created for your newlot ### Cause of the issue: Applying all quantities is expecting to toggle them as counted before applying to update the existing quants: https://github.com/odoo/enterprise/blob/c8535a7a0e2eae811048a34a0bae187a1fa45311/stock_barcode/static/src/models/barcode_quant_model.js#L72-L82 https://github.com/odoo/enterprise/blob/c8535a7a0e2eae811048a34a0bae187a1fa45311/stock_barcode/static/src/models/barcode_quant_model.js#L287-L296 However, only line tracked by serial numbers are set as counted: https://github.com/odoo/enterprise/blob/c8535a7a0e2eae811048a34a0bae187a1fa45311/stock_barcode/static/src/models/barcode_quant_model.js#L60-L63 opw-6212923 Forward-Port-Of: odoo/enterprise#118373
This update corrects a bug that prevented the salary distribution map from being recalculated when bank accounts were archived or restored. Previously, this could lead to inaccurate salary calculations. This fix ensures that salary distributions are always up-to-date, improving payroll accuracy.
Original PR description
When archiving or unarchiving bank accounts, salary distribution map is not recomputed. Task-6180142 Forward-Port-Of: odoo/odoo#262255
This update resolves an issue where demo leave allocations wouldn't properly validate during an Odoo upgrade from 17.0 to 18.0. The fix ensures that the approval process is executed correctly, guaranteeing accurate leave allocation management across all installation scenarios. This prevents data inconsistencies and ensures the Indian Payroll demo data functions as expected.
Original PR description
Steps: - Install an Odoo 17.0 database with the Indian Payroll module and demo data. - Upgrade the database to 18.0. Issue: - The Indian payroll demo data creates leave allocations and approves them…
Steps: - Install an Odoo 17.0 database with the Indian Payroll module and demo data. - Upgrade the database to 18.0. Issue: - The Indian payroll demo data creates leave allocations and approves them through an XML function call. - During a fresh installation, demo files are loaded in 'init' mode, so the approval function is executed and the allocations move from 'confirm' to 'validate'. - However, during a 17.0 >>> 18.0 upgrade, demo files are loaded in 'update' mode. Odoo automatically loads demo files with 'noupdate=True' from the load_demo() >> load_data() function: - This value is passed to the XML importer and becomes the default noupdate state for the file. Since the demo XML file does not explicitly override this value, the function tag uses 'noupdate=True'. - When the XML parser reaches the approval function, _tag_function() skips its execution because of noupdate = 'True' and mode = 'update' condition. - As a result, the approval function is not executed during the upgrade and the leave allocations remain in 'confirm' state. Subsequent demo payroll data expects validated allocations and fails during loading. Fix: - Explicitly set 'noupdate=0' on the demo XML file. This overrides the default 'noupdate=True' value applied to demo files, making the parser evaluate the section with 'noupdate=False'. - As a result, '_tag_function()' executes the approval method during upgrades, the demo leave allocations are validated in both fresh/new db installations and 17.0 >>> 18.0 upgrade scenarios. runbot error-https://runbot.odoo.com/odoo/error/230430 task-6268381 Forward-Port-Of: odoo/enterprise#119217
This update corrects a potential issue in the Swiss payroll module where users could incorrectly request refunds on payslips. Swiss payroll regulations limit payments to one per month, so the system now directs users to cancel and re-create the payslip for accurate corrections. This ensures compliance with Swiss tax laws.
Original PR description
Prevent refunds for CH payslips since only one payslip per month is allowed for Swiss payroll. Users should cancel the payslip and create a new one to apply corrections. task-5951981 Forward-Port-Of: odoo/enterprise#107943
This update fixes an issue where 401K matching contributions were incorrectly calculated for hourly employees with zero fixed wages. The fix ensures that matching contributions are accurately determined based on actual gross pay, providing consistent and correct retirement plan benefits. This improves payroll accuracy and compliance.
Original PR description
*= test_l10n_us_hr_payroll_account The employer matching cap for pre-retirement plans (401KMATCHING) evaluates to zero for hourly wage employees if wage is set to zero. ### **Steps to Reproduce:** 1)…
*= test_l10n_us_hr_payroll_account The employer matching cap for pre-retirement plans (401KMATCHING) evaluates to zero for hourly wage employees if wage is set to zero. ### **Steps to Reproduce:** 1) Install l10n_us_hr_payroll. 2) Create an employee with an hourly wage and set the fixed wage to 0. 3) Configure the retirement plan parameters as follows: - 401(k) = 3% - Matching Amount = 100% - Matching Yearly Cap = 100% 4) Generate a payslip for this employee and compute the sheet. ### **Observed Behavior:** The "Benefits Matching to Retirement Plans" line computes as zero for the hourly employee. ### **Expected Behavior:** The employer matching contribution should dynamically scale based on the actual gross pay period earnings instead of evaluating to zero. ### **Root Cause:** The calculation of `partial_cap` uses `version.wage` directly at [1]. For hourly employees, the fixed 'wage' field defaults to zero, causing the entire multiplication to cancel out. [1]- https://github.com/odoo/enterprise/blob/4c540f450d4de8b59b871662123f85ed54cca2a9/l10n_us_hr_payroll/data/hr_salary_rule_data.xml#L167 ### **Fix:** This commit computes the retirement matching eligibility cap from `gross annualized wages` and applies the employer matching percentage on the eligible contribution amount. This ensures retirement matching is calculated consistently regardless of the employee's contract type. **opw-6181024** Forward-Port-Of: odoo/enterprise#119370
This update fixes an issue where sale order references were incorrectly linked to the user's company instead of the order's company. Now, the system uses the correct company context for journal lookups, ensuring accurate reference processing across different company environments. This prevents errors and improves the reliability of sale order referencing.
Original PR description
Description of the issue/feature this PR addresses: Fixes an issue where the sale order reference computation was fetching the invoice journal based on the logged-in user's current company instead of…
Description of the issue/feature this PR addresses: Fixes an issue where the sale order reference computation was fetching the invoice journal based on the logged-in user's current company instead of the company associated with the specific payment provider or transaction context. This caused incorrect reference processing or errors in multi-company environments when a user was logged into one company but processing an order from another. Current behavior before PR: The function searches for the account.journal using self.company_id.id. Since self in this context (likely a payment provider or transaction record) might be evaluated under the active user's environment context, it fetched the journal from the user's currently active company (allowed_company_ids), disregarding the actual company related to the sale order or the transaction. Desired behavior after PR is merged: The invoice journal search uses the correct company context (e.g., order.company_id.id or the specific company linked to the payment record), ensuring that the sale order reference is processed using the appropriate journal from the correct company, regardless of which company the logged-in user is currently switched into. --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269558
This update resolves an issue where reloading the Point of Sale while the system was in a specific state caused data loss and errors. The fix prevents a race condition between sending data and loading new information, ensuring a smoother and more reliable user experience for Point of Sale operations. This enhances the overall stability of the POS functionality.
Original PR description
When the user reloads the POS while the session is in opening_control, the beforeunload sendBeacon and the new pos_web request race. If the beacon is processed first it deletes the session and load_data fails. task-6259527 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#268668 Forward-Port-Of: odoo/odoo#267190
This update corrects a bug where the stock valuation closing entry incorrectly calculated accounting balances for companies with multiple stock locations. The fix ensures that the closing entry accurately reflects the stock valuation for each company, resolving discrepancies in initial balances and variation lines. This ensures accurate financial reporting across multiple companies.
Original PR description
**Steps to reproduce on a new db:** (bug also reproducable on runbot but the impact is less easy to compute because of influence of other existing companies) - create a new company as company 2 and…
**Steps to reproduce on a new db:** (bug also reproducable on runbot but the impact is less easy to compute because of influence of other existing companies) - create a new company as company 2 and use the existing default company as company 1. - create a warehouse for both company - for both comp, in settings for the 'fiscal localization' set Package : Generic Chart of account, if not already set (to have account journals). - for both comp, in settings for inventory valuation set 'periodic' and for periodic valuation set 'daily' From company 1 : - create a storable product with standard price method and set a cost of 30 - set an onhand quantity of 1 if you navigate to 'inventory valuation' you'll see that : - initial balance is 0 - ending stock is 30 - the variation lines have a balance of 30 - all of this is expected From company 2 : - change the cost of the product to 10 - set an onhand quantity of 1 if you navigate to 'inventory valuation' you'll see that : - initial balance is 0 - ending stock is 10 - the variation lines have a balance of 10 - all of this is expected From any company : - navigate to 'scheduled actions' and select the action 'Stock Account: Inventory Valuation Closing' - click on 'Run Manually' - navigate to 'inventory valuation' **Current behavior:** with company 1 selected : - the initial balance is now 30 - ending stock still 30 - no variation lines - the initial balance was correctly increased by the closing entry with company 2 selected: - the initial balance is now 40 - the ending stock is still 10 - the variation lines credit 30 in stock valuation In company 2 the closing entry debitted 40 in stock valuation instead of 10 which increased the initial balance to 40 instead of 10 If you open the journal items you'll find the closing amls have a balance of 40 instead of 10 **Cause of the issue:** The _cron_post_stock_valuation() method calls action_close_stock_valuation() on both companies https://github.com/odoo/odoo/blob/bfa39854e56da4bf23295d62f63d66973ad0d78e/addons/stock_account/models/res_company.py#L143-L144 This methods calls _action_close_stock_valuation with a context modified with only self.env.company.ids in 'allowed_company_ids' https://github.com/odoo/odoo/blob/bfa39854e56da4bf23295d62f63d66973ad0d78e/addons/stock_account/models/res_company.py#L56 This is needed because inside stock_value() we use the total value of the product https://github.com/odoo/odoo/blob/bfa39854e56da4bf23295d62f63d66973ad0d78e/addons/stock_account/models/res_company.py#L92 which will be the sum of the values of the product for each company inside allowed_company_id https://github.com/odoo/odoo/blob/bfa39854e56da4bf23295d62f63d66973ad0d78e/addons/stock_account/models/product.py#L274 So in case action_close_stock_valuation() was called from the 'generate entry' button from the inventory valuation view we need only the main company selected to be in the 'allowed_company_ids' so that the inventory value is computed based only on this company (as is the accounting value). The problem is that this does not work when calling the method from _cron_post_stock_valuation because then there is no 'allowed_company_ids' in the context (because it was called from _process_job() with a new env). so self.env.company will be the company of the user which will be company 1. https://github.com/odoo/odoo/blob/bfa39854e56da4bf23295d62f63d66973ad0d78e/odoo/orm/environments.py#L243 Therefore when _action_close_stock_valuation will be called on company 2, in the context, allowed_company_ids will be company 1. Then, when computing 'products', with_company() will add self (company 2) to the context. https://github.com/odoo/odoo/blob/616e82d7b3a53b1facf481e783baed3e99393d3c/addons/stock_account/models/res_company.py#L151-L152 So stock_value will return the sum of the total_value of each product for company 1 and company 2 which is 40 (instead of 10 for just company 2) https://github.com/odoo/odoo/blob/616e82d7b3a53b1facf481e783baed3e99393d3c/addons/stock_account/models/res_company.py#L242 We then create the closing accounting entry to match the accounting value with the stock value, which explains why the new initial accounting balance of company 2 is 40. **fix:** We set the context using self instead of self.env.companies This makes more sense as both in the cron use case and the generate entry use case the stock value we want is the one of the company in self. - In cron use case, it's obvious as the method is called in a for loop on each company - In the generate entry use case, self will also be the main company, because it's called, in actionGenerateEntry, on this.companyId https://github.com/odoo/odoo/blob/616e82d7b3a53b1facf481e783baed3e99393d3c/addons/stock_account/static/src/stock_valuation/controller.js#L75 which is computed based on the get_report_values https://github.com/odoo/odoo/blob/616e82d7b3a53b1facf481e783baed3e99393d3c/addons/stock_account/static/src/stock_valuation/controller.js#L21 https://github.com/odoo/odoo/blob/616e82d7b3a53b1facf481e783baed3e99393d3c/addons/stock_account/static/src/stock_valuation/controller.js#L28-L30 Which returns the main company https://github.com/odoo/odoo/blob/616e82d7b3a53b1facf481e783baed3e99393d3c/addons/stock_account/report/stock_valuation_report.py#L29 Most importantly, this is also aligned with how the accounting values are computed. https://github.com/odoo/odoo/blob/616e82d7b3a53b1facf481e783baed3e99393d3c/addons/stock_account/models/res_company.py#L103-L105 opw-6237402 Forward-Port-Of: odoo/odoo#266932
5 changes
Resolved issues and error corrections
This update resolves two issues related to attaching documents to employee records. Previously, attachments were created in the root employee folder, which was inconvenient. Now, attachments are correctly created, including those for sick leave, ensuring proper document management for employee records. This improves the user experience and data integrity.
Original PR description
Before this commit, when adding an attachment to a leave or a employee version the mixin was configured to create the document in the root folder of Employees which was not very convenient. In addition, when creating a Sick leave with an attachment, no document was ever created. This commit fix both those bugs. Task-6095811 Forward-Port-Of: odoo/enterprise#112993
This update corrects an issue in the Datev ledger export, ensuring accurate currency calculations. Previously, the system incorrectly used the company currency instead of the invoice's currency, leading to discrepancies in reported values. This fix ensures Datev exports reflect the correct financial data.
Original PR description
There is an issue in the Datev export functionality. In the current functionality, the code calculates a delta between the taxes in the `tax_totals` and the ones on the journal items. Issue is, the tax amounts from tax_totals were always in company currency, while the entry itself can use a foreign one. This replaces the use of company currency with the use of the invoice's currency and appropriately adjusts the test featuring foreign currency. Steps: Create a foreign currency. Create an invoice with a taxed product using the currency. Export the ledger to Datev. Inspect the resulting csv. Note that neither the final listed price, nor the rate listed for the currency align with the ones in the db. opw-6275889 Forward-Port-Of: odoo/enterprise#120293
This update resolves an issue where demo leave allocations weren't correctly processed during an upgrade from Odoo 17 to 18.4. The fix ensures that leave allocations are properly validated and updated, preventing data inconsistencies and ensuring the Indian Payroll demo data functions correctly in both new installations and upgrades.
Original PR description
Steps: - Install an Odoo 17.0 database with the Indian Payroll module and demo data. - Upgrade the database to 18.0. Issue: - The Indian payroll demo data creates leave allocations and approves them…
Steps: - Install an Odoo 17.0 database with the Indian Payroll module and demo data. - Upgrade the database to 18.0. Issue: - The Indian payroll demo data creates leave allocations and approves them through an XML function call. - During a fresh installation, demo files are loaded in 'init' mode, so the approval function is executed and the allocations move from 'confirm' to 'validate'. - However, during a 17.0 >>> 18.0 upgrade, demo files are loaded in 'update' mode. Odoo automatically loads demo files with 'noupdate=True' from the load_demo() >> load_data() function: - This value is passed to the XML importer and becomes the default noupdate state for the file. Since the demo XML file does not explicitly override this value, the function tag uses 'noupdate=True'. - When the XML parser reaches the approval function, _tag_function() skips its execution because of noupdate = 'True' and mode = 'update' condition. - As a result, the approval function is not executed during the upgrade and the leave allocations remain in 'confirm' state. Subsequent demo payroll data expects validated allocations and fails during loading. Fix: - Explicitly set 'noupdate=0' on the demo XML file. This overrides the default 'noupdate=True' value applied to demo files, making the parser evaluate the section with 'noupdate=False'. - As a result, '_tag_function()' executes the approval method during upgrades, the demo leave allocations are validated in both fresh/new db installations and 17.0 >>> 18.0 upgrade scenarios. runbot error-https://runbot.odoo.com/odoo/error/230430 task-6268381 Forward-Port-Of: odoo/enterprise#119217
This update fixes a bug that prevented proper error messages from appearing when new IoT Boxes encountered scaling problems. Previously, the system didn't correctly display error information, making it difficult to diagnose and resolve issues. This ensures users receive clear notifications about scale errors, improving troubleshooting and operational efficiency.
Original PR description
This completes odoo/enterprise#11196, which missed error message handling for new IoT Boxes errors. `message_body` was undefined on `data.status` when `data.status === "error"`. <img width="1871" height="942" alt="image" src="https://github.com/user-attachments/assets/30b54c5b-da0d-497d-8d9e-912f7139140b" /> Forward-Port-Of: odoo/enterprise#119425 Forward-Port-Of: odoo/enterprise#119228
This update corrects a potential issue in the Swiss payroll module where users could incorrectly request refunds on payslips. Swiss payroll regulations limit payments to one per month, so the system now guides users to cancel and re-create a payslip for any necessary adjustments. This ensures compliance with Swiss tax laws.
Original PR description
Prevent refunds for CH payslips since only one payslip per month is allowed for Swiss payroll. Users should cancel the payslip and create a new one to apply corrections. task-5951981 Forward-Port-Of: odoo/enterprise#107943
10 changes
Resolved issues and error corrections
This update fixes an issue where purchase order line prices were incorrectly set to zero when using reordering rules. The fix ensures that the product's original cost or a valid fallback price is used, preventing inaccurate pricing on purchase orders. This improves the reliability of purchase order generation.
Original PR description
Version: ---------- - 18.0+ Steps to reproduce: ----------------------- 1 - Install the `purchase` and `stock` modules. 2 - Create a storable product with tracking enabled. Set the Cost (standard…
Version: ---------- - 18.0+ Steps to reproduce: ----------------------- 1 - Install the `purchase` and `stock` modules. 2 - Create a storable product with tracking enabled. Set the Cost (standard price) to 50. 3 - Open the product form and go to the Purchase tab. * Add a vendor with: * Quantity: 2 * Price: 10 4 - Create a Reordering Rule for this product: * Route: Buy * Trigger: Manual * To Order Quantity: 2 5 - Click on the Order button to generate a purchase order. 6 - Open the generated Purchase Order and verify the Unit Price on the purchase order line. 7 - Open the same product and go to the Purchase tab. In the existing vendor line, add an End Date lower than today so the vendor pricelist becomes expired. 8 - Reopen the same reordering rule. Change To Order Quantity to 1. 9 - Click on the Order button again Issue: ----- The generated purchase order line gets a Unit Price of 0 instead of keeping the product cost or a valid fallback price. Root Cause: -------------- - When clicking on `Order`, it triggers `action_replenish`, which calls the procurement flow: `_procure_orderpoint_confirm` → `run` → `run` → `_run_buy`. - Inside `_run_buy`, the system checks whether a `purchase.order.line` already exists. In this case, the PO line exists, so it calls `_update_purchase_order_line`. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/purchase_stock/models/stock_rule.py#L137 - In `_update_purchase_order_line`, the system tries to fetch a seller using `_select_seller`, - which internally calls `_get_filtered_sellers`. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/product/models/product_product.py#L759 - However, if the seller's `end_date` is less than `today`, `_get_filtered_sellers` skips that seller and returns no valid seller. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/product/models/product_product.py#L731-L733 - As a result, `_update_purchase_order_line` does not find any seller and falls back to setting `price_unit` to `0`, causing the purchase order line price to be updated incorrectly. https://github.com/odoo/odoo/blob/47ef8b75d0c90001b9989a95f09b962c5b286c53/addons/purchase_stock/models/stock_rule.py#L259 --- opw-6117461 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269909 Forward-Port-Of: odoo/odoo#262396
This update optimizes the process of validating purchase orders by preventing unnecessary calculations of location weights. By reordering checks, the system avoids computing weights when other conditions already rule out a location, resulting in significantly faster validation times, especially when dealing with many locations using the same storage category.
Original PR description
When checking if a stock.move.line can use a location as destination with the method `_check_can_be_used()`, we start by checking if the incoming products can be stored without exceeding the maximal…
When checking if a stock.move.line can use a location as destination with the method `_check_can_be_used()`, we start by checking if the incoming products can be stored without exceeding the maximal weight of the location. This needs to call the `_get_weight()` method to compute the forecasted weight for the location. This method relies on heavy computations and can become a bottleneck when we need to loop over a high number of locations. In some cases, we can rule out the location based on less expensive conditions that are verified after the weight one. We propose to invert the conditions check order to avoid computing the location weight when other conditions are not met. Steps to reproduce --------------- - Install stock and purchase modules; - Enable storage locations and categories in the settings; - Create a storage category: allow_new_product = same, max_weight=10.0 kg; - Create N locations using this category, parent_id=WH/stock; - Create a putaway rule to each location from WH/stock, for the new storage category and using a product A with a weight of 2 kg; - Create a stock.quant per location to store a product B, weight=2kg; - Create a purchase order with X lines for 1 unit of product A; - Validate the purchase order. The validation should take several seconds to execute as every locations will be rejected due to the storage category, but it will call _get_weight() first. Benchmark --------------- This improvement is very data specific and will be most useful when a lot of locations are using a storage category of type "empty" or "same". In addition, it also relies on the order in which we are treating the locations, if the acceptable locations are the first to be received in the method, it won't need to loop over all of them. The following benchmark was established in a production database in which every 6068 locations are using a category of type "same". | No stock.move.lines | Before PR | After PR | |---------------------|-----------|----------| | 40 | 168 s | 7.3 s | | 72 | 264 s | 12.33 s | When the only condition that can reject locations is the exceeding weight, this modification will slow down the process. However, the time loss in this case is smaller than the gain in the first case. The following benchmark was obtained by validating a purchase 1 line order with only fully filled locations. | No locations | Before PR | After PR | |--------------|-----------|----------| | 500 | 2.02s | 2.37 s | | 2000 | 7.85s | 9.76 s | | 10000 | 39.16 s | 48.86 s | opw-5949370 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#266872
This update resolves an issue where expense descriptions weren't automatically translated when using different database languages (like French). The fix ensures that OCR-extracted descriptions are correctly applied, regardless of the user's language setting, improving the accuracy of expense data. This prevents placeholder text from remaining on expense records.
Original PR description
### Issue On Runbot, trial, and client databases, the automatic extraction of the description does not work when a user changes the database language When an expense is first generated up to 19.0, it…
### Issue
On Runbot, trial, and client databases, the automatic extraction of the description does not work when a user changes the database language
When an expense is first generated up to 19.0, it requires a name and is temporarily given a localized placeholder like "Dépense sans titre..." in French
When the OCR results arrive, the system is supposed to detect this generic fallback string and overwrite it with the real extracted description
However, because of a language mismatch, the system fails to recognize its own placeholder. It incorrectly assumes the user manually entered that text and, to prevent losing user data, refuses to replace it
Before the fix, the title remains stuck on the placeholder
In very rare cases, the translation applies correctly, but it fails most of the time
### Cause
The OCR successfully finds the correct description, but in `_fill_document_with_results`, the expense name is not replaced
This seems to happen because `self` in `self._get_untitled_expense_name("")` carries a residual context that could override the correct language to use during the automated extraction process
Even though the user record and the detected language are correctly set to the alternative language, `default_receipt_name` appears to be generated in English ("Untitled Expense")
This would cause the subsequent string comparison with the actual translated name stored in the database to fail, blocking the update
### Fix
I made some tests in some generated RunBot and the user is correct and also the associated lang
I supposed self was containing lang details overriding the correct language to use
`self.env['hr.expense'].with_context(lang=user_id.lang)` seems to be working
### Steps to reproduce
The issue cannot be reproduced locally, follow these steps on a Runbot instance:
- Retrieve IAP OCR credentials from a trial database
- Enable Developer Mode in Settings
- Go to Settings -> Technical -> IAP -> IAP Accounts
- Add the credentials for the Document Digitization service
- Go to the Expenses app
- Change the user's language to French
- Import the expense image from the ticket
- Open the newly created Expense and click Refresh
Before the fix, the title should stay `Dépense sans titre...` If it's not the case, try a second import, it works times to times
opw-6103935This update fixes an issue where Datev exports incorrectly displayed currency amounts due to a mismatch between the invoice currency and the company currency used in calculations. The fix ensures that Datev exports accurately reflect the currency of the invoice, improving the reliability of financial reporting for our German clients.
Original PR description
There is an issue in the Datev export functionality. In the current functionality, the code calculates a delta between the taxes in the `tax_totals` and the ones on the journal items. Issue is, the tax amounts from tax_totals were always in company currency, while the entry itself can use a foreign one. This replaces the use of company currency with the use of the invoice's currency and appropriately adjusts the test featuring foreign currency. Steps: Create a foreign currency. Create an invoice with a taxed product using the currency. Export the ledger to Datev. Inspect the resulting csv. Note that neither the final listed price, nor the rate listed for the currency align with the ones in the db. opw-6275889 Forward-Port-Of: odoo/enterprise#120293
This update ensures that combo prices shown in the configurator dialog accurately reflect the order's currency. Previously, extra prices were displayed incorrectly due to a lack of currency conversion. Now, prices are automatically converted, guaranteeing accurate totals and matching sale order line prices.
Original PR description
Description of the issue/feature this PR addresses: In the combo configurator dialog, a combo item's extra_price and the price_extra of no_variant attributes are stored in the company/product…
Description of the issue/feature this PR addresses: In the combo configurator dialog, a combo item's extra_price and the price_extra of no_variant attributes are stored in the company/product currency but were sent to the front-end without conversion. When the order uses a pricelist in a different currency, the popup shows these extras at face value (e.g. an extra of USD 1700 appears as ARS 1700 instead of being converted). The sale order line itself already converts these extras, so the popup price and the actual line price didn't match. Current behavior before PR: _get_combo_item_data and _get_selected_ptavs_data return extra_price / price_extra raw, in the company currency. With a foreign-currency pricelist the combo configurator popup adds them 1-to-1 to the already-converted base price, displaying an incorrect total that doesn't match the resulting sale order line. Desired behavior after PR is merged: The controller converts extra_price and price_extra to the configurator's currency (via currency._convert()) before serializing them, so the popup shows the correct amounts in the pricelist currency and matches the price computed on the sale order line. A test (test_sale_combo_multicurrency.py) covers combo extra-price conversion with a foreign-currency pricelist. --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269386
This update resolves an issue where demo leave allocations wouldn't properly validate during an Odoo 18 upgrade. The fix ensures that demo data is processed correctly, preventing errors and maintaining accurate leave tracking. This improves the stability of the Indian Payroll module for new and upgraded installations.
Original PR description
Steps: - Install an Odoo 17.0 database with the Indian Payroll module and demo data. - Upgrade the database to 18.0. Issue: - The Indian payroll demo data creates leave allocations and approves them…
Steps: - Install an Odoo 17.0 database with the Indian Payroll module and demo data. - Upgrade the database to 18.0. Issue: - The Indian payroll demo data creates leave allocations and approves them through an XML function call. - During a fresh installation, demo files are loaded in 'init' mode, so the approval function is executed and the allocations move from 'confirm' to 'validate'. - However, during a 17.0 >>> 18.0 upgrade, demo files are loaded in 'update' mode. Odoo automatically loads demo files with 'noupdate=True' from the load_demo() >> load_data() function: - This value is passed to the XML importer and becomes the default noupdate state for the file. Since the demo XML file does not explicitly override this value, the function tag uses 'noupdate=True'. - When the XML parser reaches the approval function, _tag_function() skips its execution because of noupdate = 'True' and mode = 'update' condition. - As a result, the approval function is not executed during the upgrade and the leave allocations remain in 'confirm' state. Subsequent demo payroll data expects validated allocations and fails during loading. Fix: - Explicitly set 'noupdate=0' on the demo XML file. This overrides the default 'noupdate=True' value applied to demo files, making the parser evaluate the section with 'noupdate=False'. - As a result, '_tag_function()' executes the approval method during upgrades, the demo leave allocations are validated in both fresh/new db installations and 17.0 >>> 18.0 upgrade scenarios. runbot error-https://runbot.odoo.com/odoo/error/230430 task-6268381 Forward-Port-Of: odoo/enterprise#119217
This update fixes an issue where Odoo's cron workers weren't efficiently managing database connections. By introducing a new configuration option, we can now set a lower memory limit for cron workers, preventing them from cycling through all databases and improving overall system performance. This ensures smoother operation for background tasks.
Original PR description
The configuration option `registry_lru_size` does not exist and does not work at all in recent versions. Defining odoo-specific environment variables to handle: - ODOO_REGISTRY_LRU_SIZE: the default registries size - ODOO_REGISTRY_LRU_SIZE_CRON: overwrite for cron workers Cron workers have often a different workload than HTTP workers and we may set a different limit there. If the limit is lower than the number of databases, a cron job will not reuse registries because it cycles through all known ones - in such cases, we can set a lower limit to keep the memory lower. --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269606 Forward-Port-Of: odoo/odoo#268587
This update corrects a potential issue in the Swiss payroll module where users could incorrectly request refunds on payslips. Swiss regulations limit payments to one per month, so the system now directs users to cancel and re-create the payslip for accurate corrections. This ensures compliance with Swiss payroll rules.
Original PR description
Prevent refunds for CH payslips since only one payslip per month is allowed for Swiss payroll. Users should cancel the payslip and create a new one to apply corrections. task-5951981 Forward-Port-Of: odoo/enterprise#107943
This update ensures that the analytic account specified on a sale order is correctly applied to the stock moves generated during the delivery process. Currently, stock moves didn't inherit this analytic information, leading to inconsistent reporting. This change aligns the behavior with invoices, providing more accurate cost tracking for sales transactions.
Original PR description
PR very similar to https://github.com/odoo/odoo/pull/263236 but here on the SO side instead of PO **Problem:** account move created by stock valuation layer does not take analytic account from SO…
PR very similar to https://github.com/odoo/odoo/pull/263236 but here on the SO side instead of PO **Problem:** account move created by stock valuation layer does not take analytic account from SO **Steps to reproduce:** - make sure you have at least one analytic account - create a storable product with categ standard automated - set a positive cost and a positive on hand quantity - create a SO for 1 quantity - on the SO line of the product, in the analytic distribution column (might need to be unfiltered) set an analytic account - confirm SO and validate delivery - click on the valuation smart button and on the book widget of the stock valuation layer **Current behavior:** the account move lines have no analytic distribution **Expected behavior:** The account move lines should inherit the analytic account from the sale order line like it's the case for the invoice. For the analytic distribution of the Invoice, the selection is : 1) take analytic distribution from SO if one 2) if not, take from distribution model if there is one 3) empty Currently for the account move lines of the svl the selection is: 1) take from distribution model if there is one 2) empty But we should use same selection as for the invoice **Cause of the issue:** When setting the analytic distribution we first try to use the one from PO/SO by calling _related_analytic_distribution() https://github.com/odoo/odoo/blob/4cc1e6884be673523f768d5ec471a1ffa19c5fb4/addons/account/models/account_move_line.py#L1157 But since the account move lines have no sale_line_ids no analytic distribution will be returned https://github.com/odoo/odoo/blob/261b15953ca89657644f52d1cb9ecda6e3b686c5/addons/sale/models/account_move_line.py#L41-L46 opw-6022695 Forward-Port-Of: odoo/odoo#268866 Forward-Port-Of: odoo/odoo#268031
This update fixes an error in the Luxembourg fiscal localization settings. The incorrect valuation account (60761 Merchandise) has been replaced with the correct current asset account (301 Inventories of raw materials), ensuring accurate financial reporting for Luxembourg businesses. This change improves the reliability of accounting data.
Original PR description
**Problem:** Valuation account for luxembourg is currently 60761 Merchandise which is incorrect because it's an expense account. We should rather use a current asset account like 301 Inventories of raw materials **Steps to reproduce on a fresh db:** - create a new db with modules stock_account and accountant (without demo data) - On the 'fiscal localization setting' set the package as 'Luxembourg' and save - ativate the automatic accounting setting **Current Behavior:** The 'stock valuation account' appearing below the automatic accounting setting is : 60761 Merchandise **Expected behaviour:** It should be 301 Inventories of raw materials Forward-Port-Of: odoo/odoo#269469
1 change
Resolved issues and error corrections
This update fixes an issue where the Datev export incorrectly displayed currency amounts due to a mismatch between the invoice currency and the company currency. The change ensures that currency calculations in the Datev export align with the invoice's currency, improving the accuracy of financial reporting for German customers.
Original PR description
There is an issue in the Datev export functionality. In the current functionality, the code calculates a delta between the taxes in the `tax_totals` and the ones on the journal items. Issue is, the tax amounts from tax_totals were always in company currency, while the entry itself can use a foreign one. This replaces the use of company currency with the use of the invoice's currency and appropriately adjusts the test featuring foreign currency. Steps: Create a foreign currency. Create an invoice with a taxed product using the currency. Export the ledger to Datev. Inspect the resulting csv. Note that neither the final listed price, nor the rate listed for the currency align with the ones in the db. opw-6275889 Forward-Port-Of: odoo/enterprise#120293
11 changes
Enhancements to existing features
This update adjusts the Odoo Enterprise menu to place the Obox application at the end of the app list, just before the 'Apps' and 'Settings' sections. This change improves user discoverability of Obox within the application interface.
Original PR description
This commit changes the Obox menu sequence so that the app appears at the end of the apps list by default (just before Apps and Settings). task-6275407 Forward-Port-Of: odoo/enterprise#119337
Resolved issues and error corrections
This update enhances the clarity of bank statements for transactions split into multiple lines. Previously, all split lines received the same generic message, making it difficult to understand each charge. Now, transaction details are added to the label, aligning with the CodaBox breakdown and improving user understanding.
Original PR description
Currently, when global transaction is split into multiple lines, Odoo assigns the exact same communication text to every single split line. This makes it difficult for users to identify what each specific charge is for. To fix this, this commit introduces the transaction category data. Using this data to append specific transaction details to the end of the communication label. As a result, each split line now has a clear, descriptive label that closely matches the detailed breakdown provided by CodaBox. task-6059709 Forward-Port-Of: odoo/enterprise#113811
This update ensures that tax details for order items are now included in the test orders sent to UrbanPiper. Previously, these details were missing, leading to test failures. This change improves the accuracy of our integration testing and ensures correct tax calculations are sent to the external system.
Original PR description
Commit 1: ======== Before this commit: =================== - Test orders sent to UrbanPiper did not include tax details for order items. After this commit: ================== - Tax details are now included in the order item payload of test orders. Task-6013007 --- Commit 2: ======== Cause: ====== In the `without demo` environment, the discount product does not have any `taxes_id`, causing the test assertion to fail. Fix: ==== Set a tax on the discount product in the test to ensure the same behavior in both `with demo` and `without demo` environments. Error-241138 Forward-Port-Of: odoo/enterprise#120310 Forward-Port-Of: odoo/enterprise#109958
This update fixes a problem where receipt printing in Austria was incorrect due to an incorrect offset calculation. It also resolves a deadlock issue during authentication with Fiskaly and FON, ensuring smoother operation. This improves the reliability of the point-of-sale system for Austrian businesses.
Original PR description
In this task: -------------- - Fixed Austria closing receipt printing by calculating the offset from the last closed month instead of the current month. Closing records are returned in ascending order and exist only for completed months, so the latest month must use offset 0. - Prevent a deadlock during Fiskaly and FON authentication by checking for open sessions before starting any authentication flow, instead of after the first step of authentication. - The resp was used to show error which was not in the scope. task: 5420256 Forward-Port-Of: odoo/enterprise#120033 Forward-Port-Of: odoo/enterprise#102313
This update fixes a problem where tax lines were missing from the 2307 tax return PDF when the report was folded. The fix ensures that tax information is always included in the PDF, regardless of the report's layout. A new test has been added to verify this correction.
Original PR description
Current behavior: -- Tax lines are missing from the 2307 certificate PDF. Expected behavior: -- The tax lines should always appear on the certificate, regardless of the fold state of the report. Steps to reproduce: -- 1. Create and confirm a bill with any tax on the PH localization. 2. Open the 2307 tax return and export the certificate to PDF. 3. The tax line is missing from the PDF. Cause of the issue: -- The PDF is exported with the report folded, so the partner lines' children (the tax/ATC lines) are never generated. _custom_line_postprocessor then has no tax lines to decorate with the month-wise amounts. Fix: -- Expand each folded partner line down to the ATC level in _custom_line_postprocessor, and mark it unfolded so the new lines survive _filter_out_folded_children. Also added a test covering the folded lines. opw-6235956
This update fixes an error in the Spanish VAT reports where withholding tax was incorrectly included in the total VAT calculation. The fix excludes 'retencion' (withholding tax) from the VAT calculation, ensuring accurate reporting of VAT liabilities for Spanish businesses. This improves the reliability of financial data.
Original PR description
Step to reproduce - install `l10n_es_reports` and switch to ES company - create a invoice, add a product, set price = 100 - add two taxes (one should be withholding tax) ex: 21%G and 19%whi - confirm it, total payable is now 100 + 21 - 19 = 102 - open vat Books report for ES, see line for this invoice Observation: - for this invoice, in total vat column, we get 102 value - it should be 100+ 21 i.e 121 as we do not include withholding taxes in total vat Cause: - the query for report used to sum up all the taxes for calculating vat Fix: - excluded tax of type "retencion" in tax summation opw-6082329 Forward-Port-Of: odoo/enterprise#120270 Forward-Port-Of: odoo/enterprise#114137
This update resolves an issue preventing users from selecting contacts with VAT numbers as feedback recipients within appraisals. Previously, a technical restriction based on VAT presence incorrectly classified these contacts as 'companies.' Removing this restriction now allows for broader feedback recipient selection, though users may need to perform a manual sort.
Original PR description
Issue: ---------------------------------------- We cannot add a contact with a VAT as a feedback recipient. Steps to reproduce: ---------------------------------------- - Have a contact with a VAT - Go to a confirmed appraisal and select 'Ask Feedback' - We cannot add the contact as recipient. Cause: ---------------------------------------- There is a domain on the field to only accept non company contacts. The idea of the domain was to restrict the field to persons only. But since f2965048f60fe6c815b3e50fa714c97a93dfb5d3 the field `is_company` is computed based on the VAT presence. So a contact with a VAT specified is considered a company. Solution: ---------------------------------------- Remove the domain. We allow to select all contacts, the users will have to do the sort. opw-6280689 Forward-Port-Of: odoo/enterprise#120236
This update resolves an issue where currency differences were incorrectly aggregated in hierarchical reports, leading to inaccurate financial summaries. The change ensures that report totals are calculated accurately based on the currency of each individual transaction, improving the reliability of financial reporting. This update impacts the general ledger report.
Original PR description
opw-6015098 Forward-Port-Of: odoo/enterprise#119420 Forward-Port-Of: odoo/enterprise#114827
This update ensures that non-mandatory text fields in sign documents appear with a transparent background when using dark mode in browsers. A recent update to PDF.js automatically adjusts element colors based on the browser theme, and this fix prevents the non-mandatory fields from inheriting the dark background color.
Original PR description
## Issue When using the browser's dark mode, non-mandatory text fields in sign documents appear with a dark background, which does not match the aesthetic of the rest of the page. ## Steps to…
## Issue
When using the browser's dark mode, non-mandatory text fields in sign documents appear with a dark background, which does not match the aesthetic of the rest of the page.
## Steps to reproduce
1. Set your browser's theme to a dark theme (in Chrome, go to Settings > Appearance > Theme, chose a theme from the dark options)
2. Install Sign (`sign`)
3. Open a Sign template and add 3 Text fields:
- Mandatory
- Non-mandatory
- Read-only (for comparison)
4. Click *Sign Now*
5. **The non-mandatory text field has a dark background.**
## Cause
Since a [PDF.js update](https://github.com/mozilla/pdf.js/commit/ae1cbc6a9ecc738d6777830488ad5481b97338bc), the `light dark` color-theme was added to `:root`. This means that the element will react to the settings of the browser and adapt its background and text color. In this case, there's no other `background-color` provided to mandatory fields, resulting in them using the dark color of the browser theme.
## Fix
We make the default background of text fields transparent then we update the selector of `.o_sign_sign_item_required` to prevent their `background-color` from being overwritten by that new transparent background.
| | Before | After |
|------------|--------|-------|
| **Light mode** | <img width="211" height="99" alt="6213059-before-light" src="https://github.com/user-attachments/assets/c4c70394-c7c2-4dbf-92b9-c1362d1cf9c8" /> | <img width="207" height="89" alt="6213059-after-light" src="https://github.com/user-attachments/assets/63142be5-9f7d-4d5d-94e8-ef9428e1b778" /> |
| **Dark mode** | <img width="220" height="95" alt="6213059-before-dark" src="https://github.com/user-attachments/assets/19149c3d-511e-407c-821e-f318f373368a" /> | <img width="210" height="103" alt="6213059-after-dark" src="https://github.com/user-attachments/assets/0b412d4f-061f-41b3-aae9-569b9a8219dc" /> |
opw-6213059
Forward-Port-Of: odoo/enterprise#117589This update corrects a visual issue where new timesheet entries created from the systray menu were always added to the bottom of the list, requiring users to scroll to see the most recent entry. The fix ensures entries are sorted by creation date, placing the newest entries at the top for easier viewing. This improves user efficiency and the overall timesheet experience.
Original PR description
## Issues When creating a new timesheet entry from the systray menu, that entry is added at the end of the list, which is inconvenient when the list gets long, as it requires to scroll through the…
## Issues When creating a new timesheet entry from the systray menu, that entry is added at the end of the list, which is inconvenient when the list gets long, as it requires to scroll through the entirety of it to see the most recent entry. ## Steps to reproduce 1. Install Timesheets (`timesheet_grid`) 2. Open the systray menu 3. Create two timesheet entries 4. The second (= most recent) entry appears below the first (= oldest) entry ## Cause Since https://github.com/odoo/enterprise/commit/5901619141c81085111f2ee65b54492abf1e324f the entries are sorted based on the create date in ascending orer. This means that the oldest entries appear at the top, and the most recent at the bottom. On top of that, new entries were added at the end of the list instead of the start. ## Test The existing test `Creating a new timesheet places it at the top of the list` was only adding one entry to the list, thus was not properly testing **where** the new entries were added. opw-6284059 Forward-Port-Of: odoo/enterprise#120258
This update resolves an issue where users without HR access rights were seeing a placeholder image instead of their avatar in the timesheet grid view. The fix ensures that the correct employee avatar is displayed, regardless of user permissions, improving the user experience.
Original PR description
Steps to reproduce: ------------------- - Install the hr_timesheet module - Create a user without HR access rights - Create a timesheet - Log in with the above user - Open the kanban view Issue: ------- Instead of showing the employee's avatar, a placeholder image is displayed. Reason: ---------- The user does not have access to the hr.employee model. Fix: ----- In this commit, if the user does not have access to hr.employee,we fetch the image from the hr.employee.public model. task: 4461272 Forward-Port-Of: odoo/enterprise#120361 Forward-Port-Of: odoo/enterprise#83574
4 changes
Resolved issues and error corrections
This update resolves a technical issue that prevented users from correctly resizing task pills in the Gantt view when no dependent tasks were involved. The fix ensures the system handles empty rescheduling lists gracefully, preventing a crash and maintaining proper Gantt functionality. This improves the overall stability and usability of the project scheduling feature.
Original PR description
Steps to reproduce: - Create a project with task dependencies enabled - Create a task with planned dates and no dependent tasks - Open the Gantt view - Select Auto-Reschedule (Use Buffer or Keep Buffer) - Shrink the task pill by dragging its right edge to the left Issue: A traceback occurs: ValueError: max() iterable argument is empty Cause: when no dependent task needs to be rescheduled, the candidates is empty and max() is called on an empty list. Solution: Check that candidates exist before computing the maximum deadline from the dependent tasks. task-6268332 Related PR https://github.com/odoo/enterprise/pull/113787
This update resolves an issue where inactive and archived taxes were incorrectly displayed in the bank reconciliation widget. The fix ensures that only active taxes are available for selection, improving data accuracy and preventing users from selecting irrelevant tax codes during reconciliation processes. This enhances the reliability of financial reporting.
Original PR description
### Issue:
When editing a line within the bank reconciliation widget, inactive and archived taxes are incorrectly available for selection
### Cause:
The bank reconciliation edit line form view carried the `{'active_test': False}` context on the `tax_ids` field
This context allowed archived taxes to be loaded and selected during creation and manual edition
### Fix:
Explicitly force `active_test: True` in the view context for the tax field to ensure only active taxes can be searched and selected by the user
### Steps to reproduce:
- Install `account_accountant`
- Create a new tax and set it to inactive
- Go to the Bank Reconciliation widget
- Create a bank statement line
- Set the account to 600000 Expenses
- Edit the line by clicking on the pencil icon
- Open the Taxes selection dropdown
Before the fix, the inactive tax is visible and available for selection by default
opw-6245641This update corrects a bug in the Datev ledger export that previously miscalculated currency amounts. The fix ensures that tax and currency values align with the invoice's currency, improving the accuracy of the exported data for Datev reporting. This resolves discrepancies between the database and the Datev export.
Original PR description
There is an issue in the Datev export functionality. In the current functionality, the code calculates a delta between the taxes in the `tax_totals` and the ones on the journal items. Issue is, the tax amounts from tax_totals were always in company currency, while the entry itself can use a foreign one. This replaces the use of company currency with the use of the invoice's currency and appropriately adjusts the test featuring foreign currency. Steps: Create a foreign currency. Create an invoice with a taxed product using the currency. Export the ledger to Datev. Inspect the resulting csv. Note that neither the final listed price, nor the rate listed for the currency align with the ones in the db. opw-6275889 Forward-Port-Of: odoo/enterprise#120293
This update resolves an issue where demo leave allocations wouldn't correctly update during an Odoo upgrade from 17.0 to 18.0. The fix ensures that demo data is processed correctly, validating leave allocations regardless of the installation method (fresh or upgrade).
Original PR description
Steps: - Install an Odoo 17.0 database with the Indian Payroll module and demo data. - Upgrade the database to 18.0. Issue: - The Indian payroll demo data creates leave allocations and approves them…
Steps: - Install an Odoo 17.0 database with the Indian Payroll module and demo data. - Upgrade the database to 18.0. Issue: - The Indian payroll demo data creates leave allocations and approves them through an XML function call. - During a fresh installation, demo files are loaded in 'init' mode, so the approval function is executed and the allocations move from 'confirm' to 'validate'. - However, during a 17.0 >>> 18.0 upgrade, demo files are loaded in 'update' mode. Odoo automatically loads demo files with 'noupdate=True' from the load_demo() >> load_data() function: - This value is passed to the XML importer and becomes the default noupdate state for the file. Since the demo XML file does not explicitly override this value, the function tag uses 'noupdate=True'. - When the XML parser reaches the approval function, _tag_function() skips its execution because of noupdate = 'True' and mode = 'update' condition. - As a result, the approval function is not executed during the upgrade and the leave allocations remain in 'confirm' state. Subsequent demo payroll data expects validated allocations and fails during loading. Fix: - Explicitly set 'noupdate=0' on the demo XML file. This overrides the default 'noupdate=True' value applied to demo files, making the parser evaluate the section with 'noupdate=False'. - As a result, '_tag_function()' executes the approval method during upgrades, the demo leave allocations are validated in both fresh/new db installations and 17.0 >>> 18.0 upgrade scenarios. runbot error-https://runbot.odoo.com/odoo/error/230430 task-6268381 Forward-Port-Of: odoo/enterprise#119217
7 changes
Resolved issues and error corrections
This update corrects a bug where submitting the Contact Us form incorrectly updated both new tasks and existing project details with the same customer information. The fix ensures that task customer data remains accurate and prevents unintended changes to existing customer records, maintaining data integrity.
Original PR description
Steps to reproduce: -------------------------------------------- 1. Install `website_project` module 2. Create a new project 3. Add a customer to the project 4. Go to customer > add email and phone…
Steps to reproduce:
--------------------------------------------
1. Install `website_project` module
2. Create a new project
3. Add a customer to the project
4. Go to customer > add email and phone
5. Create a new task in that project:
* Observe that the customer is the same as the project
6. Go to Website > Contact Us > Edit > Click on submit button
7. Set action to 'Create a Task' and select the created project in 'Project'
8. Click on Save and Open the URL in Incognito Mode
9. Go to the Contact Us page > Fill in the details > Submit
10. Comeback to our window and open tasks of the created project
Observation:
--------------------------------------------
1. A new task is created using the customer details entered in the form.
2. The existing task’s customer and the project’s customer are also incorrectly updated to this new customer.
Issue:
--------------------------------------------
The bug is in the `extract_data` method of the website form controller for projects.
A non-logged-in user submits the Contact Us form with name and an email that doesn't match any existing partner. The old code's `else` branch would set `partner_name` in the task record values without setting a `partner_id` https://github.com/odoo/odoo/blob/cd080047578b9992811608a5af73a982a414da39/addons/website_project/controllers/main.py#L65-L66
During task creation, the computed field `_compute_partner_id` automatically sets `partner_id` to the project's partner
https://github.com/odoo/odoo/blob/cd080047578b9992811608a5af73a982a414da39/addons/project/models/project_task.py#L1440-L1441
`partner_name` is defined as
https://github.com/odoo/odoo/blob/cd080047578b9992811608a5af73a982a414da39/addons/website_project/models/project_task.py#L12
In Odoo, a related field is essentially a shortcut to a field on a linked record The key attribute here is `readonly=False`. This tells Odoo:
* On read: Get the value from `self.partner_id.name`
* On write: Propagate the write back to `self.partner_id.name` (this is the inverse). So writing `task.partner_name = 'TEST'` is equivalent to writing `task.partner_id.name = 'TEST'`. It modifies the partner record itself, not just the task.
So, the partner record itself was renamed. Every record that references a partner now sees the new name
Solution:
--------------------------------------------
The fix passes `False` to `partner_id`, this way:
* The existing partner is untouched
* All other tasks and the sales order keep their correct customer
opw-6206080This update resolves a critical issue where the due date calculation was incorrect for November transactions, returning a month of 0. Additionally, a bug preventing errors when processing empty recordsets has been fixed, improving the stability and reliability of the French PD Partnership module. This ensures accurate financial reporting and avoids potential data inconsistencies.
Original PR description
- Fix due date calculation (returned month 0 if move date was in November) - Fix ensure_one error, avoid calling _deduce_country_code() on an empty recordset opw-6293701
This update optimizes the process of validating purchase orders by preventing unnecessary calculations of location weights. By reordering checks, the system avoids computing weights when other conditions already rule out a location, resulting in significantly faster validation times, particularly when dealing with many locations using the same storage categories.
Original PR description
When checking if a stock.move.line can use a location as destination with the method `_check_can_be_used()`, we start by checking if the incoming products can be stored without exceeding the maximal…
When checking if a stock.move.line can use a location as destination with the method `_check_can_be_used()`, we start by checking if the incoming products can be stored without exceeding the maximal weight of the location. This needs to call the `_get_weight()` method to compute the forecasted weight for the location. This method relies on heavy computations and can become a bottleneck when we need to loop over a high number of locations. In some cases, we can rule out the location based on less expensive conditions that are verified after the weight one. We propose to invert the conditions check order to avoid computing the location weight when other conditions are not met. Steps to reproduce --------------- - Install stock and purchase modules; - Enable storage locations and categories in the settings; - Create a storage category: allow_new_product = same, max_weight=10.0 kg; - Create N locations using this category, parent_id=WH/stock; - Create a putaway rule to each location from WH/stock, for the new storage category and using a product A with a weight of 2 kg; - Create a stock.quant per location to store a product B, weight=2kg; - Create a purchase order with X lines for 1 unit of product A; - Validate the purchase order. The validation should take several seconds to execute as every locations will be rejected due to the storage category, but it will call _get_weight() first. Benchmark --------------- This improvement is very data specific and will be most useful when a lot of locations are using a storage category of type "empty" or "same". In addition, it also relies on the order in which we are treating the locations, if the acceptable locations are the first to be received in the method, it won't need to loop over all of them. The following benchmark was established in a production database in which every 6068 locations are using a category of type "same". | No stock.move.lines | Before PR | After PR | |---------------------|-----------|----------| | 40 | 168 s | 7.3 s | | 72 | 264 s | 12.33 s | When the only condition that can reject locations is the exceeding weight, this modification will slow down the process. However, the time loss in this case is smaller than the gain in the first case. The following benchmark was obtained by validating a purchase 1 line order with only fully filled locations. | No locations | Before PR | After PR | |--------------|-----------|----------| | 500 | 2.02s | 2.37 s | | 2000 | 7.85s | 9.76 s | | 10000 | 39.16 s | 48.86 s | opw-5949370 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#266872
This update ensures that the Philippine sales and purchase reports (SLSP) exports consistently maintain a predictable order for partner VAT values and row sequences. Previously, a random order caused test failures and potential discrepancies in exported data. This fix guarantees data accuracy and reliability for reporting in the Philippines.
Original PR description
Description of the issue this commit addresses: SLSP XLSX partner rows were emitted in a non-deterministic order, which made the PH sales/purchases export tests sometimes swap partner VAT values. --- Desired behavior after this commit is merged: This commit keeps the SLSP partner rows in a stable order so the XLSX export always matches the expected partner VAT and row sequence. --- runbot-[162182](https://runbot.odoo.com/odoo/error/162182)
This update resolves an issue where the due date calculation for French VAT reporting was inaccurate, particularly when the move date fell in November. It also corrects a technical error that prevented the system from properly processing certain records. This ensures accurate VAT reporting and avoids potential reporting delays.
Original PR description
- Fix due date calculation (returned month 0 if move date was in November) - Fix ensure_one error, avoid calling _deduce_country_code() on an empty recordset opw-6293701
This update corrects a potential issue in the Swiss payroll module where users could incorrectly request refunds on payslips. Swiss regulations limit payments to one per month, so the system now directs users to cancel and re-create payslips for accurate corrections. This ensures compliance with Swiss tax laws.
Original PR description
Prevent refunds for CH payslips since only one payslip per month is allowed for Swiss payroll. Users should cancel the payslip and create a new one to apply corrections. task-5951981 Forward-Port-Of: odoo/enterprise#107943
This update fixes an issue where international UPS shipments were failing due to incorrect commercial invoice addresses. The fix initially used the delivery address, but this caused further problems. Now, the system defaults back to the delivery address if country codes don't match, with a warning displayed to the user to ensure accurate invoice information.
Original PR description
Issue ----- When making an international delivery to a partner with different invoice and delivery addresses, we send the delivery address as the `Sold To` address as well. Problematic case 1 ----- -…
Issue ----- When making an international delivery to a partner with different invoice and delivery addresses, we send the delivery address as the `Sold To` address as well. Problematic case 1 ----- - Create a belgian company - Setup UPS - Create a French customer - Add a different french delivery address - Create a product (with some weight) - Create a SO (with UPS delivery) to the customer & confirm - Validate the transfer > Commercial invoice `Sold To` uses the delivery address Solution for case 1 ----- Use the delivery address' `commercial_partner_id`. This leads to another issue in some edge cases... Problematic case 2 (caused by case 1 fix) ----- - Create a belgian company - Setup UPS - Create a French customer - Add a delivery address in Switzerland - Create a product (with some weight) - Create a SO (with UPS delivery) to the customer & confirm - Validate the transfer > UPS error `The Sold To party's country code must be the same as the Ship To party's country code with the exception of Canada and satellite countries.` Solution for case 2 ----- Default back to delivery address for the `Sold To` field when countries don't match, as this is a limitation of the UPS API. Warn the user, either on the SO or the transfer itself (if no SO). Warning looks like this (on SO): <img width="1914" height="716" alt="image" src="https://github.com/user-attachments/assets/f7aa73c4-f24c-42da-8f3e-6a58765ef020" /> ----- Ticket: opw-6200263 Forward-Port-Of: odoo/enterprise#118031
5 changes
Enhancements to existing features
This update allows Odoo to correctly handle the new 20-digit format for China's digital e-fapiao invoices. Previously, Odoo only supported the older 8-digit format. This change ensures that Chinese vendors can accurately store and use their e-fapiao numbers without errors, improving invoice processing.
Original PR description
* https://hainan.chinatax.gov.cn/ssxc_3_23_1/12155283.html China's STA fully digitized e-fapiao uses a unique 20-digit invoice number, while legacy paper fapiao kept an 8-digit number. Accept both formats so CN vendor bills and invoices can store electronic fapiao numbers without validation errors. Description of the issue/feature this PR addresses: Current behavior before PR: Desired behavior after PR is merged: --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr
Resolved issues and error corrections
This update resolves a validation issue with ZATCA tax reporting caused by how discount quantities were handled in XML generation. The change ensures negative discount quantities are treated like negative unit prices, resulting in accurate totals and preventing validation warnings. This improves the reliability of financial reporting for Saudi Arabia.
Original PR description
Before this commit, using a negative quantity for a discount line caused ZATCA validation warnings (BR-S-08, BR-CO-10 and BR-CO-13), as it was not handled like a negative price. This commit fixes the XML generation to treat negative quantities identically to negative unit prices, ensuring correct totals. task-5883377
This update fixes a rendering issue in Outlook Desktop where the layout of emails with the 's_three_columns' design was not displaying correctly. Specifically, column heights and button styling were inconsistent. The change ensures a more professional and visually accurate email experience for users on Outlook Desktop.
Original PR description
Problem: - `s_three_columns` is not rendered correctly in Outlook Desktop when the equal-height option is enabled. - Button padding, border radius, and background color are not rendered properly in…
Problem: - `s_three_columns` is not rendered correctly in Outlook Desktop when the equal-height option is enabled. - Button padding, border radius, and background color are not rendered properly in Outlook Desktop. Solution: - Set the `height` attribute on `td.card-body` along with `valign` so columns keep the same height in Outlook Desktop. - Use `v:roundrect` to support rounded corners (`arcsize`) and background colors (`fillcolor`), making buttons render consistently with the editor in Outlook Desktop. Before: <img width="1249" height="1297" alt="image" src="https://github.com/user-attachments/assets/828bc42b-1e21-404c-a5ae-81d4ee688802" /> After: <img width="1249" height="1309" alt="image" src="https://github.com/user-attachments/assets/263a1c30-fe86-4e40-b3c2-476abc2bf84a" /> Steps to reproduce: - Add the `s_three_columns` snippet with one card containing more content than the others. - Add some buttons. - Send or preview the email in Outlook Desktop. - Observe that column heights and button styling are not rendered correctly. opw-6044725 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#269274
This update fixes an issue where cancelled Point of Sale (POS) orders weren't being fully removed from the system. Previously, refunds triggered a state change but didn't delete the order. Now, cancelled orders are properly deleted, streamlining order management and preventing data inconsistencies.
Original PR description
Steps to reproduce: - install `pos_self_order` - In POS, purchase something - Refund from the backend but don't validate it yet. - Delete order from POS by clicking on the Trash icon, from order list…
Steps to reproduce: - install `pos_self_order` - In POS, purchase something - Refund from the backend but don't validate it yet. - Delete order from POS by clicking on the Trash icon, from order list - Return to the backend and observe that the state has been moved to Cancelled. Current behavior: - The order is moved to cancelled instead of being deleted. Expected behavior: - The order should be deleted. Cause: - `pos_self_order` overrides `remove_from_ui` and cancels the order before calling `super()`. https://github.com/odoo/odoo/blob/7c47336246aa5443c1e95cb253fea7ac0f8aab0e/addons/pos_self_order/models/pos_order.py#L72-L79 - However, the original method only cleans up orders in `draft` state. https://github.com/odoo/odoo/blob/4a2d74bf802fbbc65d316b2da07b8a27913a0a7f/addons/point_of_sale/models/pos_order.py#L1162-L1168 Fix: Allow `remove_from_ui` to also clean up already cancelled orders. opw-6223411 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr
This change ensures that fully-discounted product lines in Mexican CFDI invoices are correctly reported to the SAT. Previously, these lines were omitted, causing issues with inventory and tax traceability. Now, the invoice accurately reflects the transaction, aligning with SAT requirements.
Original PR description
Steps to reproduce: - Set up a Mexican company (MXN, l10n_mx_edi) able to send CFDI. - Create a Gift Card / eWallet program (e.g. 680 MXN). - Create a sale order with two products (e.g. 400 and 300).…
Steps to reproduce: - Set up a Mexican company (MXN, l10n_mx_edi) able to send CFDI. - Create a Gift Card / eWallet program (e.g. 680 MXN). - Create a sale order with two products (e.g. 400 and 300). - Apply the gift card so the first product is fully covered. - Deliver, invoice, confirm and send to the SAT. Issue: The product entirely covered by the gift card (net amount = 0) is missing from the generated CFDI. The SAT requires every delivered product to appear in the XML for inventory and tax traceability, so omitting the line makes the document no longer reflect the transaction. The line was dropped because the negative-line dispatching (`_dispatch_negative_lines`) moves a positive line that is fully consumed by a negative one into `nulled_candidate_lines`, and those were never re-added to the CFDI lines. Simply re-adding them is not enough: a fully-discounted line has a tax base of zero, and the SAT rejects a Traslado/Retención with Base = 0 (CFDI40174 / CFDI40181). Fix: Re-add the nulled candidate lines so the concepto is kept with Descuento == Importe, and, when the line net is zero, drop its tax breakdown so it is reported as "No objeto de impuesto" (ObjetoImp '01') without an Impuestos node. This matches the behaviour already present in later versions. opw-6062845