[IMP] sale: ease catalog inheritance
closes odoo/odoo#132341 Signed-off-by: Victor Feyens (vfe) <vfe@odoo.com>
This commit is contained in:
committed by
Valentin Chevalier
parent
960b4c8616
commit
484210c5d3
@@ -30,27 +30,22 @@ class CatalogController(Controller):
|
||||
):
|
||||
if(product.id not in product_ids):
|
||||
continue
|
||||
if (len(lines) > 1) or lines[0].product_uom != product.uom_id:
|
||||
price_unit = order.pricelist_id._get_product_price(
|
||||
product=product,
|
||||
quantity=1.0,
|
||||
currency=order.currency_id,
|
||||
date=order.date_order,
|
||||
)
|
||||
sale_order_line_info[product.id] = dict(
|
||||
readOnly=True,
|
||||
price=price_unit,
|
||||
)
|
||||
else:
|
||||
line = lines[0]
|
||||
sale_order_line_info[product.id] = dict(
|
||||
quantity=line.product_uom_qty,
|
||||
price=line.price_unit,
|
||||
)
|
||||
|
||||
sale_order_line_info[product.id] = request.env['sale.order.line'].browse(
|
||||
line.id for line in lines # groupby gives a list and not a recordset
|
||||
)._get_catalog_info()
|
||||
|
||||
product_ids.remove(product.id)
|
||||
|
||||
default_data = request.env['sale.order.line']._get_catalog_info()
|
||||
default_data['readOnly'] = order._is_readonly()
|
||||
|
||||
sale_order_line_info.update({
|
||||
id: dict(price=price) for id, price in order.pricelist_id._get_products_price(
|
||||
id: {
|
||||
**default_data,
|
||||
'price': price,
|
||||
}
|
||||
for id, price in order.pricelist_id._get_products_price(
|
||||
quantity=1.0,
|
||||
products=request.env['product.product'].browse(product_ids),
|
||||
currency=order.currency_id,
|
||||
|
||||
@@ -1658,3 +1658,17 @@ class SaleOrder(models.Model):
|
||||
# Override for correct taxcloud computation
|
||||
# when using coupon and delivery
|
||||
return True
|
||||
|
||||
#=== TOOLING ===#
|
||||
|
||||
def _is_readonly(self):
|
||||
""" Return Whether the sale order is read-only or not based on the state or the lock status.
|
||||
|
||||
A sale order is considered read-only if its state is 'cancel' or if the sale order is
|
||||
locked.
|
||||
|
||||
:return: Whether the sale order is read-only or not.
|
||||
:rtype: bool
|
||||
"""
|
||||
self.ensure_one()
|
||||
return self.state == 'cancel' or self.locked
|
||||
|
||||
@@ -1188,6 +1188,62 @@ class SaleOrderLine(models.Model):
|
||||
product_catalog_digits=order.order_line._fields['price_unit'].get_digits(order.env),
|
||||
)
|
||||
|
||||
def _get_catalog_info(self):
|
||||
""" Return information about sale order lines in `self`.
|
||||
|
||||
If `self` is empty, this method returns only the default value(s) needed for the product
|
||||
catalog. In this case, the quantity that equals 0.
|
||||
|
||||
Otherwise, it returns a quantity and a price based on the product of the SOL(s) and whether
|
||||
the product is read-only or not.
|
||||
|
||||
A product is considered read-only if the order is considered read-only (see
|
||||
``SaleOrder._is_readonly`` for more details) or if `self` contains multiple records.
|
||||
|
||||
Note: This method cannot be called with multiple records that have different products linked.
|
||||
|
||||
:raise odoo.exceptions.ValueError: ``len(self.product_id) != 1``
|
||||
:rtype: dict
|
||||
:return: A dict with the following structure:
|
||||
{
|
||||
'quantity': float,
|
||||
'price': float,
|
||||
'readOnly': bool,
|
||||
}
|
||||
"""
|
||||
if len(self) == 1:
|
||||
return {
|
||||
'quantity': self.product_uom_qty,
|
||||
'price': self.price_unit,
|
||||
'readOnly': self.order_id._is_readonly(),
|
||||
}
|
||||
elif self:
|
||||
self.product_id.ensure_one()
|
||||
order_line = self[0]
|
||||
order = order_line.order_id
|
||||
return {
|
||||
'readOnly': True,
|
||||
'price': order.pricelist._get_product_price(
|
||||
product=order_line.product_id,
|
||||
quantity=1.0,
|
||||
currency=order.currency_id,
|
||||
date=order.date_order,
|
||||
),
|
||||
'quantity': sum(
|
||||
self.mapped(
|
||||
lambda line: line.product_uom._compute_quantity(
|
||||
qty=line.product_uom_qty,
|
||||
to_unit=line.product_id.uom_id,
|
||||
)
|
||||
)
|
||||
),
|
||||
}
|
||||
else:
|
||||
return {
|
||||
'quantity': 0,
|
||||
# price will be computed in batch with pricelist utils so not given here
|
||||
}
|
||||
|
||||
#=== TOOLING ===#
|
||||
|
||||
def _convert_to_sol_currency(self, amount, currency):
|
||||
|
||||
@@ -23,7 +23,6 @@ export class ProductCatalogKanbanModel extends RelationalModel {
|
||||
});
|
||||
for (const record of result.records) {
|
||||
record.productCatalogData = saleOrderLinesInfo[record.id];
|
||||
record.productCatalogData.quantity = record.productCatalogData.quantity || 0;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -11,10 +11,7 @@
|
||||
t-att-class="{'text-bg-primary': productCatalogData.quantity || productCatalogData.readOnly}">
|
||||
<t t-call="{{ templates[this.constructor.KANBAN_BOX_ATTRIBUTE] }}"
|
||||
t-call-context="this.renderingContext"/>
|
||||
<ProductCatalogSOL productId="props.record.resId"
|
||||
quantity="productCatalogData.quantity"
|
||||
price="productCatalogData.price"
|
||||
readOnly="productCatalogData.readOnly"/>
|
||||
<ProductCatalogSOL productId="props.record.resId" t-props="productCatalogData"/>
|
||||
</div>
|
||||
<t t-call="{{ this.constructor.menuTemplate }}"/>
|
||||
</div>
|
||||
|
||||
@@ -331,7 +331,32 @@ class SaleOrderLine(models.Model):
|
||||
raise UserError(_('The ordered quantity cannot be decreased below the amount already delivered. Instead, create a return in your inventory.'))
|
||||
super(SaleOrderLine, self)._update_line_quantity(values)
|
||||
|
||||
#=== HOOKS ===#
|
||||
|
||||
def _get_action_add_from_catalog_extra_context(self, order):
|
||||
extra_context = super()._get_action_add_from_catalog_extra_context(order)
|
||||
extra_context.update(warehouse=order.warehouse_id.id)
|
||||
return extra_context
|
||||
|
||||
def _get_catalog_info(self):
|
||||
""" Override of `sale` to add the delivered quantity.
|
||||
|
||||
:rtype: dict
|
||||
:return: A dict with the following structure:
|
||||
{
|
||||
'deliveredQty': float,
|
||||
'quantity': float,
|
||||
'price': float,
|
||||
'readOnly': bool,
|
||||
}
|
||||
"""
|
||||
res = super()._get_catalog_info()
|
||||
res['deliveredQty'] = sum(
|
||||
self.mapped(
|
||||
lambda line: line.product_uom._compute_quantity(
|
||||
qty=line.qty_delivered,
|
||||
to_unit=line.product_id.uom_id,
|
||||
)
|
||||
)
|
||||
)
|
||||
return res
|
||||
|
||||
@@ -0,0 +1,11 @@
|
||||
/** @odoo-module */
|
||||
|
||||
import { ProductCatalogSOL } from "@sale/js/product_catalog/sale_order_line/sale_order_line";
|
||||
import { patch } from "@web/core/utils/patch";
|
||||
|
||||
patch(ProductCatalogSOL, {
|
||||
props: {
|
||||
...ProductCatalogSOL.props,
|
||||
deliveredQty: Number,
|
||||
},
|
||||
});
|
||||
Reference in New Issue
Block a user