Skip to content

viindoo - #65

Open
odoochain wants to merge 205 commits into
odoochain:19.0from
Viindoo:19.0
Open

viindoo#65
odoochain wants to merge 205 commits into
odoochain:19.0from
Viindoo:19.0

Conversation

@odoochain

Copy link
Copy Markdown
Owner

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

@odoochain odoochain left a comment

Copy link
Copy Markdown
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why

yp-oerp and others added 26 commits August 16, 2026 15:39
Deleting a draft customer invoice linked to timesheets resets their
timesheet_invoice_id so the hours become invoiceable again. This write
also marks the timesheets' so_line for recompute, and the re-derivation
runs while the lines are no longer protected by the invoice link. When
the task or project no longer resolves to a sale order item (e.g. it was
unlinked after invoicing), the timesheets lose their sale order item or
get reassigned to another one, so the delivered hours silently disappear
from the original order line.

Protect so_line during the write and drop the pending recompute: deleting
an invoice must only make the hours invoiceable again, not change their
allocation.

Steps to reproduce:
- Install Sales and Timesheets
- Create a service product with invoice policy "Based on Timesheets" and
  "Create a task in a new project"
- Create and confirm a sale order with this product
- Log a timesheet on the generated task
- Create the invoice (keep it in draft)
- Remove the Sales Order Item from the task and from the project settings
  (or point them to a sale order item of another order)
- Delete the draft invoice
- Open the timesheet: its Sales Order Item is emptied (or replaced by the
  other order's item, whose delivered quantity now includes the hours sold
  on the original order), and the original line's delivered quantity is reset

closes odoo#281558

X-original-commit: 777966e
Signed-off-by: Xavier Bol (xbo) <xbo@odoo.com>
In this commit 004b56a we added
the `l10n_fr_pdp.what_is_pdp` action as PDP version of the
`account_peppol.what_is_peppol` action.

But one case does not work / was not tested properly:
We are registered on PDP already.
In that case we just want to go back to the "move send" wizard.
But the `what_is_pdp` action does not support that currently.
So there is a traceback.

Steps to reproduce:
1. Install `l10n_fr_pdp`
2. Activate French E-Invoicing / PDP in Demo mode
3. Create and post an invoice for a French PDP partner (e.g. just use the "FR Company")
4. Click "Send"
5. In the "move send" wizard disable the "French E-Invoicing (Demo)" option
6. Click on "Why should you use it?" in the warning
7. Click "Got it" in the window that pops up.
8. Traceback (see below)

```
Traceback (most recent call last):
  File "/home/odoo/src/odoo/odoo/http.py", line 2167, in _transactioning
    return service_model.retrying(func, env=self.env)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/odoo/src/odoo/odoo/service/model.py", line 157, in retrying
    result = func()
             ^^^^^^
  File "/home/odoo/src/odoo/odoo/http.py", line 2134, in _serve_ir_http
    response = self.dispatcher.dispatch(rule.endpoint, args)
               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/odoo/src/odoo/odoo/http.py", line 2382, in dispatch
    result = self.request.registry['ir.http']._dispatch(endpoint)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/odoo/src/odoo/odoo/addons/base/models/ir_http.py", line 333, in _dispatch
    result = endpoint(**request.params)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/odoo/src/odoo/odoo/http.py", line 754, in route_wrapper
    result = endpoint(self, *args, **params_ok)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/odoo/src/odoo/addons/web/controllers/dataset.py", line 36, in call_kw
    return call_kw(request.env[model], method, args, kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/odoo/src/odoo/odoo/api.py", line 535, in call_kw
    result = getattr(recs, name)(*args, **kwargs)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/odoo/src/odoo/addons/account_peppol/models/res_config_settings.py", line 159, in button_peppol_reregister
    self.ensure_one()
  File "/home/odoo/src/odoo/odoo/models.py", line 6277, in ensure_one
    raise ValueError("Expected singleton: %s" % self)
ValueError: Expected singleton: res.config.settings()
```

task-None

closes odoo#282557

X-original-commit: 29410f4
Signed-off-by: Wala Gauthier (gawa) <gawa@odoo.com>
Signed-off-by: Sven Führ (svfu) <svfu@odoo.com>
…pute

## Issue
When filtering projects using the "Timesheets >100%" filter, some projects
with negative remaining hours (and with their `is_project_overtime` field
set to True) won't be displayed, even though their expected hours are
completed.

This happens with projects which have tasks set to the "Done" or
"Cancelled" state. The timesheets entries in those tasks are not taken
into account when searching using the "Timesheets >100%" filter.

## Steps to reproduce
1. Install *Task Logs* (`hr_timesheet`)
2. Create a Project P (with Timehseets enabled)
3. Set the allocated hours of the project to 3:00 (3 hours)
4. Create two tasks:
    - T1: State "In progress", and one timesheet entry of 2:00 (2 hours)
    - T2: State "Done", and one timesheet entry of 2:00 (2 hours)
5. Back to the project view, set the filter to "Timesheets >100%"
6. **Project P is not shown, even though the total time spent on the
project is 4 hours, completing the allocated hours set on the project.**

## Cause
The `_search_is_project_overtime` method filters out the tasks in "closed"
states (Done/Cancelled) when computing the amount of time spent on the project.

