Login  Register

Price Agreements with customers

Posted by Jacopo Cappellato on Aug 01, 2006; 10:22am
URL: http://ofbiz.116.s1.nabble.com/Price-Agreements-with-customers-tp170273.html

Hi all,

I've implemented a new price list feature that can be used to set up
price lists for specific customers. It is based on the Agreement data model.
There are only two relevant changes (please see the attached patch)
needed, and I'd really love to get your feedback about them before
committing:

a) added a new price field to the AgreementProductAppl entity
b) added a new optional input parameter, "agreementId", to the
calculateProductPrice service; if the agreementId is passed, and if a
valid price for the product is found in the AgreementProductAppl entity,
this price overrides the default price in the ProductPrice entity.

Here are the steps needed to test this stuff:

* create an agreement (of type sales) between the Company and the customer
* create an agreement item of type price list for a given currency
* associate products to the price list (agreement item) and set the
price there (this is a new field AgreementProductAppl.price)
* when you start a sales order, select the agreement

Jacopo

Index: applications/party/entitydef/entitymodel.xml
===================================================================
--- applications/party/entitydef/entitymodel.xml (revision 427048)
+++ applications/party/entitydef/entitymodel.xml (working copy)
@@ -242,6 +242,7 @@
       <field name="agreementId" type="id-ne"></field>
       <field name="agreementItemSeqId" type="id-ne"></field>
       <field name="productId" type="id-ne"></field>
+      <field name="price" type="currency-precise"></field>
       <prim-key field="agreementId"/>
       <prim-key field="agreementItemSeqId"/>
       <prim-key field="productId"/>
Index: applications/order/src/org/ofbiz/order/shoppingcart/ShoppingCartItem.java
===================================================================
--- applications/order/src/org/ofbiz/order/shoppingcart/ShoppingCartItem.java (revision 427048)
+++ applications/order/src/org/ofbiz/order/shoppingcart/ShoppingCartItem.java (working copy)
@@ -876,6 +876,7 @@
                     priceContext.put("prodCatalogId", this.getProdCatalogId());
                     priceContext.put("webSiteId", cart.getWebSiteId());
                     priceContext.put("productStoreId", cart.getProductStoreId());
+                    priceContext.put("agreementId", cart.getAgreementId());
                     Map priceResult = dispatcher.runSync("calculateProductPrice", priceContext);
                     if (ServiceUtil.isError(priceResult)) {
                         throw new CartItemModifyException("There was an error while calculating the price: " + ServiceUtil.getErrorMessage(priceResult));
Index: applications/order/webapp/ordermgr/WEB-INF/actions/entry/catalog/productsummary.bsh
===================================================================
--- applications/order/webapp/ordermgr/WEB-INF/actions/entry/catalog/productsummary.bsh (revision 427048)
+++ applications/order/webapp/ordermgr/WEB-INF/actions/entry/catalog/productsummary.bsh (working copy)
@@ -85,6 +85,7 @@
         priceContext.put("webSiteId", webSiteId);
         priceContext.put("prodCatalogId", catalogId);
         priceContext.put("productStoreId", productStoreId);
+        priceContext.put("agreementId", cart.getAgreementId());
         priceContext.put("checkIncludeVat", "Y");
         priceMap = dispatcher.runSync("calculateProductPrice", priceContext);
 
Index: applications/order/webapp/ordermgr/WEB-INF/actions/entry/catalog/productdetail.bsh
===================================================================
--- applications/order/webapp/ordermgr/WEB-INF/actions/entry/catalog/productdetail.bsh (revision 427048)
+++ applications/order/webapp/ordermgr/WEB-INF/actions/entry/catalog/productdetail.bsh (working copy)
@@ -170,6 +170,7 @@
         priceContext.put("webSiteId", webSiteId);
         priceContext.put("productStoreId", productStoreId);
         priceContext.put("checkIncludeVat", "Y");
+        priceContext.put("agreementId", cart.getAgreementId());
         priceMap = dispatcher.runSync("calculateProductPrice", priceContext);
         context.put("priceMap", priceMap);
     } else {
Index: applications/product/servicedef/services_pricepromo.xml
===================================================================
--- applications/product/servicedef/services_pricepromo.xml (revision 427048)
+++ applications/product/servicedef/services_pricepromo.xml (working copy)
@@ -32,6 +32,7 @@
         <attribute name="partyId" type="String" mode="IN" optional="true"/>
         <attribute name="productStoreId" type="String" mode="IN" optional="true"/>
         <attribute name="productStoreGroupId" type="String" mode="IN" optional="true"/>
+        <attribute name="agreementId" type="String" mode="IN" optional="true"/>
         <attribute name="quantity" type="Double" mode="IN" optional="true"/>
         <attribute name="currencyUomId" type="String" mode="IN" optional="true"/>
         <attribute name="productPricePurposeId" type="String" mode="IN" optional="true"><!-- defaults to PURCHASE --></attribute>
Index: applications/product/src/org/ofbiz/product/price/PriceServices.java
===================================================================
--- applications/product/src/org/ofbiz/product/price/PriceServices.java (revision 427192)
+++ applications/product/src/org/ofbiz/product/price/PriceServices.java (working copy)
@@ -70,6 +70,7 @@
      *   <li>webSiteId
      *   <li>productStoreId
      *   <li>productStoreGroupId
+     *   <li>agreementId
      *   <li>quantity
      *   <li>currencyUomId
      *   <li>checkIncludeVat
@@ -96,6 +97,8 @@
         String webSiteId = (String) context.get("webSiteId");
         String checkIncludeVat = (String) context.get("checkIncludeVat");
 
+        String agreementId = (String) context.get("agreementId");
+
         String productStoreId = (String) context.get("productStoreId");
         String productStoreGroupId = (String) context.get("productStoreGroupId");
         GenericValue productStore = null;
@@ -230,6 +233,23 @@
             if (Debug.infoOn()) Debug.logInfo("There is more than one DEFAULT_PRICE with the currencyUomId " + currencyUomId + " and productId " + productId + ", using the latest found with price: " + defaultPriceValue.getDouble("price"), module);
         }
 
+        // If there is an agreement between the company and the client, and there is
+        // a price for the product in it, it will override the default price of the
+        // ProductPrice entity.
+        if (UtilValidate.isNotEmpty(agreementId)) {
+            try {
+                List agreementPrices = delegator.findByAnd("AgreementItemAndProductAppl", UtilMisc.toMap("agreementId", agreementId, "productId", productId, "currencyUomId", currencyUomId));
+                GenericValue agreementPriceValue = EntityUtil.getFirst(agreementPrices);
+                if (agreementPriceValue != null && agreementPriceValue.get("price") != null) {
+                    defaultPriceValue = agreementPriceValue;
+                }
+            } catch (GenericEntityException e) {
+                String errMsg = "Error getting agreement info from the database while calculating price" + e.toString();
+                Debug.logError(e, errMsg, module);
+                return ServiceUtil.returnError(errMsg);
+            }
+        }
+
         List competitivePrices = EntityUtil.filterByAnd(productPrices, UtilMisc.toMap("productPriceTypeId", "COMPETITIVE_PRICE"));
         GenericValue competitivePriceValue = EntityUtil.getFirst(competitivePrices);
         if (competitivePrices != null && competitivePrices.size() > 1) {