feat: implement location restriction overrides for stock reservation and search methods
This commit is contained in:
parent
d26425ea84
commit
dd0b07a23b
@ -68,6 +68,69 @@ class StockQuant(models.Model):
|
|||||||
|
|
||||||
return allowed_location_ids
|
return allowed_location_ids
|
||||||
|
|
||||||
|
@api.model
|
||||||
|
def _get_gather_domain(self, product_id, location_id, lot_id=None, package_id=None, owner_id=None, strict=False):
|
||||||
|
"""Override to apply location restrictions during reservation (gather)"""
|
||||||
|
result_domain = super()._get_gather_domain(product_id, location_id, lot_id, package_id, owner_id, strict)
|
||||||
|
|
||||||
|
# FIX: If reserving from a non-internal location, DO NOT apply internal restrictions.
|
||||||
|
if location_id and location_id.usage != 'internal':
|
||||||
|
return result_domain
|
||||||
|
|
||||||
|
allowed_location_ids = self._get_allowed_locations()
|
||||||
|
if allowed_location_ids:
|
||||||
|
# 1. Smart Domain Swap: find if there's already a location_id restriction (like child_of)
|
||||||
|
found_collision = False
|
||||||
|
new_domain = []
|
||||||
|
for leaf in result_domain:
|
||||||
|
if (isinstance(leaf, (list, tuple)) and
|
||||||
|
len(leaf) == 3 and
|
||||||
|
leaf[0] == 'location_id' and
|
||||||
|
leaf[1] in ('child_of', '=', 'in')):
|
||||||
|
|
||||||
|
new_domain.append(('location_id', 'in', allowed_location_ids))
|
||||||
|
found_collision = True
|
||||||
|
else:
|
||||||
|
new_domain.append(leaf)
|
||||||
|
if found_collision:
|
||||||
|
result_domain = new_domain
|
||||||
|
else:
|
||||||
|
result_domain = Domain.AND([result_domain, [('location_id', 'in', allowed_location_ids)]])
|
||||||
|
|
||||||
|
return result_domain
|
||||||
|
|
||||||
|
def _search(self, domain, offset=0, limit=None, order=None, *args, **kwargs):
|
||||||
|
"""Override to apply location restrictions during search (e.g. catalog or list selection)"""
|
||||||
|
# CRITICAL FIX: If we are searching for specific IDs (e.g., Odoo is fetching selected records for save),
|
||||||
|
# we must NOT restrict the search results or we trigger 'Missing Product' validation errors
|
||||||
|
# on backend fallback create logic.
|
||||||
|
search_by_id = any(isinstance(leaf, (list, tuple)) and leaf[0] == 'id' for leaf in domain)
|
||||||
|
if search_by_id:
|
||||||
|
return super()._search(domain, offset=offset, limit=limit, order=order, *args, **kwargs)
|
||||||
|
|
||||||
|
allowed_location_ids = self._get_allowed_locations()
|
||||||
|
if allowed_location_ids:
|
||||||
|
# 1. Smart Domain Swap: find if there's already a location_id restriction (like child_of)
|
||||||
|
found_collision = False
|
||||||
|
new_domain = []
|
||||||
|
for leaf in domain:
|
||||||
|
if (isinstance(leaf, (list, tuple)) and
|
||||||
|
len(leaf) == 3 and
|
||||||
|
leaf[0] == 'location_id' and
|
||||||
|
leaf[1] == 'child_of'):
|
||||||
|
|
||||||
|
new_domain.append(('location_id', 'in', allowed_location_ids))
|
||||||
|
found_collision = True
|
||||||
|
else:
|
||||||
|
new_domain.append(leaf)
|
||||||
|
|
||||||
|
if found_collision:
|
||||||
|
domain = new_domain
|
||||||
|
else:
|
||||||
|
domain = Domain.AND([domain, [('location_id', 'in', allowed_location_ids)]])
|
||||||
|
|
||||||
|
return super()._search(domain, offset=offset, limit=limit, order=order, *args, **kwargs)
|
||||||
|
|
||||||
|
|
||||||
class StockLocation(models.Model):
|
class StockLocation(models.Model):
|
||||||
_inherit = 'stock.location'
|
_inherit = 'stock.location'
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user