first commit

This commit is contained in:
root
2026-03-14 09:42:12 +00:00
commit 0adbd20c2c
10991 changed files with 1646955 additions and 0 deletions

View File

@@ -0,0 +1,2 @@
# This file is part of Tryton. The COPYRIGHT file at the top level of
# this repository contains the full copyright notices and license terms.

View File

@@ -0,0 +1,116 @@
=================================
Stock Lot Assign Request Scenario
=================================
Imports::
>>> import datetime as dt
>>> from decimal import Decimal
>>> from proteus import Model
>>> from trytond.modules.company.tests.tools import create_company
>>> from trytond.tests.tools import activate_modules
>>> today = dt.date.today()
Activate modules::
>>> config = activate_modules('stock_lot', create_company)
>>> Inventory = Model.get('stock.inventory')
>>> Location = Model.get('stock.location')
>>> Lot = Model.get('stock.lot')
>>> Party = Model.get('party.party')
>>> ProductTemplate = Model.get('product.template')
>>> ProductUom = Model.get('product.uom')
>>> ShipmentOut = Model.get('stock.shipment.out')
Create customer::
>>> customer = Party(name='Customer')
>>> customer.save()
Create product::
>>> unit, = ProductUom.find([('name', '=', 'Unit')])
>>> template = ProductTemplate()
>>> template.name = 'Product'
>>> template.default_uom = unit
>>> template.type = 'goods'
>>> template.list_price = Decimal('20')
>>> template.save()
>>> product, = template.products
Create lot::
>>> lot = Lot()
>>> lot.number = 'LOT'
>>> lot.product = product
>>> lot.save()
Get stock locations::
>>> warehouse_loc, = Location.find([('code', '=', 'WH')])
>>> supplier_loc, = Location.find([('code', '=', 'SUP')])
>>> customer_loc, = Location.find([('code', '=', 'CUS')])
>>> output_loc, = Location.find([('code', '=', 'OUT')])
>>> storage_loc, = Location.find([('code', '=', 'STO')])
>>> zone1 = Location(name='Zone1')
>>> zone1.parent = storage_loc
>>> zone1.type = 'storage'
>>> zone1.save()
>>> zone2, = zone1.duplicate(default={'name': 'Zone2'})
Add product quantities on zones storage locations::
>>> inventory = Inventory()
>>> inventory.location = zone1
>>> inventory_line = inventory.lines.new(product=product)
>>> inventory_line.quantity = 100.0
>>> inventory_line.expected_quantity = 0.0
>>> inventory.click('confirm')
>>> inventory.state
'done'
>>> inventory = Inventory()
>>> inventory.location = zone2
>>> inventory_line = inventory.lines.new()
>>> inventory_line.product = product
>>> inventory_line.lot = lot
>>> inventory_line.quantity = 100.0
>>> inventory_line.expected_quantity = 0.0
>>> inventory.click('confirm')
>>> inventory.state
'done'
Create shipment out::
>>> shipment = ShipmentOut()
>>> shipment.planned_date = today
>>> shipment.customer = customer
>>> shipment.warehouse = warehouse_loc
>>> move = shipment.outgoing_moves.new()
>>> move.product = product
>>> move.unit = unit
>>> move.quantity = 10
>>> move.from_location = output_loc
>>> move.to_location = customer_loc
>>> move.company = shipment.company
>>> move.unit_price = Decimal('1')
>>> move.currency = shipment.company.currency
>>> shipment.click('wait')
Request specific lot in stock assignation::
>>> move, = shipment.inventory_moves
>>> move.lot = lot
>>> move.save()
Assign the shipment::
>>> shipment.click('assign_try')
>>> shipment.state
'assigned'
>>> move, = shipment.inventory_moves
>>> move.from_location.name
'Zone2'

View File

