[rules-users] rules for promotional offers

Sandeep Bandela gibsosmat at gmail.com
Fri Sep 9 03:58:14 EDT 2011


Hi here is the same thing converted to mvl

// this Bundler.java has integer member that keeps incrementing
global Bundler bundler

rule "Apply 10% discount if you purchase 2 items"
    when
        $s1 : CartItem( *productId == 219759*, processed == false)
        $s2 : CartItem( this != $s1, productId == $s1.productId, processed
== false)
        $m : RuleMessage()
 then
        $m.addMessage("Found item1: " + $s1.getName() + " id:
"+$s1.getId());
        $m.addMessage("Found item2: " + $s2.getName() + " id:
"+$s2.getId());
        modify($s1){
        setProcessed(true),
        setPromoItemDiscount($s1.getPrice() * 0.1),
        setPromoId("1"),
        setBundleId(bundler.getId()),
        setAggrigatorId(1)
        };
        modify($s2){
        setProcessed(true),
        setPromoItemDiscount($s2.getPrice() * 0.1),
        setPromoId("1"),
        setBundleId(bundler.getId()),
        setAggrigatorId(1)
        };
        $m.addMessage("bundled ["+*bundler.getId()*+"]
"+$s1.getId()+","+$s2.getId());
        bundler.increment();
end

the above rule dosent fire, but if I change the highlighter to
getProductId() == 219759, or use productId == "219759", may be this is some
edge case but it took long time for me to figure it out productId is String.
now consider the *bundler.getId()*, if I use *bundler.id* I get compilation
error.

Rule Compilation error : [Rule name='Apply 10% discount if you purchase 2
items']

com/example/promotions/promotionEngine/Rule_Apply_10__discount_if_you_purchase_2_items_0.java
(23:1592) : The field Bundler.id is not visible
2011-09-09 13:18:39,863  INFO [STDOUT] - 2011-09-09 13:18:39,863  INFO
[PromotionsManager] - ksession initialized
2011-09-09 13:18:39,863  INFO [STDOUT] - 2011-09-09 13:18:39,863  INFO
[PromotionsManager] - Exploding items and inserting cart
2011-09-09 13:18:39,864  INFO [STDOUT] - 2011-09-09 13:18:39,863 ERROR
[CheckOutBasedUtilities] - Failed to apply promo offers
java.lang.RuntimeException: Unexpected global [bundler]
    at
org.drools.common.AbstractWorkingMemory.setGlobal(AbstractWorkingMemory.java:613)
    at
org.drools.impl.StatefulKnowledgeSessionImpl.setGlobal(StatefulKnowledgeSessionImpl.java:332)
    at
com.example.promotions.promotionEngine.PromotionsManager.applyOffers(PromotionsManager.java:154)
    at
com.example.promotions.promotionEngine.PromotionsManager.shuffleForOffers(PromotionsManager.java:61)`

lastly my actual problem that I am looking for a solution lets say we have
"Buy X items of A and get Y Items of B". X=5 & Y=4 from the original problem
I want to template the rule and load the values of X,A,Y,B from database or
excel etc. if I use modify the error is as follows

*my rule*


rule "Buy X units of Product A and Get Y units of Product B Free"
    when
        $itemsX : ArrayList( size == 2 ) from collect( CartItem(
getProductId() == 24257, !isProcessed()))
        $itemsY : ArrayList( size == 1) from collect(CartItem(
getProductId() == 24260, !isProcessed()))
        $m : RuleMessage()
 then
         for(Object item : $itemsX){
             CartItem ci = (CartItem) item;
             $m.addMessage( ci.getId()+")Found item: "+ci.getItemId()+"
name: "+ci.getName());
             modify(ci){
                setProcessed(true),
                setPromoItemDiscount(0),
                setPromoId("2"),
                setBundleId(bundler.getId()),
                setAggrigatorId(1)
            };
         }
         for(Object item : $itemsY){
         CartItem ci = (CartItem) item;
             $m.addMessage( ci.getId()+")Found item: "+ci.getItemId()+"
name: "+ci.getName());
             modify(ci){
                setProcessed(true),
                setPromoItemDiscount(ci.getPrice()),
                setPromoId("2"),
                setBundleId(bundler.getId()),
                setAggrigatorId(2)
            };
         }
        bundler.increment();
end

Rule Compilation error : [Rule name='Buy X units of Product A and Get Y
units of Product B Free']

com/example/promotions/promotionEngine/Rule_Buy_X_units_of_Product_A_and_Get_Y_units_of_Product_B_Free_0.java
(11:1236) : The method setProcessed(boolean) is undefined for the type
Object

com/example/promotions/promotionEngine/Rule_Buy_X_units_of_Product_A_and_Get_Y_units_of_Product_B_Free_0.java
(12:1265) : The method setPromoItemDiscount(int) is undefined for the type
Object

com/example/promotions/promotionEngine/Rule_Buy_X_units_of_Product_A_and_Get_Y_units_of_Product_B_Free_0.java
(13:1299) : The method setPromoId(String) is undefined for the type Object

com/example/promotions/promotionEngine/Rule_Buy_X_units_of_Product_A_and_Get_Y_units_of_Product_B_Free_0.java
(14:1325) : The method setBundleId(Integer) is undefined for the type Object

com/example/promotions/promotionEngine/Rule_Buy_X_units_of_Product_A_and_Get_Y_units_of_Product_B_Free_0.java
(15:1364) : The method setAggrigatorId(int) is undefined for the type Object

com/example/promotions/promotionEngine/Rule_Buy_X_units_of_Product_A_and_Get_Y_units_of_Product_B_Free_0.java
(22:1702) : The method setProcessed(boolean) is undefined for the type
Object

com/example/promotions/promotionEngine/Rule_Buy_X_units_of_Product_A_and_Get_Y_units_of_Product_B_Free_0.java
(23:1731) : The method setPromoItemDiscount(Double) is undefined for the
type Object

com/example/promotions/promotionEngine/Rule_Buy_X_units_of_Product_A_and_Get_Y_units_of_Product_B_Free_0.java
(24:1777) : The method setPromoId(String) is undefined for the type Object

com/example/promotions/promotionEngine/Rule_Buy_X_units_of_Product_A_and_Get_Y_units_of_Product_B_Free_0.java
(25:1803) : The method setBundleId(Integer) is undefined for the type Object

com/example/promotions/promotionEngine/Rule_Buy_X_units_of_Product_A_and_Get_Y_units_of_Product_B_Free_0.java
(26:1842) : The method setAggrigatorId(int) is undefined for the type Object

Rule Compilation error : [Rule name='Apply 10% discount if you purchase 2
items']

com/example/promotions/promotionEngine/Rule_Apply_10__discount_if_you_purchase_2_items_0.java
(23:1592) : The field Bundler.id is not visible


On Fri, Sep 9, 2011 at 12:40 PM, Sandeep Bandela <gibsosmat at gmail.com>wrote:

> Hi Wolfgang,
> This is what I did initially but for product > 2 I didnt find a generic way
> to do this. following is my first rule. I didnt use field names because it
> was giving error that member is not accessible. I will attach the errors of
> each case in a few mins.
>
> rule "Apply 10% discount if you purchase 2 items"
>     dialect "java"
>     when
>         $s1 : CartItem( getProductId() == 236061, !isProcessed())
>         $s2 : CartItem( getProductId() == 236061, getId() != $s1.getId(),
> !isProcessed())
>         $m : RuleMessage()
>  then
>         $m.addMessage("Found item1: " + $s1.getName() + " id:
> "+$s1.getId());
>         $m.addMessage("Found item2: " + $s2.getName() + " id:
> "+$s2.getId());
>         modify($s1){
>         setProcessed(true),
>         setPromoItemDiscount($s1.getPrice() * 0.1),
>         setPromoId("1"),
>         setBundleId(bundler.getId()),
>         setAggrigatorId(1)
>         };
>         modify($s2){
>         setProcessed(true),
>         setPromoItemDiscount($s2.getPrice() * 0.1),
>         setPromoId("1"),
>         setBundleId(bundler.getId()),
>         setAggrigatorId(1)
>         };
>         bundler.increment();
> end
>
>
> 2011/9/9 Wolfgang Laun <wolfgang.laun at gmail.com>
>
>> Your rule exhibits procedural thinking. (For an aspiring rule programmer
>> his is typical teething troubles.)
>>
>> There's no need to collect all A's and B's in order to determine their
>> number being greater than one or two - this is achieved automatically by a
>> simple triple match rule. Consider
>>
>> rule "2A - 1B"
>> when
>>    $a1: CartItem( productId == "A", processed == false )
>>    $a2: CartItem( this != $a1, productId == "A", processed == false )
>>    $b: CartItem( productId == "B", processed == false )
>> then
>>    modify( $a1 ){...}
>>    modify( $a2 ){...}
>>    modify( $b ){...}
>> end
>>
>> Note:
>>
>>    - The modify is essential. (When you say "doesn't work", always
>>    provide details.)
>>    - Use the field name rather than the getter call - it improves
>>    readability.
>>    - I'm not sure whether 5.2.0 final handles boolean fields correctly -
>>    IIRC, there were some issues. It's possible that CartItem(..., !processed)
>>    works.
>>
>> -W
>>
>> 2011/9/8 Sandeep Bandela <gibsosmat at gmail.com>
>>
>>> Hi,
>>> I am new to rules engine, after going through the examples shipped
>>> (shopping.drl, petstore.drl)
>>> I am trying to implement promotional discounting using drools 5.2.0
>>> final, stateful session. assume cart has all the items that customer wants
>>> to buy,
>>> I am trying to bundle them together with the existing offers
>>>
>>> rule "Buy X units of Product A and Get Y units of Product B Free"
>>>     dialect "java"
>>> when
>>>     $itemsA : ArrayList( size >= 2) from collect( CartItem(
>>> getProductId() == "A", !isProcessed()))
>>>     $itemsB : ArrayList( size >= 1) from collect( CartItem(
>>> getProductId() == "B", !isProcessed()))
>>> then
>>>     // current scenario buy 2*A and get 1*B
>>>     int x = 2;
>>>     int y = 1;
>>>     for(int i=0 ; i < x ; i++){
>>>         CartItem $ci = (CartItem) $itemsA.get(i);
>>>         // modify($ci){setProcessed(true) ... } dosent work
>>>         $ci.setProcessed(true);
>>>         $ci.setItemDiscount(0.0);
>>>         $ci.setBundleId(bundler.getId());
>>>     }
>>>
>>>     for(int i=0 ; i < y  ; i++){
>>>         CartItem $ci = (CartItem) $itemsB.get(i);
>>>         $ci.setProcessed(true);
>>>         $ci.setItemDiscount($ci.getPrice());
>>>         $ci.setBundleId(bundler.getId());
>>>     }
>>>     // global counter to identify bundled items
>>>     bundler.increment();
>>> end
>>>
>>> the above rule calculates only for 1 set of offer i.e first 2*A & 1*B are
>>> considered, rest in the cart are not bundled.
>>> if customer buys 4*A + 2*B it dosent consider it. am I missing anything?
>>> is this the right way to do it?
>>> any feedback is appreciated.
>>>
>>>
>>>
>>>
>>> --
>>> Regards,
>>> Sandeep Bandela.
>>>
>>>
>>> _______________________________________________
>>> rules-users mailing list
>>> rules-users at lists.jboss.org
>>> https://lists.jboss.org/mailman/listinfo/rules-users
>>>
>>>
>>
>> _______________________________________________
>> rules-users mailing list
>> rules-users at lists.jboss.org
>> https://lists.jboss.org/mailman/listinfo/rules-users
>>
>>
>
>
> --
> Regards,
> Sandeep Bandela.
>
>


-- 
Regards,
Sandeep Bandela.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.jboss.org/pipermail/rules-users/attachments/20110909/7a394380/attachment.html 


More information about the rules-users mailing list