Daily updates from Odoo
Wednesday, July 1, 2026
22 changes · 19.0
Resolved issues and error corrections
This update fixes a problem in the barcode-based inventory workflow. It helps ensure users can complete stock operations more reliably when using barcode scanning, reducing interruptions during warehouse tasks.
This update makes rental products work properly with Click & Collect in the online shop. It uses the rental period to show the correct availability, improves the add-to-cart experience when items are unavailable, and reduces confusing warning messages for shoppers.
Original PR description
**Purpose:** - Click & Collect and Rental are not working together, the rental dates are not used to display the availability of the product. - Unmute rental period selector when out of stock - Display muted Add to Cart button when out of stock - Remove renting warning message - Select the first valide date when adding to cart from the shop page instead of showing an error message if the product is not available for the default date **Specification:** Create a new bridge module between website_sale_collect and website_sale_renting to ensure that we use the rental dates to compute the availability if this is a rental product. Task-6081690 See also: - https://github.com/odoo/odoo/pull/266874
This update relaxes an automated test so it accepts any valid document number format instead of expecting one exact value. It prevents false failures when the document number increases during repeated testing, making the validation more reliable.
Original PR description
**Why the fix:** This step failed from time to time as we did some batch testing on the runbot with the same database, and because of this, the Número de Documento increased, making it SETF990000002 or more. This error existed before 68da209 but by fixing the refund flow in said commit, this error has been appearing way more frequently. As this has already happened a few times in 18.2, it is still the targeted version for this fix. We now use a regex to make sure that we have **Número de Documento: SETF** followed by some numbers, but we do not specify that it should be SETF990000001 anymore. runbot-241997 Forward-Port-Of: odoo/enterprise#121211
This change fixes an issue that prevented PDF downloads for a specific type of Guatemala vendor bill. Users can now generate and download the document successfully after sending it to the tax authority.
Original PR description
**Steps to reproduce:** - Install the `l10n_gt_edi` module and switch to a `GT Company`. - Create a new vendor bill with: - Vendor: GT Company - GT Document Type: `FESP` - Add taxes `VAT Withholding…
**Steps to reproduce:** - Install the `l10n_gt_edi` module and switch to a `GT Company`. - Create a new vendor bill with: - Vendor: GT Company - GT Document Type: `FESP` - Add taxes `VAT Withholding 12%` and `ISR Withholding 5%` in Invoice lines. - `Confirm` the bill and `Send to SAT`. - From the gear icon, click `Download` > `PDF`. **Error1:** `KeyError: 'gran_total'` **Error2:** `KeyError: 'retencion_grand_total'` **Root Cause:** In commit [1], the code at [2] missed calling `_l10n_gt_edi_add_base_values()` before `_l10n_gt_edi_add_withholding_values()`. However, `_l10n_gt_edi_add_withholding_values()` uses the `gran_total` value, which is initialized by `_l10n_gt_edi_add_base_values()`, resulting in a `KeyError`. Additionally, the report template at [3] references `retencion_grand_total` instead of the correct key `retencion_gran_total`, causing another `KeyError`. **Fix:** This commit prevents errors and ensures users can successfully download the PDF by applying a fix similar to [4], [1]: https://github.com/odoo/enterprise/commit/44afd19e4ed0827e343af0e584c81e579935c9e8 [2]: https://github.com/odoo/enterprise/blob/9846b337cfe1876017c7c2ce3041569d7a2ac03f/l10n_gt_edi/models/account_move.py#L305-L328 [3]: https://github.com/odoo/enterprise/blob/9846b337cfe1876017c7c2ce3041569d7a2ac03f/l10n_gt_edi/views/report_invoice.xml#L72 [4]: https://github.com/odoo/enterprise/blob/9846b337cfe1876017c7c2ce3041569d7a2ac03f/l10n_gt_edi/models/account_move.py#L790-L800 opw-6323049 Forward-Port-Of: odoo/enterprise#122030
This update corrects a test for Mexican electronic invoicing so it works whether the accounting app is installed or not. It matters because payment statuses can now be recognized consistently, preventing false test failures in automation.
Original PR description
If accountant is installed, payment state of unreconciled payment switch from 'paid' to 'in_payment'. Not having accountant break the test. runbot-939445 Forward-Port-Of: odoo/enterprise#121113
This fix prevents Instagram post publishing from crashing the server when the image upload process times out or encounters a network problem. Instead of an error interruption, the post is now marked as failed and users receive a clearer message, including a suggestion to try a smaller image when the issue is likely caused by image size or processing time.
Original PR description
Making an Instagram containing an image can crash the server with an unhandled `ReadTimeout` instead of marking the post as failed. ### Cause When creating a media container, Odoo passes a URL pointing to its own server and Instagram fetches the image from it server-side before responding. The timeout therefore covers network latency, Instagram's download speed from the Odoo server, and image processing time, making it prone to being exceeded. When it is, `requests` raises a `ReadTimeout` which is unhandled, leading to a raw RPC error instead of a clean `state='failed'`. ### Fix Catch the network errors and mark the post as failed instead of letting them crash the request. Timeouts get a message suggesting a smaller image, since they are usually caused by Instagram fetching and processing a large image server-side. Any other request error falls back to a generic message. opw-6015997 Forward-Port-Of: odoo/enterprise#112573
Payslips created from a parent company will now correctly show employees belonging to its branch companies. This fixes an inconsistency that prevented some Belgian branch employees from being selected, making payroll processing more reliable.
Original PR description
Bug: employees registered on branch companies don't appear in the
employee_id field when creating a payslip from the parent company.
Reason: the domain used ('company_id', '=', company_id) which only
matches the exact company, not its children.
Solution: replaced '=' with 'child_of' to include all descendant
companies in the hierarchy.
task - 6299634
Forward-Port-Of: odoo/enterprise#121360
Forward-Port-Of: odoo/enterprise#120974The email shown in signature certificate logs is now taken from the applicant’s own sign-in details instead of a fallback user email. This prevents certificates from showing the wrong address when candidates sign offers from recruitment.
Original PR description
When generating an offer from the recruitment application and signing it, the applicant's email address is incorrectly displayed. ### **Steps to Reproduce:** 1) Install sign, recruitment,…
When generating an offer from the recruitment application and signing it, the applicant's email address is incorrectly displayed. ### **Steps to Reproduce:** 1) Install sign, recruitment, hr_contract_salary 2) Create an new application and add basic detail like name and email as (path and `path@test.com`) 3) Generate offer and sign with all the required signer(applicant and Marc Demo). 4) Open the application form view and open the certificate. ### **Observed Behavior:** Email is not set correctly in the generated certificate (appearing as `john@example.com`). ### **Expected Behavior:** The email of the applicant should be correctly set(e.g as `path@test.com`) ### **Root Cause:** When the applicant signs the document, their email is explicitly set to `False` at [1]. This is done because the applicant is not linked to any user yet. Later, when generating the certificate, the system attempts to display the user's partner email at [2], which is `False`, causing the default fallback value (`john@example.com`) to be printed. [1]- https://github.com/odoo/enterprise/blob/49226f4109c7d7bb48340949951e70f4245d0e5b/hr_contract_salary/controllers/main.py#L53-L54 [2]- https://github.com/odoo/enterprise/blob/49226f4109c7d7bb48340949951e70f4245d0e5b/sign/report/sign_log_reports.xml#L59 ### **Fix:** Use `signer_email` instead of the partner's email to ensure the correct email is displayed on the certificate every time. opw-6280170 Forward-Port-Of: odoo/enterprise#120566
The Helpdesk quick-create form now only shows customers that belong to the user’s selected company. This prevents agents from accidentally choosing a customer from another company and helps keep tickets correctly assigned.
Original PR description
Steps to reproduce: - Create two companies (Company A and Company B) - Create one partner in each company - Enable both companies for the user - Open Helpdesk and go to the tickets Kanban view for a Company A team. - In the quick create form, the customer dropdown shows customers from Company B Issue: - Customers from other companies are visible in the customer field, Cause: - The partner_id field in the quick create view had no domain, so it displayed partners from all allowed companies. Solution: - Added a domain on partner_id in the ticket quick create form view. task-4971466 Forward-Port-Of: odoo/enterprise#121944
This fix removes an access error that blocked standard POS users from opening the Kitchen Display app directly from the main dashboard. It now lets them reach the same screen they could already access from inside POS, making the experience consistent and preventing unnecessary interruptions.
Original PR description
**Description of the issue/feature this PR addresses:** When a POS user attempts to open the Kitchen Display app from the main dashboard, they are blocked by an Access Error, despite being able to…
**Description of the issue/feature this PR addresses:**
When a POS user attempts to open the Kitchen Display app from the main dashboard, they are blocked by an Access Error, despite being able to access the interface from within the POS app's sub-menu.
This occurs because the dashboard menu triggers a server action (`action_pos_preparation_display_kitchen_display`) to route the user. When a server action has no explicitly defined `group_ids`, Odoo's `_can_execute_action_on_records` method falls back to requiring `write` access on the underlying model (`pos.prep.display`) to execute the code. Since standard POS users do not have 'write' access to this model, the execution engine blocks the routing attempt.
This commit resolves the issue by explicitly appending the POS User group to the server action's `group_ids`.
opw-6305014
**Steps to reproduce:**
- As Mitchell Admin:
- Settings > Users & Companies > Users > Marc Demo > Access Rights > Sales > set POS to User
- As Marc Demo:
- Attempt to access Kitchen Display app > observe Access Error
- POS > Orders > Preparation Display > observe no error
**Current behavior before PR:**
- POS Users receive an Access Error when attempting to access the Kitchen Display app from the main dashboard
**Desired behavior after PR is merged:**
- No Access Error when POS Users access the Kitchen Display appWhen a business card is scanned, the city information is now imported correctly along with the other contact details. This makes newly created or updated contacts more complete and saves users from entering the city manually.
Original PR description
Previously, when user scans any business card, every information was fetched except for the city name. After this commit the city field will be properly fetched. task-6332914 Forward-Port-Of: odoo/enterprise#121766
When users choose documents to attach or link, the extra action buttons now stay hidden in that selection dialog. This makes the interface less cluttered and helps prevent confusion while picking documents.
Original PR description
When selecting documents for attachment/link, control panel actions were displayed upon selection. The document selection dialog uses the secondary documents view introduced in: https://github.com/odoo/enterprise/pull/89030/changes/f93c159c106d1dde70910ec590f8739e549b19cf Several document management actions were already hidden through the `documents_view_secondary` context, but `DocumentsAction` was still displayed upon selection. Hide `DocumentsAction` in the secondary view. Task-6236888
This fix ensures goods that fail quality checks remain available for vendor returns instead of being pulled back into the warehouse reception flow. As a result, teams can complete returns without the items getting stuck in another quality check process.
Original PR description
Steps to reproduce --- 1. Set a warehouse to three-step reception. 2. Add a quality control point on the Quality Control operation with a failure location. 3. Receive a storable product and fail the…
Steps to reproduce --- 1. Set a warehouse to three-step reception. 2. Add a quality control point on the Quality Control operation with a failure location. 3. Receive a storable product and fail the quality check, so the goods are moved to the failure location. 4. Return the failed goods to the vendor. Issue --- The vendor return never becomes available, because the returned goods are pulled back into the reception route instead of being free to ship back to the vendor. A failed check moves the goods to the failure location by changing the destination of the operation's move, so returning them brings the goods back through WH/Input. https://github.com/odoo/enterprise/blob/885edbc270a86ab76e0a6eff4acb5767c0fe29d1/quality_control/models/quality.py#L577-L589 A move applies the reception route's push rules once it is done, so landing back in WH/Input re-pushes the returned unit into Quality Control and re-creates a quality check on it, that push reserves the unit, and whether the new check is passed (pushed onward to stock) or failed (sent back to the failure location), it never stays available to continue to the vendor. https://github.com/odoo/odoo/blob/161715c850496d3683baa5d1600380470d0b5ff5/addons/stock/models/stock_move.py#L2285-L2287 opw-6243147
The Depreciation Schedule report now leaves the account code blank when that information is not available, instead of showing the word “False”. This makes the report clearer and avoids confusing output when multiple companies are selected.
Original PR description
The issue is occur, when multiple companies are selected and the Depreciation Schedule report is opened, report correctly displays the account code for the company selected as the root company.…
The issue is occur, when multiple companies are selected and the Depreciation Schedule report is opened, report correctly displays the account code for the company selected as the root company. However for the other selected companies, the account code is displayed as False To avoid displaying False in the report changed the behavior to pass a null value whenever the account code is not available. For more details, please refer to the attached video. Root Cause The issue occurs because the code field is set to `False` [here](https://github.com/odoo/odoo/blob/ff64328283ee3bcc361fa0604bd4b9da8e62e803/addons/account/models/account_account.py#L337) for companies that are not considered the root company. As a result the report directly displays False instead of leaving the field null Steps to Reproduce 1.create a demo database in 19.0 2. Create two assets, each belonging to a different company. 3. Open the Depreciation Schedule report. 4. Select the first company, then select the second company as well. 5. Notice that the account code is displayed correctly for the root company, while `False` is shown for the other company. OPW-6239737 UPG-4196503 with out fix <img width="1852" height="579" alt="image" src="https://github.com/user-attachments/assets/b99f343d-b624-4d95-b826-6afdd2ebaa4c" /> with fix <img width="1912" height="731" alt="image" src="https://github.com/user-attachments/assets/19112a08-1958-496d-868f-a4091a745842" /> see video https://github.com/user-attachments/assets/ec51bb47-6c64-4cee-b484-7a359ed36ee0
This update corrects the Peru Kardex PLE stock report so balances, costs, invoices, and return movements are calculated consistently in Odoo 19. It also improves support for related stock operations and landed costs, helping reduce reporting errors and manual corrections.
Original PR description
## Summary Forward-port of PR #88592 (Kardex PLE 12.1/13.1 report fixes) adapted to 19.0's `stock.move` architecture, where `stock.valuation.layer` was removed as an independent model. - **Running…
## Summary
Forward-port of PR #88592 (Kardex PLE 12.1/13.1 report fixes) adapted to 19.0's `stock.move` architecture, where `stock.valuation.layer` was removed as an independent model.
- **Running balances**: Replace per-move `remaining_qty`/`remaining_value` with accumulated `data_per_products` dict for correct cumulative totals
- **Fix broken `_append_historic_valuation_lines()`**: The existing 19.0 code called `self.env.cr.dictfetchall()` without prior SQL execution — replaced with proper `_read_group` tuple unpacking
- **Fix `_append_valuation_line()`**: Use `_read_group` on `stock.move` (is_in/is_out aggregation) instead of `qty_available` with `to_date` which doesn't provide correct cost data
- **Fix invoice association**: Use `.sorted('id')[:1]` to consistently pick the first-created invoice, matching 18.0's SQL `ORDER BY am.id NULLS LAST` behavior
- **Return operation types**: Add `stock_picking_return.py` to assign operation types 24/25/21 for return pickings
- **MRP support**: Detect `mrp_operation` picking type and assign operation types 19/27
- **Float formatting**: Add `float_repr` with 2-decimal precision for all numeric fields
- **19.0 API adaptations**: `is_storable` filter (replaces `type='product'`), `fields_list` parameter naming, security comment on `sudo()`
Related: #88592, #106679This change prevents a traceback when a negative forecast demand is entered in the last planning period. It ensures the remaining negative quantity is correctly carried into the first forecast, so planning continues to work as expected.
Original PR description
Steps to reproduce: - Fresh DB - Add a negative number to the forecast demand in the last period Cause: A variable was used without declaration Fix: According to odoo/enterprise#56128, it was intended that any remaining negative quantity to add should be added to the first forecast. Forward-Port-Of: odoo/enterprise#122261
This change restores the ability to book multiple appointments on the same resource when that is expected by the appointment setup. It prevents resources from being treated as unavailable too early, so scheduling works correctly for both capacity-managed appointment types and shareable resources.
Original PR description
There are 2 modes to manage multiple appointments per resource: - either the resource manages its limits - or the appointment type does Commit https://github.com/odoo/enterprise/commit/4c05037…
There are 2 modes to manage multiple appointments per resource: - either the resource manages its limits - or the appointment type does Commit https://github.com/odoo/enterprise/commit/4c05037 introduced batch computation to improve the performance of availability computations, but inadvertently prevented that second use-case from working. The problem was in the logic to decide which resources are allowed to have overlapping bookings. After https://github.com/odoo/enterprise/commit/4c05037 (but before this revision), only appointment types where manage_capacity = True and resource.shareable = True were allowed to overlap. After this commit, appointment types where manage_capacity = False (regardless of shareability of the resource) are allowed (up to the max_bookings capacity set on the type) as well as types where manage_capacity = True and the resource is shareable (as they were before https://github.com/odoo/enterprise/commit/4c05037). Tests are introduced to prevent future regressions. Task-4144524 Task-6344700
The Journal Audit report now generates PDFs without an extra blank page at the end when certain summary content is missing. This makes the printed report cleaner and avoids confusion for users reviewing or sharing it.
Original PR description
Steps to reproduce: 1. Set the active company as My Company (san francisco) 2. Navigate to Accounting > Review > Journal Audit 3. Remove all journals from the report except Bank and Misc. 4. Use the PDF action button to print the report. 5. The last page of the report is completely empty. https://drive.google.com/file/d/1otpniJgt1UNCe2hrUBwqIK58dGuXpu8T/view?usp=sharing This commit ensures that the Journal Audit report does not have blank pages when the global tax summary section is not present. It uses some features of QWeb outlined in the following docs article: https://www.odoo.com/documentation/19.0/developer/reference/frontend/qweb.html#loops opw-6224670
This change prevents an error that could occur when generating the GSTR-1 Excel report for one company while report data from multiple companies exists. It ensures the export completes successfully instead of failing, improving reliability for businesses using Indian localization.
Original PR description
Steps to reproduce: - Install `l10n_in_reports` module(Indian Localisation) - Create a branch in `IN Company` > Select both - Create separate invoices for each company - Created the GSTR-1 report for…
Steps to reproduce:
- Install `l10n_in_reports` module(Indian Localisation)
- Create a branch in `IN Company` > Select both
- Create separate invoices for each company
- Created the GSTR-1 report for both company
- While generating Excel, select only main company
Traceback:
```py
File "/home/odoo/src/enterprise/19.0/l10n_in_reports/models/account_return.py", line 2537, in action_generate_gstr1_xlsx
gstr1_json = self._get_l10n_in_gstr1_json()
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/home/odoo/src/enterprise/19.0/l10n_in_reports/models/account_return.py", line 1071, in _get_l10n_in_gstr1_json
'b2cs': _get_b2cs_json(AccountMoveLine.search(self._get_section_domain('b2cs'))),
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/home/odoo/src/enterprise/19.0/l10n_in_reports/models/account_return.py", line 672, in _get_b2cs_json
for line, line_tax_details in tax_details.items():
^^^^^^^^^^^^^^^^^
AttributeError: 'NoneType' object has no attribute 'items'
```
Cause:
This issue occurs because, while generating the GSTR-1 Excel report for a particular month, [journal_items] contains account moves from both companies. This happens because the [domain] fetches records for both companies, resulting in move [lines] from both companies being included.
However, while generating the Excel report, only one company is selected. As a result, [tax_details_by_move] does not contain the move data for the branch company, which returns None, causing the error to be raised.
Solution:
Pass an empty `{}` for `tax_details` when only a single company is selected.
[journal_items]: https://github.com/odoo/enterprise/blob/3c3641d9f0753c1ca62285667c4a2786c15e2444/l10n_in_reports/models/account_return.py#L877
[domain]: https://github.com/odoo/enterprise/blob/770ffaac14bfcd2c54a7ce6aca27e0010e7884d4/l10n_in_reports/models/account_return.py#L1387-L1393
[lines]:
https://github.com/odoo/enterprise/blob/3c3641d9f0753c1ca62285667c4a2786c15e2444/l10n_in_reports/models/account_return.py#L1074
[tax_details_by_move]:
https://github.com/odoo/enterprise/blob/3c3641d9f0753c1ca62285667c4a2786c15e2444/l10n_in_reports/models/account_return.py#L880
opw-6242824## **Issue:** When validating a delivery, users with Sales: Own Documents Only and Inventory Administrator access rights can encounter an access error if the delivery belongs to a sale order owned by another salesperson. ## **Steps to reproduce:** - Install sale_subscription_stock. - Create a user with Sales: Own Documents Only and Inventory Administrator access rights. - Create a sale order as another user. - Validate the delivery with the restricted user. ## **Solution:** During _a
Original PR description
## **Issue:** When validating a delivery, users with Sales: Own Documents Only and Inventory Administrator access rights can encounter an access error if the delivery belongs to a sale order owned by…
## **Issue:** When validating a delivery, users with Sales: Own Documents Only and Inventory Administrator access rights can encounter an access error if the delivery belongs to a sale order owned by another salesperson. ## **Steps to reproduce:** - Install sale_subscription_stock. - Create a user with Sales: Own Documents Only and Inventory Administrator access rights. - Create a sale order as another user. - Validate the delivery with the restricted user. ## **Solution:** During _action_done(), [This line](https://github.com/odoo/enterprise/blob/19.0/sale_subscription_stock/models/stock_picking.py#L45) is checking subscription_state. Since the user does not have read access to the sale order, reading this field raises an access error and prevents the delivery from being validated. As the method only needs to read the subscription state, access the field with sudo() to avoid the unnecessary access error while preserving the existing business logic. Runbot Video : [Video](https://drive.google.com/file/d/1d7U2jTCxaaVk2YJcy3bi2SlYuT-yXMsu/view?usp=drive_link) OPW - 6295712
Steps to reproduce =================== - Install documents_hr. - Log in with admin. - Create a new company `Test`. - Go to Document and choose the new company (top right). - Go to `My Drive`: a folder named `Employees - Test` has been created. This new folder should be created in the `Company` root instead of the `My Drive,` which will hold all the employee folders. Technical =========== When the main employee folder is created via `_generate_employee_documents_main_folders` `ow
Original PR description
Steps to reproduce =================== - Install documents_hr. - Log in with admin. - Create a new company `Test`. - Go to Document and choose the new company (top right). - Go to `My Drive`: a folder named `Employees - Test` has been created. This new folder should be created in the `Company` root instead of the `My Drive,` which will hold all the employee folders. Technical =========== When the main employee folder is created via `_generate_employee_documents_main_folders` `owner_id` falls back to the current user, which leads to computing the `user_folder_id` as `My drive,` and so that's why the newly created folder starts appearing there instead of the `Company` root. This PR addresses the issue and sets the `owner_id` to False, which leads to show the main employee folder in the company root. Task-6267352
This update ensures invoices sent to Guatemala’s Infile service are encoded properly, so names and product details with characters like ñ, á, and é are preserved. It helps prevent invoice rejections and avoids corrupted text in certified XML documents.
Original PR description
**Steps to reproduce:** * Install the **l10n_gt_edi** module. * Configure a Guatemalan company with valid Infile credentials in the settings. * Create a product or customer with special characters…
**Steps to reproduce:**
* Install the **l10n_gt_edi** module.
* Configure a Guatemalan company with valid Infile credentials in the settings.
* Create a product or customer with special characters (e.g. `ñ`, `á`, `é`) in their name.
* Create a customer invoice containing this product/customer.
* Confirm the invoice to trigger the EDI send to the SAT (Infile).
**Observed behavior:**
* Infile intermittently rejects the invoice due to validation errors, or accepts it but the resulting certified XML has truncated or malformed text exactly where the special characters were located.
**Cause:**
* Odoo uses the `requests.post()` library to send the XML payload to Infile. By default, `requests` encodes string payloads using `latin-1` unless told otherwise.
* Because the request was missing the explicit `Content-Type: application/xml` header and the XML string was not explicitly encoded to `utf-8` before sending, Infile parsed the payload using an incorrect encoding. This caused it to drop or misinterpret special characters, leading to validation failures or corrupted XML content.
**Fix:**
* Explicitly include the `'Content-Type': 'application/xml'` header in the request to Infile.
* Explicitly encode the `xml_data` payload to `utf-8` (`xml_data.encode('utf-8')`) before passing it to `requests.post()` to guarantee the correct encoding is sent over the wire.
opw-6315654
Forward-Port-Of: odoo/enterprise#121729