https://github.com/odoo/odoo/blob/126b5bdd1e85771549198976f8570cd2ff167608/addons/hr_timesheet/models/project_project.py#L103-L114

This does not match with the behavior of the `_compute_is_project_overtime`,
which does not take into account the state of the tasks to determine the
value of the field:

https://github.com/odoo/odoo/blob/126b5bdd1e85771549198976f8570cd2ff167608/addons/hr_timesheet/models/project_project.py#L85-L94

This leads to a confusing behavior, where a project can have its
`is_project_overtime` field set to True, but will still not be shown when
using the "Timsheets >100%", even though that filter is defined as
`[("is_project_overtime", "=", True)]`.

The compute method was updated by odoo@d425282,
but the related search method was left unchanged, leading to this slight
incoherence between the two methods.

opw-6422173

closes odoo#282549

X-original-commit: 430311e
Signed-off-by: Quentin Colla (qucol) <qucol@odoo.com>
Signed-off-by: Xavier Bol (xbo) <xbo@odoo.com>
…tras

Steps to reproduce:
- Install `website_sale` module.
- Enable `Product Variants` and `Prevent Sale of Zero Priced Product` in
  settings.
- Create new attribute > set `Variant Creation` as `Never` and also add
  value with extra price.
- Create a product with sales price = 0, assign the attribute, and publish it.
- As a public user (incognito), try to add the product to the cart.

Issue:
- In terminal error `The given product does not exist therefore it cannot be
  added to cart` is raised.

Root cause:
- In `_is_add_to_cart_allowed()`[1], the method calls `_get_contextual_price()`
  [2] to check if the product's price is zero when `prevent_zero_price_sale`
  is enabled.
- However, `_get_contextual_price()` is called without the no-variant attribute
  values in the context, so it does not account for their `price_extra`. For a
  product with list price as 0 and attribute with extra price, the price is
  incorrectly computed as 0, causing `_is_add_to_cart_allowed()` to
  return `False`.

Solution:
- Before calling `_is_add_to_cart_allowed()`, set the product's context with the
  no-variant attribute values via `_get_product_price_context()`, so that
  `_get_contextual_price()` correctly includes the price extra in its
  computation.

[1]: https://github.com/odoo/odoo/blob/bbafbbd8950ec7123ab652851ede5479484eee26/addons/website_sale/controllers/cart.py#L117-L120

[2]: https://github.com/odoo/odoo/blob/bbafbbd8950ec7123ab652851ede5479484eee26/addons/website_sale/models/product_product.py#L149-L150

opw-6365566

closes odoo#278620

Signed-off-by: Valentin Chevalier <vcr@odoo.com>
Steps to produce;
- Install `sales` module.
- Go to Settings and enable `Units of Measure and Packaging`.
- Set a long name for `units` UoM.
- Create a Sale Order and add a product via the catalog.

Issue:
- Long UoM names are not fully visible in the catalog view.

Root cause:
- The outer `<div>` has `d-flex` but lacks `w-100`, causing it to overflow
  its container.

Solution:
- Added `w-100` to the outer `<div>` to prevent overflow.
- Adjusted the quantity selector layout for better visibility.

opw-6253382

closes odoo#282551

X-original-commit: c12323a
Related: odoo/enterprise#127984
Signed-off-by: Krishna Arvindkumar Patel (krip) <krip@odoo.com>
Adds ir.rule for model product.attribute.custom.value for
portal users and employees.

Salespeople and product managers already hold a write access on that
model, so a second rule keeps them unrestricted.
**Steps to reproduce:**
1. Install Accounting
2. Import a new invoice with more than 1000 lines (xlsx file found in ticket attachments)
3. Test the imported records

**Issue:**
- `RecursionError: maximum recursion depth exceeded`.

**Cause:**
- In a previous commit (3e32d7b) aimed at fixing stale analytic
distribution totals, the assignment loop in `_compute_discount_allocation_needed` was changed
from iterating over `self` to `self.move_id.line_ids`.
- While this ensured all lines generated updated distribution ratios, it violated the compute logic:
assigning values to records outside the current compute batch (`self`).
- By executing `line.discount_allocation_dirty = True` on external sibling lines, the method forced
the ORM to trigger out-of-band `write()` calls. These writes re-triggered dependency checks
(`_field_will_change`), which invoked the compute method again, leading to a recursive loop.

**Fix:**
1. Revert the assignment iteration back to `for line in self:`.
2. To preserve the intention of the previous commit (ensuring all lines recompute their shared
distribution pool when one line changes), modify the method's `@api.depends` to be
`move_id.line_ids.discount` and `move_id.line_ids.analytic_distribution`.

By declaring these relational dependencies, modifying a single line now batches all sibling lines
into `self` from the start. This allows the lines to synchronize properly without triggering
new ORM writes, eliminating the recursion.

opw-6451854

closes odoo#282542

X-original-commit: 8842397
Signed-off-by: Olivier Colson (oco) <oco@odoo.com>
Signed-off-by: Waleed Elgamal (waelg) <waelg@odoo.com>
closes odoo#280403