@@ -0,0 +1,74 @@
==================================
Stock Lot Inventory Count Scenario
==================================
Imports::
>>> from proteus import Model
>>> from trytond.modules.company.tests.tools import create_company
>>> from trytond.tests.tools import activate_modules, assertEqual
Activate modules::
>>> config = activate_modules('stock_lot', create_company)
>>> config.skip_warning = True
>>> Inventory = Model.get('stock.inventory')
>>> Location = Model.get('stock.location')
>>> Lot = Model.get('stock.lot')
>>> ProductTemplate = Model.get('product.template')
>>> ProductUom = Model.get('product.uom')
Get stock location::
>>> storage_loc, = Location.find([('code', '=', 'STO')])
Create product and lot::
>>> unit, = ProductUom.find([('name', '=', 'Unit')])
>>> template = ProductTemplate()
>>> template.name = 'Product'
>>> template.default_uom = unit
>>> template.type = 'goods'
>>> template.lot_required = ['storage']
>>> template.save()
>>> product, = template.products
>>> lot = Lot(number="0001", product=product)
>>> lot.save()
Create an inventory::
>>> inventory = Inventory()
>>> inventory.location = storage_loc
>>> inventory.empty_quantity = 'keep'
>>> inventory.save()
Count inventory::
>>> count = inventory.click('do_count')
>>> count.form.search = product
>>> count.execute('quantity')
Traceback (most recent call last):
...
RequiredValidationError: ...
>>> count.form.search = lot
>>> count.execute('quantity')
>>> assertEqual(count.form.product, product)
>>> assertEqual(count.form.lot, lot)
>>> count.form.quantity
1.0
>>> count.form.total_quantity
1.0
>>> count.execute('add')
>>> count.execute('end')
Check inventory::
>>> line, = inventory.lines
>>> assertEqual(line.product, product)
>>> assertEqual(line.lot, lot)
>>> line.quantity
1.0

View File

@@ -0,0 +1,107 @@
===========================
Stock Lot Move Add Scenario
===========================
Imports::
>>> from decimal import Decimal
>>> from proteus import Model
>>> from trytond.modules.company.tests.tools import create_company
>>> from trytond.modules.currency.tests.tools import get_currency
>>> from trytond.tests.tools import activate_modules, assertEqual
Activate modules::
>>> modules = ['stock_lot']
>>> if globals().get('stock_split', False):
... modules.append('stock_split')
>>> config = activate_modules(modules, create_company)
Create product::
>>> ProductUom = Model.get('product.uom')
>>> ProductTemplate = Model.get('product.template')
>>> unit, = ProductUom.find([('name', '=', 'Unit')])
>>> template = ProductTemplate()
>>> template.name = 'Product'
>>> template.default_uom = unit
>>> template.type = 'goods'
>>> template.list_price = Decimal('20')
>>> template.save()
>>> product, = template.products
Get stock locations::
>>> Location = Model.get('stock.location')
>>> storage_loc, = Location.find([('code', '=', 'STO')])
>>> customer_loc, = Location.find([('code', '=', 'CUS')])
Create a move::
>>> Move = Model.get('stock.move')
>>> move = Move()
>>> move.from_location = storage_loc
>>> move.to_location = customer_loc
>>> move.product = product
>>> move.quantity = 10
>>> move.unit_price = Decimal('20')
>>> move.currency = get_currency()
>>> move.save()
Create a lot::
>>> Lot = Model.get('stock.lot')
>>> lot2 = Lot(number='02', product=product)
>>> lot2.save()
Add few lots::
>>> add_lots = move.click('add_lots_wizard')
>>> assertEqual(add_lots.form.product, product)
>>> add_lots.form.quantity
10.0
>>> assertEqual(add_lots.form.unit, unit)
>>> add_lots.form.quantity_remaining
10.0
>>> lot = add_lots.form.lots.new()
>>> lot.quantity
10.0
>>> lot.number = '01'
>>> lot.quantity = 2
>>> lot = add_lots.form.lots.new()
>>> lot.quantity
8.0
>>> lot.number = '02'
>>> lot.quantity = 1
>>> add_lots.execute('add')
Check moves::
>>> move, = Move.find([('lot.number', '=', '01')])
>>> move.quantity
2.0
>>> move, = Move.find([('lot.number', '=', '02')])
>>> move.quantity
1.0
>>> assertEqual(move.lot, lot2)
>>> move, = Move.find([('lot', '=', None)])
>>> move.quantity
7.0
Add lot to remaining::
>>> add_lots = move.click('add_lots_wizard')
>>> lot = add_lots.form.lots.new()
>>> lot.number = '03'
>>> add_lots.execute('add')
>>> len(Move.find([]))
3
>>> move.lot.number
'03'
>>> move.quantity
7.0

