Using hybris rule engine for product recommendations


There are the following user cases for the recommendation engines,

  • Substitute products:
    • (1) Based on attribute similarity. It can rely on the properties of the item(s), which are analyzed to determine what else the user may like.
      • Example: Apple iphone 6 and Samsung Galaxy S6 are substitutes because they have a lot of similar/same characteristics (product attributes).
    • (2) Based on association rules 
      • Example: Coke and Pepsi are substitutes. Note that it is a manual work to connect them into the group.
  • Сomplementary products
    • (3) Based on collaborative filtering (frequently bought together)
      • Example: the IPA beer and Kettle Jalapeno chips are complementary products because people like to buy them together.
    • (4) Based on association rules (for co-purchased products)
      • Example: the IPA beer and Lays are complementary products because the merchant wants to sell more Lays than Kettle.

Hybris out-of-the-box supports #2 and #4, but the association rules in it are extremely basic: the simple product linking SKU<->SKU. In hybris you need to manually select other up-sell/cross-sell products or use the external tool. It means that in order to link the five digital cameras with a dozen of memory cards you need to manually or automatically create 24×5=120 records of the reference product information. The number of the records is getting bigger for the large product catalogs.

Two other mentioned approaches, the collaborative filtering and attribute similarity are out of scope of this post. The algorithms used there are good for a large amount of data and traffic. A main goal of the recommendation engine of this kind is to extract new knowledge from the available sources (such as the PIM database, CRM and webserver logs) and use it to enrich the customer experience and increase the sales.

The purpose of this article is to show the PoC of the recommendation system based on the rule engine. Hybris has already had the powerful rule engine for the product promotion management, so I decided to reuse it for the recommendation system.


There are two pieces of functionality,

  • Rule builder for the promotion engine
  • Recommendation engine
As you can see in the diagram below, these modules are not connected with each other.  Builder produces the rules, and the recommendation engine uses them.


There are some examples of the rules which are available in the system already:

  • If you visit the product page with one of Film Camera products, the system must recommend the color and black&white films as complimentary products, if any.
  • If the product has “memory stick” in the “Supported memory cards” classification attribute, the system must recommend the Memory Stick products, if any.
  • For the Products X,Y,Z the system must recommend the products from categories A and B except the products with the attribute N=<something>

Actually, the range of possible rules it truly indefinite. The hybris rule builder allows customizing the conditions and actions.

If more than one rule is fulfilled, the results will be mixed.


Rule Builder

Rule Builder is initially designed for promotions. It is a brand-new product: SAP added it to hybris in April 2016 (version 6.0)

In order to use it for the product recommendation rules, I added custom conditions and actions.

Generating recommended products

This module uses hybris Drools engine for evaluating rules against the products (one or more). The result is a SOLR request.

Custom Conditions

For the demo I created two custom conditions:

  • product title condition
  • product classification attribute condition.

It is easy to create a universal product condition that deals with all product attributes available.

It is important that in my solution conditions work with ProductModel attributes for filtering while actions deal with indexed properties.

Custom actions

For the demo I created one custom condition:

  • Filter all products with specified Indexed Properties.

Post processing

The resulting SOLR request is a merge of the rules output.




Technical details


INSERT_UPDATE RuleConditionDefinition;id[unique=true] ;name[lang=en] ;priority;breadcrumb[lang=$lang] ;allowsChildren ;translatorId ;translatorParameters;categories(id)
;producttitle ;Product title ;200 ;Product ;false ;simpleProductAttributeConditionTranslator ; ;general
;Example_Compatible_memory_cards ;Compatible memory cards ;200 ;Product ;false ;extProductAttributeConditionTranslator ; ;general

INSERT_UPDATE RuleConditionDefinitionParameter;definition(id)[unique=true];id[unique=true];priority;name[lang=$lang];description[lang=$lang];type;value;required[default=true];
#y_cart_total;operator;1100;Operator;Operator to compare the cart total value;Enum(de.hybris.platform.ruledefinitions.AmountOperator);”””GREATER_THAN_OR_EQUAL”””;
;producttitle ;titlestr ;1000 ;Title Substring ;Title Substring ;java.lang.String;;
;Example_Compatible_memory_cards;comp_mc;1001;Example Compatible memory cards (Substring);Example Compatible memory cards (Substring); java.lang.String

INSERT_UPDATE RuleConditionDefinitionRuleTypeMapping;definition(id)[unique=true];ruleType(code)[unique=true]



INSERT_UPDATE RuleActionDefinitionCategory;id[unique=true];name[lang=$lang];priority

INSERT_UPDATE RuleActionDefinition;id[unique=true];name[lang=$lang];priority;breadcrumb[lang=$lang];translatorId;translatorParameters;categories(id)
;recommend_products;Add products to recommendations;200;Add product to recommendations;ruleExecutableActionTranslator;actionId->ruleAddProductsToRecommendedAction;recommendations

INSERT_UPDATE RuleActionDefinitionParameter;definition(id)[unique=true];id[unique=true];priority;name[lang=$lang];description[lang=$lang];type;value;required[default=true]
;recommend_products;solrProperty;100;Solr Property;Solr Property;ItemType(SolrIndexedProperty);
;recommend_products;value;102;Value of the Field;Product Title Substring;java.lang.String;;

INSERT_UPDATE RuleActionDefinitionRuleTypeMapping;definition(id)[unique=true];ruleType(code)[default=PromotionSourceRule][unique=true]


  • Custom ProductRAO populator. Converts0 ProductModel to ProductRAO. By default, only “code” and “supercategories” are populated. I added all the remaining product properties, including classification attributes.
  • Custom Product Attribute Condition Translators. This classes are used to convert the values from the condition parameters (see impex) into DroolsRules (more exact, into the RuleIrCondition that used for the drools rules composition). I created two custom translators, as an example, for the product title and for the product classification attribute. It is trivial to convert it into something more comprehensive.
  • Custom Rule Executable Action. I use only one type of action, “ProductsToRecommend”. This action is executed each time the rule condition is fulfilled. Internally, all this class do is adding ProductToRecommendRAO with configurable rule-dependent data as a fact.
  • ProductToRecommendRAO item type. I used the only custom attribute here, solrCondition (Map type). This structure is used for the messages from actions back to the controller or service. The messages contain the solr attribute name and value.


Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: