Adapt to Tryton 5.2
This commit is contained in:
parent
f7d148af03
commit
8af668823e
|
@ -0,0 +1,8 @@
|
||||||
|
<?xml version="1.0"?>
|
||||||
|
<tryton>
|
||||||
|
<data group="1">
|
||||||
|
<record model="ir.message" id="msg_uneven_costs">
|
||||||
|
<field name="text">The costs (%(move_unit_price)s) of the move (%(move)s) does not match the cost (%(lot_unit_price)s) of the lot (%(lot)s).</field>
|
||||||
|
</record>
|
||||||
|
</data>
|
||||||
|
</tryton>
|
|
@ -4,19 +4,20 @@ from decimal import Decimal
|
||||||
from trytond.model import fields
|
from trytond.model import fields
|
||||||
from trytond.pool import Pool, PoolMeta
|
from trytond.pool import Pool, PoolMeta
|
||||||
from trytond.transaction import Transaction
|
from trytond.transaction import Transaction
|
||||||
|
from trytond.exceptions import UserError
|
||||||
|
from trytond.i18n import gettext
|
||||||
|
|
||||||
__all__ = ['BOM', 'Lot', 'Production', 'StockMove']
|
__all__ = ['BOM', 'Lot', 'Production', 'StockMove']
|
||||||
__metaclass__ = PoolMeta
|
|
||||||
|
|
||||||
|
|
||||||
class BOM:
|
class BOM(metaclass=PoolMeta):
|
||||||
__name__ = 'production.bom'
|
__name__ = 'production.bom'
|
||||||
infrastructure_cost = fields.Numeric('Infrastructure Cost',
|
infrastructure_cost = fields.Numeric('Infrastructure Cost',
|
||||||
digits=(16, 4),
|
digits=(16, 4),
|
||||||
help='Infrastructure cost per lot unit')
|
help='Infrastructure cost per lot unit')
|
||||||
|
|
||||||
|
|
||||||
class Lot:
|
class Lot(metaclass=PoolMeta):
|
||||||
__name__ = 'stock.lot'
|
__name__ = 'stock.lot'
|
||||||
|
|
||||||
def _on_change_product_cost_lines(self):
|
def _on_change_product_cost_lines(self):
|
||||||
|
@ -32,7 +33,7 @@ class Lot:
|
||||||
return super(Lot, self)._on_change_product_cost_lines()
|
return super(Lot, self)._on_change_product_cost_lines()
|
||||||
|
|
||||||
|
|
||||||
class Production:
|
class Production(metaclass=PoolMeta):
|
||||||
__name__ = 'production'
|
__name__ = 'production'
|
||||||
|
|
||||||
@property
|
@property
|
||||||
|
@ -52,17 +53,20 @@ class Production:
|
||||||
self.infrastructure_cost)
|
self.infrastructure_cost)
|
||||||
return cost
|
return cost
|
||||||
|
|
||||||
def explode_bom(self):
|
#def explode_bom(self):
|
||||||
super(Production, self).explode_bom()
|
#super(Production, self).explode_bom()
|
||||||
outputs = self.outputs
|
#outputs = self.outputs
|
||||||
for move in outputs:
|
#for move in outputs:
|
||||||
if self.infrastructure_cost and move.product == self.product:
|
#if self.infrastructure_cost and move.product == self.product:
|
||||||
move.unit_price += self.infrastructure_cost
|
#move.unit_price += self.infrastructure_cost
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def done(cls, productions):
|
def set_cost(cls, productions):
|
||||||
super(Production, cls).done(productions)
|
Lot = Pool().get('stock.lot')
|
||||||
|
|
||||||
|
super(Production, cls).set_cost(productions)
|
||||||
|
|
||||||
|
to_save = []
|
||||||
for production in productions:
|
for production in productions:
|
||||||
for output in production.outputs:
|
for output in production.outputs:
|
||||||
if not output.lot:
|
if not output.lot:
|
||||||
|
@ -70,21 +74,14 @@ class Production:
|
||||||
if not output.lot.cost_lines:
|
if not output.lot.cost_lines:
|
||||||
cost_lines = output._get_production_output_lot_cost_lines()
|
cost_lines = output._get_production_output_lot_cost_lines()
|
||||||
output.lot.cost_lines = cost_lines
|
output.lot.cost_lines = cost_lines
|
||||||
output.lot.save()
|
to_save.append(output.lot)
|
||||||
|
if to_save:
|
||||||
|
Lot.save(to_save)
|
||||||
|
|
||||||
|
|
||||||
class StockMove:
|
class StockMove(metaclass=PoolMeta):
|
||||||
__name__ = 'stock.move'
|
__name__ = 'stock.move'
|
||||||
|
|
||||||
@classmethod
|
|
||||||
def __setup__(cls):
|
|
||||||
super(StockMove, cls).__setup__()
|
|
||||||
cls._error_messages.update({
|
|
||||||
'uneven_costs': 'The costs (%(move_unit_price)s) of the move '
|
|
||||||
'(%(move)s) does not match the cost (%(lot_unit_price)s) '
|
|
||||||
'of the lot (%(lot)s).'
|
|
||||||
})
|
|
||||||
|
|
||||||
def check_lot_cost(self, lot):
|
def check_lot_cost(self, lot):
|
||||||
'''
|
'''
|
||||||
If production output quantity is changed manually, it cannot be
|
If production output quantity is changed manually, it cannot be
|
||||||
|
@ -94,12 +91,12 @@ class StockMove:
|
||||||
for cost_line in lot.cost_lines:
|
for cost_line in lot.cost_lines:
|
||||||
lot_cost += cost_line.unit_price
|
lot_cost += cost_line.unit_price
|
||||||
if self.unit_price != lot_cost:
|
if self.unit_price != lot_cost:
|
||||||
self.raise_user_error('uneven_costs', {
|
raise UserError(gettext('production_lot_cost.msg_uneven_costs',
|
||||||
'move': self.rec_name,
|
move=self.rec_name,
|
||||||
'move_unit_price': self.unit_price,
|
move_unit_price=self.unit_price,
|
||||||
'lot': self.lot,
|
lot=self.lot,
|
||||||
'lot_unit_price': lot_cost,
|
lot_unit_price=lot_cost,
|
||||||
})
|
))
|
||||||
|
|
||||||
def get_production_output_lot(self):
|
def get_production_output_lot(self):
|
||||||
lot = super(StockMove, self).get_production_output_lot()
|
lot = super(StockMove, self).get_production_output_lot()
|
||||||
|
@ -136,7 +133,6 @@ class StockMove:
|
||||||
cost_price = input_.product.cost_price
|
cost_price = input_.product.cost_price
|
||||||
cost += (Decimal(str(input_.internal_quantity)) * cost_price)
|
cost += (Decimal(str(input_.internal_quantity)) * cost_price)
|
||||||
|
|
||||||
|
|
||||||
digits = production.__class__.cost.digits
|
digits = production.__class__.cost.digits
|
||||||
cost = cost.quantize(Decimal(str(10 ** -digits[1])))
|
cost = cost.quantize(Decimal(str(10 ** -digits[1])))
|
||||||
|
|
||||||
|
|
4
setup.py
4
setup.py
|
@ -4,7 +4,7 @@
|
||||||
from setuptools import setup
|
from setuptools import setup
|
||||||
import re
|
import re
|
||||||
import os
|
import os
|
||||||
import ConfigParser
|
import configparser
|
||||||
|
|
||||||
MODULE = 'production_lot_cost'
|
MODULE = 'production_lot_cost'
|
||||||
PREFIX = 'nantic'
|
PREFIX = 'nantic'
|
||||||
|
@ -14,7 +14,7 @@ MODULE2PREFIX = {}
|
||||||
def read(fname):
|
def read(fname):
|
||||||
return open(os.path.join(os.path.dirname(__file__), fname)).read()
|
return open(os.path.join(os.path.dirname(__file__), fname)).read()
|
||||||
|
|
||||||
config = ConfigParser.ConfigParser()
|
config = configparser.ConfigParser()
|
||||||
config.readfp(open('tryton.cfg'))
|
config.readfp(open('tryton.cfg'))
|
||||||
info = dict(config.items('tryton'))
|
info = dict(config.items('tryton'))
|
||||||
for key in ('depends', 'extras_depend', 'xml'):
|
for key in ('depends', 'extras_depend', 'xml'):
|
||||||
|
|
|
@ -2,10 +2,6 @@
|
||||||
Production Lot Cost Scenario
|
Production Lot Cost Scenario
|
||||||
============================
|
============================
|
||||||
|
|
||||||
=============
|
|
||||||
General Setup
|
|
||||||
=============
|
|
||||||
|
|
||||||
Imports::
|
Imports::
|
||||||
|
|
||||||
>>> import datetime
|
>>> import datetime
|
||||||
|
@ -126,9 +122,9 @@ Create an Inventory::
|
||||||
>>> inventory_line2.product = component2
|
>>> inventory_line2.product = component2
|
||||||
>>> inventory_line2.quantity = 10
|
>>> inventory_line2.quantity = 10
|
||||||
>>> inventory.save()
|
>>> inventory.save()
|
||||||
>>> Inventory.confirm([inventory.id], config.context)
|
>>> inventory.click('confirm')
|
||||||
>>> inventory.state
|
>>> inventory.state
|
||||||
u'done'
|
'done'
|
||||||
|
|
||||||
Create a production of product::
|
Create a production of product::
|
||||||
|
|
||||||
|
@ -142,9 +138,16 @@ Create a production of product::
|
||||||
>>> output, = production.outputs
|
>>> output, = production.outputs
|
||||||
>>> output.quantity == 2
|
>>> output.quantity == 2
|
||||||
True
|
True
|
||||||
|
>>> production.click('wait')
|
||||||
|
>>> production.click('assign_force')
|
||||||
|
>>> production.click('run')
|
||||||
|
>>> production.click('done')
|
||||||
|
>>> production.state
|
||||||
|
'done'
|
||||||
>>> production.cost == Decimal('25')
|
>>> production.cost == Decimal('25')
|
||||||
True
|
True
|
||||||
>>> output.unit_price
|
>>> output.reload()
|
||||||
|
>>> output.unit_price, production.outputs, output.state
|
||||||
Decimal('12.5000')
|
Decimal('12.5000')
|
||||||
>>> production.save()
|
>>> production.save()
|
||||||
|
|
||||||
|
@ -165,7 +168,7 @@ Make the production::
|
||||||
|
|
||||||
>>> Production.wait([production.id], config.context)
|
>>> Production.wait([production.id], config.context)
|
||||||
>>> production.state
|
>>> production.state
|
||||||
u'waiting'
|
'waiting'
|
||||||
>>> Production.assign_try([production.id], config.context)
|
>>> Production.assign_try([production.id], config.context)
|
||||||
True
|
True
|
||||||
>>> production.reload()
|
>>> production.reload()
|
||||||
|
@ -179,7 +182,7 @@ Make the production::
|
||||||
>>> production.reload()
|
>>> production.reload()
|
||||||
>>> output, = production.outputs
|
>>> output, = production.outputs
|
||||||
>>> output.state
|
>>> output.state
|
||||||
u'done'
|
'done'
|
||||||
>>> output.lot.cost_price == Decimal('12.5')
|
>>> output.lot.cost_price == Decimal('12.5')
|
||||||
True
|
True
|
||||||
|
|
||||||
|
@ -213,7 +216,7 @@ Make a production with infrastructure cost::
|
||||||
>>> del config._context['from_move']
|
>>> del config._context['from_move']
|
||||||
>>> Production.wait([production.id], config.context)
|
>>> Production.wait([production.id], config.context)
|
||||||
>>> production.state
|
>>> production.state
|
||||||
u'waiting'
|
'waiting'
|
||||||
>>> Production.assign_try([production.id], config.context)
|
>>> Production.assign_try([production.id], config.context)
|
||||||
True
|
True
|
||||||
>>> production.reload()
|
>>> production.reload()
|
||||||
|
@ -227,7 +230,7 @@ Make a production with infrastructure cost::
|
||||||
>>> production.reload()
|
>>> production.reload()
|
||||||
>>> output, = production.outputs
|
>>> output, = production.outputs
|
||||||
>>> output.state
|
>>> output.state
|
||||||
u'done'
|
'done'
|
||||||
>>> len(output.lot.cost_lines)
|
>>> len(output.lot.cost_lines)
|
||||||
2
|
2
|
||||||
>>> output.lot.cost_price
|
>>> output.lot.cost_price
|
||||||
|
|
|
@ -146,7 +146,7 @@ Create an Inventory::
|
||||||
>>> inventory.save()
|
>>> inventory.save()
|
||||||
>>> Inventory.confirm([inventory.id], config.context)
|
>>> Inventory.confirm([inventory.id], config.context)
|
||||||
>>> inventory.state
|
>>> inventory.state
|
||||||
u'done'
|
'done'
|
||||||
|
|
||||||
Configure production to automatically create lots on running state::
|
Configure production to automatically create lots on running state::
|
||||||
|
|
||||||
|
@ -169,14 +169,18 @@ production is Running::
|
||||||
>>> output, = production.outputs
|
>>> output, = production.outputs
|
||||||
>>> output.quantity == 2
|
>>> output.quantity == 2
|
||||||
True
|
True
|
||||||
>>> production.cost == Decimal('25')
|
>>> production.click('wait')
|
||||||
|
>>> production.click('assign_force')
|
||||||
|
>>> production.click('run')
|
||||||
|
>>> production.click('done')
|
||||||
|
>>> production.cost == Decimal('25'), production.cost
|
||||||
True
|
True
|
||||||
>>> output.unit_price
|
>>> output.unit_price
|
||||||
Decimal('13.5000')
|
Decimal('13.5000')
|
||||||
>>> production.save()
|
>>> production.save()
|
||||||
>>> Production.wait([production.id], config.context)
|
>>> Production.wait([production.id], config.context)
|
||||||
>>> production.state
|
>>> production.state
|
||||||
u'waiting'
|
'waiting'
|
||||||
>>> Production.assign_try([production.id], config.context)
|
>>> Production.assign_try([production.id], config.context)
|
||||||
True
|
True
|
||||||
>>> production.reload()
|
>>> production.reload()
|
||||||
|
@ -194,7 +198,7 @@ production is Running::
|
||||||
>>> production.reload()
|
>>> production.reload()
|
||||||
>>> output, = production.outputs
|
>>> output, = production.outputs
|
||||||
>>> output.state
|
>>> output.state
|
||||||
u'done'
|
'done'
|
||||||
>>> len(output.lot.cost_lines)
|
>>> len(output.lot.cost_lines)
|
||||||
2
|
2
|
||||||
>>> output.lot.cost_price == Decimal('13.5')
|
>>> output.lot.cost_price == Decimal('13.5')
|
||||||
|
@ -224,7 +228,7 @@ production is done::
|
||||||
>>> production.save()
|
>>> production.save()
|
||||||
>>> Production.wait([production.id], config.context)
|
>>> Production.wait([production.id], config.context)
|
||||||
>>> production.state
|
>>> production.state
|
||||||
u'waiting'
|
'waiting'
|
||||||
>>> Production.assign_try([production.id], config.context)
|
>>> Production.assign_try([production.id], config.context)
|
||||||
True
|
True
|
||||||
>>> production.reload()
|
>>> production.reload()
|
||||||
|
@ -240,7 +244,7 @@ production is done::
|
||||||
>>> production.reload()
|
>>> production.reload()
|
||||||
>>> output, = production.outputs
|
>>> output, = production.outputs
|
||||||
>>> output.state
|
>>> output.state
|
||||||
u'done'
|
'done'
|
||||||
>>> output.lot != None
|
>>> output.lot != None
|
||||||
True
|
True
|
||||||
>>> len(output.lot.cost_lines)
|
>>> len(output.lot.cost_lines)
|
||||||
|
|
|
@ -7,3 +7,4 @@ extras_depend:
|
||||||
production_output_lot
|
production_output_lot
|
||||||
xml:
|
xml:
|
||||||
production.xml
|
production.xml
|
||||||
|
message.xml
|
||||||
|
|
Loading…
Reference in New Issue