[FIX] Try to fix mrp tests and mrp
authorJosse Colpaert <jco@openerp.com>
Wed, 18 Sep 2013 13:56:12 +0000 (15:56 +0200)
committerJosse Colpaert <jco@openerp.com>
Wed, 18 Sep 2013 13:56:12 +0000 (15:56 +0200)
bzr revid: jco@openerp.com-20130918135612-n8d1qqbxh0rbgtcw

addons/mrp/__openerp__.py
addons/mrp/mrp.py
addons/mrp/mrp_view.xml
addons/mrp/mrp_workflow.xml
addons/mrp/stock.py
addons/mrp/test/order_process.yml
addons/mrp/wizard/change_production_qty.py
addons/sale/sale_workflow.xml

index 773d696..783201e 100644 (file)
@@ -77,8 +77,8 @@ Dashboard / Reports for MRP will include:
     #TODO: This yml tests are needed to be completely reviewed again because the product wood panel is removed in product demo as it does not suit for new demo context of computer and consultant company
     # so the ymls are too complex to change at this stage
     'test': [
-#         'test/order_demo.yml',
-#         'test/order_process.yml',
+        'test/order_demo.yml',
+        'test/order_process.yml',
 #         'test/cancel_order.yml',
     ],
     'installable': True,
index 273647f..26ca5ed 100644 (file)
@@ -824,14 +824,14 @@ class mrp_production(osv.osv):
                 if rest_qty > 0 :
                     stock_mov_obj.action_consume(cr, uid, [produce_product.id], (subproduct_factor * production_qty), context=context)
 
-        for raw_product in production.move_lines2:
-            new_parent_ids = []
-            parent_move_ids = [x.id for x in raw_product.move_history_ids]
-            for final_product in production.move_created_ids2:
-                if final_product.id not in parent_move_ids:
-                    new_parent_ids.append(final_product.id)
-            for new_parent_id in new_parent_ids:
-                stock_mov_obj.write(cr, uid, [raw_product.id], {'move_history_ids': [(4,new_parent_id)]})
+#         for raw_product in production.move_lines2:
+#             new_parent_ids = []
+#             parent_move_ids = [x.id for x in raw_product.move_history_ids]
+#             for final_product in production.move_created_ids2:
+#                 if final_product.id not in parent_move_ids:
+#                     new_parent_ids.append(final_product.id)
+#             for new_parent_id in new_parent_ids:
+#                 stock_mov_obj.write(cr, uid, [raw_product.id], {'move_history_ids': [(4,new_parent_id)]})
         self.message_post(cr, uid, production_id, body=_("%s produced") % self._description, context=context)
         self.signal_button_produce_done(cr, uid, [production_id])
         return True
@@ -896,6 +896,28 @@ class mrp_production(osv.osv):
                 if not self.action_compute(cr, uid, [production.id]):
                     res = False
         return res
+    
+    def consume_lines_get(self, cr, uid, ids, *args):
+        res = []
+        for order in self.browse(cr, uid, ids, context={}):
+            res += [x.id for x in order.move_lines]
+        return res
+    
+    
+    def test_ready2(self, cr, uid, ids):
+        res = True
+        assign = self._moves_assigned(cr, uid, ids, False, False)
+        for production in ids:
+            if not assign[production]:
+                res = False
+        return res
+    
+    def test_ready(self, cr, uid, ids):
+        res = True
+        for production in self.browse(cr, uid, ids):
+            if not production.ready_production:
+                res = False
+        return res
 
     def _make_production_produce_line(self, cr, uid, production, context=None):
         stock_move = self.pool.get('stock.move')
@@ -933,9 +955,8 @@ class mrp_production(osv.osv):
             'name': production.name,
             'date': production.date_planned,
             'product_id': production_line.product_id.id,
-            'product_qty': production_line.product_qty,
-            'product_uom_qty': production.product_qty, 
-            'product_uom': production_line.product_uom.id,
+            'product_uom_qty': production_line.product_qty,
+            'product_uom': production_line.product_uom.id, 
             'product_uos_qty': production_line.product_uos and production_line.product_uos_qty or False,
             'product_uos': production_line.product_uos and production_line.product_uos.id or False,
             'location_id': source_location_id,
