Daily updates from Odoo
Friday, June 27, 2025
36 changes · master
Enhancements to existing features
Odoo's San Francisco office address has been updated in customer-facing content templates. This helps ensure communications and knowledge content reference the correct location and avoid pointing people to an unrelated business.
Original PR description
Update the Odoo SF Office address as they moved to make sure to not end up mentioning another unrelated business. related: https://github.com/odoo/odoo/pull/212916 Task-4844152
The rental date and time picker on the website has been visually refined so its navigation buttons better match different page backgrounds. This improves the storefront experience without changing backend editor behavior.
Original PR description
This PR fine-tunes the design of the datetime picker within the front-end after the merge of Commit[^1]. - Requires https://github.com/odoo/odoo/pull/215763 ---------------- Prior Commit[^1], the…
This PR fine-tunes the design of the datetime picker within the front-end after the merge of Commit[^1]. - Requires https://github.com/odoo/odoo/pull/215763 ---------------- Prior Commit[^1], the previous, next, and month selection buttons were all placed in a flex at the top of the datetime picker. After Commit[^1], buttons are re-ordered in a different layout, with the right button class on each of them. After this change, each button is separated and thus has its radius and background. In the backend, this `btn-light` is okay since it matches the background of our views, while in the front-end, this color is dynamic and does not match the page background. As each button is separated, it results in a weird visual result. To fix this issue, we remove these `btn-light` classes and add a `btn-sm` one to handle the size of these buttons. This change is meant to affect the datetime picker occurrences within the front-end but does not affect the `web_editor` one, as it inherits the backend design. task-4893742 [^1]: [e2b78fca435f268515f9593c2af821616aff7ebb](https://github.com/odoo/odoo/commit/e2b78fca435f268515f9593c2af821616aff7ebb)
VoIP now uses newer formatting helpers to handle displayed content more consistently. This should make call-related text safer and more reliable without changing day-to-day workflows.
Original PR description
Make the most of the newly introduced HTML helpers in the VoIP code.
This update improves the tooltip shown for subscription templates, making it easier for users to understand the related option or field. The change helps sales and subscription teams work with templates more confidently with minimal impact on existing workflows.
This update modernizes how Odoo defines filtering rules across Sales, Subscriptions, Rentals, POS, Planning, and related localization features. It is mainly an internal improvement that helps keep these business flows easier to maintain and more reliable without changing day-to-day user workflows.
Original PR description
odoo/odoo#206894
The helpdesk mail plugin setup information was updated to match related mail plugin modules. This keeps module configuration consistent and helps avoid small setup or dependency issues.
Original PR description
Consistency with other *_mail_plugin modules
Spreadsheet pivot tables in Documents now align with the updated behavior that no longer shows a label for the first row grouping. This keeps automated checks consistent with the intended interface and supports a cleaner spreadsheet experience.
Original PR description
This commit removes adapts the tests to the removal of the label of the first row group by in the pivot table. See https://github.com/odoo/o-spreadsheet/pull/4363 Task: 3975326
Customers will now see the successful payment message only when they return after completing a payment or from a payment confirmation email. This avoids showing an outdated success message every time they open the subscription portal, reducing confusion.
Original PR description
Before this commit, the successful payment message showed up every time the user opened the portal view. After this commit, the message will only appear if the user is redirected after making a payment or coming from a payment confirmation email. task-4420352
Demo products for rentals and subscriptions now include more short descriptions. This makes it easier to showcase how product descriptions can be enabled or disabled in sales demos.
Original PR description
*: sale_subscription Before this commit, only the first four demo products in website_sale had descriptions, showcasing a variety of none/short/long formats. This commit adds short descriptions (max 50 characters) to additional demo products to better demonstrate the "Enable/Disable Description" feature. In this case, the printer and car leasing products were updated to expand variety and highlight the use of none/short descriptions in a renting context. requires: https://github.com/odoo/odoo/pull/216043 task-4893752
This update adjusts the AI chat plugin to better mark content that works with plain text. It helps ensure AI-generated or processed chat content can be handled more consistently across contexts where formatting may not be supported.
Resolved issues and error corrections
This change removes a previously added date picker customization for website rentals because the related main component update was not included. It keeps the rental booking interface aligned with the supported design approach and avoids unintended frontend behavior.
Original PR description
This reverts commit[1]. The goal of Commit[1] was to introduce more flexibility to the datetime picker by using props to handle the design of the component within the frontend, to preserve the design introduced with the revamp of the component within the backend while fine-tuning its design within the frontend. During the review process, it was decided that changes would be applied on the main component directly instead of monkey patching the component, which invalidated the need of props. As the counterpart was not merged, this change shouldn't have landed as well. [1]: https://github.com/odoo/enterprise/commit/e650409bd8b027074f262dfdfc407d8d71bb8e36
This fixes a misleading or incorrect label used when grouping subscription records. It helps users interpret grouped subscription views more easily and reduces confusion in day-to-day navigation.
The Belgian payroll report for double holiday pay now uses the correct label instead of referring to the 13th month. This makes the report name clearer and helps avoid confusion for payroll teams and employees.
Original PR description
Originally, the name structure for double holiday follows "13th Month -[Legal Name] -[year]". It has been renamed to "Double Holiday Pay - [Legal Name] -[year]" .
Code cleanup and technical improvements
The Documents app code was reorganized to use safer standard markup helpers and to align with required formatting checks. This is an internal cleanup that reduces security scan noise and helps future changes be easier to review, without changing user-facing behavior.
Original PR description
Use markup template and html functions to make the code cleaner and safer while no longer triggering ci/security flag.
This update simplifies internal test infrastructure to reduce memory use and improve performance in the JavaScript test suite. It removes an older testing mechanism and adapts affected tests, helping make ongoing development and quality checks more reliable.
Original PR description
This PR aims at reducing the memory footprint and performance issues of the JS unit test suite. See commit messages for more details. Community: https://github.com/odoo/odoo/pull/215920
The project planning view code was tidied up to use safer, standard ways of building on-screen content. This reduces false security warnings in checks and helps keep the Project app easier to maintain without changing user-facing behavior.
Original PR description
Use markup template and html functions to make the code cleaner and safer while no longer triggering ci/security flag.
The Planning module has been updated to use safer, cleaner methods for displaying formatted content. This reduces internal security scan warnings while keeping the user experience unchanged.
Original PR description
Use markup template and html functions to make the code cleaner and safer while no longer triggering ci/security flag.
Spreadsheet pivot formulas were updated to use a clearer internal way of handling pivot filters and domains. This should make pivot-related spreadsheet behavior easier to maintain and more consistent, with no expected change to day-to-day user workflows.
Spreadsheet side panels now use a shared text input component for fields such as filters, lists, and pivots. This makes the interface more consistent and easier to maintain without changing core business workflows.
Original PR description
The component TextInput is meant to be used whenever a text input is necessary in a side panel. This commit replaces all theses inputs by the component TextInput Task: 3964069
This update replaces older internal model properties with their current equivalents across accounting-related enterprise modules. It helps keep the codebase aligned with the latest platform standards, reducing future maintenance risk without changing day-to-day user workflows.
Original PR description
odoo/odoo#193636
The automated website shopping tests now better detect when a page reload or redirect is expected. This reduces inconsistent test results and helps teams catch issues earlier before changes reach users.
Original PR description
In this commit, we uncomment the listener on beforeUnload to ensure that expectUnloadPage is correctly used in tours.
Miscellaneous changes
Content passed to a t-value directive is not translated. This commit redefines as text nodes human-readable content that was incorrectly placed in a t-value, so that it is now translated. Community: https://github.com/odoo/odoo/pull/216136 Forward-Port-Of: odoo/enterprise#88666
Original PR description
Content passed to a t-value directive is not translated. This commit redefines as text nodes human-readable content that was incorrectly placed in a t-value, so that it is now translated. Community: https://github.com/odoo/odoo/pull/216136 Forward-Port-Of: odoo/enterprise#88666
This reverts commit f40533c0b3410676aee29a2b48454213966613f7. In this commit, we added a customization for the bank rec widget by changing the way selection records in a list view works. Before the change: selecting a record then clicking on the line of another record -> the last record is selected, others already selected are ignored After the change: selecting a record then clicking on the line of another record -> the last record is added to the selection But after this: https://gith
Original PR description
This reverts commit f40533c0b3410676aee29a2b48454213966613f7. In this commit, we added a customization for the bank rec widget by changing the way selection records in a list view works. Before the change: selecting a record then clicking on the line of another record -> the last record is selected, others already selected are ignored After the change: selecting a record then clicking on the line of another record -> the last record is added to the selection But after this: https://github.com/odoo/odoo/pull/212148, this is the standard behaviour, so the bank rec customization is no more needed. task-4816580 Forward-Port-Of: odoo/enterprise#87474
Before this commit, when one tries to upload a file to a document request for the first time it does nothing. This is caused by an async memoize call which causes the file to be cleared between the memoize rpc call and the file processing after that call... After that first call the user can upload a new file without issue but it's still annoying. This commit fix this issue by storing the file in a variable before doing the memoize rpc call. Task-4778429 Forward-Port-Of: odoo/enterpri
Original PR description
Before this commit, when one tries to upload a file to a document request for the first time it does nothing.
This is caused by an async memoize call which causes the file to be cleared between the memoize rpc call and the file processing after that call... After that first call the user can upload a new file without issue but it's still annoying.
This commit fix this issue by storing the file in a variable before doing the memoize rpc call.
Task-4778429
Forward-Port-Of: odoo/enterprise#88660
Forward-Port-Of: odoo/enterprise#86002Forward-Port-Of: odoo/enterprise#87119
Original PR description
Forward-Port-Of: odoo/enterprise#87119
the field vat_check_vies on res.company is added in the base_vat module, which is not a required dependency for account_reports. the function _generic_vies_vat_check might therefore result in an error with a missing field. runbot issue: 227603 Forward-Port-Of: odoo/enterprise#88497
Original PR description
the field vat_check_vies on res.company is added in the base_vat module, which is not a required dependency for account_reports. the function _generic_vies_vat_check might therefore result in an error with a missing field. runbot issue: 227603 Forward-Port-Of: odoo/enterprise#88497
Description ----------- During bank statement reconciliation, finding matching journal entries generates a complex and resource-intensive query due to elaborate domain. This commit optimizes query performance by introducing a new `search_account_id` field that pre-filters the condition on `account_id` criteria. This allows the domain leaf to be resolved early and the resulting IDs to be re-injected into the main query. The optimization enables Postgres to leverage `pg_stats` directly for
Original PR description
Description ----------- During bank statement reconciliation, finding matching journal entries generates a complex and resource-intensive query due to elaborate domain. This commit optimizes query…
Description ----------- During bank statement reconciliation, finding matching journal entries generates a complex and resource-intensive query due to elaborate domain. This commit optimizes query performance by introducing a new `search_account_id` field that pre-filters the condition on `account_id` criteria. This allows the domain leaf to be resolved early and the resulting IDs to be re-injected into the main query. The optimization enables Postgres to leverage `pg_stats` directly for more accurate cost estimates. It also eliminates the need to join `account.account` with large tables like `account.move.line` and `account.move`. Overall performance improves significantly, given that `account.account` is a relatively small table, making it efficient to reuse the filtered IDs in the main query without impacting performance negatively. Benchmark --------- Clicking on "Reconcile" to open the wizard with the list view of matching Journal Entries (150k matches) from the new reconciliation view, on odoo.com takes (hot timings): | Before | After | Speed-up | |--------|-------|----------| | 14.7s | 5.75s | ~2.5x | Reference --------- task-4863071 Forward-Port-Of: odoo/enterprise#87427
The module `l10n_co_edi_mandate` [inherits](https://github.com/odoo/enterprise/blob/ce9eed675db4de3bcd1b283688c5c44d2e1ecf12/l10n_co_edi_mandate/models/account_edi_xml_ubl_dian.py#L5) a model defined in `l10n_co_dian` module, and the workflow in the module also depends[[1]](https://github.com/odoo/enterprise/blob/ce9eed675db4de3bcd1b283688c5c44d2e1ecf12/l10n_co_edi_mandate/models/account_invoice.py#L9)[[2]](https://github.com/odoo/enterprise/blob/ce9eed675db4de3bcd1b283688c5c44d2e1ecf12/l10n_co
Original PR description
The module `l10n_co_edi_mandate` [inherits](https://github.com/odoo/enterprise/blob/ce9eed675db4de3bcd1b283688c5c44d2e1ecf12/l10n_co_edi_mandate/models/account_edi_xml_ubl_dian.py#L5) a model defined…
The module `l10n_co_edi_mandate` [inherits](https://github.com/odoo/enterprise/blob/ce9eed675db4de3bcd1b283688c5c44d2e1ecf12/l10n_co_edi_mandate/models/account_edi_xml_ubl_dian.py#L5) a model defined in `l10n_co_dian` module, and the workflow in the module also depends[[1]](https://github.com/odoo/enterprise/blob/ce9eed675db4de3bcd1b283688c5c44d2e1ecf12/l10n_co_edi_mandate/models/account_invoice.py#L9)[[2]](https://github.com/odoo/enterprise/blob/ce9eed675db4de3bcd1b283688c5c44d2e1ecf12/l10n_co_edi_mandate/models/product_template.py#L8) on DIAN being installed. Both modules have the same dependency `l10n_co_edi` and are autoinstalled. This can easily break if the user chooses to uninstall the dian module. The module will fail to install if dian is not installed. The uninstall of the dian module will also cause an error if this module is installed. The upgrade will fail if the user has dian uninstalled (edi_mandate is a new module and will try to autoinstall) This fix makes the dependency explicit. Forward-Port-Of: odoo/enterprise#88607
The tour in `test_worksheet_quality_check` expects the "Select Work Centers" dialog to open automatically on load. This only happens if: - `localStorage` has no previous selection, and - the user has `group_mrp_routings` As seen [Here](https://github.com/odoo-dev/enterprise/blob/df3c6642cae9b40700b0b17e0335cec00ce23d3e/mrp_workorder/static/src/mrp_display/mrp_display.js#L124) in `MrpDisplay.onWillStart()`: `if (localStorage === null && this.group_mrp_routings) { this.to
Original PR description
The tour in `test_worksheet_quality_check` expects the "Select Work Centers" dialog to open automatically on load.
This only happens if:
- `localStorage` has no previous selection, and
- the user has `group_mrp_routings`
As seen [Here](https://github.com/odoo-dev/enterprise/blob/df3c6642cae9b40700b0b17e0335cec00ce23d3e/mrp_workorder/static/src/mrp_display/mrp_display.js#L124) in `MrpDisplay.onWillStart()`:
`if (localStorage === null && this.group_mrp_routings) {
this.toggleWorkcenterDialog(false);
}`
When running with `--without-demo=all`, the admin user does not have this group, so the dialog does not show and the test fails.
We fix this by explicitly assigning the group:
`self.env.ref("base.user_admin").groups_id += self.env.ref('mrp.group_mrp_routings')`
[runbot-161194](https://runbot.odoo.com/odoo/error/161194)
Forward-Port-Of: odoo/enterprise#87891
Forward-Port-Of: odoo/enterprise#87218Steps to reproduce: - Install payroll, l10n_mx_hr_payroll (mexican localisation) - Install l10n_mx_hr_payroll_account - Switch to a Mexican Company - Create a payslip for a mexican employee with amount < 4000 - Compute the sheet for the payslip Error message appears, this error message is not a descriptive to the user or not telling what could have gone wrong. This happens because the mexican pay structure has some salary rules that has to be computed, one of these rules is `Retiremen
Original PR description
Steps to reproduce: - Install payroll, l10n_mx_hr_payroll (mexican localisation) - Install l10n_mx_hr_payroll_account - Switch to a Mexican Company - Create a payslip for a mexican employee with…
Steps to reproduce: - Install payroll, l10n_mx_hr_payroll (mexican localisation) - Install l10n_mx_hr_payroll_account - Switch to a Mexican Company - Create a payslip for a mexican employee with amount < 4000 - Compute the sheet for the payslip Error message appears, this error message is not a descriptive to the user or not telling what could have gone wrong. This happens because the mexican pay structure has some salary rules that has to be computed, one of these rules is `Retirement, assault in elderly and old age (CEAV) IMSS (Employer)` that has mode of code. This mode means calling safe_eval on the code raw text of it written in the xml file on the data folder. This rule aims to find the suitable taxation level to be applied on the salary. It reads the limits of each level and check if the `integrated_daily_wage` of the employee falls in this level and applies that taxation level. There is no upper limit on the salary, But there is a min level, hence if the integrated_daily_wage < mdw (minimum daily wage) the function returns None that used as index in the taxation table leading to an unreadable Exception from the safe_eval call. https://github.com/odoo/enterprise/blob/747482f34ca8210d89d81b3363ec5a8fc3a4ff6f/l10n_mx_hr_payroll/data/salary_rules/hr_salary_rule_regular_pay_data.xml#L1111-L1120 opw-4576482 Forward-Port-Of: odoo/enterprise#88560 Forward-Port-Of: odoo/enterprise#83364
Improving UX by adding all of the AI related functionalities when AI module is installed. issue ticket task-4855178 Divagations --- In the future (19.0) the ai_fields and ai_server_actions modules should be merged into the ai module. with ticket task-4889610 Forward-Port-Of: odoo/enterprise#88542
Original PR description
Improving UX by adding all of the AI related functionalities when AI module is installed. issue ticket task-4855178 Divagations --- In the future (19.0) the ai_fields and ai_server_actions modules should be merged into the ai module. with ticket task-4889610 Forward-Port-Of: odoo/enterprise#88542
steps to reproduce: 1- install l10n_mx_edi_landing 2- without demo data 3 - run test_make_cfdi_report_carry_over_canceled_invoice missing sudo in test case to create sale order in the test build_error-226771 Forward-Port-Of: odoo/enterprise#87946
Original PR description
steps to reproduce: 1- install l10n_mx_edi_landing 2- without demo data 3 - run test_make_cfdi_report_carry_over_canceled_invoice missing sudo in test case to create sale order in the test build_error-226771 Forward-Port-Of: odoo/enterprise#87946
*: website_sale_renting, website_studio This refactor adds `export` to all classes extending `BuilderAction`, allowing them to be reused or imported from other modules. It improves modularity. Forward-Port-Of: odoo/enterprise#88537
Original PR description
*: website_sale_renting, website_studio This refactor adds `export` to all classes extending `BuilderAction`, allowing them to be reused or imported from other modules. It improves modularity. Forward-Port-Of: odoo/enterprise#88537
reduce the size of the label that took nearly half the width of the sidepanel. Forward-Port-Of: odoo/enterprise#88331
Original PR description
reduce the size of the label that took nearly half the width of the sidepanel. Forward-Port-Of: odoo/enterprise#88331
## Issue When there are heavy (or a lot of) documents in a folder, the user cannot archive this folder as it would trigger a `MemoryError`. ### Analysis The `write` override could unnecessarily fetch the `datas` field (binary file content). This happened because a condition checking `record.datas` was evaluated before checking if `datas` or `url` was actually present in the values being written. This could lead to slowness when e.g. archiving/unarchiving documents, as the ORM would fetch t
Original PR description
## Issue When there are heavy (or a lot of) documents in a folder, the user cannot archive this folder as it would trigger a `MemoryError`. ### Analysis The `write` override could unnecessarily fetch…
## Issue
When there are heavy (or a lot of) documents in a folder, the user cannot archive this folder as it would trigger a `MemoryError`.
### Analysis
The `write` override could unnecessarily fetch the `datas` field (binary file content).
This happened because a condition checking `record.datas` was evaluated before checking if `datas` or `url` was actually present in the values being written. This could lead to slowness when e.g. archiving/unarchiving documents, as the ORM would fetch the binary content even when it was not needed.
## Solution
We leverage Python's boolean short-circuiting to ensure that this behavior is avoided.
### Benchmarks
Profiling peak memory consumption when moving 8 documents (66 Mb each) to the trash:
| Before | After | % |
|------------|------------| --- |
| 1.3 GiB | 96 Mb | - ~93% |
Query count when unlinking account.move (using Runbot data):
| Before | After |
|------------|------------|
| 66 | 72 |
(we may avoid these additional queries by prefetching the fields beforehand, let me know your thoughts)
```
[0.564 ms] query: SELECT "ir_attachment"."id", "ir_attachment"."name", "ir_attachment"."description", "ir_attachment"."res_model", "ir_attachment"."res_field", "ir_attachment"."res_id", "ir_attachment"."company_id", "ir_attachment"."type", "ir_attachment"."url", "ir_attachment"."public", "ir_attachment"."access_token", "ir_attachment"."store_fname", "ir_attachment"."file_size", "ir_attachment"."checksum", "ir_attachment"."mimetype", "ir_attachment"."create_uid", "ir_attachment"."create_date", "ir_attachment"."write_uid", "ir_attachment"."write_date", "ir_attachment"."original_id", "ir_attachment"."key", "ir_attachment"."website_id", "ir_attachment"."theme_template_id" FROM "ir_attachment" WHERE "ir_attachment"."id" IN (3398)
[0.713 ms] query: UPDATE "ir_attachment"
SET "res_id" = "__tmp"."res_id"::int4, "res_model" = "__tmp"."res_model"::VARCHAR, "write_date" = "__tmp"."write_date"::timestamp, "write_uid" = "__tmp"."write_uid"::int4
FROM (VALUES (3398, 117, 'documents.document', '2025-06-17T15:24:12.867699'::timestamp, 22)) AS "__tmp"("id", "res_id", "res_model", "write_date", "write_uid")
WHERE "ir_attachment"."id" = "__tmp"."id"
[0.305 ms] query: SELECT "ir_attachment"."id", "ir_attachment"."res_model", "ir_attachment"."res_id", "ir_attachment"."res_field", "ir_attachment"."public", "ir_attachment"."create_uid" FROM "ir_attachment" WHERE ("ir_attachment"."id" IN (3397))
[0.666 ms] query: SELECT "account_move"."id" FROM "account_move" WHERE ("account_move"."id" IN (255)) AND ("account_move"."company_id" IN (10)) ORDER BY "account_move"."date" DESC , "account_move"."name" DESC , "account_move"."invoice_date" DESC , "account_move"."id" DESC
[0.436 ms] query: SELECT "ir_attachment"."id", "ir_attachment"."name", "ir_attachment"."description", "ir_attachment"."res_model", "ir_attachment"."res_field", "ir_attachment"."res_id", "ir_attachment"."company_id", "ir_attachment"."type", "ir_attachment"."url", "ir_attachment"."public", "ir_attachment"."access_token", "ir_attachment"."store_fname", "ir_attachment"."file_size", "ir_attachment"."checksum", "ir_attachment"."mimetype", "ir_attachment"."create_uid", "ir_attachment"."create_date", "ir_attachment"."write_uid", "ir_attachment"."write_date", "ir_attachment"."original_id", "ir_attachment"."key", "ir_attachment"."website_id", "ir_attachment"."theme_template_id" FROM "ir_attachment" WHERE "ir_attachment"."id" IN (3397)
[0.436 ms] query: SELECT "documents_document"."id", "documents_document"."attachment_id", "documents_document"."active" FROM "documents_document" WHERE ("documents_document"."attachment_id" IN (3397)) ORDER BY "documents_document"."id" DESC
```
### References
opw-4552436
Memory flamegraphs available on the ticket
Forward-Port-Of: odoo/enterprise#88180
Forward-Port-Of: odoo/enterprise#85020When generating the German tax report, field Kz83 was included in the XML even when the value was 0.00. This caused the exported file to be rejected by the ELSTER platform. This fix removes Kz83 from the XML when its value is null or zero. The ELSTER platform automatically calculates this field if it's missing. source: https://help.deltek.com/product/maconomy/documentation/BPMReporting/CountryReports/Appendix_Germany.html opw-4783544 Forward-Port-Of: odoo/enterprise#86978
Original PR description
When generating the German tax report, field Kz83 was included in the XML even when the value was 0.00. This caused the exported file to be rejected by the ELSTER platform. This fix removes Kz83 from the XML when its value is null or zero. The ELSTER platform automatically calculates this field if it's missing. source: https://help.deltek.com/product/maconomy/documentation/BPMReporting/CountryReports/Appendix_Germany.html opw-4783544 Forward-Port-Of: odoo/enterprise#86978