View File

@@ -0,0 +1,65 @@
=========================
Stock Lot Number Scenario
=========================
Imports::
>>> from proteus import Model
>>> from trytond.tests.tools import activate_modules, assertEqual
Activate modules::
>>> config = activate_modules('stock_lot')
Create lot sequence::
>>> Sequence = Model.get('ir.sequence')
>>> SequenceType = Model.get('ir.sequence.type')
>>> sequence_type, = SequenceType.find(
... [('name', '=', "Stock Lot")], limit=1)
>>> sequence = Sequence(name="Lot", sequence_type=sequence_type)
>>> sequence.save()
Set default sequence::
>>> Configuration = Model.get('product.configuration')
>>> configuration = Configuration(1)
>>> configuration.default_lot_sequence = sequence
>>> configuration.save()
Create product::
>>> ProductUom = Model.get('product.uom')
>>> ProductTemplate = Model.get('product.template')
>>> unit, = ProductUom.find([('name', '=', 'Unit')])
>>> template = ProductTemplate()
>>> assertEqual(template.lot_sequence, sequence)
>>> template.name = 'Product'
>>> template.default_uom = unit
>>> template.type = 'goods'
>>> template.save()
>>> product, = template.products
Create lot without number::
>>> Lot = Model.get('stock.lot')
>>> lot = Lot(product=product)
>>> lot.save()
>>> lot.number
'1'
Copy set a new number::
>>> lot2, = lot.duplicate()
>>> lot2.number
'2'
Copy without sequence keep same number::
>>> template.lot_sequence = None
>>> template.save()
>>> lot3, = lot.duplicate()
>>> lot3.number
'1'

View File

@@ -0,0 +1,91 @@
==============================
Stock Lot Shipment In Scenario
==============================
Imports::
>>> from decimal import Decimal
>>> from proteus import Model
>>> from trytond.modules.company.tests.tools import create_company
>>> from trytond.tests.tools import activate_modules, assertEqual
Activate modules::
>>> config = activate_modules('stock_lot', create_company)
>>> Location = Model.get('stock.location')
>>> Lot = Model.get('stock.lot')
>>> Party = Model.get('party.party')
>>> ProductTemplate = Model.get('product.template')
>>> ProductUom = Model.get('product.uom')
>>> ShipmentIn = Model.get('stock.shipment.in')
Create supplier::
>>> supplier = Party(name='Supplier')
>>> supplier.save()
Create product::
>>> unit, = ProductUom.find([('name', '=', "Unit")])
>>> template = ProductTemplate()
>>> template.name = "Product"
>>> template.default_uom = unit
>>> template.type = 'goods'
>>> template.list_price = Decimal('20')
>>> template.save()
>>> product, = template.products
Get stock locations::
>>> supplier_loc, = Location.find([('code', '=', 'SUP')])
>>> input_loc, = Location.find([('code', '=', 'IN')])
>>> storage_loc, = Location.find([('code', '=', 'STO')])
Set 2 lots::
>>> lot1 = Lot(number="1", product=product)
>>> lot1.save()
>>> lot2 = Lot(number="2", product=product)
>>> lot2.save()
Create a shipment::
>>> shipment = ShipmentIn()
>>> shipment.supplier = supplier
>>> move = shipment.incoming_moves.new()
>>> move.product = product
>>> move.quantity = 10
>>> move.from_location = supplier_loc
>>> move.to_location = input_loc
>>> move.unit_price = Decimal('5')
>>> move.currency = shipment.company.currency
>>> shipment.save()
Receive the shipment with one lot::
>>> incoming_move, = shipment.incoming_moves
>>> incoming_move.lot = lot1
>>> shipment.click('receive')
>>> shipment.state
'received'
Change lot and try to finish::
>>> incoming_move, = shipment.inventory_moves
>>> assertEqual(incoming_move.lot, lot1)
>>> incoming_move.lot = lot2
>>> shipment.click('do')
Traceback (most recent call last):
...
ShipmentCheckQuantityWarning: ...
>>> incoming_move.reload()
>>> incoming_move.lot = lot1
>>> incoming_move.save()
Finish the shipment::
>>> shipment.click('do')
>>> shipment.state
'done'

View File

@@ -0,0 +1,153 @@
===============================
Stock Lot Shipment Out Scenario
===============================
Imports::
>>> import datetime as dt
>>> from decimal import Decimal
>>> from proteus import Model
>>> from trytond.modules.company.tests.tools import create_company
>>> from trytond.modules.currency.tests.tools import get_currency
>>> from trytond.tests.tools import activate_modules, assertEqual
>>> today = dt.date.today()
Activate modules::
>>> config = activate_modules('stock_lot', create_company)
Create customer::
>>> Party = Model.get('party.party')
>>> customer = Party(name='Customer')
>>> customer.save()
Create product::
>>> ProductUom = Model.get('product.uom')
>>> ProductTemplate = Model.get('product.template')
>>> unit, = ProductUom.find([('name', '=', 'Unit')])
>>> template = ProductTemplate()
>>> template.name = 'Product'
>>> template.default_uom = unit
>>> template.type = 'goods'
>>> template.list_price = Decimal('20')
>>> template.lot_required = ['storage']
>>> template.save()
>>> product, = template.products
Get stock locations::
>>> Location = Model.get('stock.location')
>>> warehouse_loc, = Location.find([('code', '=', 'WH')])
>>> supplier_loc, = Location.find([('code', '=', 'SUP')])
>>> customer_loc, = Location.find([('code', '=', 'CUS')])
>>> output_loc, = Location.find([('code', '=', 'OUT')])
>>> storage_loc, = Location.find([('code', '=', 'STO')])
Create Shipment Out::
>>> ShipmentOut = Model.get('stock.shipment.out')
>>> shipment_out = ShipmentOut()
>>> shipment_out.planned_date = today
>>> shipment_out.customer = customer
>>> shipment_out.warehouse = warehouse_loc
>>> move = shipment_out.outgoing_moves.new()
>>> move.product = product
>>> move.unit = unit
>>> move.quantity = 10
>>> move.from_location = output_loc
>>> move.to_location = customer_loc
>>> move.unit_price = Decimal('1')
>>> move.currency = get_currency()
>>> shipment_out.save()
Set the shipment state to waiting::
>>> shipment_out.click('wait')
>>> len(shipment_out.outgoing_moves)
1
>>> len(shipment_out.inventory_moves)
1
Split inventory move::
>>> move, = shipment_out.inventory_moves
>>> move.quantity = 7
>>> move.save()
>>> with config.set_context(_stock_move_split=True):
... _ = move.duplicate(default=dict(quantity=3))
>>> shipment_out.reload()
Assign the shipment::
>>> shipment_out.click('assign_force')
>>> shipment_out.state
'assigned'
>>> len(shipment_out.outgoing_moves)
1
Check the inventory moves origin::
>>> outgoing_move, = shipment_out.outgoing_moves
>>> for move in shipment_out.inventory_moves:
... assertEqual(move.origin, outgoing_move)
Try to pick without lot::
>>> shipment_out.click('pick')
Traceback (most recent call last):
...
RequiredValidationError: ...
Set 2 lots::
>>> Lot = Model.get('stock.lot')
>>> for i, move in enumerate(shipment_out.inventory_moves, start=1):
... lot = Lot(number='%05i' % i, product=move.product)
... lot.save()
... move.lot = lot
>>> shipment_out.save()
Pick the shipment::
>>> shipment_out.click('pick')
>>> shipment_out.state
'picked'
>>> len(shipment_out.outgoing_moves)
3
>>> sorted([m.quantity for m in shipment_out.outgoing_moves])
[0.0, 3.0, 7.0]
>>> lot_quantities = {}
>>> for move in shipment_out.outgoing_moves:
... number = move.lot.number if move.lot else ''
... quantity = lot_quantities.setdefault(number, 0)
... lot_quantities[number] += move.quantity
>>> sorted(lot_quantities.items())
[('', 0.0), ('00001', 7.0), ('00002', 3.0)]
Check the inventory moves have an outgoing move origin with the same lot::
>>> for move in shipment_out.inventory_moves:
... assertEqual(move.lot, move.origin.lot)
Pack the shipment and return to pick::
>>> shipment_out.click('pack')
>>> shipment_out.state
'packed'
>>> len(shipment_out.outgoing_moves)
2
>>> shipment_out.click('pick')
>>> shipment_out.state
'picked'
>>> len(shipment_out.outgoing_moves)
2
Check the inventory moves still have an outgoing move origin with the same lot::
>>> for move in shipment_out.inventory_moves:
... assertEqual(move.lot, move.origin.lot)