Related: odoo/enterprise#127041
Signed-off-by: Valeriya Chuprina (vchu) <vchu@odoo.com>
**Steps to reproduce:**
1. Install Sales and payment_authorize modules
2. Enable "Online Payment" in the settings and Configure the payment
method to be Authorize.net
3. Create a sale order, confirm it and create the invoice
4. Pay the invoice with an eCheck (ACH) payment method through the
Authorize.net provider
5. Wait for the payment to be settled by Authorize.net (_around 24 hours_)
6. Initiate a refund of the payment

**Issue:**
The refund fails with error `E00003: "The 'AnetApi/xml/v1/schema/AnetApiSchema.xsd:cardNumber'
element is invalid - The value XX is invalid according to its datatype 'String' - The actual
length is less than the MinLength value`

**Expected behavior:**
The refund should be processed successfully regardless of whether
the original payment was made by credit card or eCheck (ACH)

**Why this happens:**
- The `refund()` method in `AuthorizeAPI` builds the refund request
using a `creditCard` payment payload
- When the original transaction was an ACH/eCheck payment, the `creditCard`
key is absent from the transaction details returned by Authorize.net
- The resulting request is rejected by Authorize.net because it does not
satisfy the minimum length constraint for `cardNumber`

**Fix:**
- Detects whether the original payment used `creditCard` or `bankAccount`
from the transaction details and build the appropriate payload according
to Authorize.net API documentation: https://developer.authorize.net/api/reference/index.html#payment-transactions-credit-a-bank-account

opw-6359726

closes odoo#277742

Signed-off-by: Waleed Elgamal (waelg) <waelg@odoo.com>
The `create_calendar_meeting` field on `hr.leave.type` allows users to
choose if leave requests created with a given time off type generate a
corresponding entry in the Calendar app. However, this field was not
displayed on the form view.

This commit adds `create_calendar_meeting` to the `hr.leave.type` form view
inside the configuration section, along with dedicated help text explaining
its behavior.

closes odoo#282548

X-original-commit: b2b6355
Signed-off-by: Yannick Tivisse (yti) <yti@odoo.com>
Signed-off-by: Ahmed Amin Naem (ahnae) <ahnae@odoo.com>
Problem: When a `table` with a `color`/`backgroundColor` contains a
nested `table`, `distributeTableColorsToAllCells` propagates the outer
table's color to every `td` in the subtree, including cells belonging
to the inner table. The inner table's own color is then discarded
since its `td`s already have a value.

Cause: `table.querySelectorAll("td")` returns every `td` in the entire
subtree, not just the table's own direct cells.

Solution: Scope the selected `td`s to `td.closest("table") === table`,
so a table's color is only distributed to its own cells.

Steps to reproduce:
1. Add a `background-color` to an outer `table`.
2. Nest a `table` with a different `background-color` inside one of
   its cells.
3. Load/normalize the content in the editor.
4. Observe both tables' cells carry the outer table's color.

opw-6438972

closes odoo#281850

X-original-commit: 1110422
Signed-off-by: David Monjoie (dmo) <dmo@odoo.com>
Signed-off-by: Walid Sahli (wasa) <wasa@odoo.com>
Steps:
- Install sale_management
- Make sure you have 100 quotations with 1 activity each
- Open activity view
- Default pager displays `1-100/100`
- Activity count display `To-do 80`

ActivityController uses `useModel` which passes the raw `component.props` to
`model.load()`, including the limit from `ir.actions.act_window` (default 80).
This value ended up in `fetchActivityData` via `params.limit || this.initialLimit`,
overriding `ActivityModel.DEFAULT_LIMIT` (100).

The records list was not affected because `RelationalModel._getNextConfig` never
reads `params.limit` (limit is not a `SEARCH_KEY`), so it always loaded 100
records correctly. But `fetchActivityData` used 80, causing a mismatch between
the records shown and the activity counts in the column headers.

```js
export const SEARCH_KEYS = ["comparison", "context", "domain", "groupBy", "orderBy"];
```

The fix strips `params.limit` in `ActivityModel.load()` before passing params to
`fetchActivityData`, so it falls back to `this.initialLimit (100)`. The pager
`onUpdate` handler calls `fetchActivityData` directly with its own `params.limit`
and is not affected.

However, `ActivityController` never forwards `limit` to the model. This
is why we always have `ActivityModel.DEFAULT_LIMIT (100)` without taking
into account actions's limit. To fix this we have to add the limit via
`this.props.limit`, as `ListController`.

`useModelWithSampleData` already had the correct behavior by calling
`model.load(getSearchParams(props))` which filters out non-search params like
limit. In 19.0 useModel was updated to do the same, so the issue does not
exist there.

Link to 19.0 fix: odoo#211697

opw-6281125

closes odoo#281163

X-original-commit: ba372de
Signed-off-by: Renaud Thiry (reth) <reth@odoo.com>
Signed-off-by: Achraf Ben Azzouz (abz) <abz@odoo.com>
***Steps to reproduce*:**

* Install `l10n_din5008` module.
* Navigate to **Accounting** and create a new Purchase Journal.
* Enable **Self Billing** for the journal.
* Create a vendor bill.
* Print the vendor bill.

***Observed behavior*:**

* The printed document displays the regular vendor bill header instead of the
   self-billing header.

***Cause*:**

* The condition required to display the self-billing header was missing from the
   report template if self-billing is enabled.

***Fix*:**

