great CPU optimisation on calculate price

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
5 messages Options
Reply | Threaded
Open this post in threaded view
|

great CPU optimisation on calculate price

oceatoon
Hi everyone

Here's how we managed to gain great performance optimisation overall. This
divided our CPU consuption by half.

Optimisation Price Rule through Cache
<http://192.168.215.62:8000/trac/wiki/priceRules#OptimisationPriceRulethroughCache>

Since calculateProductPrice is used at every/any time a product is viewed
(category page, product page, addToCart) and whenever Price Rules are
applied, we can optimize the access to this Service by using Ofbiz's
UtilCache System. This means that instead of recalculating a product price
at every visit, when entering the calculatePrice Service an existence check
is made in the Product Price cache with a catalog+productId key.

   - If it exist it will simply return the Map this Service should have
   returned for this ProductId
   - otherwise it will execute the complete Service, save the result to
   Cache for the next visit, and return the requested result.

Our use case needed more than 4000 Price Rules to be applied. This
drastically slowed down ofbiz's performance. This Caching process can be
used for any recurent service call.
Existence Check and Return
<http://192.168.215.62:8000/trac/wiki/priceRules#ExistenceCheckandReturn>

        UtilCache productPricesCache = (UtilCache)
UtilCache.utilCacheTable.get("productPriceCache");
        if (productPricesCache == null)
            productPricesCache = new UtilCache("productPriceCache",0,0);
        String productPriceCacheKey =
productId+prodCatalogId+webSiteId+productStoreId+productStoreGroupId;
        //if Cache exists
        if (productPricesCache != null)
        {
           Map productPrice = (Map)productPricesCache.get(productPriceCacheKey);
           //if the Key exists
           if(productPrice!=null)
                return productPrice;
        }

        //else if cache key doesn't exist go through the whole service
        // build the result Map
        //add it to the Cache for the next Visit
        productPricesCache.put(productPriceCacheKey,result);
        return result;

Important Clear Cache
<http://192.168.215.62:8000/trac/wiki/priceRules#ImportantClearCache>

Offcourse since Price Rules Change, or Product Prices Change the cache needs
to be emptied according to project internal rules so that Product Prices
contain the result of a modification.

   - for a specific Cache Cleanup Method :
UtilCache.clearCache("productPriceCache");

   - for a global Cache Clean Method : UtilCache.clearAll();

in our use case , we have a clear cache that is made

   - on each Synchronisation
   - every time a price rule is manuelly modified (on Back Office price
   rule form update submit )
   - every day scheduled job at 00h00, since this is when some price
   rules can end



Best Regards
Tibor
Reply | Threaded
Open this post in threaded view
|

RE: great CPU optimisation on calculate price

PRONZATO Cedric RD-BIZZ-GRE
Hi Tibor,

Can you provide us the public IP of your wiki because you used a private one (if it is available)?

Thank you,
Cédric

-----Message d'origine-----
De : tibor katelbach [mailto:[hidden email]]
Envoyé : lundi 15 janvier 2007 15:41
À : [hidden email]
Objet : great CPU optimisation on calculate price

Hi everyone

Here's how we managed to gain great performance optimisation overall. This divided our CPU consuption by half.

Optimisation Price Rule through Cache
<http://192.168.215.62:8000/trac/wiki/priceRules#OptimisationPriceRulethroughCache>

Since calculateProductPrice is used at every/any time a product is viewed (category page, product page, addToCart) and whenever Price Rules are applied, we can optimize the access to this Service by using Ofbiz's UtilCache System. This means that instead of recalculating a product price at every visit, when entering the calculatePrice Service an existence check is made in the Product Price cache with a catalog+productId key.

   - If it exist it will simply return the Map this Service should have
   returned for this ProductId
   - otherwise it will execute the complete Service, save the result to
   Cache for the next visit, and return the requested result.