View File

@@ -0,0 +1,133 @@
====================================
Stock Lot Shipment Internal Scenario
====================================
Imports::
>>> import datetime as dt
>>> from decimal import Decimal
>>> from proteus import Model
>>> from trytond.modules.company.tests.tools import create_company
>>> from trytond.tests.tools import activate_modules, assertEqual, assertTrue
>>> today = dt.date.today()
>>> yesterday = today - dt.timedelta(days=1)
>>> tomorrow = today + dt.timedelta(days=1)
Activate modules::
>>> config = activate_modules('stock_lot', create_company)
>>> LeadTime = Model.get('stock.location.lead_time')
>>> Location = Model.get('stock.location')
>>> Lot = Model.get('stock.lot')
>>> ProductTemplate = Model.get('product.template')
>>> ProductUom = Model.get('product.uom')
>>> Shipment = Model.get('stock.shipment.internal')
Create product::
>>> unit, = ProductUom.find([('name', '=', 'Unit')])
>>> template = ProductTemplate()
>>> template.name = "Product"
>>> template.default_uom = unit
>>> template.type = 'goods'
>>> template.list_price = Decimal('20')
>>> template.save()
>>> product, = template.products
Get stock locations::
>>> warehouse1, = Location.find([('type', '=', 'warehouse')])
>>> warehouse2, = warehouse1.duplicate()
Add lead time between warehouses::
>>> lead_time = LeadTime()
>>> lead_time.warehouse_from = warehouse1
>>> lead_time.warehouse_to = warehouse2
>>> lead_time.lead_time = dt.timedelta(1)
>>> lead_time.save()
Create Internal Shipment with lead time::
>>> shipment = Shipment()
>>> shipment.planned_date = tomorrow
>>> shipment.from_location = warehouse1.storage_location
>>> shipment.to_location = warehouse2.storage_location
>>> assertTrue(shipment.transit_location)
>>> assertEqual(shipment.planned_start_date, today)
>>> move = shipment.moves.new()
>>> move.product = product
>>> move.quantity = 3
>>> move.from_location = shipment.from_location
>>> move.to_location = shipment.to_location
>>> shipment.save()
Set the shipment state to waiting::
>>> shipment.click('wait')
>>> shipment.state
'waiting'
>>> len(shipment.outgoing_moves)
1
>>> len(shipment.incoming_moves)
1
Split outgoing moves::
>>> move, = shipment.outgoing_moves
>>> move.quantity = 1
>>> move.save()
>>> with config.set_context(_stock_move_split=True):
... _ = move.duplicate(default=dict(quantity=2))
>>> shipment.reload()
Assign the shipment::
>>> shipment.click('assign_force')
>>> shipment.state
'assigned'
>>> len(shipment.incoming_moves)
1
Check the inventory moves origin::
>>> incoming_move, = shipment.incoming_moves
>>> for move in shipment.outgoing_moves:
... assertEqual(move.origin, incoming_move)
Set 2 lots::
>>> for i, move in enumerate(shipment.outgoing_moves, start=1):
... lot = Lot(number='%05i' % i, product=move.product)
... lot.save()
... move.lot = lot
>>> shipment.save()
Ship the shipment::
>>> shipment.effective_start_date = yesterday
>>> shipment.click('pack')
>>> shipment.click('ship')
>>> shipment.state
'shipped'
>>> len(shipment.incoming_moves)
3
>>> sorted([m.quantity for m in shipment.incoming_moves])
[0.0, 1.0, 2.0]
>>> lot_quantities = {}
>>> for move in shipment.incoming_moves:
... number = move.lot.number if move.lot else ''
... quantity = lot_quantities.setdefault(number, 0)
... lot_quantities[number] += move.quantity
>>> sorted(lot_quantities.items())
[('', 0.0), ('00001', 1.0), ('00002', 2.0)]
Check the outgoing moves have an incoming move origin with the same lot::
>>> for move in shipment.outgoing_moves:
... assertEqual(move.lot, move.origin.lot)