* Add the missing condition so that the self-billing header is displayed when
 **Self Billing** is enabled on the journal.

opw-6281066

closes odoo#282664

X-original-commit: bf46784
Signed-off-by: Paolo Gatti (pgi) <pgi@odoo.com>
Signed-off-by: Krishna Pathak (pkri) <pkri@odoo.com>
`IrHttp._check_identity()` forwarded the client-supplied `credential` dict
straight to `_check_credentials()` without checking that `credential['type']`
was one of the user's actually-enabled authentication methods
(`user._get_auth_methods()`).

An authenticated user can send a credential of a type they don't have
enabled - e.g. `{"type": "totp", "token": "000000"}` against an account
without TOTP configured - which raises an unhandled `TypeError` deep inside
`base64.b32decode(False)` instead of a clean authentication failure:

    curl -s -b "$JAR" "$BASE/auth-timeout/session/check-identity" \
      -H 'Content-Type: application/json' \
      -d '{"jsonrpc":"2.0","method":"call","params":{"type":"totp","token":"000000"},"id":null}'

`_check_identity()` validates `credential['type']` against the user's
enabled auth methods before forwarding it to `_check_credentials()`. Any
mismatch (e.g. a TOTP credential sent to an account without TOTP enabled,
or any unrecognized type) now raises a clean `AccessDenied` (403) instead
of an unhandled `TypeError`.

---
I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr

Part-of: odoo#272563
Signed-off-by: Julien Castiaux (juc) <juc@odoo.com>
closes odoo#272563

Signed-off-by: Julien Castiaux (juc) <juc@odoo.com>
Be sure that combo product of the current line belong to its combo
parent line.

closes odoo#281741

Signed-off-by: Manu Vaillant (manv) <manv@odoo.com>
Some generic validation errors raised by core account models lack
enough context to identify which record caused the issue, making FEC
imports harder to troubleshoot.

This commit improves the two error cases identified for this use case:
- `account.account._check_account_code` now includes the invalid
  account code in the error message.
- `account.move.write` now includes the move name/reference with
  showing technical field names when attempting to modify
  read-only fields on posted entries.

Although motivated by FEC import, these are generic core validations,
so the improvements are implemented at the source to benefit all
callers rather than only the FEC import flow.

Enrichment is scoped to the two cases above; other constraints/errors
across these models are intentionally left unchanged for now, since
editing core error messages more broadly should be done deliberately
and on a case-by-case basis, not as a blanket rewrite.

task-5346068

closes odoo#281746

Signed-off-by: Maximilien La Barre (malb) <malb@odoo.com>
*: pos_online_payment_self_order

Before this commit:

- Self-orders with a total amount of zero are still redirected to the payment
  page, which was unnecessary.

After this commit:

- The payment step is now skipped for zero-amount self-orders, providing a
  smoother checkout flow.

task-5106938

closes odoo#230218

Signed-off-by: David Monnom (moda) <moda@odoo.com>
Fix the function signature of the _reset_peppol_configuration function

Step to reproduce:
- Install l10n_fr_pdp and register a company on Peppol
- When the _peppol_out_of_sync_disconnect_this_database will be called,
it will call the _reset_peppol_configuration(soft=True), and since
l10n_fr_pdp overrides this function but don't declare the soft parameter,
it will raise a TypeError.

opw-5728596

closes odoo#282763

Signed-off-by: Claire Bretton (clbr) <clbr@odoo.com>
Allow resetting sent moves to draft. Ensures a rectificative flow exists or is created.
Allow to create an empty rectificative report (if no more invoices to report after being reste to draft).

closes odoo#282120

Task: 6273211
X-original-commit: 84a5125
Signed-off-by: Florian Gilbert (flg) <flg@odoo.com>
Signed-off-by: de Wouters de Bouchout Jean-Benoît (jbw) <jbw@odoo.com>
We reintroduce the default code on the product configuration
modal, and ensure that searching for a variant reference opens
the right variant.

task-6463377

closes odoo#282707

Signed-off-by: Yaroslav Soroko (yaso) <yaso@odoo.com>
Before this commit:
Downloading a file with a filename field which you do not have access
returns with a 403.

After this commit:
The filename falls back to the default name to ensure smooth download.

opw-6446124
…efund

closes odoo#282554

Signed-off-by: Valeriya Chuprina (vchu) <vchu@odoo.com>
Fixed some typos and inconsistencies on the LNA checklist document

