Monday, July 7, 2025
17 changes · saas-18.4
Enhancements to existing features
This update reduces duplicate server requests and reuses cached grouped data in list and kanban views, helping screens load faster and putting less load on servers. Project task template data is also cached so project task views can benefit from these performance improvements.
Original PR description
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
Saudi e-invoicing journals now use unique names and automatically generated serial numbers during onboarding. This reduces setup errors and prompts existing users to re-onboard journals that may have duplicate identifiers.
Original PR description
… common name to be unique per journal Previously, the company name was used as the common name when onboarding the journal. However, the common name has to be unique. The fix changes the common name to use the journal's short code, journal name, and company name to ensure uniquness. Additionally, an improvement is applied to the serial number on journals. Previously, users inputted this field manually. Now, the system uses the journal's id as the serial number to ensure uniqueness. A post-migration script was added to notify users that they need to re-onboard their journals. This is done in case users previously onboarded journals with non-unique serial numbers. task-4797124 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#217120 Forward-Port-Of: odoo/odoo#215012
The website builder now displays an image size tag when editors select an image or an element with a background image. This helps content teams quickly understand image dimensions while editing pages, making it easier to choose appropriately sized visuals.
Original PR description
In the website builder in edit mode, when clicking on an image or an element with a background image there is no way of knowing its size. This is why a tag to indicate the size of the image was added.
Aged Partner reports now use invoice date information already available in accounting line data instead of looking it up from a separate table. This reduces unnecessary database work and can significantly speed up report generation on large accounting databases.
Original PR description
The Aged Partner reports query in `_aged_partner_report_custom_engine_common` is joining on the `account_move` table solely to get the `invoice_date` column. As this `invoice_date` is aggregated in `ARRAY_AGG(DISTINCT invoice_date)` and there's already a denormalized field `invoice_date` on `account_move_line` that is a related stored field, we can drop the join and use this field instead. This saves us the need to scan the account.move table when running the reports query. In a database with 37M amls, 10M account.move (and a really bad correlation for account_move_line.move_id), this saves us around 10 minutes for the Aged Receivable report's query. Forward-Port-Of: odoo/enterprise#89325
Resolved issues and error corrections
Translation export now shows a warning instead of blocking the process when no translatable text is found. This keeps automated synchronization running smoothly and gives users an option to try another export while preserving the correct export window title.
Original PR description
A blocking error is too much, because it impedes the automatic sync flow. Warnings have been added to the `i18n` command and the `base_language_export` wizard. A retry / more button has been added,…
A blocking error is too much, because it impedes the automatic sync flow. Warnings have been added to the `i18n` command and the `base_language_export` wizard. A retry / more button has been added, in case the user wants to export something else. The title was changing to the default `Odoo` after switching state. Now it stays `Export Translation` <details><summary>Screenshots (click me)</summary> Model:    Module:    CLI:  </details> *(note: retargeted to saas-18.4)* ref: https://github.com/odoo/odoo/pull/194933#discussion_r2176924160
The website builder now shows snippet previews in the correct right-to-left layout when editing RTL websites. This prevents confusing or incorrect preview layouts, especially when the website language direction differs from the user's language.
Original PR description
__Current behavior before commit:__ When using a right-to-left (RTL) language on a website, the snippet dialog in the website builder does not correctly apply the RTL direction to the snippet previews. The CSS for the frontend assets is loaded without considering the RTL context of the website. This is mainly an issue when the website default language has a different direction than the user language. __Description of the fix:__ This commit corrects the RTL behavior in the snippet dialog by: - Setting the dir attribute to the snippet preview container based on the direction of the editable element. - Ensuring the correct CSS bundle (including the RTL version) is loaded for the snippet previews by retrieving the CSS bundle URL from the editor's document similarly as it was done in `web_editor`. - Adding a tour to test the fix. Website refactor: https://github.com/odoo/odoo/pull/187419 task-4367641
This fix lets payments made with branded card methods, such as Visa through Adyen, use the manual and partial capture settings of the main card payment method. It also allows related card brands like Hipercard and Elo to be enabled correctly, reducing failed or blocked payment operations for merchants.
Original PR description
Versions -------- - saas-18.2+ Steps ----- 1. Set up Adyen as a payment provider; 2. enable manual capture; 3. set up a sales order; 4. pay for sales order with Adyen using VISA; 5. do a partial manual capture. Issue ----- Payment method doesn't support partial capture. Additionally, you're not allowed to enable the Hipercard & Elo payment method brands for the Card payment method. Cause ----- Commit 25feb5b11c2df added the `support_manual_capture` field to `payment.method`. This field is only set to a non-default value for primary payment methods, e.g. Card. For branded payment method, e.g. VISA, it defaults to 'none'. Solution -------- Add a `_get_primary_method` method to `payment.method` and `payment.transaction`, retrieving the relevant primary payment method to check support on. opw-4817961 Forward-Port-Of: odoo/odoo#216890
Changing the organizer of a regular Odoo calendar event no longer archives the original event and creates a replacement. This prevents accidental loss or confusion for users while keeping the special handling limited to Microsoft-synced events.
Original PR description
**Issue:** when you change an odoo event organizer the original gets archived and a new one is created this behavior should only be happening with microsoft synced events **Steps to reproduce:** - install microsoft_calendar - create new event - change organizer and save the event is archived opw-4765254 Forward-Port-Of: odoo/odoo#217462 Forward-Port-Of: odoo/odoo#210100
This fix ensures calendar events open with the specific edit form configured for that calendar view. It prevents Odoo from overriding that choice behind the scenes, making behavior more consistent for users in HR holidays, homeworking calendars, projects, and other calendar views.
Original PR description
*hr_holidays,hr_homeworking_calendar Before this commit, when clicking on a calendar event to edit it, a `get_formview_id` rpc was done to retrieve the id of the form view to use to edit the event. However, the documentation [1] states that the attribute `form_view_id` can be set in the arch, for the same purpose. The given id was then overruled by the id returned by `get_formview_id`. This commit removes the rpc, so the id is always the one given in the arch, as written in the documentation. [1] https://www.odoo.com/documentation/18.0/developer/reference/user_interface/view_architectures.html#calendar Task-4910395 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
This fix prevents public website components from being accidentally saved into page content while editing, avoiding duplicated or inactive elements after publishing. It also makes component behavior in edit mode more predictable, reducing the risk of broken-looking pages for website editors.
Original PR description
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
Portal discussions now distinguish between the logged-in user and the portal contact they are allowed to act for. This avoids confusing labels and hints that incorrectly make messages, mentions, or actions look like they belong to the current user.
Original PR description
Since [1], discuss considers both the logged in and the portal partner as "self". However, even if the token grants access to act as the portal partner, it doesn't mean that both users are the same. Visually, it's confusing that every hint in the UI assimilate the current user to the portal partner (messages, mentions, ...). This commit fixes that by separating the concept of portal partner and "self". The user providing the portal token can access portal partner actions (editing/deleting message) but is considered a different user. [1]: https://github.com/odoo/odoo/pull/211204 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 Forward-Port-Of: odoo/odoo#217395 Forward-Port-Of: odoo/odoo#217062
This fix prevents manufacturing replenishment flows from generating duplicate manufacturing order names when orders originate from combined references. It helps avoid scheduler failures and keeps automated manufacturing replenishment running reliably.
Original PR description
__Issue:__ Condition used for MOs triggered under the `pbm_sam` manufacturing flow only checks the start of the group name, not the whole name, which could fail in case triggered by reordering rules where the origin might be a compound string such as: "OP/00001,WH/MO/00001" __Steps to reproduce:__ 1.) Install sales; inventory; manufacturing 2.) Enable multi-step routes 3.) Unarchive MTO 4.) Set warehouse manufacture steps to: Pick components, manufacture, then store products (3 steps) (manufacture_steps == 'pbm_sam') 5.) Create product A-bom (enable manufacture and mto routes) 6.) Create product B (enable manufacture) 7.) Add Product A as bom for product B 8.) Add a reordering rule (manufacture) for product B 9.) run SA Procurement: run scheduler Error: duplicate key value violates unique constraint opw-4866263 bug found: [[#c50cb9d]](https://github.com/odoo/odoo/commit/c50cb9d552f352bde4e3b8d92e8509476f194830) Forward-Port-Of: odoo/odoo#216874
This fix keeps Discuss call controls usable on browsers that do not support picture-in-picture. Instead of failing or hiding the call view, Odoo now opens the call in a separate popout window so users can continue their conversation reliably.
Original PR description
Use popout as a fallback to the pip feature when pip is not available on the browser.
Users can now print several invoices at once without the process failing. This prevents an error screen during bulk invoice printing and keeps accounting workflows moving smoothly.
Original PR description
When User tries to print multiple invoices, A traceback will appear. Steps to reproduce the error: - Install ``account`` module with demo data - Go to Invoices > Select multiple invoices > Print Traceback: ``` ValueError: Expected singleton: account.move(2, 1) ``` After this commit: https://github.com/odoo/odoo/commit/1a8123177dbcb01435f3608508302f40532477c1 https://github.com/odoo/odoo/blob/871c7d23336cf06619998795c073bd2001b20af1/addons/account_edi_ubl_cii/models/account_move.py#L76 When user prints multiple invoices, self will have multiple records. So, checking ``self.state`` will lead to the above traceback. opw-4912628 sentry-6717623103 --- I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr Forward-Port-Of: odoo/odoo#216807
Customer statement emails now respect the sender or reply-to address configured on the email template. This ensures statements are sent from the expected business contact instead of unexpectedly defaulting to the current user's address.
Original PR description
Steps to reproduce:
Go to Settings> Email templates
Open the template Customer statements
Change the value in email from or reply to
Go to Accounting > Customers > Customers
Open a customer
Send a customer statement
Issue:
The address in use is not the same as we specified in the customer template
Cause:
if no email_from is provided, we will use the current partner's use's email address https://github.com/odoo/odoo/blob/cc0aaff5f93d5332c60d5bd8097173326a0a12b3/addons/mail/models/mail_thread.py#L2863-L2864
We don't check if the template has any email_from address defined
Note:
As from this fix, if no address is defined, by default it will be the `{{ object._get_followup_responsible().email_formatted }}`
opw-4864155
Forward-Port-Of: odoo/enterprise#88262Appointment bookings now avoid matching a website visitor to a customer record from a company the appointment staff cannot access. This prevents failed opportunity creation in multi-company setups and keeps online booking flows working reliably.
Original PR description
**Steps to reproduce:** - Set up CRM / Appointment / Website apps - Create new company (2) - Create partner contact with specific email and the new company - Create appointment type linked to a staff…
**Steps to reproduce:**
- Set up CRM / Appointment / Website apps
- Create new company (2)
- Create partner contact with specific email and the new company
- Create appointment type linked to a staff user of another company (1) who has no access to the new one
- Enable `Create Opportunities` on the new appointment type
- Go to the website as an anonymous user
- Submit an appointment request using the partner's email
- `Incompatible companies on records:` error
**Issue:**
Previous solution (17.0) was trying to use existing partner if the email was provided and existed in the database
`customer = request.env['res.partner'].sudo().search([('email_normalized', '=', email_normalized)], limit=1`
This means that, in a multi-company environment, the lead created by the new appointment for the appointment user of company 1 can be linked to the partner contact of company 2 and throw an error on validation.
**Fix:**
Restricted partner search domain using current allowed companies using the `staff_user` or the user which created the `appointement_type`.
opw-4713060
Forward-Port-Of: odoo/enterprise#89196
Forward-Port-Of: odoo/enterprise#84006Marketing automation campaign tests can now use tracked links again, so teams can validate click-based journeys before launch. The update also prevents overlapping tests for the same campaign and recipient details, reducing confusing or failed test results while still allowing separate tests to run in parallel.
Original PR description
Previously, marketing campaign testing (through debug) could cause an issue where tracked links could cause a traceback if a marketing activity was edited after a test was attempted. To work around…
Previously, marketing campaign testing (through debug) could cause an issue where tracked links could cause a traceback if a marketing activity was edited after a test was attempted. To work around this, #13665 deactivated link tracking in marketing campaign tests. However, this meant that flows including click actions could no longer be tested. As this issue has been resolved in odoo/odoo#48845, this commit reverts https://github.com/odoo/enterprise/pull/13665 to once again permit marketing automation testing. -- Additional changes are needed to fix other issues: Tests using one's own coordinates are prone to breaking due to newer mailing traces attaching themselves to the oldest marketing trace. This commit makes it so that marketing campaign tests for the same marketing campaign and coordinates cannot run concurrently, by cancelling older test campaigns upon starting a new one. Different tests can still run concurrently on distinct partners/leads/ etc. Additionally: - Running tests are now visible on campaigns in the "New" state; - Activities don't mark themselves as needing sync unless their campaign is in the "Running" state. task-4557855 Forward-Port-Of: odoo/enterprise#89473 Forward-Port-Of: odoo/enterprise#78793