diff --git a/addons/stock/models/product.py b/addons/stock/models/product.py index cc11c576f65..9809fba10d3 100644 --- a/addons/stock/models/product.py +++ b/addons/stock/models/product.py @@ -221,6 +221,19 @@ class Product(models.Model): domain + loc_domain + ['!'] + dest_loc_domain if dest_loc_domain else domain + loc_domain ) + def _search_qty_available(self, operator, value): + # In the very specific case we want to retrieve products with stock available, we only need + # to use the quants, not the stock moves. Therefore, we bypass the usual + # '_search_product_quantity' method and call '_search_qty_available_new' instead. This + # allows better performances. + if value == 0.0 and operator == '>' and not ({'from_date', 'to_date'} & set(self.env.context.keys())): + product_ids = self._search_qty_available_new( + operator, value, self.env.context.get('lot_id'), self.env.context.get('owner_id'), + self.env.context.get('package_id') + ) + return [('id', 'in', product_ids)] + return self._search_product_quantity(operator, value, 'qty_available') + def _search_virtual_available(self, operator, value): # TDE FIXME: should probably clean the search methods return self._search_product_quantity(operator, value, 'virtual_available') @@ -245,24 +258,13 @@ class Product(models.Model): # TODO: Still optimization possible when searching virtual quantities ids = [] - for product in self.search([]): + for product in self.with_context(prefetch_fields=False).search([]): if OPERATORS[operator](product[field], value): ids.append(product.id) return [('id', 'in', ids)] - def _search_qty_available(self, operator, value): - # TDE FIXME: should probably clean the search methods - if value == 0.0 and operator in ('=', '>=', '<='): - return self._search_product_quantity(operator, value, 'qty_available') - product_ids = self._search_qty_available_new(operator, value, self._context.get('lot_id'), self._context.get('owner_id'), self._context.get('package_id')) - if (value > 0 and operator in ('<=', '<')) or (value < 0 and operator in ('>=', '>')): - # include also unavailable products - domain = self._search_product_quantity(operator, value, 'qty_available') - product_ids += domain[0][2] - return [('id', 'in', product_ids)] - def _search_qty_available_new(self, operator, value, lot_id=False, owner_id=False, package_id=False): - # TDE FIXME: should probably clean the search methods + ''' Optimized method which doesn't search on stock.moves, only on stock.quants. ''' product_ids = set() domain_quant = self._get_domain_locations()[0] if lot_id: