Author: jleroux
Date: Tue Feb 24 13:04:31 2009
New Revision: 747364

URL: http://svn.apache.org/viewvc?rev=747364&view=rev
Log:
A modified old forgotten patch from Rashko Rejmer "Implementation of a service 
to compute the product average cost" 
https://issues.apache.org/jira/browse/OFBIZ-1742 - OFBIZ-1742
I changed :
* bsh to groovy (with up to date code : no entity-expr for instance)
* used engine="entity-auto" instead of simple-method (not tested but should be 
ok)
* Had to introduce encode-output="false" for display type="currency" in 
ListInventoryAverageCosts form (I will post a comment about that in dev ML)

Added:
    
ofbiz/trunk/applications/product/webapp/facility/WEB-INF/actions/inventory/InventoryAverageCosts.groovy
Modified:
    ofbiz/trunk/applications/accounting/servicedef/services_cost.xml
    ofbiz/trunk/applications/product/config/ProductUiLabels.xml
    
ofbiz/trunk/applications/product/script/org/ofbiz/product/cost/CostServices.xml
    ofbiz/trunk/applications/product/servicedef/services_cost.xml
    ofbiz/trunk/applications/product/webapp/facility/WEB-INF/controller.xml
    ofbiz/trunk/applications/product/webapp/facility/facility/FacilityForms.xml
    ofbiz/trunk/applications/product/widget/facility/FacilityScreens.xml

Modified: ofbiz/trunk/applications/accounting/servicedef/services_cost.xml
URL: 
http://svn.apache.org/viewvc/ofbiz/trunk/applications/accounting/servicedef/services_cost.xml?rev=747364&r1=747363&r2=747364&view=diff
==============================================================================
--- ofbiz/trunk/applications/accounting/servicedef/services_cost.xml (original)
+++ ofbiz/trunk/applications/accounting/servicedef/services_cost.xml Tue Feb 24 
13:04:31 2009
@@ -70,4 +70,27 @@
         <description>Accounting Cost Permission Checking Logic</description>
         <implements service="permissionInterface"/>
     </service>
+    
+    <service name="createProductAverageCost" 
default-entity-name="ProductAverageCost" engine="entity-auto" invoke="create" 
auth="true">
+        <description>Create Product Average Cost record</description>
+        <permission-service service-name="acctgCostPermissionCheck" 
main-action="CREATE"/>
+        <auto-attributes include="pk" mode="IN" optional="false"/>
+        <auto-attributes include="nonpk" mode="IN" optional="true"/>
+        <override name="fromDate" optional="true"/>
+        <override name="averageCost" optional="false"/>
+    </service>
+    
+    <service name="updateProductAverageCost" 
default-entity-name="ProductAverageCost" engine="entity-auto" invoke="update" 
auth="true">
+        <description>Update a Product Average Cost record</description>
+        <permission-service service-name="acctgCostPermissionCheck" 
main-action="UPDATE"/>
+        <auto-attributes include="pk" mode="IN" optional="false"/>
+        <auto-attributes include="nonpk" mode="IN" optional="true"/>
+    </service>
+    
+    <service name="deleteProductAverageCost" 
default-entity-name="ProductAverageCost" engine="entity-auto" invoke="delete" 
auth="true">
+        <description>Delete a Product Average Cost record</description>
+        <permission-service service-name="acctgCostPermissionCheck" 
main-action="DELETE"/>
+        <auto-attributes include="pk" mode="IN" optional="false"/>
+    </service>
+    
 </services>

Modified: ofbiz/trunk/applications/product/config/ProductUiLabels.xml
URL: 
http://svn.apache.org/viewvc/ofbiz/trunk/applications/product/config/ProductUiLabels.xml?rev=747364&r1=747363&r2=747364&view=diff
==============================================================================
--- ofbiz/trunk/applications/product/config/ProductUiLabels.xml (original)
+++ ofbiz/trunk/applications/product/config/ProductUiLabels.xml Tue Feb 24 
13:04:31 2009
@@ -8971,6 +8971,10 @@
         <value 
