Khushboo Bhatt(openerp) has proposed merging 
lp:~openerp-dev/openobject-addons/trunk-opw-579043-port-kbh into 
lp:openobject-addons.

Requested reviews:
  OpenERP Core Team (openerp)

For more details, see:
https://code.launchpad.net/~openerp-dev/openobject-addons/trunk-opw-579043-port-kbh/+merge/138114

Hello,

[FIX] mrp_subproduct doesnt pull sub products from bill of material when we 
have type phantom"

Issue :
After adding a suproduct line in Bill of matirial of type=Phantom we hope to 
see the material asigned in sub product of phantom bill of material when 
confirming the production order with the parent bill of material that the 
mrp_subproduct fills in finished product, but it doesn't do it.

Steps:
Check this video : http://youtu.be/Fp4Vj5aNtrw

Code is forward port from 6.1

Thanks,
Khushboo.

-- 
https://code.launchpad.net/~openerp-dev/openobject-addons/trunk-opw-579043-port-kbh/+merge/138114
Your team OpenERP R&D Team is subscribed to branch 
lp:~openerp-dev/openobject-addons/trunk-opw-579043-port-kbh.
=== modified file 'mrp_byproduct/mrp_byproduct.py'
--- mrp_byproduct/mrp_byproduct.py	2012-12-08 10:33:38 +0000
+++ mrp_byproduct/mrp_byproduct.py	2012-12-10 09:10:26 +0000
@@ -21,6 +21,8 @@
 
 from osv import fields
 from osv import osv
+
+import tools
 import decimal_precision as dp
 from tools.translate import _
 
@@ -75,38 +77,106 @@
         'sub_products':fields.one2many('mrp.subproduct', 'bom_id', 'Byproducts'),
     }
 
+    def _bom_explode(self, cr, uid, bom, factor, properties=[], addthis=False, level=0, routing_id=False, result_subproducts=False):
+        """ Finds sub products and work centers for related bom lines which has several sub products defined in it.
+        @param bom: BoM of particular product.
+        @param factor: Factor of product UoM.
+        @param properties: A List of properties Ids.
+        @param addthis: If BoM found then True else False.
+        @param level: Depth level to find BoM lines starts from 10.
+        @return: result: List of dictionaries containing product details.
+                 result2: List of dictionaries containing Work Center details.
+        """
+        if result_subproducts is False:
+            result_subproducts = []
+        if self._columns.has_key('sub_products'):#if module mrp_subproduct is installed
+            for sub_product in bom.sub_products:
+                qty1 = sub_product.product_qty
+                if sub_product.subproduct_type == 'variable':
+                   qty1 = factor*qty1/bom.product_uom.factor_inv
+                result_subproducts.append({
+                    'product_id': sub_product.product_id.id,
+                    'product_qty': qty1,
+                    'product_uom': sub_product.product_uom.id,
+                })
+        routing_obj = self.pool.get('mrp.routing')
+        factor = factor / (bom.product_efficiency or 1.0)
+        factor = rounding(factor, bom.product_rounding)
+        if factor < bom.product_rounding:
+            factor = bom.product_rounding
+        result = []
+        result2 = []
+        phantom = False
+        if bom.type == 'phantom' and not bom.bom_lines:
+            newbom = self._bom_find(cr, uid, bom.product_id.id, bom.product_uom.id, properties)
+            
+            if newbom:
+                newbom_pool = self.browse(cr, uid, newbom)
+                res = self._bom_explode(cr, uid, self.browse(cr, uid, [newbom])[0], factor*bom.product_qty/(newbom_pool.product_qty*newbom_pool.product_uom.factor_inv), properties, addthis=True, level=level+10, result_subproducts=result_subproducts)
+                result = result + res[0]
+                result2 = result2 + res[1]
+                phantom = True
+            else:
+                phantom = False
+        if not phantom:
+            if addthis and not bom.bom_lines:
+                result.append(
+                {
+                    'name': bom.product_id.name,
+                    'product_id': bom.product_id.id,
+                    'product_qty': bom.product_qty * factor,
+                    'product_uom': bom.product_uom.id,
+                    'product_uos_qty': bom.product_uos and bom.product_uos_qty * factor or False,
+                    'product_uos': bom.product_uos and bom.product_uos.id or False,
+                })
+            routing = (routing_id and routing_obj.browse(cr, uid, routing_id)) or bom.routing_id or False
+            if routing:
+                for wc_use in routing.workcenter_lines:
+                    wc = wc_use.workcenter_id
+                    d, m = divmod(factor, wc_use.workcenter_id.capacity_per_cycle)
+                    mult = (d + (m and 1.0 or 0.0))
+                    cycle = mult * wc_use.cycle_nbr
+                    result2.append({
+                        'name': tools.ustr(wc_use.name) + ' - '  + tools.ustr(bom.product_id.name),
+                        'workcenter_id': wc.id,
+                        'sequence': level+(wc_use.sequence or 0),
+                        'cycle': cycle,
+                        'hour': float(wc_use.hour_nbr*mult + ((wc.time_start or 0.0)+(wc.time_stop or 0.0)+cycle*(wc.time_cycle or 0.0)) * (wc.time_efficiency or 1.0)),
+                    })
+            for bom2 in bom.bom_lines:
+                res = self._bom_explode(cr, uid, bom2, factor, properties, addthis=True, level=level+10, result_subproducts=result_subproducts)
+                result = result + res[0]
+                result2 = result2 + res[1]
+        return result, result2
+
 mrp_bom()
 
 class mrp_production(osv.osv):
     _description = 'Production'
     _inherit= 'mrp.production'
 
-
     def action_confirm(self, cr, uid, ids):
         """ Confirms production order and calculates quantity based on subproduct_type.
         @return: Newly generated picking Id.
         """
+        bom_obj = self.pool.get('mrp.bom')
+        uom_obj = self.pool.get('product.uom')
         picking_id = super(mrp_production,self).action_confirm(cr, uid, ids)
         for production in self.browse(cr, uid, ids):
             source = production.product_id.product_tmpl_id.property_stock_production.id
-            if not production.bom_id:
+            bom_id = production.bom_id
+            if not bom_id:
                 continue
-            for sub_product in production.bom_id.sub_products:
-                qty1 = sub_product.product_qty
-                qty2 = production.product_uos and production.product_uos_qty or False
-                if sub_product.subproduct_type == 'variable':
-                    if production.product_qty:
-                        qty1 *= production.product_qty / (production.bom_id.product_qty or 1.0)
-                    if production.product_uos_qty:
-                        qty2 *= production.product_uos_qty / (production.bom_id.product_uos_qty or 1.0)
+            factor = uom_obj._compute_qty(cr, uid, production.product_uom.id, production.product_qty, bom_id.product_uom.id)
+            result_subproducts =[]
+            res = bom_obj._bom_explode(cr, uid, bom_id, factor / bom_id.product_qty, properties=False, routing_id=False, result_subproducts=result_subproducts)
+            for sub_product in result_subproducts:
                 data = {
                     'name': 'PROD:'+production.name,
                     'date': production.date_planned,
-                    'product_id': sub_product.product_id.id,
-                    'product_qty': qty1,
-                    'product_uom': sub_product.product_uom.id,
-                    'product_uos_qty': qty2,
-                    'product_uos': production.product_uos and production.product_uos.id or False,
+                    'product_id': sub_product['product_id'],
+                    'product_qty': sub_product['product_qty'],
+                    'product_uom': sub_product['product_uom'],
                     'location_id': source,
                     'location_dest_id': production.location_dest_id.id,
                     'move_dest_id': production.move_prod_id.id,
@@ -140,6 +210,12 @@
 
 mrp_production()
 
+def rounding(f, r):
+        import math
+        if not r:
+            return f
+        return math.ceil(f / r) * r
+
 class change_production_qty(osv.osv_memory):
     _inherit = 'change.production.qty'
 

_______________________________________________
Mailing list: https://launchpad.net/~openerp-dev-gtk
Post to     : openerp-dev-gtk@lists.launchpad.net
Unsubscribe : https://launchpad.net/~openerp-dev-gtk
More help   : https://help.launchpad.net/ListHelp

Reply via email to