Our use case needed more than 4000 Price Rules to be applied. This drastically slowed down ofbiz's performance. This Caching process can be used for any recurent service call.
Existence Check and Return
<http://192.168.215.62:8000/trac/wiki/priceRules#ExistenceCheckandReturn>

        UtilCache productPricesCache = (UtilCache) UtilCache.utilCacheTable.get("productPriceCache");
        if (productPricesCache == null)
            productPricesCache = new UtilCache("productPriceCache",0,0);
        String productPriceCacheKey =
productId+prodCatalogId+webSiteId+productStoreId+productStoreGroupId;
        //if Cache exists
        if (productPricesCache != null)
        {
           Map productPrice = (Map)productPricesCache.get(productPriceCacheKey);
           //if the Key exists
           if(productPrice!=null)
                return productPrice;
        }

        //else if cache key doesn't exist go through the whole service
        // build the result Map
        //add it to the Cache for the next Visit
        productPricesCache.put(productPriceCacheKey,result);
        return result;

Important Clear Cache
<http://192.168.215.62:8000/trac/wiki/priceRules#ImportantClearCache>

Offcourse since Price Rules Change, or Product Prices Change the cache needs to be emptied according to project internal rules so that Product Prices contain the result of a modification.

   - for a specific Cache Cleanup Method :
UtilCache.clearCache("productPriceCache");

   - for a global Cache Clean Method : UtilCache.clearAll();

in our use case , we have a clear cache that is made

   - on each Synchronisation
   - every time a price rule is manuelly modified (on Back Office price
   rule form update submit )
   - every day scheduled job at 00h00, since this is when some price
   rules can end



Best Regards
Tibor
Reply | Threaded
Open this post in threaded view
|

Re: great CPU optimisation on calculate price

oceatoon
sorry they weren't supposed to come out, and I don't think there is a public
access
but everything you need should be in the post if you have trouble setting it
up, don't hesitate to post,
I'll throw in any needed extra information.

Tibor

On 1/15/07, PRONZATO Cedric RD-BIZZ-GRE <[hidden email]>
wrote:

>
> Hi Tibor,
>
> Can you provide us the public IP of your wiki because you used a private
> one (if it is available)?
>
> Thank you,
> Cédric
>
> -----Message d'origine-----
> De : tibor katelbach [mailto:[hidden email]]
> Envoyé : lundi 15 janvier 2007 15:41
> À : [hidden email]
> Objet : great CPU optimisation on calculate price
>
> Hi everyone
>
> Here's how we managed to gain great performance optimisation overall. This
> divided our CPU consuption by half.
>
> Optimisation Price Rule through Cache
> <
> http://192.168.215.62:8000/trac/wiki/priceRules#OptimisationPriceRulethroughCache
> >
>
> Since calculateProductPrice is used at every/any time a product is viewed
> (category page, product page, addToCart) and whenever Price Rules are
> applied, we can optimize the access to this Service by using Ofbiz's
> UtilCache System. This means that instead of recalculating a product price
> at every visit, when entering the calculatePrice Service an existence check
> is made in the Product Price cache with a catalog+productId key.
>
>    - If it exist it will simply return the Map this Service should have
>    returned for this ProductId
>    - otherwise it will execute the complete Service, save the result to
>    Cache for the next visit, and return the requested result.
>
> Our use case needed more than 4000 Price Rules to be applied. This
> drastically slowed down ofbiz's performance. This Caching process can be
> used for any recurent service call.
> Existence Check and Return
> <http://192.168.215.62:8000/trac/wiki/priceRules#ExistenceCheckandReturn>
>
>         UtilCache productPricesCache = (UtilCache)
> UtilCache.utilCacheTable.get("productPriceCache");
>         if (productPricesCache == null)
>             productPricesCache = new UtilCache("productPriceCache",0,0);
>         String productPriceCacheKey =
> productId+prodCatalogId+webSiteId+productStoreId+productStoreGroupId;
>         //if Cache exists
>         if (productPricesCache != null)
>         {
>            Map productPrice =
> (Map)productPricesCache.get(productPriceCacheKey);
>            //if the Key exists
>            if(productPrice!=null)
>                 return productPrice;
>         }
>
>         //else if cache key doesn't exist go through the whole service
>         // build the result Map
>         //add it to the Cache for the next Visit
>         productPricesCache.put(productPriceCacheKey,result);
>         return result;
>
> Important Clear Cache
> <http://192.168.215.62:8000/trac/wiki/priceRules#ImportantClearCache>
>
> Offcourse since Price Rules Change, or Product Prices Change the cache
> needs to be emptied according to project internal rules so that Product
> Prices contain the result of a modification.
>
>    - for a specific Cache Cleanup Method :
> UtilCache.clearCache("productPriceCache");
>
>    - for a global Cache Clean Method : UtilCache.clearAll();
>
> in our use case , we have a clear cache that is made
>
>    - on each Synchronisation
>    - every time a price rule is manuelly modified (on Back Office price
>    rule form update submit )
>    - every day scheduled job at 00h00, since this is when some price
>    rules can end
>
>
>
> Best Regards
> Tibor
>
Reply | Threaded
Open this post in threaded view
|