xml:lang="th">สำหรับหน้าจอในไฟล์อื่น
 ๆ ใช้เหมือนบางสิ่ง</value>
         <value xml:lang="zh">为其它文件中的屏幕使用类似于</value>
     </property>
+    <property key="ProductDifferentCurrencies">
+        <value xml:lang="en">Items with different currencies</value>
+        <value xml:lang="fr">Articles utilisant différentes devises</value>
+    </property>
     <property key="ProductDiscount">
         <value xml:lang="de">Rabatt</value>
         <value xml:lang="en">Discount</value>
@@ -11060,6 +11064,10 @@
         <value xml:lang="ru">Дост</value>
         <value xml:lang="th">ใช้ประโยชน์</value>
     </property>
+    <property key="ProductInventoryAverageCosts">
+        <value xml:lang="en">Inventory Average Costs</value>
+        <value xml:lang="fr">Coûts moyens de stockage</value>
+    </property>
     <property key="ProductInventoryByProduct">
         <value xml:lang="de">Lager nach Produkt</value>
         <value xml:lang="en">Inventory By Product</value>

Modified: 
ofbiz/trunk/applications/product/script/org/ofbiz/product/cost/CostServices.xml
URL: 
http://svn.apache.org/viewvc/ofbiz/trunk/applications/product/script/org/ofbiz/product/cost/CostServices.xml?rev=747364&r1=747363&r2=747364&view=diff
==============================================================================
--- 
ofbiz/trunk/applications/product/script/org/ofbiz/product/cost/CostServices.xml 
(original)
+++ 
ofbiz/trunk/applications/product/script/org/ofbiz/product/cost/CostServices.xml 
Tue Feb 24 13:04:31 2009
@@ -334,4 +334,104 @@
         
         <field-to-result field="totalCost"/>
     </simple-method>
+    <simple-method method-name="calculateProductAverageCost" 
short-description="Calculate inventory average cost for a product">
+        <entity-condition entity-name="InventoryItem" list="inventoryItems">
+            <condition-list>
+                <condition-expr field-name="productId" 
from-field="parameters.productId"/>
+                <condition-expr field-name="facilityId" 
from-field="parameters.facilityId" ignore-if-empty="true"/>
+                <condition-expr field-name="ownerPartyId" 
from-field="parameters.ownerPartyId" ignore-if-empty="true"/>
+                <condition-expr field-name="unitCost" operator="not-equals" 
from-field="nullField"/>
+            </condition-list>
+            <select-field field-name="quantityOnHandTotal"/>
+            <select-field field-name="unitCost"/>
+            <select-field field-name="currencyUomId"/>
+        </entity-condition>
+        <set field="totalQuantityOnHand" type="BigDecimal" value="0"/>
+        <set field="totalInventoryCost" type="BigDecimal" value="0"/>
+        <set field="absValOfTotalQOH" type="BigDecimal" value="0"/>
+        <set field="absValOfTotalInvCost" type="BigDecimal" value="0"/>
+        <set field="differentCurrencies" type="Boolean" value="false"/>
+        <iterate list="inventoryItems" entry="inventoryItem">
+            <calculate field="totalQuantityOnHand">
+                <calcop operator="add" >
+                    <calcop operator="get" field="totalQuantityOnHand"/>
+                    <calcop operator="get" 
field="inventoryItem.quantityOnHandTotal"/>
+                </calcop>
+            </calculate>
+            
+            <if-empty field="currencyUomId">
+                <set field="currencyUomId" 
from-field="inventoryItem.currencyUomId"/>
+            </if-empty>
+            <if-compare field="differentCurrencies" operator="equals" 
value="false" type="Boolean">
+                <if-compare-field field="inventoryItem.currencyUomId" 
operator="equals" to-field="currencyUomId">
+                    <calculate field="totalInventoryCost" type="BigDecimal">
+                        <calcop operator="add">
+                            <calcop operator="get" field="totalInventoryCost"/>
+                            <calcop operator="multiply">
+                                <calcop operator="get" 
field="inventoryItem.quantityOnHandTotal"/>
+                                <calcop operator="get" 
field="inventoryItem.unitCost"/>
+                            </calcop>
+                        </calcop>
+                    </calculate>
+                    
+                    <!-- calculation of absolute values of QOH and total 
inventory cost -->
+                    <if-compare field="inventoryItem.quantityOnHandTotal" 
operator="less" value="0">
+                        <calculate field="absValOfTotalQOH">
+                            <calcop operator="add">
+                                <calcop operator="get" 
field="absValOfTotalQOH"/>
+                                <calcop operator="negative" 
field="inventoryItem.quantityOnHandTotal" />
+                            </calcop>
+                        </calculate>
+                        <calculate field="absValOfTotalInvCost" 
type="BigDecimal">
+                            <calcop operator="add">
+                                <calcop operator="get" 
field="absValOfTotalInvCost"/>
+                                <calcop operator="multiply">
+                                    <calcop operator="negative" 
field="inventoryItem.quantityOnHandTotal"/>
+                                    <calcop operator="get" 
field="inventoryItem.unitCost"/>
+                                </calcop>
+                            </calcop>
+                        </calculate>
+                        <else>
+                        <calculate field="absValOfTotalQOH">
+                            <calcop operator="add" >
+                                <calcop operator="get" 
field="absValOfTotalQOH"/>
+                                <calcop operator="get" 
field="inventoryItem.quantityOnHandTotal"/>
+                            </calcop>
+                        </calculate>
+                        <calculate field="absValOfTotalInvCost" 
type="BigDecimal">
+                            <calcop operator="add">
+                                <calcop operator="get" 
field="absValOfTotalInvCost"/>
+                                <calcop operator="multiply">
+                                    <calcop operator="get" 
field="inventoryItem.quantityOnHandTotal"/>
+                                    <calcop operator="get" 
field="inventoryItem.unitCost"/>
+                                </calcop>
+                            </calcop>
+                        </calculate>
+                        </else>
+                    </if-compare>
+                <else>
+                    <set field="differentCurrencies" type="Boolean" 
value="true"/>
+                </else>
+                </if-compare-field>
+            </if-compare>
+        </iterate>
+        
+        <if-compare field="absValOfTotalQOH" operator="not-equals" value="0" 
type="BigDecimal">
+            <calculate field="productAverageCost" type="BigDecimal">
+                <calcop operator="divide">
+                    <calcop operator="get" field="absValOfTotalInvCost"/>
+                    <calcop operator="get" field="absValOfTotalQOH"/>
+                </calcop>
+            </calculate>
+        <else>
+            <set field="productAverageCost" type="BigDecimal" value="0"/>
+        </else>
+        </if-compare>
+        <field-to-result field="totalQuantityOnHand"/>
+        <if-compare field="differentCurrencies" operator="equals" 
value="false" type="Boolean">
+            <field-to-result field="totalInventoryCost"/>
+            <field-to-result field="productAverageCost"/>
+            <field-to-result field="currencyUomId"/>
+        </if-compare>
+    </simple-method>
 </simple-methods>

Modified: ofbiz/trunk/applications/product/servicedef/services_cost.xml
URL: 
http://svn.apache.org/viewvc/ofbiz/trunk/applications/product/servicedef/services_cost.xml?rev=747364&r1=747363&r2=747364&view=diff
==============================================================================
--- ofbiz/trunk/applications/product/servicedef/services_cost.xml (original)
+++ ofbiz/trunk/applications/product/servicedef/services_cost.xml Tue Feb 24 
13:04:31 2009
@@ -87,4 +87,15 @@
         <attribute mode="IN" name="currencyUomId" optional="false" 
type="String"/>
         <attribute mode="IN" name="costComponentTypePrefix" optional="false" 