View File

@@ -0,0 +1,80 @@
========================
Stock Lot Trace Scenario
========================
Imports::
>>> from decimal import Decimal
>>> from proteus import Model
>>> from trytond.modules.company.tests.tools import create_company
>>> from trytond.modules.currency.tests.tools import get_currency
>>> from trytond.tests.tools import activate_modules
Activate modules::
>>> config = activate_modules('stock_lot', create_company)
>>> Location = Model.get('stock.location')
>>> Lot = Model.get('stock.lot')
>>> LotTrace = Model.get('stock.lot.trace')
>>> Move = Model.get('stock.move')
>>> ProductTemplate = Model.get('product.template')
>>> UoM = Model.get('product.uom')
Create product::
>>> unit, = UoM.find([('name', '=', "Unit")])
>>> template = ProductTemplate(name="Product")
>>> template.type = 'goods'
>>> template.default_uom = unit
>>> template.save()
>>> product, = template.products
Create lot::
>>> lot = Lot(product=product, number="1")
>>> lot.save()
Get locations::
>>> supplier_loc, = Location.find([('code', '=', 'SUP')])
>>> storage_loc, = Location.find([('code', '=', 'STO')])
>>> customer_loc, = Location.find([('code', '=', 'CUS')])
Make some moves::
>>> move_in = Move(product=product, lot=lot)
>>> move_in.quantity = 10
>>> move_in.from_location = supplier_loc
>>> move_in.to_location = storage_loc
>>> move_in.currency = get_currency()
>>> move_in.unit_price = Decimal('0')
>>> move_in.click('do')
>>> move_in.state
'done'
>>> move_out = Move(product=product, lot=lot)
>>> move_out.quantity = 2
>>> move_out.from_location = storage_loc
>>> move_out.to_location = customer_loc
>>> move_out.currency = get_currency()
>>> move_out.unit_price = Decimal('0')
>>> move_out.click('do')
>>> move_out.state
'done'
Check lot traces::
>>> trace = LotTrace(move_in.id)
>>> trace.upward_traces == [LotTrace(move_out.id)]
True
>>> trace.downward_traces
[]
>>> trace = LotTrace(move_out.id)
>>> trace.upward_traces
[]
>>> trace.downward_traces == [LotTrace(move_in.id)]
True

View File