Re: great CPU optimisation on calculate price

Jacques Le Roux
Administrator
In reply to this post by oceatoon
Hi all,

I wonder if someone has applied this trick or/and if somebody can see any flaws in it (of course clearing caches depends of usage and should be very carefully done...)

Thanks for any comments

Jacques

tibor katelbach wrote
Hi everyone

Here's how we managed to gain great performance optimisation overall. This
divided our CPU consuption by half.

Optimisation Price Rule through Cache
<http://192.168.215.62:8000/trac/wiki/priceRules#OptimisationPriceRulethroughCache>

Since calculateProductPrice is used at every/any time a product is viewed
(category page, product page, addToCart) and whenever Price Rules are
applied, we can optimize the access to this Service by using Ofbiz's
UtilCache System. This means that instead of recalculating a product price
at every visit, when entering the calculatePrice Service an existence check
is made in the Product Price cache with a catalog+productId key.

   - If it exist it will simply return the Map this Service should have
   returned for this ProductId
   - otherwise it will execute the complete Service, save the result to
   Cache for the next visit, and return the requested result.

Our use case needed more than 4000 Price Rules to be applied. This
drastically slowed down ofbiz's performance. This Caching process can be
used for any recurent service call.
Existence Check and Return
<http://192.168.215.62:8000/trac/wiki/priceRules#ExistenceCheckandReturn>

        UtilCache productPricesCache = (UtilCache)
UtilCache.utilCacheTable.get("productPriceCache");
        if (productPricesCache == null)
            productPricesCache = new UtilCache("productPriceCache",0,0);
        String productPriceCacheKey =
productId+prodCatalogId+webSiteId+productStoreId+productStoreGroupId;
        //if Cache exists
        if (productPricesCache != null)
        {
           Map productPrice = (Map)productPricesCache.get(productPriceCacheKey);
           //if the Key exists
           if(productPrice!=null)
                return productPrice;
        }

        //else if cache key doesn't exist go through the whole service
        // build the result Map
        //add it to the Cache for the next Visit
        productPricesCache.put(productPriceCacheKey,result);
        return result;

Important Clear Cache
<http://192.168.215.62:8000/trac/wiki/priceRules#ImportantClearCache>

Offcourse since Price Rules Change, or Product Prices Change the cache needs
to be emptied according to project internal rules so that Product Prices
contain the result of a modification.

   - for a specific Cache Cleanup Method :
UtilCache.clearCache("productPriceCache");

   - for a global Cache Clean Method : UtilCache.clearAll();

in our use case , we have a clear cache that is made

   - on each Synchronisation
   - every time a price rule is manuelly modified (on Back Office price
   rule form update submit )
   - every day scheduled job at 00h00, since this is when some price
   rules can end



Best Regards
Tibor
Reply | Threaded
Open this post in threaded view
|