@@ -972,8 +993,10 @@ class mrp_production(osv.osv):
         @param *args: Arguments
         @return: True
         """
-        pick_obj = self.pool.get('stock.picking')
-        pick_obj.force_assign(cr, uid, [prod.picking_id.id for prod in self.browse(cr, uid, ids)])
+        
+        move_obj = self.pool.get('stock.move')
+        for order in self.browse(cr, uid, ids):
+            move_obj.force_assign(cr, uid, [x.id for x in order.move_lines])
         return True
 
 
index 0e47396..2f2c04a 100644 (file)
                 <form string="Manufacturing Orders" version="7.0">
                 <header>
                     <button name="button_confirm" states="draft" string="Confirm Production" class="oe_highlight"/>
-                    <button name="%(act_mrp_product_produce)d" states="confirmed,ready,in_production" string="Produce" type="action" class="oe_highlight"/>
+                    <button name="%(act_mrp_product_produce)d" states="ready,in_production" string="Produce" type="action" class="oe_highlight"/>
                     <button name="force_production" states="confirmed" string="Force Reservation" type="object"/>
                     <button name="force_production" states="picking_except" string="Force Reservation" type="object"/>
                     <button name="button_produce" states="ready" string="Mark as Started"/>
index 388dd90..144db24 100644 (file)
@@ -17,8 +17,6 @@
         <record id="prod_act_picking" model="workflow.activity">
             <field name="wkf_id" ref="wkf_prod"/>
             <field name="name">picking</field>
-            <field name="kind">subflow</field>
-            <field name="subflow_id" search="[('osv','=','stock.picking')]"/>
             <field name="action">action_confirm()</field>
         </record>
         <record id="prod_act_ready" model="workflow.activity">
@@ -69,8 +67,9 @@
         <record id="prod_trans_picking_ready" model="workflow.transition">
             <field name="act_from" ref="prod_act_picking"/>
             <field name="act_to" ref="prod_act_ready"/>
-            <field name="signal"></field>
-            <field name="condition">ready_production</field>
+            <field name="trigger_model">stock.move</field>
+            <field name="trigger_expr_id">consume_lines_get()</field>
+            <field name="condition">test_ready2()</field>
         </record>
         <record id="prod_trans_ready_in_production" model="workflow.transition">
             <field name="act_from" ref="prod_act_ready"/>
             <field name="signal">button_produce_done</field>
             <field name="condition">test_production_done()</field>
         </record>
-        <record id="prod_trans_picking_picking_exception" model="workflow.transition">
+        <!--<record id="prod_trans_picking_picking_exception" model="workflow.transition">
             <field name="act_from" ref="prod_act_picking"/>
             <field name="act_to" ref="prod_act_picking_exception"/>
-            <field name="signal">subflow.cancel</field>
-        </record>
+            <field name="condition">False</field>
+        </record>-->
         <record id="prod_trans_picking_exception_cancel" model="workflow.transition">
             <field name="act_from" ref="prod_act_picking_exception"/>
             <field name="act_to" ref="prod_act_cancel"/>
index dc331f7..7456b85 100644 (file)
@@ -109,7 +109,7 @@ class StockMove(osv.osv):
             for prod in production_obj.browse(cr, uid, production_ids, context=context):
                 if prod.state == 'confirmed':
                     production_obj.force_production(cr, uid, [prod.id])
-            production_obj.signal_button_produce(cr, uid, production_ids)                
+            production_obj.signal_button_produce(cr, uid, production_ids)
             for new_move in new_moves:
                 if new_move == move.id:
                     #This move is already there in move lines of production order
@@ -138,6 +138,15 @@ class StockMove(osv.osv):
         return res
 
 
+    def write(self, cr, uid, ids, vals, context=None):
+        if isinstance(ids, (int, long)):
+            ids = [ids]
+        res = super(StockMove, self).write(cr, uid, ids, vals, context=context)
+        from openerp import workflow
+        for move in self.browse(cr, uid, ids, context=context):
+            if move.production_id and move.production_id.state == 'confirmed':
+                workflow.trg_trigger(uid, 'stock.move', move.production_id.id, cr)
+        return res
 
 class StockPicking(osv.osv):
     _inherit = 'stock.picking'
index acbfea4..f4454c3 100644 (file)
     move = order.move_created_ids[0]
     source_location_id = order.product_id.property_stock_production.id
     assert move.date == order.date_planned, "Planned date is not correspond."
-    assert move.product_id.id == order.product_id.id, "Product is not correspond."
-    assert move.product_uom.id == order.product_uom.id, "UOM is not correspond."
-    assert move.product_qty == order.product_qty, "Qty is not correspond."
-    assert move.product_uos_qty == order.product_uos and order.product_uos_qty or order.product_qty, "UOS qty is not correspond."
+    assert move.product_id.id == order.product_id.id, "Product does not correspond."
+    assert move.product_uom.id == order.product_uom.id, "UOM does not correspond."
+    assert move.product_qty == order.product_qty, "Qty does not correspond."
+    assert move.product_uos_qty == order.product_uos and order.product_uos_qty or order.product_qty, "UOS qty does not correspond."
     if order.product_uos:
-        assert move.product_uos.id == order.product_uos.id, "UOS is not correspond."
-    assert move.location_id.id == source_location_id, "Source Location is not correspond."
-    assert move.location_dest_id.id == order.location_dest_id.id, "Destination Location is not correspond."
+        assert move.product_uos.id == order.product_uos.id, "UOS does not correspond."
+    assert move.location_id.id == source_location_id, "Source Location does not correspond."
+    assert move.location_dest_id.id == order.location_dest_id.id, "Destination Location does not correspond."
     routing_loc = None
     if order.bom_id.routing_id and order.bom_id.routing_id.location_id:
         routing_loc = order.bom_id.routing_id.location_id.id
     date_planned = order.date_planned
     for move_line in order.move_lines:
         for order_line in order.product_lines:
-            if move_line.product_id.type not in ('product', 'consu'):
-                continue
-            if move_line.product_id.id == order_line.product_id.id:
-                assert move_line.date == date_planned, "Planned date is not correspond in 'To consume line'."
-                assert move_line.product_qty == order_line.product_qty, "Qty is not correspond in 'To consume line'."
-                assert move_line.product_uom.id == order_line.product_uom.id, "UOM is not correspond in 'To consume line'."
-                assert move_line.product_uos_qty == order_line.product_uos and order_line.product_uos_qty or order_line.product_qty, "UOS qty is not correspond in 'To consume line'."
-                if order_line.product_uos:
-                    assert move_line.product_uos.id == order_line.product_uos.id, "UOS is not correspond in 'To consume line'."
-                assert move_line.location_id.id == routing_loc or order.location_src_id.id, "Source location is not correspond in 'To consume line'."
-                assert move_line.location_dest_id.id == source_location_id, "Destination Location is not correspond in 'To consume line'."
--
-  I check details of an Internal Shipment after confirmed production order to bring components in Raw Materials Location.
--
-  !python {model: mrp.production}: |
-    procurement = self.pool.get('procurement.order')
-    order = self.browse(cr, uid, ref("mrp_production_test1"))
-    assert order.picking_id, 'Internal Shipment should be created!'
-
-    routing_loc = None
-    pick_type = 'internal'
-    partner_id = False
-    if order.bom_id.routing_id and order.bom_id.routing_id.location_id:
-        routing_loc = order.bom_id.routing_id.location_id
-        if routing_loc.usage != 'internal':
-            pick_type = 'out'
-        partner_id = routing_loc.partner_id and routing_loc.partner_id.id or False
-        routing_loc = routing_loc.id
-    assert order.picking_id.type == pick_type, "Shipment should be Internal."
-    assert order.picking_id.partner_id.id ==  partner_id, "Shipment Address is not correspond with Adderss of Routing Location."
-    date_planned = order.date_planned
-    for move_line in order.picking_id.move_lines:
-        for order_line in order.product_lines:
-            if move_line.product_id.type not in ('product', 'consu'):
-                continue
-            if move_line.product_id.id == order_line.product_id.id:
-                assert move_line.date == date_planned, "Planned date is not correspond."
-                assert move_line.product_qty == order_line.product_qty, "Qty is not correspond."
-                assert move_line.product_uom.id == order_line.product_uom.id, "UOM is not correspond."
-                assert move_line.product_uos_qty == order_line.product_uos and order_line.product_uos_qty or order_line.product_qty, "UOS qty is not correspond."
-                if order_line.product_uos:
-                    assert move_line.product_uos.id == order_line.product_uos.id, "UOS is not correspond."
-                assert move_line.location_id.id == order.location_src_id.id, "Source location is not correspond."
-                assert move_line.location_dest_id.id == routing_loc or order.location_src_id.id, "Destination Location is not correspond."
-                procurement_ids = procurement.search(cr, uid, [('move_id','=',move_line.id)])
-                assert procurement_ids, "Procurement should be created for shipment line of raw materials."
-                shipment_procurement = procurement.browse(cr, uid, procurement_ids[0], context=context)
-                assert shipment_procurement.date_planned == date_planned, "Planned date is not correspond in procurement."
-                assert shipment_procurement.product_id.id == order_line.product_id.id, "Product is not correspond in procurement."
-                assert shipment_procurement.product_qty == order_line.product_qty, "Qty is not correspond in procurement."
-                assert shipment_procurement.product_uom.id == order_line.product_uom.id, "UOM is not correspond in procurement."
-                assert shipment_procurement.product_uos_qty == order_line.product_uos and order_line.product_uos_qty or order_line.product_qty, "UOS qty is not correspond in procurement."
-                if order_line.product_uos:
-                    assert shipment_procurement.product_uos.id == order_line.product_uos.id, "UOS is not correspond in procurement."
-                assert shipment_procurement.location_id.id == order.location_src_id.id, "Location is not correspond in procurement."
-                assert shipment_procurement.procure_method == order_line.product_id.procure_method, "Procure method is not correspond in procurement."
+          if move_line.product_id.type not in ('product', 'consu'):
+            continue
+          if move_line.product_id.id == order_line.product_id.id:
+            assert move_line.date == date_planned, "Planned date does not correspond in 'To consume line'."
+            assert move_line.product_qty == order_line.product_qty, "Qty does not correspond in 'To consume line'."
+            assert move_line.product_uom.id == order_line.product_uom.id, "UOM does not correspond in 'To consume line'."
+            assert move_line.product_uos_qty == order_line.product_uos and order_line.product_uos_qty or order_line.product_qty, "UOS qty is not correspond in 'To consume line'."
+            if order_line.product_uos:
+              assert move_line.product_uos.id == order_line.product_uos.id, "UOS is not correspond in 'To consume line'."
+            assert move_line.location_id.id == routing_loc or order.location_src_id.id, "Source location is not correspond in 'To consume line'."
+            assert move_line.location_dest_id.id == source_location_id, "Destination Location is not correspond in 'To consume line'."
+-
+  I check procurements have been generated for every consume line
+- 
+  !python {model: procurement.order}: |
+    order = self.pool.get("mrp.production").browse(cr, uid, ref("mrp_production_test1"))
+    move_line_ids = [x.id for x in order.move_lines]
+    procurements = self.search(cr, uid, [('move_dest_id', 'in', move_line_ids)])
+    for proc in self.browse(cr, uid, procurements):
+      for order_line in order.product_lines:
+        date_planned = order.date_planned
+        if proc.product_id.type not in ('product', 'consu'):
+          continue
+        if proc.product_id.id == order_line.product_id.id:
+          assert proc.date_planned == date_planned, "Planned date does not correspond"
+          assert proc.product_qty == order_line.product_qty, "Qty does not correspond"
+          assert proc.location_id.id == order.location_src_id.id, "Input location and procurement location do not correspond"
+          assert proc.product_uom.id == order_line.product_uom.id, "UOM does not correspond in procurement."
+          assert proc.product_uos_qty == order_line.product_uos and order_line.product_uos_qty or order_line.product_qty, "UOS qty does not correspond in procurement."
+          if order_line.product_uos:
+            assert proc.product_uos.id == order_line.product_uos.id, "UOS is not correspond in procurement."
 -
   I change production qty with 3 PC Assemble SC349.
 -
   !python {model: procurement.order}: |
     self.run_scheduler(cr, uid)
 -
-  The production order is Waiting Goods, I forcefully done internal shipment.
+  The production order is Waiting Goods, will force production which should set consume lines as available
 -
   !python {model: mrp.production}: |
     self.force_production(cr, uid, [ref("mrp_production_test1")])
 -
-  I check that production order in ready state after forcefully done internal shipment.
+  I check that production order in ready state after forcing production.
 -
   !python {model: mrp.production}: |
     order = self.browse(cr, uid, ref("mrp_production_test1"))
     assert order.state == 'ready', 'Production order should be in Ready State.'
-    assert order.picking_id.state == 'done', 'Internal shipment should be done.'
 -
   Now I start production.
 -
     scrap_location_id = scrap_location_ids[0]
     order = self.browse(cr, uid, ref("mrp_production_test1"))
     for move in order.move_lines:
-        move.action_consume(move.product_qty)
         if move.product_id.id == ref("product.product_product_6"):
             move.action_scrap(5.0, scrap_location_id)
+        move.action_consume(move.product_qty)
+        
 -
   I produce product.
 -
                     raise AssertionError('unknown cost line: %s' % line)
                 assert line.general_account_id.id == wc.costs_general_account_id.id, "General Account is not correspond."
                 assert line.journal_id.id == wc.costs_journal_id.id, "Account Journal is not correspond."
-                assert line.product_id.id == wc.product_id.id, "Product is not correspond."
-                assert line.product_uom_id.id == wc.product_id.uom_id.id, "UOM is not correspond."
+                assert line.product_id.id == wc.product_id.id, "Product does not correspond."
+                assert line.product_uom_id.id == wc.product_id.uom_id.id, "UOM does not correspond."
 -
   I print a "BOM Structure".
 -
     ctx.update({'model': 'mrp.workcenter','active_ids': [ref('mrp_workcenter_0'),ref('mrp_workcenter_1')]})
     data_dict = {'time_unit': 'day', 'measure_unit': 'hours'}
     from openerp.tools import test_reports
-    test_reports.try_report_action(cr, uid, 'action_mrp_workcenter_load_wizard',wiz_data=data_dict, context=ctx, our_module='mrp')
-    
+    test_reports.try_report_action(cr, uid, 'action_mrp_workcenter_load_wizard',wiz_data=data_dict, context=ctx, our_module='mrp')
\ No newline at end of file
index 88e1e99..0f3d0cb 100644 (file)
@@ -90,12 +90,9 @@ class change_production_qty(osv.osv_memory):
                 factor = prod.product_qty * prod.product_uom.factor / bom_point.product_uom.factor
                 product_details, workcenter_details = \
                     bom_obj._bom_explode(cr, uid, bom_point, factor / bom_point.product_qty, [])
-                product_move = dict((mv.product_id.id, mv.id) for mv in prod.picking_id.move_lines)
                 for r in product_details:
                     if r['product_id'] == move.product_id.id:
                         move_obj.write(cr, uid, [move.id], {'product_uom_qty': r['product_qty']})
-                    if r['product_id'] in product_move:
-                        move_obj.write(cr, uid, [product_move[r['product_id']]], {'product_uom_qty': r['product_qty']})
             if prod.move_prod_id:
                 move_obj.write(cr, uid, [prod.move_prod_id.id], {'product_uom_qty' :  wiz_qty.product_qty})
             self._update_product_to_produce(cr, uid, prod, wiz_qty.product_qty, context=context)
index 8699690..41794d6 100644 (file)
@@ -19,7 +19,7 @@
             <field name="name">sent</field>
             <field name="kind">function</field>
             <field name="action">write({'state':'sent'})</field>
-        </record>   
+        </record>
      
         <record id="act_router" model="workflow.activity">
             <field name="wkf_id" ref="wkf_sale"/>