2010-02-19 10:51:45 +00:00
# -*- coding: utf-8 -*-
##############################################################################
2010-06-13 22:35:25 +00:00
#
2010-02-19 10:51:45 +00:00
# OpenERP, Open Source Management Solution
# Copyright (C) 2004-2010 Tiny SPRL (<http://tiny.be>).
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
# published by the Free Software Foundation, either version 3 of the
# License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
2010-06-13 22:35:25 +00:00
# along with this program. If not, see <http://www.gnu.org/licenses/>.
2010-02-19 10:51:45 +00:00
#
##############################################################################
from osv import fields , osv
2011-03-09 12:24:21 +00:00
import decimal_precision as dp
2010-02-19 10:51:45 +00:00
class stock_move_track ( osv . osv_memory ) :
_name = " stock.move.track "
_description = " Track moves "
2010-06-13 22:35:25 +00:00
2010-02-19 10:51:45 +00:00
_columns = {
2010-06-13 22:35:25 +00:00
' tracking_prefix ' : fields . char ( ' Tracking prefix ' , size = 64 ) ,
2010-02-19 10:51:45 +00:00
' quantity ' : fields . float ( " Quantity per lot " )
2010-05-26 12:59:30 +00:00
}
2010-02-19 10:51:45 +00:00
_defaults = {
' quantity ' : lambda * x : 1
2010-05-26 12:59:30 +00:00
}
2010-06-13 22:35:25 +00:00
2010-11-22 10:37:53 +00:00
def track_lines ( self , cr , uid , ids , context = None ) :
2010-05-26 12:59:30 +00:00
""" To track stock moves lines
@param self : The object pointer .
@param cr : A database cursor
@param uid : ID of the user currently logged in
2010-06-13 22:35:25 +00:00
@param ids : An ID or list of IDs if we want more than one
@param context : A standard dictionary
@return :
"""
2010-02-19 10:51:45 +00:00
datas = self . read ( cr , uid , ids ) [ 0 ]
move_obj = self . pool . get ( ' stock.move ' )
move_obj . _track_lines ( cr , uid , context [ ' active_id ' ] , datas , context = context )
2010-12-28 10:41:38 +00:00
return { ' type ' : ' ir.actions.act_window_close ' }
2010-02-19 10:51:45 +00:00
stock_move_track ( )
class stock_move_consume ( osv . osv_memory ) :
_name = " stock.move.consume "
_description = " Consume Products "
2010-06-13 22:35:25 +00:00
2010-02-19 10:51:45 +00:00
_columns = {
2010-06-13 22:35:25 +00:00
' product_id ' : fields . many2one ( ' product.product ' , ' Product ' , required = True , select = True ) ,
' product_qty ' : fields . float ( ' Quantity ' , required = True ) ,
' product_uom ' : fields . many2one ( ' product.uom ' , ' Product UOM ' , required = True ) ,
2010-02-23 05:34:00 +00:00
' location_id ' : fields . many2one ( ' stock.location ' , ' Location ' , required = True )
2010-03-17 07:56:05 +00:00
}
2010-02-19 10:51:45 +00:00
2010-03-22 12:16:37 +00:00
def default_get ( self , cr , uid , fields , context = None ) :
2010-05-26 12:59:30 +00:00
""" Get default values
@param self : The object pointer .
@param cr : A database cursor
@param uid : ID of the user currently logged in
2010-06-13 22:35:25 +00:00
@param fields : List of fields for default value
@param context : A standard dictionary
2010-05-26 12:59:30 +00:00
@return : default values of fields
2010-03-16 06:46:43 +00:00
"""
2010-11-23 07:05:05 +00:00
if context is None :
2010-11-22 10:37:53 +00:00
context = { }
2010-06-13 22:35:25 +00:00
res = super ( stock_move_consume , self ) . default_get ( cr , uid , fields , context = context )
2010-02-19 10:51:45 +00:00
move = self . pool . get ( ' stock.move ' ) . browse ( cr , uid , context [ ' active_id ' ] , context = context )
2010-03-19 07:20:12 +00:00
if ' product_id ' in fields :
2010-06-13 22:35:25 +00:00
res . update ( { ' product_id ' : move . product_id . id } )
2010-03-19 07:20:12 +00:00
if ' product_uom ' in fields :
2010-06-13 22:35:25 +00:00
res . update ( { ' product_uom ' : move . product_uom . id } )
2010-03-19 07:20:12 +00:00
if ' product_qty ' in fields :
2010-05-04 11:14:19 +00:00
res . update ( { ' product_qty ' : move . product_qty } )
if ' location_id ' in fields :
res . update ( { ' location_id ' : move . location_id . id } )
2010-06-13 22:35:25 +00:00
return res
2010-11-22 10:37:53 +00:00
def do_move_consume ( self , cr , uid , ids , context = None ) :
2010-05-26 12:59:30 +00:00
""" To move consumed products
@param self : The object pointer .
@param cr : A database cursor
@param uid : ID of the user currently logged in
2010-06-13 22:35:25 +00:00
@param ids : the ID or list of IDs if we want more than one
@param context : A standard dictionary
@return :
"""
2010-11-23 07:05:05 +00:00
if context is None :
2010-11-22 10:37:53 +00:00
context = { }
2010-02-19 10:51:45 +00:00
move_obj = self . pool . get ( ' stock.move ' )
2010-02-23 05:34:00 +00:00
move_ids = context [ ' active_ids ' ]
2011-03-15 15:03:48 +00:00
for data in self . browse ( cr , uid , ids , context = context ) :
2010-06-13 22:35:25 +00:00
move_obj . action_consume ( cr , uid , move_ids ,
2011-03-15 15:03:48 +00:00
data . product_qty , data . location_id . id ,
2010-02-23 05:34:00 +00:00
context = context )
2010-12-28 10:41:38 +00:00
return { ' type ' : ' ir.actions.act_window_close ' }
2010-02-19 10:51:45 +00:00
stock_move_consume ( )
class stock_move_scrap ( osv . osv_memory ) :
_name = " stock.move.scrap "
_description = " Scrap Products "
_inherit = " stock.move.consume "
2010-06-13 22:35:25 +00:00
2010-02-19 10:51:45 +00:00
_defaults = {
2010-05-04 11:14:19 +00:00
' location_id ' : lambda * x : False
2010-02-23 05:34:00 +00:00
}
2010-02-19 10:51:45 +00:00
2010-05-04 11:14:19 +00:00
def default_get ( self , cr , uid , fields , context = None ) :
2010-05-26 12:59:30 +00:00
""" Get default values
@param self : The object pointer .
@param cr : A database cursor
@param uid : ID of the user currently logged in
2010-06-13 22:35:25 +00:00
@param fields : List of fields for default value
@param context : A standard dictionary
2010-05-26 12:59:30 +00:00
@return : default values of fields
2010-05-04 11:14:19 +00:00
"""
2010-11-23 07:05:05 +00:00
if context is None :
2010-11-22 10:37:53 +00:00
context = { }
2010-06-13 22:35:25 +00:00
res = super ( stock_move_consume , self ) . default_get ( cr , uid , fields , context = context )
2010-05-04 11:14:19 +00:00
move = self . pool . get ( ' stock.move ' ) . browse ( cr , uid , context [ ' active_id ' ] , context = context )
location_obj = self . pool . get ( ' stock.location ' )
2010-05-06 12:16:04 +00:00
scrpaed_location_ids = location_obj . search ( cr , uid , [ ( ' scrap_location ' , ' = ' , True ) ] )
2010-06-13 22:35:25 +00:00
2010-05-04 11:14:19 +00:00
if ' product_id ' in fields :
2010-06-13 22:35:25 +00:00
res . update ( { ' product_id ' : move . product_id . id } )
2010-05-04 11:14:19 +00:00
if ' product_uom ' in fields :
2010-06-13 22:35:25 +00:00
res . update ( { ' product_uom ' : move . product_uom . id } )
2010-05-04 11:14:19 +00:00
if ' product_qty ' in fields :
res . update ( { ' product_qty ' : move . product_qty } )
if ' location_id ' in fields :
if scrpaed_location_ids :
res . update ( { ' location_id ' : scrpaed_location_ids [ 0 ] } )
else :
res . update ( { ' location_id ' : False } )
2010-06-13 22:35:25 +00:00
2010-05-04 11:14:19 +00:00
return res
2010-06-13 22:35:25 +00:00
2010-11-22 10:37:53 +00:00
def move_scrap ( self , cr , uid , ids , context = None ) :
2010-08-31 06:54:27 +00:00
""" To move scrapped products
2010-05-26 12:59:30 +00:00
@param self : The object pointer .
@param cr : A database cursor
@param uid : ID of the user currently logged in
2010-06-13 22:35:25 +00:00
@param ids : the ID or list of IDs if we want more than one
@param context : A standard dictionary
@return :
"""
2010-11-23 07:05:05 +00:00
if context is None :
2010-11-22 10:37:53 +00:00
context = { }
2010-06-13 22:35:25 +00:00
move_obj = self . pool . get ( ' stock.move ' )
2010-02-23 05:34:00 +00:00
move_ids = context [ ' active_ids ' ]
2011-03-24 13:23:58 +00:00
for data in self . browse ( cr , uid , ids ) :
2010-06-13 22:35:25 +00:00
move_obj . action_scrap ( cr , uid , move_ids ,
2011-03-24 13:23:58 +00:00
data . product_qty , data . location_id . id ,
2010-02-23 05:34:00 +00:00
context = context )
2010-12-28 10:41:38 +00:00
return { ' type ' : ' ir.actions.act_window_close ' }
2010-02-19 10:51:45 +00:00
2010-02-19 13:44:55 +00:00
stock_move_scrap ( )
2010-03-05 10:08:13 +00:00
class split_in_production_lot ( osv . osv_memory ) :
_name = " stock.move.split "
2010-02-23 05:34:00 +00:00
_description = " Split in Production lots "
2010-06-13 22:35:25 +00:00
2010-03-22 12:16:37 +00:00
def default_get ( self , cr , uid , fields , context = None ) :
2010-05-26 12:59:30 +00:00
""" Get default values
@param self : The object pointer .
@param cr : A database cursor
@param uid : ID of the user currently logged in
2010-06-13 22:35:25 +00:00
@param fields : List of fields for default value
@param context : A standard dictionary
2010-05-26 12:59:30 +00:00
@return : Default values of fields
2010-03-19 07:20:12 +00:00
"""
2010-11-23 07:05:05 +00:00
if context is None :
2010-11-22 10:37:53 +00:00
context = { }
2010-06-13 22:35:25 +00:00
res = super ( split_in_production_lot , self ) . default_get ( cr , uid , fields , context = context )
2010-06-18 09:53:21 +00:00
if context . get ( ' active_id ' ) :
move = self . pool . get ( ' stock.move ' ) . browse ( cr , uid , context [ ' active_id ' ] , context = context )
if ' product_id ' in fields :
res . update ( { ' product_id ' : move . product_id . id } )
if ' product_uom ' in fields :
res . update ( { ' product_uom ' : move . product_uom . id } )
if ' qty ' in fields :
res . update ( { ' qty ' : move . product_qty } )
if ' use_exist ' in fields :
res . update ( { ' use_exist ' : ( move . picking_id and move . picking_id . type == ' out ' and True ) or False } )
2010-03-19 07:20:12 +00:00
return res
2010-06-13 22:35:25 +00:00
2010-02-19 13:44:55 +00:00
_columns = {
2011-03-09 12:24:21 +00:00
' qty ' : fields . float ( ' Quantity ' , digits_compute = dp . get_precision ( ' Product UoM ' ) ) ,
2010-02-19 13:44:55 +00:00
' product_id ' : fields . many2one ( ' product.product ' , ' Product ' , required = True , select = True ) ,
2010-09-06 11:48:17 +00:00
' product_uom ' : fields . many2one ( ' product.uom ' , ' UoM ' ) ,
' line_ids ' : fields . one2many ( ' stock.move.split.lines ' , ' lot_id ' , ' Production Lots ' ) ,
' line_exist_ids ' : fields . one2many ( ' stock.move.split.lines.exist ' , ' lot_id ' , ' Production Lots ' ) ,
' use_exist ' : fields . boolean ( ' Existing Lots ' , help = " Check this option to select existing lots in the list below, otherwise you should enter new ones line by line. " ) ,
2010-02-23 05:34:00 +00:00
}
2010-06-13 22:35:25 +00:00
2010-02-19 13:44:55 +00:00
def split_lot ( self , cr , uid , ids , context = None ) :
2010-05-26 12:59:30 +00:00
""" To split a lot
@param self : The object pointer .
@param cr : A database cursor
@param uid : ID of the user currently logged in
2010-06-13 22:35:25 +00:00
@param ids : An ID or list of IDs if we want more than one
@param context : A standard dictionary
@return :
"""
2010-11-23 07:05:05 +00:00
if context is None :
2010-11-22 10:37:53 +00:00
context = { }
2010-02-23 05:34:00 +00:00
self . split ( cr , uid , ids , context . get ( ' active_ids ' ) , context = context )
2010-12-28 10:41:38 +00:00
return { ' type ' : ' ir.actions.act_window_close ' }
2010-02-19 13:44:55 +00:00
2010-02-23 05:34:00 +00:00
def split ( self , cr , uid , ids , move_ids , context = None ) :
2010-05-26 12:59:30 +00:00
""" To split stock moves into production lot
@param self : The object pointer .
@param cr : A database cursor
@param uid : ID of the user currently logged in
2010-06-13 22:35:25 +00:00
@param ids : the ID or list of IDs if we want more than one
2010-05-26 12:59:30 +00:00
@param move_ids : the ID or list of IDs of stock move we want to split
2010-06-13 22:35:25 +00:00
@param context : A standard dictionary
@return :
"""
2010-11-19 14:21:59 +00:00
if context is None :
context = { }
2010-11-22 10:53:10 +00:00
inventory_id = context . get ( ' inventory_id ' , False )
2010-02-23 05:34:00 +00:00
prodlot_obj = self . pool . get ( ' stock.production.lot ' )
2010-11-19 14:21:59 +00:00
inventory_obj = self . pool . get ( ' stock.inventory ' )
2010-02-23 05:34:00 +00:00
move_obj = self . pool . get ( ' stock.move ' )
2010-06-13 22:35:25 +00:00
new_move = [ ]
2010-11-22 10:37:53 +00:00
for data in self . browse ( cr , uid , ids , context = context ) :
for move in move_obj . browse ( cr , uid , move_ids , context = context ) :
2010-02-23 05:34:00 +00:00
move_qty = move . product_qty
quantity_rest = move . product_qty
uos_qty_rest = move . product_uos_qty
2010-06-13 22:35:25 +00:00
new_move = [ ]
2010-06-10 08:59:12 +00:00
if data . use_exist :
lines = [ l for l in data . line_exist_ids if l ]
else :
lines = [ l for l in data . line_ids if l ]
for line in lines :
2010-02-23 05:34:00 +00:00
quantity = line . quantity
if quantity < = 0 or move_qty == 0 :
continue
quantity_rest - = quantity
uos_qty = quantity / move_qty * move . product_uos_qty
uos_qty_rest = quantity_rest / move_qty * move . product_uos_qty
2010-06-07 14:26:20 +00:00
if quantity_rest < 0 :
2010-02-23 05:34:00 +00:00
quantity_rest = quantity
break
default_val = {
2010-06-13 22:35:25 +00:00
' product_qty ' : quantity ,
' product_uos_qty ' : uos_qty ,
2010-06-14 11:49:11 +00:00
' state ' : move . state
2010-02-23 05:34:00 +00:00
}
2010-06-07 14:26:20 +00:00
if quantity_rest > 0 :
2010-11-24 10:50:29 +00:00
current_move = move_obj . copy ( cr , uid , move . id , default_val , context = context )
2010-11-24 11:27:43 +00:00
if inventory_id and current_move :
inventory_obj . write ( cr , uid , inventory_id , { ' move_ids ' : [ ( 4 , current_move ) ] } , context = context )
2010-06-07 14:26:20 +00:00
new_move . append ( current_move )
2010-11-19 14:21:59 +00:00
2010-06-07 14:26:20 +00:00
if quantity_rest == 0 :
current_move = move . id
2010-02-23 05:34:00 +00:00
prodlot_id = False
2010-06-21 18:40:58 +00:00
if data . use_exist :
prodlot_id = line . prodlot_id . id
2010-02-23 05:34:00 +00:00
if not prodlot_id :
2010-06-21 18:40:58 +00:00
prodlot_id = prodlot_obj . create ( cr , uid , {
' name ' : line . name ,
' product_id ' : move . product_id . id } ,
context = context )
2010-11-19 14:21:59 +00:00
2010-06-15 20:20:04 +00:00
move_obj . write ( cr , uid , [ current_move ] , { ' prodlot_id ' : prodlot_id , ' state ' : move . state } )
2010-06-13 22:35:25 +00:00
2010-02-23 05:34:00 +00:00
update_val = { }
2010-06-13 22:35:25 +00:00
if quantity_rest > 0 :
2010-02-23 05:34:00 +00:00
update_val [ ' product_qty ' ] = quantity_rest
2010-06-13 22:35:25 +00:00
update_val [ ' product_uos_qty ' ] = uos_qty_rest
2010-06-15 20:20:04 +00:00
update_val [ ' state ' ] = move . state
2010-02-23 05:34:00 +00:00
move_obj . write ( cr , uid , [ move . id ] , update_val )
2010-11-19 14:21:59 +00:00
2010-02-23 05:34:00 +00:00
return new_move
2010-11-24 10:50:29 +00:00
2010-03-05 10:08:13 +00:00
split_in_production_lot ( )
2010-02-23 05:34:00 +00:00
2010-06-10 08:59:12 +00:00
class stock_move_split_lines_exist ( osv . osv_memory ) :
_name = " stock.move.split.lines.exist "
_description = " Exist Split lines "
_columns = {
2010-06-13 22:35:25 +00:00
' name ' : fields . char ( ' Tracking serial ' , size = 64 ) ,
2011-03-09 12:24:21 +00:00
' quantity ' : fields . float ( ' Quantity ' , digits_compute = dp . get_precision ( ' Product UoM ' ) ) ,
2010-06-10 08:59:12 +00:00
' lot_id ' : fields . many2one ( ' stock.move.split ' , ' Lot ' ) ,
' prodlot_id ' : fields . many2one ( ' stock.production.lot ' , ' Production Lot ' ) ,
}
_defaults = {
2011-05-02 18:46:43 +00:00
' quantity ' : 1.0 ,
2010-06-10 08:59:12 +00:00
}
stock_move_split_lines_exist ( )
2010-03-05 10:08:13 +00:00
class stock_move_split_lines ( osv . osv_memory ) :
_name = " stock.move.split.lines "
2010-02-23 05:34:00 +00:00
_description = " Split lines "
2010-02-19 13:44:55 +00:00
_columns = {
2010-06-13 22:35:25 +00:00
' name ' : fields . char ( ' Tracking serial ' , size = 64 ) ,
2011-03-09 12:24:21 +00:00
' quantity ' : fields . float ( ' Quantity ' , digits_compute = dp . get_precision ( ' Product UoM ' ) ) ,
2010-06-26 15:15:23 +00:00
' use_exist ' : fields . boolean ( ' Existing Lot ' ) ,
2010-03-05 10:08:13 +00:00
' lot_id ' : fields . many2one ( ' stock.move.split ' , ' Lot ' ) ,
2010-02-23 05:34:00 +00:00
' action ' : fields . selection ( [ ( ' split ' , ' Split ' ) , ( ' keepinone ' , ' Keep in one lot ' ) ] , ' Action ' ) ,
}
_defaults = {
2011-05-02 18:46:43 +00:00
' quantity ' : 1.00 ,
' action ' : ' split ' ,
2010-02-23 05:34:00 +00:00
}
2010-03-05 10:08:13 +00:00
stock_move_split_lines ( )