Re: great CPU optimisation on calculate price

jonwimp
No problems with this approach. Except...

Isn't it possible to clear specific cache lines in a cache? More fine-grained.

We will need to do a good comb-through to find all spots in OFBiz where the price rule can be
affected. For each of those spots, wire in a "cache clear" or "cache recalculate".

A good way to do this in OFBiz is to use the EECAs.

That covers the 2nd cache clear item in Tibor's list of 3 cache clear items.

For Tibor's 3rd cache clear item, it might be more reliable (cache updates more timely) if we use
JobSandbox to schedule a recalculation of price rules for each expiration time.

I don't understand Tibor's 1st cache clear item (Synchronization). Will there be more than 1
database? If so, yes, a cache clear here and a recalculation is required.

Jonathon

jacques.le.roux wrote:

> Hi all,
>
> I wonder if someone has applied this trick or/and if somebody can see any
> flaws in it (of course clearing caches depends of usage and should be very
> carefully done...)
>
> Thanks for any comments
>
> Jacques
>
>
> tibor katelbach wrote:
>> Hi everyone
>>
>> Here's how we managed to gain great performance optimisation overall. This
>> divided our CPU consuption by half.
>>
>> Optimisation Price Rule through Cache
>> <http://192.168.215.62:8000/trac/wiki/priceRules#OptimisationPriceRulethroughCache>
>>
>> Since calculateProductPrice is used at every/any time a product is viewed
>> (category page, product page, addToCart) and whenever Price Rules are
>> applied, we can optimize the access to this Service by using Ofbiz's
>> UtilCache System. This means that instead of recalculating a product price
>> at every visit, when entering the calculatePrice Service an existence
>> check
>> is made in the Product Price cache with a catalog+productId key.
>>
>>    - If it exist it will simply return the Map this Service should have
>>    returned for this ProductId
>>    - otherwise it will execute the complete Service, save the result to
>>    Cache for the next visit, and return the requested result.
>>
>> Our use case needed more than 4000 Price Rules to be applied. This
>> drastically slowed down ofbiz's performance. This Caching process can be
>> used for any recurent service call.
>> Existence Check and Return
>> <http://192.168.215.62:8000/trac/wiki/priceRules#ExistenceCheckandReturn>
>>
>>         UtilCache productPricesCache = (UtilCache)
>> UtilCache.utilCacheTable.get("productPriceCache");
>>         if (productPricesCache == null)
>>             productPricesCache = new UtilCache("productPriceCache",0,0);
>>         String productPriceCacheKey =
>> productId+prodCatalogId+webSiteId+productStoreId+productStoreGroupId;
>> //if Cache exists
>>         if (productPricesCache != null)
>>         {
>>            Map productPrice =
>> (Map)productPricesCache.get(productPriceCacheKey);
>>            //if the Key exists
>>            if(productPrice!=null)
>> return productPrice;
>> }
>>
>>         //else if cache key doesn't exist go through the whole service
>>         // build the result Map
>>         //add it to the Cache for the next Visit
>>         productPricesCache.put(productPriceCacheKey,result);
>>         return result;
>>
>> Important Clear Cache
>> <http://192.168.215.62:8000/trac/wiki/priceRules#ImportantClearCache>
>>
>> Offcourse since Price Rules Change, or Product Prices Change the cache
>> needs
>> to be emptied according to project internal rules so that Product Prices
>> contain the result of a modification.
>>
>>    - for a specific Cache Cleanup Method :
>> UtilCache.clearCache("productPriceCache");
>>
>>    - for a global Cache Clean Method : UtilCache.clearAll();
>>
>> in our use case , we have a clear cache that is made
>>
>>    - on each Synchronisation
>>    - every time a price rule is manuelly modified (on Back Office price
>>    rule form update submit )
>>    - every day scheduled job at 00h00, since this is when some price
>>    rules can end
>>
>>
>>
>> Best Regards
>> Tibor
>>
>>
>