type="String"/>
     </service>
+    <service name="calculateProductAverageCost" engine="simple" auth="true"
+            location="org/ofbiz/product/cost/CostServices.xml" 
invoke="calculateProductAverageCost">
+        <description>Calculate inventory average cost for a 
product</description>
+        <attribute name="productId" type="String" mode="IN"/>
+        <attribute name="facilityId" type="String" mode="IN" optional="true"/>
+        <attribute name="ownerPartyId" type="String" mode="IN" 
optional="true"/>
+        <attribute name="totalQuantityOnHand" type="BigDecimal" mode="OUT"/>
+        <attribute name="totalInventoryCost" type="BigDecimal" mode="OUT" 
optional="true"/>
+        <attribute name="productAverageCost" type="BigDecimal" mode="OUT" 
optional="true"/>
+        <attribute name="currencyUomId" type="String" mode="OUT" 
optional="true"/>
+    </service>
 </services>

Added: 
ofbiz/trunk/applications/product/webapp/facility/WEB-INF/actions/inventory/InventoryAverageCosts.groovy
URL: 
http://svn.apache.org/viewvc/ofbiz/trunk/applications/product/webapp/facility/WEB-INF/actions/inventory/InventoryAverageCosts.groovy?rev=747364&view=auto
==============================================================================
--- 
ofbiz/trunk/applications/product/webapp/facility/WEB-INF/actions/inventory/InventoryAverageCosts.groovy
 (added)
+++ 
ofbiz/trunk/applications/product/webapp/facility/WEB-INF/actions/inventory/InventoryAverageCosts.groovy
 Tue Feb 24 13:04:31 2009
@@ -0,0 +1,51 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import java.util.*;
+import javolution.util.FastList;
+import org.ofbiz.base.util.UtilMisc;
+import org.ofbiz.base.util.UtilValidate;
+import org.ofbiz.entity.condition.EntityCondition;
+import org.ofbiz.entity.condition.EntityOperator;
+import org.ofbiz.entity.util.EntityUtil;
+
+facilityId = context.get("facilityId");
+
+EntityCondition whereConditions = EntityCondition.makeCondition("facilityId", 
EntityOperator.EQUALS, facilityId); 
+inventoryItems = delegator.findByCondition("InventoryItem", whereConditions, 
null, UtilMisc.toList("productId"), null, null);
+inventoryItemProducts = EntityUtil.getFieldListFromEntityList(inventoryItems, 
"productId", true);
+      
+inventoryAverageCosts = FastList.newInstance();
+inventoryItemProducts.each { productId ->
+    productFacility = delegator.findByPrimaryKey("ProductFacility", 
UtilMisc.toMap("productId", productId, "facilityId", facilityId));
+    if (UtilValidate.isNotEmpty(productFacility)) {
+        result = dispatcher.runSync("calculateProductAverageCost", 
UtilMisc.toMap("productId", productId, "facilityId", facilityId, "userLogin", 
userLogin));
+        totalQuantityOnHand = result.get("totalQuantityOnHand");
+        
+        totalInventoryCost = result.get("totalInventoryCost");
+        productAverageCost = result.get("productAverageCost");
+        currencyUomId = result.get("currencyUomId");
+        if (!totalQuantityOnHand.equals(BigDecimal.ZERO)) {
+            inventoryAverageCosts.add(UtilMisc.toMap("productId", productId, 
"totalQuantityOnHand", totalQuantityOnHand, 
+                    "productAverageCost", productAverageCost, 
"totalInventoryCost", totalInventoryCost, "currencyUomId", currencyUomId));
+        }
+    }
+}
+
+context.inventoryAverageCosts = inventoryAverageCosts;
\ No newline at end of file