@@ -0,0 +1,313 @@
# This file is part of Tryton. The COPYRIGHT file at the top level of
# this repository contains the full copyright notices and license terms.
import datetime as dt
from decimal import Decimal
from trytond.modules.company.tests import (
CompanyTestMixin, create_company, set_company)
from trytond.pool import Pool
from trytond.tests.test_tryton import ModuleTestCase, with_transaction
from trytond.transaction import Transaction
class StockLotTestCase(CompanyTestMixin, ModuleTestCase):
'Test Stock Lot module'
module = 'stock_lot'
extras = ['stock_split']
@with_transaction()
def test_products_by_location(self):
'Test products_by_location'
pool = Pool()
Uom = pool.get('product.uom')
Template = pool.get('product.template')
Product = pool.get('product.product')
Location = pool.get('stock.location')
Move = pool.get('stock.move')
Lot = pool.get('stock.lot')
kg, = Uom.search([('name', '=', 'Kilogram')])
g, = Uom.search([('name', '=', 'Gram')])
template, = Template.create([{
'name': 'Test products_by_location',
'type': 'goods',
'default_uom': kg.id,
}])
product, = Product.create([{
'template': template.id,
}])
supplier, = Location.search([('code', '=', 'SUP')])
customer, = Location.search([('code', '=', 'CUS')])
storage, = Location.search([('code', '=', 'STO')])
company = create_company()
currency = company.currency
with set_company(company):
lot1, lot2 = Lot.create([{
'number': '1',
'product': product.id,
}, {
'number': '2',
'product': product.id,
}])
moves = Move.create([{
'product': product.id,
'lot': lot1.id,
'unit': kg.id,
'quantity': 5,
'from_location': supplier.id,
'to_location': storage.id,
'company': company.id,
'unit_price': Decimal('1'),
'currency': currency.id,
}, {
'product': product.id,
'lot': lot2.id,
'unit': kg.id,
'quantity': 10,
'from_location': supplier.id,
'to_location': storage.id,
'company': company.id,
'unit_price': Decimal('1'),
'currency': currency.id,
}, {
'product': product.id,
'lot': lot2.id,
'unit': kg.id,
'quantity': 2,
'from_location': storage.id,
'to_location': customer.id,
'company': company.id,
'unit_price': Decimal('1'),
'currency': currency.id,
}, {
'product': product.id,
'lot': None,
'unit': kg.id,
'quantity': 3,
'from_location': supplier.id,
'to_location': storage.id,
'company': company.id,
'unit_price': Decimal('1'),
'currency': currency.id,
}])
Move.do(moves)
self.assertEqual(Product.products_by_location([storage.id],
grouping_filter=([product.id],)), {
(storage.id, product.id): 16,
})
self.assertEqual(Product.products_by_location([storage.id],
grouping=('product', 'lot',),
grouping_filter=([product.id],)), {
(storage.id, product.id, lot1.id): 5,
(storage.id, product.id, lot2.id): 8,
(storage.id, product.id, None): 3,
})
with Transaction().set_context(locations=[storage.id]):
lot1, lot2 = Lot.browse([lot1, lot2])
self.assertEqual(lot1.quantity, 5)
self.assertEqual(lot2.quantity, 8)
@with_transaction()
def test_period(self):
'Test period'
pool = Pool()
Uom = pool.get('product.uom')
Template = pool.get('product.template')
Product = pool.get('product.product')
Location = pool.get('stock.location')
Move = pool.get('stock.move')
Lot = pool.get('stock.lot')
Period = pool.get('stock.period')
unit, = Uom.search([('name', '=', 'Unit')])
template, = Template.create([{
'name': 'Test period',
'type': 'goods',
'default_uom': unit.id,
}])
product, = Product.create([{
'template': template.id,
}])
supplier, = Location.search([('code', '=', 'SUP')])
storage, = Location.search([('code', '=', 'STO')])
company = create_company()
currency = company.currency
with set_company(company):
lot1, lot2 = Lot.create([{
'number': '1',
'product': product.id,
}, {
'number': '2',
'product': product.id,
}])
today = dt.date.today()
moves = Move.create([{
'product': product.id,
'lot': lot1.id,
'unit': unit.id,
'quantity': 5,
'from_location': supplier.id,
'to_location': storage.id,
'planned_date': today - dt.timedelta(days=1),
'effective_date': today - dt.timedelta(days=1),
'company': company.id,
'unit_price': Decimal('1'),
'currency': currency.id,
}, {
'product': product.id,
'lot': lot2.id,
'unit': unit.id,
'quantity': 10,
'from_location': supplier.id,
'to_location': storage.id,
'planned_date': today - dt.timedelta(days=1),
'effective_date': today - dt.timedelta(days=1),
'company': company.id,
'unit_price': Decimal('1'),
'currency': currency.id,
}, {
'product': product.id,
'lot': None,
'unit': unit.id,
'quantity': 3,
'from_location': supplier.id,
'to_location': storage.id,
'planned_date': today - dt.timedelta(days=1),
'effective_date': today - dt.timedelta(days=1),
'company': company.id,
'unit_price': Decimal('1'),
'currency': currency.id,
}])
Move.do(moves)
period, = Period.create([{
'date': today - dt.timedelta(days=1),
'company': company.id,
}])
Period.close([period])
self.assertEqual(period.state, 'closed')
quantities = {
supplier: -18,
storage: 18,
}
for cache in period.caches:
self.assertEqual(cache.product, product)
self.assertEqual(cache.internal_quantity,
quantities[cache.location])
quantities = {
(supplier, lot1): -5,
(storage, lot1): 5,
(supplier, lot2): -10,
(storage, lot2): 10,
(supplier, None): -3,
(storage, None): 3,
}
for lot_cache in period.lot_caches:
self.assertEqual(lot_cache.product, product)
self.assertEqual(lot_cache.internal_quantity,
quantities[(lot_cache.location, lot_cache.lot)])
@with_transaction()
def test_assign_try_with_lot(self):
"Test Move assign_try with lot"
pool = Pool()
Template = pool.get('product.template')
Product = pool.get('product.product')
Uom = pool.get('product.uom')
Location = pool.get('stock.location')
Move = pool.get('stock.move')
Lot = pool.get('stock.lot')
unit, = Uom.search([('name', '=', 'Meter')])
template = Template(
name="Product",
type='goods',
default_uom=unit,
)
template.save()
product = Product(template=template.id)
product.save()
supplier, = Location.search([('code', '=', 'SUP')])
storage, = Location.search([('code', '=', 'STO')])
customer, = Location.search([('code', '=', 'CUS')])
company = create_company()
with set_company(company):
lot1, lot2 = Lot.create([{
'number': "1",
'product': product.id,
}, {
'number': "2",
'product': product.id,
}])
moves = Move.create([{
'product': product.id,
'lot': lot1.id,
'unit': unit.id,
'quantity': 2,
'from_location': supplier.id,
'to_location': storage.id,
'company': company.id,
'unit_price': Decimal(1),
'currency': company.currency.id,
}, {
'product': product.id,
'lot': lot2.id,
'unit': unit.id,
'quantity': 3,
'from_location': supplier.id,
'to_location': storage.id,
'company': company.id,
'unit_price': Decimal(1),
'currency': company.currency.id,
}, {
'product': product.id,
'lot': None,
'unit': unit.id,
'quantity': 3,
'from_location': supplier.id,
'to_location': storage.id,
'company': company.id,
'unit_price': Decimal(1),
'currency': company.currency.id,
}])
Move.do(moves)
move, = Move.create([{
'product': product.id,
'unit': unit.id,
'quantity': 10,
'from_location': storage.id,
'to_location': customer.id,
'company': company.id,
'unit_price': Decimal(1),
'currency': company.currency.id,
}])
self.assertFalse(
Move.assign_try([move], grouping=('product', 'lot')))
moves = Move.search([
('product', '=', product.id),
('from_location', '=', storage.id),
('to_location', '=', customer.id),
('company', '=', company.id),
])
self.assertEqual(len(moves), 4)
self.assertEqual({
(m.lot, m.quantity, m.state) for m in moves}, {
(lot1, 2, 'assigned'),
(lot2, 3, 'assigned'),
(None, 3, 'assigned'),
(None, 2, 'draft'),
})
del ModuleTestCase

View File

@@ -0,0 +1,8 @@
# This file is part of Tryton. The COPYRIGHT file at the top level of
# this repository contains the full copyright notices and license terms.
from trytond.tests.test_tryton import load_doc_tests
def load_tests(*args, **kwargs):
return load_doc_tests(__name__, __file__, *args, **kwargs)