Task-[6330795](https://www.odoo.com/odoo/project/1737/tasks/6330795)

closes odoo#281950

Signed-off-by: David Monnom (moda) <moda@odoo.com>
Steps to reproduce
----------------------------------------
1. Install the SMS Marketing module (mass_mailing_sms).
2. Open any SMS Marketing record in the "Sent" or "Sending" stage.
3. Click on the "Insert Field" button.

Observation
----------------------------------------
Traceback Occurs:
```
TypeError: Cannot read properties of null (reading 'getRootNode')
```

Issue
----------------------------------------
The SMS widget displays the "Insert Field" button even when the SMS message
field is readonly. The button relies on the textarea reference to open the
dynamic fields popover, but the textarea is only rendered in editable mode.

The readonly behavior of the text field can be seen here:
https://github.com/odoo/odoo/blob/ccce9fcc79edcfb1f310b49a16de8235d987b74b/addons/web/static/src/views/fields/text/text_field.xml#L5-L7

However, the SMS widget still renders the "Insert Field" button without
checking whether the message field is readonly:
https://github.com/odoo/odoo/blob/ccce9fcc79edcfb1f310b49a16de8235d987b/addons/sms/static/src/components/sms_widget/fields_sms_widget.xml#L6

As a result, clicking the button in readonly mode tries to access an
unavailable textarea reference to open the dynamic fields popover, causing
a traceback.

Solution
----------------------------------------
Hide the "Insert Field" button when the SMS message field is readonly,
preventing the dynamic fields popover from being opened when the textarea
reference is unavailable.

closes odoo#282845

Signed-off-by: Thibault Delavallee (tde) <tde@openerp.com>
- Added the BolloVirtuale in the Simplified invoice template
- Now it's possible to force the Simplified format on
  exported invoice when the `l10n_it_document_type` is set
  to a simplified one
- Factored the Italian partner recognition (_l10n_it_edi_is_italian)
- Added a check on the invoice, no simplified format
  for non-domestic / PA partners

closes odoo#282839

X-original-commit: aa6ef4b
Signed-off-by: John Laterre (jol) <jol@odoo.com>
Jinjiu Liu and others added 27 commits August 25, 2026 16:41
Before this commit: on mobile, when typing using Gboard and select a
word suggestion will only delete the last character and put the new
word at the beginning of the word to be replaced. This is because Gboard
extends the selection to the text to be corrected, then deletes it, and
inserts the corrected text. This flow falls in our previous fix for MS
Swiftkey's delete backward, and wrongly uses cached old selection
instead of using extended new selection from Gboard.

After this commit: We strict the Swiftkey fix further, and only execute
it when the cursor is at the beginning of the p element.

Related commit: odoo@822fd4e

task-6233756

closes odoo#283968

X-original-commit: 936b1ac
Signed-off-by: David Monjoie (dmo) <dmo@odoo.com>
Following the task-4034713, we used to create warehouse for all company
but after this task we only create warehouse for the main company
while testing for Indian Demo company considering the ewaybills
it's anonying to create a new warehouse for Devs and POs and even
for Demos

After this commit, we will create demo warehouse for the Indian
demo company

closes odoo#283797

Signed-off-by: William André (wan) <wan@odoo.com>
pos*: point_of_sale, pos_restaurant

Before this commit, the syncing of the order was not done when
we clicked on the send button to send order changes and the printing
failed (no preparation printer linked).

closes odoo#281676

Related: odoo/enterprise#127506
Signed-off-by: David Monnom (moda) <moda@odoo.com>
Currently, if you refund an order fro the backend it is possible
to modify the qty as if to refund more than the original order qty.

Steps to reproduce:
-------------------
* Make an order from the shop (1 product, qty 1)
* Validate the order
* Go backend
* Find the order and select the refund button
* Change qty from -1 to -3
* Save and continue the refund process
> No problem refunding more than the original quantity

Why the fix:
------------
In the frontend we cannot refund more than the original quantity,
we assume the same should be in the backend process.

The most simple way to do this is by doing a difference between
the quantity from the original order and all the refund lines
linked.

From `self.refunded_orderline_id.refund_orderline_ids` we need
to exclude the line that represents self as it holds the quantity
before the onchange and we care about the quantity we're trying to
write not the previous (allegedly correct).

opw-6328635

closes odoo#281405

Signed-off-by: Loukas Wets (lowe) <lowe@odoo.com>
**Problem:**
Since this commit odoo@48282ac,
both cogs lines have an
analytic account, which causes the cogs
to not appear on the project profitability
report because cogs lines balance each other

**Steps to reproduce:**
- enable 'anglo saxon accounting' and 'analytic accounting'
settings
- create a storable product with automated std
category, a cost of 10 and on hand quantity
- create a service product and set the
'create on order' field to 'project'
- confirm a SO for 1 unit of the product and
1 unit of the service
- validate the delivery and create and confirm invoice
- from the sale order, click on the project smart button
- from the project click on the dashboard smart button

**Current behavior:**
the cogs section don't appear in the profitability report

**Expected behavior:**
it should appear with a line with a value of -10

**Cause of the issue:**
since this commit odoo@48282ac,
both cogs line are linked to the analytic account.
That's the expected behaviour but in the case of
the project profitability reports, it prevents the user
the see the cost of the product in the cogs section.

That's because, inside the
_get_revenues_items_from_invoices() method,
bot cogs_line are added to the cogs_line list.
https://github.com/odoo/odoo/blob/141cb292dc5e456161119e19f7a91665feaa0198/addons/sale_project/models/project_project.py#L699-L700

So when computing the amount_to_invoice for
the costs ml_type, the balance of the lines
will zero out each other and amount_to_invoice
will be 0.
https://github.com/odoo/odoo/blob/141cb292dc5e456161119e19f7a91665feaa0198/addons/sale_project/models/project_project.py#L703-L716

As a consequence, the cost of goods sold
section won't be created
https://github.com/odoo/odoo/blob/141cb292dc5e456161119e19f7a91665feaa0198/addons/sale_project/models/project_project.py#L718-L719

**fix:**
only the line with an account of internal type
'expense' reflects the actual cost of the product
sold in the context of the project.
So when computing the profitability report
that's the only line we should consider

**test:**
test_report_invoice_items_anglo_saxon_automatic_valuation
checks that the cogs section is well displayed in the
project profitability report.
In the PR (mentionned above) which sets the analytic
account on the stock cogs line, lines were
added in the test to manually remove the analytic
account on the stock cogs line to make the test pass.

With the fix of this PR we can remove those additional
lines in the test and it will check our use case well again.

opw-6412409

closes odoo#284270

X-original-commit: 795ac31
Signed-off-by: Xavier Bol (xbo) <xbo@odoo.com>
Currently, `is_used` is computed using queries on `account.move.line`,
`account.reconcile.model.line`, etc. As a result, it has no depends and is not
automatically updated when records in either model are created, modified,
or deleted.

This commit reverse M2M fields for respective models and use it as
dependency to `_compute_is_used`.

It also adds a missing dependency of `is_used` to
`_compute_repartition_lines_str`.

closes odoo#283851

X-original-commit: d3302d6
Signed-off-by: William André (wan) <wan@odoo.com>
Problem:
Clicking a non-editable link does nothing, making it impossible to open
or inspect the link.

Solution:
Allow the link popover to open in read-only mode for non-editable links.

Steps to reproduce:
- Run `/article`.
- Click on the inserted article link.
- Observe that nothing happens.

opw-6442026

closes odoo#283473

X-original-commit: 5dd7218
Signed-off-by: David Monjoie (dmo) <dmo@odoo.com>
Signed-off-by: Walid Sahli (wasa) <wasa@odoo.com>
Japanese translation "海外取引先" for domestic was clearly wrong.

Also fixed the misspelling ("Oversea" -> "Overseas") and removed the unnecessary "Customer" context from the name.

closes odoo#284608

Signed-off-by: Nicolas Viseur (vin) <vin@odoo.com>
…rn orders

When a return order is created from the front end and later cancelled without
being deleted from the backend, opening the original order from the POS ticket
screen causes the UI to crash.

The issue occurs because the refundedQty getter in
`addons/point_of_sale/static/src/app/models/pos_order_line.js` assumes that
every refunded order line has a valid order_id. For cancelled return orders,
line.order_id is no longer available, resulting in the following runtime error:

`TypeError: can't access property 'state', line.order_id is undefined`

As a result, selecting the original paid order from the Ticket Screen breaks the
POS interface.

**Steps to Reproduce**
1. Create a normal sale in the POS.
2. Keep the POS session open.
3. In the backend, open the POS order and click Return Products.
4. Cancel the generated refund order (do not delete it).
5. In the POS, navigate to Ticket Screen → Orders → Paid Orders.
6. Select the original order.

closes odoo#279942

Signed-off-by: David Monnom (moda) <moda@odoo.com>
The lunch order tour selects `Farm 1` before ordering a product. However,
it only waits for the location input to be updated before clicking the
first kanban record.

With demo data installed, a product from the previous location can still
be displayed while the product model is being reloaded. The tour can
therefore order a demo product instead of the product created by the
test. This notably fails during weekends when the corresponding demo
vendor is unavailable.

To fix we need to wait for the product created by the test before
clicking it. Besides selecting the intended product, this also ensures
that the product reload following the location change has completed.

error-181572

closes odoo#284565

X-original-commit: 8cb86ec
Signed-off-by: Xavier Bol (xbo) <xbo@odoo.com>
The test `undoing something on a target outside s_popup closes it` had
a few fails in CI: the `fa-eye-slash` was not set as expected. This
commit adds a `waitSidebarUpdated` call just before to ensure owl has no
pending rendering when checking the eye.

The fix is similar to aaf0f54 which is
about a similar failure in another test.

runbot-938967

closes odoo#284475

X-original-commit: bc8c129
Signed-off-by: Francois Georis (fge) <fge@odoo.com>
Signed-off-by: Sébastien Blondiau (blse) <blse@odoo.com>
…ack to draft

Steps to reproduce:
- Create a SO and add the Event Registration - Standard product and specify an event
- Confirm the SO then select "Create/Update registrations"
- Cancel the SO, then "Set to Quotation"
- Select "Preview" and confirm the Sale Order again
- There will not be any new registration created when there should be one.

Behavior:
Usually when a sale order is confirmed the `action_sale_order_event_registration` form will be opened which when filled
correctly creates registrations. However in certain cases: confirming from the customer portal, or simply closing the
form when it is opened, will not trigger `action_make_registration` which creates registrations if it is not already the case

`action_confirm()` should be creating the registrations correctly on its own anyway by calling ´init_registrations()´ :
https://github.com/odoo/odoo/blob/beed378cde592bc96c1e79a976ac775264b843ed/addons/event_sale/models/sale_order_line.py#L49-L66

This function tries to create each missing registrations by looking at the amount in the so_line and deducting
the already created registrations, however since some of them can be cancelled, this computation is wrong.
And leads to registration not being created when they should.

opw-6444127

closes odoo#280426

Signed-off-by: Noam Sirjacobs (nosir) <nosir@odoo.com>
/website/translations does not require request.website or language
redirection logic as `lang` is passed explicitly. Drop `website=True` to
prevent unexpected language redirects and cookie conflicts.

Backport of 4faddd8 (odoo#269325).

runbot-231758

closes odoo#281738

Signed-off-by: Hubert Van De Walle <huvw@odoo.com>
Steps to reproduce:

- Insert a bullet list
- Inside of the list, insert a table
- Write before and/or after the table (in the same list item)
- Press enter before and/or after the inserted text
- Notice that the bullet is not split like in a normal list

Root Cause:

- On Enter, list plugin checked whether the list item contained unsplittable
element. Since the table was inside the list item, it always treated the list
item as unsplittable, even when the cursor was outside the table. As a result,
the list item could never be split.

Solution:

- Instead of checking the whole list item, walk up from the split target to
the list item and look for an unsplittable element along the way. This allows
the list item to split normally when the cursor is outside the unsplittable.

task-6449843

closes odoo#280903

Signed-off-by: David Monjoie (dmo) <dmo@odoo.com>
Issue before this commit:
Before this commit, users were completely blocked from creating an
invoice for a foreign partner (e.g., "Cliente del Exterior") if all
exportation journals were archived or unavailable, as the system would
immediately trigger a RedirectWarning error.

Steps to reproduce the issue:
1. Download Accounting and l10n_ar
2. Go to contacts and create a new one with:
	1. Country as United States
	2. VAT number ex. 55000002126
	3. AFIP Responsibility Type as Cliente del Exterior
3. Go to Journals, filter for sales journals and archive:
	1. Electronic Exportation Invoice (FEX)
	2. Expo Sales Journal
4. Go to invoices and create a new one for the client you just created
5. As soon as you insert the client you will receive the error: You are
trying to create an invoice for foreign partner but you don't have an
exportation journal

Cause of the issue:
https://github.com/odoo/odoo/blob/014d58e3204d17db6dcba3c8ab7d8ad35003300e/addons/l10n_ar/models/account_move.py#L186-L189
The _onchange_partner_journal method rigidly enforced the use of an
exportation journal for foreign AFIP responsibility types (codes 8, 9,
and 10). If the query failed to find an active export journal, the code
intentionally threw a hard error instead of providing a fallback
mechanism.

Reason to introduce the fix:
This fix is introduced to prevent unnecessary workflow blocks. By
catching the missing journal and defaulting the document type to
"Invoice B" (code 6), the user can now successfully generate the invoice
using a standard domestic sales journal without being forced to
configure an exportation journal.

opw-6442501

closes odoo#284561

X-original-commit: e471c26
Signed-off-by: William André (wan) <wan@odoo.com>
The Turkish chart of accounts keeps sales and sales returns on separate
accounts, and the sales journal carries the account to use for returns.

A credit note typed in by hand already lands on it, but one created from an
existing customer invoice did not. Reversing an invoice copies `account_id`
over from the invoice line, and since that field is a stored compute without
depends, nothing ever recomputes it, so the return kept the sales account.

Set the journal account on the copied product lines instead. Reversals made
to cancel an entry are left alone, as those have to mirror the original move
exactly for the two to net out, and a plain duplicate is untouched.

Task-6438412

closes odoo#284357

X-original-commit: 102924c
Signed-off-by: Maximilien La Barre (malb) <malb@odoo.com>
Signed-off-by: Majed Safadi (mdsi) <mdsi@odoo.com>
Align `default_get` behavior with `get_param` so access is validated up
front and consistently across both read paths.

Task-6501272
Steps to reproduce:

- In the settings: Enable Storage Locations
- Create a customer location "Customer stock" with "Customers" as its
  parent location
- Create a delivery operation type "Deliver Super Customer" and set its
  default destination location to "Customer stock"
- Go to Inventory > Overview > Deliver Super Customer > New
- Set a contact on the transfer
> The destination location switches from "Customer stock" to "Customers"

Cause of the issue:

The `location_dest_id` of `stock.picking` depends on its `partner_id`.
So that changing the partner recomputes the locations of the transfer.
However, as soon as the destination of the operation type has a
`customer` usage, the `property_stock_customer` of the contact replaces
it unconditionally:
https://github.com/odoo/odoo/blob/04f3a7bca99d0144a4ea871be9625db368b196ca/addons/stock/models/stock_picking.py#L949-L963
However, the `property_stock_customer` falls  back to an `ir.default`
pointing at the defaul `Customers` location when nothing is set on the
contact:
https://github.com/odoo/odoo/blob/1c40fab04b71def8f3645c4c4bb0c1441057f307/addons/stock/data/stock_data.xml#L71-L72vs

The override comes from 8a0775a, which replaced an `elif` fallback
on the contact by an "unconditional" substitution as this fallback had
become unreachable once `default_location_src_id` and
`default_location_dest_id` were made required:
https://github.com/odoo/odoo/blob/04f3a7bca99d0144a4ea871be9625db368b196ca/addons/stock/models/stock_picking.py#L34-L41

opw-6421090

closes odoo#283886

X-original-commit: 13a8ff3
Signed-off-by: Steve Van Essche <svs@odoo.com>
Signed-off-by: Lancelot Semal (lase) <lase@odoo.com>
Steps to reproduce:
- Enable presets on a restaurant PoS and tick "Amount of Guests" on the
  preset used for tables
- On device A, open a table and enter the number of guests
- On device B, open the same table

Issue:
Device B pops the guest count numpad again, even though the guest count
was already entered on device A.

Cause:
ensureGuestCustomerCount guards the popup on order.uiState.guestSetted.
uiState is only serialized to IndexedDB (SERIALIZED_UI_STATE_PROP, used by
serializeForIndexedDB); it is never sent to the server, so the flag is
local to one browser and a second device always considers the guest count
as not yet asked.

Fix:
Seed that flag in initState, which is called once per record and only when
there is no stored uiState to restore: an order that already has a server
id was created on another device, which went through the guest flow for
the preset it carries. A reload still restores the real flag, and an order
switched to a guest preset afterwards is still asked.

opw-6470180

closes odoo#283002

Signed-off-by: Manu Vaillant (manv) <manv@odoo.com>
Issue
-----
When adding all of the catalog's suggestions at once, the uom specified on the
product's vendor lines is not respected.

Steps to reproduce
-----
- Create a product
	- Add a vendor line in a different uom
- Create a past outgoing shipment of 100 of the product
- Create a PO (same vendor as vendor line)
	- Open the Catalog
	- Click "Add All" in the suggestion section on the left
- Go back to the PO

> The product is in units instead of the different uom

Cause
-----
Clicking the button calls `action_purchase_order_suggest` in Python directly

https://github.com/odoo/odoo/blob/3aec1c317aad547b1ad0c85a21cc53f735c5cbfd/addons/purchase_stock/models/purchase_order.py#L131-L134

whereas clicking on a product will go through `addProduct` in JS

https://github.com/odoo/odoo/blob/3aec1c317aad547b1ad0c85a21cc53f735c5cbfd/addons/purchase_stock/static/src/product_catalog/record/kanban_record.js#L20-L28

Which leads to `_update_order_line_info` where the purchase line is created

https://github.com/odoo/odoo/blob/f59783d43f891fea14d03f67d7c017d7ffbbe5a7/addons/purchase/models/purchase_order.py#L1322-L1328

The uom is then retrieved in the create call through `_suggest_quantity`

https://github.com/odoo/odoo/blob/f59783d43f891fea14d03f67d7c017d7ffbbe5a7/addons/purchase/models/purchase_order_line.py#L547-L549

Other issue
-----
The quantity of the product also doesn't match the suggestion since the product
`suggested_qty` is in the product's uom and not the vendor ones.

-----
Ticket:
opw-6417665

closes odoo#280934

Signed-off-by: William Henrotin (whe) <whe@odoo.com>
Copying an image attachment already linked to another record could
leave a redundant duplicate behind instead of reusing the existing
one.

opw-6463012

closes odoo#284567

X-original-commit: 0c7f643
Signed-off-by: David Monjoie (dmo) <dmo@odoo.com>
Signed-off-by: Mohammadmahdi Alijani (malj) <malj@odoo.com>
Steps to reproduce:
- Install 'l10n_fr_pdp' module > Switch to FR Company
- Activate 'French e-invoicing' (Demo mode)
- Create a New 'Credit Note' with 'FR Customer' > Send

Issue:
The system currently displays a confusing error message during EDI document
generation.

We are making the error message clearer and more user-friendly.

opw-6412521

closes odoo#284612

X-original-commit: 9e7ab3f
Signed-off-by: Claire Bretton (clbr) <clbr@odoo.com>
* [I18N] account*: fix i18n

Forward-Port-Of: #1196

* Update vi.po

---------

Co-authored-by: quyen <duyquyencnt55@gmail.com>
Co-authored-by: Roy Le <43790414+royle-vietnam@users.noreply.github.com>
<string>:38: (ERROR/3) Unexpected indentation.
<string>:43: (WARNING/2) Block quote ends without a blank line;
unexpected unindent.
On 19.0, /odoo boots via WebClient._loadDefaultApp straight into the
first app, so hr_skills_event_onsite_tour's very first step (targeting
the Employees app tile) ran before the Apps menu was ever opened. The
Apps menu is an OWL Dropdown backed by usePopover, so its tile content
is not mounted in the DOM until the navbar apps button is clicked,
which made the tour time out after 10s with "Element has not been
found".

Add stepUtils.showAppsMenuItem() as the new first step, mirroring the
identical pattern already used by the sibling tour
addons/hr_skills/static/tests/tours/skills_tour.js.

Test-only change, no production code touched.
Four POS tours typed a customer's name into the partner-search box but
never pressed Enter, so they only client-side-filtered the preloaded
slice of at most 100 partners instead of querying the server, which
searches every partner but is only triggered by pressing Enter. This
made the tours fail whenever a larger partner set in the target
database pushed the fixture partner outside that preloaded slice.

Press Enter right after opening the partner-selection screen, using
the existing PartnerList.searchCustomerValue(name, true) helper whose
true argument triggers the Enter keypress and the server-side search,
reusing the pattern already proven elsewhere in this module. Applies
to test_not_create_loyalty_card_expired_program, PosOrderClaimReward
and PosOrderNoPoints (pos_loyalty_loyalty_program_tour.js) and
test_refund_does_not_decrease_points (pos_loyalty_tour.js).

Test-only change, no production code touched.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.