Skip to content

Commit

Permalink
IMP: release and bom update performance
Browse files Browse the repository at this point in the history
  • Loading branch information
mboscolo committed Apr 10, 2024
1 parent eb2ed29 commit d26d4e1
Show file tree
Hide file tree
Showing 5 changed files with 86 additions and 50 deletions.
89 changes: 50 additions & 39 deletions plm/models/product_product.py
Original file line number Diff line number Diff line change
Expand Up @@ -304,13 +304,13 @@ def on_change_tmptreatment(self):
self.engineering_treatment = str(self.tmp_treatment.name)

@api.model
def getParentBomStructure(self, filterBomType=''):
def getParentBomStructure(self,
filterBomType=''):
bom_line_filter = [('product_id', '=', self.id)]
if filterBomType:
bom_line_filter.append(('type', '=', filterBomType))
mrpBomLines = self.env['mrp.bom.line'].search(bom_line_filter)
out = []
for mrpBomLine in mrpBomLines:
for mrpBomLine in self.env['mrp.bom.line'].search(bom_line_filter):
out.append((self.env['mrp.bom'].where_used_header(mrpBomLine),
mrpBomLine.bom_id.get_where_used_structure(filterBomType)))
return out
Expand Down Expand Up @@ -910,51 +910,62 @@ def _action_release(self):
action to be executed for Released state
"""
for comp_obj in self:
children_product_to_emit = []
product_tmpl_ids = []
defaults = {}
allProdObjs = comp_obj
exclude_statuses = ['released', 'undermodify', 'obsoleted']
include_statuses = self.env.context.get("PLM_STATE_RELEASE" ,['confirmed'])
errors, product_ids = comp_obj._get_recursive_parts(exclude_statuses, include_statuses)
children_products = product_ids.copy()
children_products_ids = product_ids.copy()
if len(product_ids) < 1 or len(errors) > 0:
raise UserError(errors)
children_products.remove(comp_obj.id)
if children_products:
self.browse(children_products).action_release()
children_products_ids.remove(comp_obj.id)
available_status = self._fields.get('state')._description_selection(self.env)
dict_status = dict(available_status)
allProdObjs = self.browse(product_ids)
if children_products_ids:
children_products= self.browse(children_products_ids)
children_products.action_release()
allProdObjs+=children_products
allProdObjs = allProdObjs.filtered(lambda x: x.engineering_code not in [False, ''])
for productBrw in allProdObjs:
old_revision = self._getbyrevision(productBrw.engineering_code, productBrw.engineering_revision - 1)
if old_revision:
defaults['engineering_writable'] = False
defaults['state'] = 'obsoleted'
old_revision.product_tmpl_id.write(defaults)
old_revision.write(defaults)
status_lable = dict_status.get(defaults.get('state', ''), '')
old_revision.wf_message_post(body=_('Status moved to: %s by %s.' % (status_lable, self.env.user.name)))
productBrw._action_ondocuments('release', include_statuses)
defaults['engineering_writable'] = False
defaults['state'] = 'released'
defaults['release_user'] = self.env.uid
defaults['release_date'] = datetime.now()
for currentProductId in allProdObjs:
if not currentProductId.release_date:
currentProductId.release_date = datetime.now()
currentProductId.release_user = self.env.uid
if currentProductId.id not in self.ids:
children_product_to_emit.append(currentProductId.id)
product_tmpl_ids.append(currentProductId.product_tmpl_id.id)
if children_product_to_emit:
self.browse(children_product_to_emit).perform_action('release')
self.browse(children_product_to_emit).write(defaults)
for objId in self.env['product.template'].browse(product_tmpl_ids):
objId.write(defaults)
for product_product_id in allProdObjs:
if product_product_id.engineering_revision>0:
old_revision = self._getbyrevision(product_product_id.engineering_code,
product_product_id.engineering_revision - 1)
#
# Set all revision status
#
if old_revision:
old_revision.product_tmpl_id.engineering_writable = False
old_revision.product_tmpl_id.state = 'obsoleted'
old_revision.engineering_writable = False
old_revision.state = 'obsoleted'
status_lable = dict_status.get('obsoleted')
old_revision.wf_message_post(body=_('Status moved to: %s by %s.' % (status_lable,
self.env.user.name)))
else:
logging.error(f"Missing previews version for {product_product_id.engineering_code}")
#
# Move the related document
#
product_product_id._action_ondocuments('release', include_statuses)
#
# Work on active product product
#
defaults = {}
defaults['engineering_writable'] = False
defaults['state'] = 'released'
defaults['release_user'] = self.env.uid
defaults['release_date'] = datetime.now()
product_product_id.write(defaults)
#
# wotk on product.template
#
product_template_id = product_product_id.product_tmpl_id
product_template_id.write(defaults)
#
# Notifie on chatter
#
status_lable = dict_status.get(defaults.get('state', ''), '')
self.browse(product_ids).wf_message_post(body=_('Status moved to: %s by %s.' % (status_lable, self.env.user.name)))
comp_obj.write(defaults)
product_product_id.wf_message_post(body=_('Status moved to: %s by %s.' % (status_lable,
self.env.user.name)))
return True

def action_obsolete(self):
Expand Down
2 changes: 1 addition & 1 deletion plm/security/base_plm_security.xml
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@
<record id="group_plm_admin_unrelease" model="res.groups">
<field name="name">Unrelease User</field>
<field name="category_id" ref="odooplm_module_category"/>
<field name="implied_ids" eval="[(4, ref('group_plm_admin'))]"/>
<field name="implied_ids" eval="[(4, ref('group_plm_integration_user'))]"/>
</record>

<!-- readonly_released -->
Expand Down
2 changes: 1 addition & 1 deletion plm_automatic_weight/models/product_product.py
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ def write(self, vals):
if product_product_id.state not in self.weight_allowed_state and not self.env.context.get('plm_force_weight',False):
if 'weight' in vals:
del vals['weight']
logging.info("Modification in status %s not allowed for the weight" % product_product_id.state)
logging.info(f"Modification of field weight not allowed for product {product_product_id.display_name} in status {product_product_id.state}")
weight_additional = product_product_id.weight_additional
if 'weight_additional' in vals:
weight_additional = vals['weight_additional']
Expand Down
6 changes: 4 additions & 2 deletions plm_date_bom/models/mrp_bom.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,11 +61,13 @@ def _obsolete_compute(self):

# If store = True is set you need to provide @api.depends because odoo has to know when to compute that field.
# If you decide to compute that field each time without store you have always to put it in the view or the field will not be computed
obsolete_presents_computed = fields.Boolean(string=_("Obsolete presents computed"), compute='_obsolete_compute')
obsolete_presents_computed = fields.Boolean(string=_("Obsolete presents computed"),
compute='_obsolete_compute')
obsolete_presents = fields.Boolean(_("Obsolete presents"))

# This fields has not to be computed fields because bom may be very big and the time too
obsolete_presents_recursive = fields.Boolean(_("Obsolete presents Recursive"), default=False)
obsolete_presents_recursive = fields.Boolean(_("Obsolete presents Recursive"),
default=False)

@api.onchange('bom_line_ids')
def onchangeBomLine(self):
Expand Down
37 changes: 30 additions & 7 deletions plm_date_bom/models/product_product.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,29 +29,52 @@ class ProductExtension(models.Model):
_inherit = 'product.template'

@api.model
def updateObsoleteRecursive(self, prodBrws, presentsFlag=True):
bomTmpl = self.env['mrp.bom']
struct = prodBrws.getParentBomStructure()
def updateObsoleteRecursive(self,
product_product_id,
presentsFlag=True):
mrp_bom_id = self.env['mrp.bom']
struct = product_product_id.getParentBomStructure()

def recursion(struct2, isRoot=False):
for vals, parentsList in struct2:
bom_id = vals.get('bom_id', False)
if bom_id:
bomBrws = bomTmpl.browse(bom_id)
bomBrws = mrp_bom_id.browse(bom_id)
bomBrws._obsolete_compute()
if not isRoot:
bomBrws.obsolete_presents_recursive = presentsFlag
recursion(parentsList)

recursion(struct, isRoot=True)

def update_used_bom(self, product_product_id):
mrp_bom_line = self.env['mrp.bom.line']
product_computed = []
#
def _update_used_bom(product_product_id):
if product_product_id.id in product_computed:
return
product_computed.append(product_product_id.id)
#
for mrp_bom_line_id in mrp_bom_line.search([('product_id','=',product_product_id.id),
('bom_id.type','not in',['ebom'])]):
bom_id = mrp_bom_line_id.bom_id
bom_id.sudo().obsolete_presents_recursive=True
bom_id.sudo().obsolete_presents = True
bom_id.sudo().obsolete_presents_computed = True
for product_product_id in bom_id.product_tmpl_id.product_variant_ids:
_update_used_bom(product_product_id)
#
_update_used_bom(product_product_id)

def write(self, vals):
res = super(ProductExtension, self).write(vals)
statePresent = vals.get('state', None)
if statePresent == 'obsoleted':
# Here I force compute obsolete presents flag in all boms
for prodTmplBrws in self:
for prodBrws in prodTmplBrws.product_variant_ids:
self.updateObsoleteRecursive(prodBrws)
for product_template_id in self:
for product_product_id in product_template_id.product_variant_ids:
#self.updateObsoleteRecursive(product_product_id)
self.update_used_bom(product_product_id)
return res

0 comments on commit d26d4e1

Please sign in to comment.