Modified: 
ofbiz/trunk/applications/product/webapp/facility/WEB-INF/controller.xml
URL: 
http://svn.apache.org/viewvc/ofbiz/trunk/applications/product/webapp/facility/WEB-INF/controller.xml?rev=747364&r1=747363&r2=747364&view=diff
==============================================================================
--- ofbiz/trunk/applications/product/webapp/facility/WEB-INF/controller.xml 
(original)
+++ ofbiz/trunk/applications/product/webapp/facility/WEB-INF/controller.xml Tue 
Feb 24 13:04:31 2009
@@ -1102,6 +1102,10 @@
         <security https="true" auth="true"/>
         <response name="success" type="view" value="InventoryItemGrandTotals"/>
     </request-map>
+    <request-map uri="InventoryAverageCosts">
+        <security https="true" auth="true"/>
+        <response name="success" type="view" value="InventoryAverageCosts"/>
+    </request-map>
     <request-map uri="InventoryItemTotalsExport.csv">
         <security https="true" auth="true"/>
         <response name="success" type="view" 
value="InventoryItemTotalsExport"/>
@@ -1200,6 +1204,8 @@
     <view-map name="InventoryReports" type="screen" 
page="component://product/widget/facility/ReportScreens.xml#InventoryReports"/>
     <view-map name="InventoryItemTotals" type="screen" 
page="component://product/widget/facility/FacilityScreens.xml#InventoryItemTotals"/>
     <view-map name="InventoryItemGrandTotals" type="screen" 
page="component://product/widget/facility/FacilityScreens.xml#InventoryItemGrandTotals"/>
+    <view-map name="InventoryAverageCosts" type="screen" 
page="component://product/widget/facility/FacilityScreens.xml#InventoryAverageCosts"/>
+    
     <view-map name="InventoryItemTotalsExport" type="screentext" 
page="component://product/widget/facility/FacilityScreens.xml#InventoryItemTotalsExport"
 content-type="text/csv" encoding="none"/>
 
     <view-map name="FacilityLocationGeoLocation" type="screen" 
page="component://product/widget/facility/FacilityScreens.xml#FacilityLocationGeoLocation"/>

Modified: 
ofbiz/trunk/applications/product/webapp/facility/facility/FacilityForms.xml
URL: 
http://svn.apache.org/viewvc/ofbiz/trunk/applications/product/webapp/facility/facility/FacilityForms.xml?rev=747364&r1=747363&r2=747364&view=diff
==============================================================================
--- ofbiz/trunk/applications/product/webapp/facility/facility/FacilityForms.xml 
(original)
+++ ofbiz/trunk/applications/product/webapp/facility/facility/FacilityForms.xml 
Tue Feb 24 13:04:31 2009
@@ -576,6 +576,18 @@
         <field name="totalCostPrice" title="${uiLabelMap.CommonTotal} 
${uiLabelMap.ProductCostPrice}"><display/></field>
         <field name="totalRetailPrice" title="${uiLabelMap.CommonTotal} 
${uiLabelMap.ProductRetailPrice}"><display/></field>
     </form>
+    <form name="ListInventoryAverageCosts" type="list" target="" title="" 
list-name="inventoryAverageCosts" 
+            odd-row-style="alternate-row" default-table-style="basic-table 
hover-bar"
+            paginate-target="InventoryAverageCosts" 
override-list-size="${overrideListSize}">
+        <field name="productId2" title="${uiLabelMap.ProductProductId}" 
entry-name="productId" widget-style="buttontext">
+            <hyperlink 
target="/catalog/control/EditProduct?productId=${productId}" 
target-type="inter-app" description="${productId}"/>
+        </field>        
+        <field name="totalQuantityOnHand" title="${uiLabelMap.CommonTotal} 
${uiLabelMap.ProductQoh}"><display/></field>
+        <field name="productAverageCost" use-when="currencyUomId!=null" 
title="${uiLabelMap.ProductAverageCost}" encode-output="false"><display 
type="currency" currency="${currencyUomId}"/></field>
+        <field name="productAverageCost" use-when="currencyUomId==null" 
title="${uiLabelMap.ProductAverageCost}" encode-output="false"><display 
description="${uiLabelMap.ProductDifferentCurrencies}"/></field>
+        <field name="totalInventoryCost" use-when="currencyUomId!=null" 
title="${uiLabelMap.CommonTotalCost}" encode-output="false"><display 
type="currency" currency="${currencyUomId}"/></field>
+        <field name="totalInventoryCost" use-when="currencyUomId==null" 
title="${uiLabelMap.CommonTotalCost}"><display 
description="${uiLabelMap.ProductDifferentCurrencies}"/></field>
+    </form>
     <form name="ListInventoryItemGrandTotals" type="list" 
list-name="inventoryItemGrandTotals"
         header-row-style="header-row-2" odd-row-style="alternate-row" 
default-table-style="basic-table hover-bar">
         <field name="qohGrandTotal" title="${uiLabelMap.ProductQoh} 
${uiLabelMap.CommonTotal} ${uiLabelMap.CommonQty}"><display/></field>

Modified: ofbiz/trunk/applications/product/widget/facility/FacilityScreens.xml
URL: 
http://svn.apache.org/viewvc/ofbiz/trunk/applications/product/widget/facility/FacilityScreens.xml?rev=747364&r1=747363&r2=747364&view=diff
==============================================================================
--- ofbiz/trunk/applications/product/widget/facility/FacilityScreens.xml 
(original)
+++ ofbiz/trunk/applications/product/widget/facility/FacilityScreens.xml Tue 
Feb 24 13:04:31 2009
@@ -415,6 +415,7 @@
                                     <link 
target="InventoryItemTotals?facilityId=${facilityId}&amp;action=Y" 
text="${uiLabelMap.ProductInventoryItemTotals}" style="buttontext"/>
                                     <link 
target="InventoryItemGrandTotals?facilityId=${facilityId}&amp;action=Y" 
text="${uiLabelMap.ProductInventoryItemGrandTotals}" style="buttontext"/>
                                     <link 
target="InventoryItemTotalsExport.csv?facilityId=${facilityId}&amp;action=Y" 
text="${uiLabelMap.ProductInventoryItemTotalsExport}" style="buttontext"/>
+                                    <link 
target="InventoryAverageCosts?facilityId=${facilityId}" 
text="${uiLabelMap.ProductInventoryAverageCosts}" style="buttontext"/>          
                          
                                 </container>
                             </decorator-section>
                             <decorator-section name="search-options">
@@ -701,6 +702,36 @@
         </section>
     </screen>
 
+    <screen name="InventoryAverageCosts">
+        <section>
+            <actions>
+                <set field="titleProperty" 
value="PageTitleEditFacilityInventoryItems"/>
+                <set field="headerItem" value="facility"/>
+                <set field="tabButtonItem" 
value="ViewFacilityInventoryByProduct"/>
+                <set field="facilityId" from-field="parameters.facilityId"/>
+                
+                <entity-one entity-name="Facility" value-field="facility" 
use-cache="true"/>
+                <script 
location="component://product/webapp/facility/WEB-INF/actions/inventory/InventoryAverageCosts.groovy"/>
+            </actions>
+            <widgets>
+                <decorator-screen name="CommonFacilityDecorator" 
location="${parameters.commonFacilityDecoratorLocation}">
+                    <decorator-section name="body">
+                        <container style="screenlet">
+                            <container style="screenlet-title-bar">
+                                <container style="h3">
+                                    <label 
text="${uiLabelMap.ProductInventoryAverageCosts} ${uiLabelMap.CommonFor} 
${facility.facilityName}"/>
+                                </container>
+                            </container>
+                            <container style="screenlet-body">
+                                <include-form name="ListInventoryAverageCosts" 
location="component://product/webapp/facility/facility/FacilityForms.xml"/>
+                            </container>
+                        </container>
+                    </decorator-section>
+                </decorator-screen>
+            </widgets>
+        </section>
+    </screen>
+    
     <screen name="EditFacilityGroups">
         <section>
             <actions>


Reply via email to