Commit f7c814f1 authored by Jérome Perrin's avatar Jérome Perrin

more and more interpolation API

parent 89c5db3e
......@@ -818,27 +818,30 @@ class TestInventory(InventoryAPITestCase):
def test_interpolation_method_linear_to_date(self):
self._makeMovement(
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
)
# With a time frame that does not contain the movement, we have 0%
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/02/01 00:00:00"),
to_date=DateTime("2016/02/02 00:00:00"),
interpolation_method='linear')
# With a time frame that contains the full movement, we have 100% of the quantity
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
to_date=DateTime("2016/01/02 00:00:00"),
interpolation_method='linear')
# corner case: exact same time, we also have 100%
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
to_date=DateTime("2016/01/01 11:00:00"),
......@@ -847,35 +850,40 @@ class TestInventory(InventoryAPITestCase):
# With a time frame containing the 50% of the movement, we have 50% of the quantity
# time frame start before movement
self.assertInventoryEquals(5,
self.assertInventoryEquals(
5,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
to_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='linear')
# time frame start at exact same time as movement
self.assertInventoryEquals(5,
self.assertInventoryEquals(
5,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
to_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='linear')
# Time frame is contained inside the movement
self.assertInventoryEquals(5,
self.assertInventoryEquals(
5,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 02:00:00"),
to_date=DateTime("2016/01/01 07:00:00"),
interpolation_method='linear')
# Time frame finishes after movement end
self.assertInventoryEquals(5,
self.assertInventoryEquals(
5,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
to_date=DateTime("2016/01/01 12:00:00"),
interpolation_method='linear')
# Time frame finishes at exact same time that movement end
self.assertInventoryEquals(5,
self.assertInventoryEquals(
5,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
to_date=DateTime("2016/01/01 11:00:00"),
......@@ -883,27 +891,30 @@ class TestInventory(InventoryAPITestCase):
def test_interpolation_method_linear_at_date(self):
self._makeMovement(
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
)
# With a time frame that does not contain the movement, we have 0%
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/02/01 00:00:00"),
at_date=DateTime("2016/02/02 00:00:00"),
interpolation_method='linear')
# With a time frame that contains the full movement, we have 100% of the quantity
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
at_date=DateTime("2016/01/02 00:00:00"),
interpolation_method='linear')
# corner case: exact same time, we also have 100%
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
at_date=DateTime("2016/01/01 11:00:00"),
......@@ -912,35 +923,40 @@ class TestInventory(InventoryAPITestCase):
# With a time frame containing the 50% of the movement, we have 50% of the quantity
# time frame start before movement
self.assertInventoryEquals(5,
self.assertInventoryEquals(
5,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
at_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='linear')
# time frame start at exact same time as movement
self.assertInventoryEquals(5,
self.assertInventoryEquals(
5,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
at_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='linear')
# Time frame is contained inside the movement
self.assertInventoryEquals(5,
self.assertInventoryEquals(
5,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 02:00:00"),
at_date=DateTime("2016/01/01 07:00:00"),
interpolation_method='linear')
# Time frame finishes after movement end
self.assertInventoryEquals(5,
self.assertInventoryEquals(
5,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
at_date=DateTime("2016/01/01 12:00:00"),
interpolation_method='linear')
# Time frame finishes at exact same time that movement end
self.assertInventoryEquals(5,
self.assertInventoryEquals(
5,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
at_date=DateTime("2016/01/01 11:00:00"),
......@@ -948,27 +964,30 @@ class TestInventory(InventoryAPITestCase):
def test_interpolation_method_XXX_one_for_all_to_date(self):
self._makeMovement(
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
)
# With a time frame that does not contain the movement, we have 0%
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/02/01 00:00:00"),
to_date=DateTime("2016/02/02 00:00:00"),
interpolation_method='one_for_all')
# With a time frame that contains the full movement, we have 100% of the quantity
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
to_date=DateTime("2016/01/02 00:00:00"),
interpolation_method='one_for_all')
# corner case: exact same time, we also have 100%
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
to_date=DateTime("2016/01/01 11:00:00"),
......@@ -978,35 +997,40 @@ class TestInventory(InventoryAPITestCase):
# this is "one_for_all" XXX naming
# time frame start before movement
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
to_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='one_for_all')
# time frame start at exact same time as movement
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
to_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='one_for_all')
# Time frame is contained inside the movement
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 02:00:00"),
to_date=DateTime("2016/01/01 07:00:00"),
interpolation_method='one_for_all')
# Time frame finishes after movement end
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
to_date=DateTime("2016/01/01 12:00:00"),
interpolation_method='one_for_all')
# Time frame finishes at exact same time that movement end
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
to_date=DateTime("2016/01/01 11:00:00"),
......@@ -1014,27 +1038,30 @@ class TestInventory(InventoryAPITestCase):
def test_interpolation_method_XXX_one_for_all_at_date(self):
self._makeMovement(
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
)
# With a time frame that does not contain the movement, we have 0%
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/02/01 00:00:00"),
at_date=DateTime("2016/02/02 00:00:00"),
interpolation_method='one_for_all')
# With a time frame that contains the full movement, we have 100% of the quantity
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
at_date=DateTime("2016/01/02 00:00:00"),
interpolation_method='one_for_all')
# corner case: exact same time, we also have 100%
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
at_date=DateTime("2016/01/01 11:00:00"),
......@@ -1044,35 +1071,40 @@ class TestInventory(InventoryAPITestCase):
# this is "one_for_all" XXX naming
# time frame start before movement
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
at_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='one_for_all')
# time frame start at exact same time as movement
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
at_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='one_for_all')
# Time frame is contained inside the movement
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 02:00:00"),
at_date=DateTime("2016/01/01 07:00:00"),
interpolation_method='one_for_all')
# Time frame finishes after movement end
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
at_date=DateTime("2016/01/01 12:00:00"),
interpolation_method='one_for_all')
# Time frame finishes at exact same time that movement end
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
at_date=DateTime("2016/01/01 11:00:00"),
......@@ -1080,27 +1112,30 @@ class TestInventory(InventoryAPITestCase):
def test_interpolation_method_XXX_all_or_nothing_to_date(self):
self._makeMovement(
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
)
# With a time frame that does not contain the movement, we have 0%
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/02/01 00:00:00"),
to_date=DateTime("2016/02/02 00:00:00"),
interpolation_method='all_or_nothing')
# With a time frame that contains the full movement, we have 100% of the quantity
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
to_date=DateTime("2016/01/02 00:00:00"),
interpolation_method='all_or_nothing')
# corner case: exact same time, we also have 100%
self.assertInventoryEquals(10,
# corner case: exact same time, we have 0%, because to_date will discard the movement
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
to_date=DateTime("2016/01/01 11:00:00"),
......@@ -1110,35 +1145,40 @@ class TestInventory(InventoryAPITestCase):
# this is "all or nothing" XXX naming
# time frame start before movement
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
to_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='all_or_nothing')
# time frame start at exact same time as movement
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
to_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='all_or_nothing')
# Time frame is contained inside the movement
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 02:00:00"),
to_date=DateTime("2016/01/01 07:00:00"),
interpolation_method='all_or_nothing')
# Time frame finishes after movement end
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
to_date=DateTime("2016/01/01 12:00:00"),
interpolation_method='all_or_nothing')
# Time frame finishes at exact same time that movement end
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
to_date=DateTime("2016/01/01 11:00:00"),
......@@ -1147,27 +1187,30 @@ class TestInventory(InventoryAPITestCase):
def test_interpolation_method_XXX_all_or_nothing_at_date(self):
self._makeMovement(
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
quantity=10,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
)
# With a time frame that does not contain the movement, we have 0%
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/02/01 00:00:00"),
at_date=DateTime("2016/02/02 00:00:00"),
interpolation_method='all_or_nothing')
# With a time frame that contains the full movement, we have 100% of the quantity
self.assertInventoryEquals(10,
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
at_date=DateTime("2016/01/02 00:00:00"),
interpolation_method='all_or_nothing')
# corner case: exact same time, we also have 0%, because at_date
self.assertInventoryEquals(0,
# corner case: exact same time, we also have 100%, because at_date include the movement
self.assertInventoryEquals(
10,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
at_date=DateTime("2016/01/01 11:00:00"),
......@@ -1177,35 +1220,40 @@ class TestInventory(InventoryAPITestCase):
# this is "all or nothing" XXX naming
# time frame start before movement
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 00:00:00"),
at_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='all_or_nothing')
# time frame start at exact same time as movement
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 01:00:00"),
at_date=DateTime("2016/01/01 06:00:00"),
interpolation_method='all_or_nothing')
# Time frame is contained inside the movement
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 02:00:00"),
at_date=DateTime("2016/01/01 07:00:00"),
interpolation_method='all_or_nothing')
# Time frame finishes after movement end
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
at_date=DateTime("2016/01/01 12:00:00"),
interpolation_method='all_or_nothing')
# Time frame finishes at exact same time that movement end
self.assertInventoryEquals(0,
self.assertInventoryEquals(
0,
node_uid=self.node.getUid(),
from_date=DateTime("2016/01/01 06:00:00"),
at_date=DateTime("2016/01/01 11:00:00"),
......@@ -1750,6 +1798,97 @@ class TestInventoryList(InventoryAPITestCase):
checkInventory(line=3, type='Future', source=1, quantity=-9)
checkInventory(line=3, type='Future', destination=1, quantity=9)
def test_interpolation_method_linear(self):
self._makeMovement(
title="M1",
quantity=10,
price=2,
destination_value=self.node,
start_date=DateTime("2016/01/01 01:00:00"),
stop_date=DateTime("2016/01/01 11:00:00"),
)
self._makeMovement(
title="M2",
quantity=5,
price=3,
destination_value=self.node,
start_date=DateTime("2016/01/01 10:00:00"),
stop_date=DateTime("2016/01/01 15:00:00"),
)
self._makeMovement(
title="M3",
quantity=10,
price=5,
destination_value=self.other_node,
start_date=DateTime("2016/01/01 05:00:00"),
stop_date=DateTime("2016/01/01 15:00:00"),
)
self._makeMovement(
title="M4",
quantity=5,
price=7,
destination_value=self.other_node,
start_date=DateTime("2016/01/01 18:00:00"),
stop_date=DateTime("2016/01/01 23:00:00"),
)
# We have created these movements:
# 00:00 10:00 20:00
# | | |
# M1 XXXXXXXXXX
# M2 XXXXX
# M3 XXXXXXXXXX
# M4 XXXXX
# | | |
inventory_list = self.getSimulationTool().getInventoryList(
group_by_node=True,
node_uid=(self.node.getUid(), self.other_node.getUid()),
from_date=DateTime("2016/01/01 08:00:00"),
at_date=DateTime("2016/01/01 12:00:00"),
interpolation_method="linear",
)
# We only query for the part between 8:00 to 12:00, so we select:
# 00:00 10:00 20:00
# | [ | [ |
# M1 XXXXXXXXXX
# ^^^ 3
# M2 XXXXX
# ^^ 2 -> total for `node`: 5
# M3 XXXXXXXXXX
# ^^^^ 4 -> total for `other_node`: 4
# M4 XXXXX
# | [ | [ |
self.assertEqual(2, len(inventory_list))
node_inventory, = [x for x in inventory_list if x.node_uid == self.node.getUid()]
self.assertEqual(3+2, node_inventory.inventory)
self.assertEqual(3*2 + 2*3, node_inventory.total_price)
other_node_inventory, = [x for x in inventory_list if x.node_uid == self.other_node.getUid()]
self.assertEqual(4, other_node_inventory.inventory)
self.assertEqual(4*5, other_node_inventory.total_price)
# this is also true if we use a precision
inventory_list = self.getSimulationTool().getInventoryList(
group_by_node=True,
precision=2,
node_uid=(self.node.getUid(), self.other_node.getUid()),
from_date=DateTime("2016/01/01 08:00:00"),
at_date=DateTime("2016/01/01 12:00:00"),
interpolation_method="linear",
)
self.assertEqual(2, len(inventory_list))
node_inventory, = [x for x in inventory_list if x.node_uid == self.node.getUid()]
self.assertEqual(3+2, node_inventory.inventory)
self.assertEqual(3*2 + 2*3, node_inventory.total_price)
other_node_inventory, = [x for x in inventory_list if x.node_uid == self.other_node.getUid()]
self.assertEqual(4, other_node_inventory.inventory)
self.assertEqual(4*5, other_node_inventory.total_price)
def test_inventory_asset_price(self):
# examples from http://accountinginfo.com/study/inventory/inventory-120.htm
movement_list = [
......
......@@ -652,6 +652,8 @@ class SimulationTool(BaseTool):
# if we consider flow, we also select movement whose mirror date is
# in the from_date/to_date range and movement whose
# start_date/stop_date contains the report range.
# The selected range is wider, but the selected movements will have an
# "interpolation_ratio" applied to their quantity and prices.
if to_date:
column_value_dict['date'] = ComplexQuery(
Query(date=(from_date, to_date), range='minmax'),
......
SELECT
<dtml-if expr="interpolation_method == 'linear'">
@interpolation_ratio := CASE
WHEN <dtml-var stock_table_id>.mirror_date = <dtml-var stock_table_id>.date THEN 1
ELSE (
UNIX_TIMESTAMP(LEAST(<dtml-sqlvar flow_valuation_method_to_date type="datetime">,
GREATEST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date) ))
- UNIX_TIMESTAMP(GREATEST(<dtml-sqlvar flow_valuation_method_from_date type="datetime">,
LEAST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date))))
/ ( UNIX_TIMESTAMP(GREATEST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date)) -
UNIX_TIMESTAMP(LEAST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date)) ) END
<dtml-else>
@interpolation_ratio := 1
</dtml-if> flow_ratio,
<dtml-let interpolation_ratio="SimulationTool_zGetInterpolationMethod(
stock_table_id=stock_table_id,
interpolation_method=interpolation_method,
interpolation_method_from_date=interpolation_method_from_date,
interpolation_method_to_date=interpolation_method_to_date,
interpolation_method_at_date=interpolation_method_at_date,
src__=1)">
SELECT
<dtml-if expr="precision is not None">
SUM(ROUND(
<dtml-var stock_table_id>.quantity
<dtml-if transformed_uid> * transformation.quantity</dtml-if>
* @interpolation_ratio, <dtml-var precision>)) AS inventory,
* <dtml-var interpolation_ratio>, <dtml-var precision>)) AS inventory,
SUM(ROUND(
<dtml-var stock_table_id>.quantity
<dtml-if transformed_uid> * transformation.quantity</dtml-if>
* @interpolation_ratio, <dtml-var precision>)) AS total_quantity,
* <dtml-var interpolation_ratio>, <dtml-var precision>)) AS total_quantity,
<dtml-if convert_quantity_result>
SUM(ROUND(<dtml-var stock_table_id>.quantity * measure.quantity
<dtml-if quantity_unit_uid> / quantity_unit_conversion.quantity</dtml-if>
* @interpolation_ratio, <dtml-var precision>))
* <dtml-var interpolation_ratio>, <dtml-var precision>))
AS converted_quantity,
</dtml-if>
IFNULL(SUM(ROUND(
<dtml-var stock_table_id>.total_price * @interpolation_ratio, <dtml-var precision>)), 0) AS total_price
<dtml-var stock_table_id>.total_price * <dtml-var interpolation_ratio>, <dtml-var precision>)), 0) AS total_price
<dtml-else>
SUM(<dtml-var stock_table_id>.quantity
<dtml-if transformed_uid> * transformation.quantity</dtml-if>
* @interpolation_ratio
* <dtml-var interpolation_ratio>
) AS inventory,
SUM(<dtml-var stock_table_id>.quantity
<dtml-if transformed_uid> * transformation.quantity</dtml-if>
* @interpolation_ratio
* <dtml-var interpolation_ratio>
) AS total_quantity,
<dtml-if convert_quantity_result>
ROUND(SUM(<dtml-var stock_table_id>.quantity * measure.quantity
<dtml-if quantity_unit_uid> / quantity_unit_conversion.quantity</dtml-if>
<dtml-if transformed_uid> * transformation.quantity</dtml-if> * @flow_ratio), 12)
<dtml-if transformed_uid> * transformation.quantity</dtml-if> * <dtml-var interpolation_ratio>), 12)
AS converted_quantity,
</dtml-if>
IFNULL(SUM(<dtml-var stock_table_id>.total_price) * @flow_ratio, 0) AS total_price
IFNULL(SUM(<dtml-var stock_table_id>.total_price * <dtml-var interpolation_ratio>), 0) AS total_price
</dtml-if>
<dtml-if inventory_list>
,
......@@ -147,3 +141,4 @@ GROUP BY
ORDER BY
<dtml-var order_by_expression>
</dtml-if>
</dtml-let>
\ No newline at end of file
<dtml-if expr="interpolation_method == 'linear'">
CASE
WHEN <dtml-var stock_table_id>.mirror_date = <dtml-var stock_table_id>.date THEN 1
ELSE (
UNIX_TIMESTAMP(LEAST(
<dtml-if interpolation_method_at_date>
<dtml-sqlvar interpolation_method_at_date type="datetime">
<dtml-else>
<dtml-sqlvar interpolation_method_to_date type="datetime">
</dtml-if>,
GREATEST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date) ))
- UNIX_TIMESTAMP(GREATEST(<dtml-sqlvar interpolation_method_from_date type="datetime">,
LEAST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date))))
/ ( UNIX_TIMESTAMP(GREATEST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date)) -
UNIX_TIMESTAMP(LEAST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date)) ) END
<dtml-elif expr="interpolation_method == 'all_or_nothing'">
CASE
WHEN (
-- movement contained in time frame
LEAST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date)
>= <dtml-sqlvar interpolation_method_from_date type="datetime"> AND
GREATEST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date)
<dtml-if interpolation_method_at_date>
<= <dtml-sqlvar interpolation_method_at_date type="datetime">
<dtml-else>
< <dtml-sqlvar interpolation_method_to_date type="datetime">
</dtml-if>
) THEN 1
ELSE 0
END
<dtml-elif expr="interpolation_method == 'one_for_all'">
CASE
WHEN (
-- movement overlaps with time frame
GREATEST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date)
<= <dtml-sqlvar interpolation_method_from_date type="datetime"> OR
LEAST(<dtml-var stock_table_id>.date, <dtml-var stock_table_id>.mirror_date)
<dtml-if interpolation_method_at_date>
>= <dtml-sqlvar interpolation_method_at_date type="datetime">
<dtml-else>
> <dtml-sqlvar interpolation_method_to_date type="datetime">
</dtml-if>
) THEN 0
ELSE 1
END
<dtml-else>
1
</dtml-if>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="SQL" module="Products.ZSQLMethods.SQL"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>arguments_src</string> </key>
<value> <string>stock_table_id\r\n
interpolation_method\r\n
interpolation_method_from_date\r\n
interpolation_method_to_date\r\n
interpolation_method_at_date</string> </value>
</item>
<item>
<key> <string>connection_id</string> </key>
<value> <string>cmf_activity_sql_connection</string> </value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>SimulationTool_zGetInterpolationMethod</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment