Configuring CRISP Addon - BloomReach Experience - Open Source CMS

This article covers a Hippo CMS version 12. There's an updated version available that covers our most recent release.

29-04-2019

Configuring CRISP Addon

Introduction

CRISP configurations are maintained in repository by default in the location at /hippo:configuration/hippo:modules/crispregistry/hippo:moduleconfig.

Since Bloomreach Experience Manager 12.6, the CRISP repository configuration path can be customized by setting crisp.moduleconfig.path property in /WEB-INF/hst-config.properties in the site web applciation like the following example:

# Setting a custom CRISP configuration path.
crisp.moduleconfig.path = /crisp/site1/hippo:moduleconfig

where /crisp/site1/hippo:moduleconfig may look like this:

/crisp:
  jcr:primaryType: nt:unstructured
  /site1:
    jcr:primaryType: nt:unstructured
    /hippo:moduleconfig:
      jcr:primaryType: crisp:moduleconfig
      /crisp:resourceresolvercontainer:
        jcr:primaryType: crisp:resourceresolvercontainer
        ...

The CRISP configuration can be set like the following:

<?xml version="1.0" encoding="UTF-8"?>
<sv:node sv:name="hippo:moduleconfig" xmlns:sv="http://www.jcp.org/jcr/sv/1.0">
  <sv:property sv:name="jcr:primaryType" sv:type="Name">
    <sv:value>crisp:moduleconfig</sv:value>
  </sv:property>
  <sv:node sv:name="crisp:resourceresolvercontainer">
    <sv:property sv:name="jcr:primaryType" sv:type="Name">
      <sv:value>crisp:resourceresolvercontainer</sv:value>
    </sv:property>
    <!-- An example ResourceResolver configuration child node for 'demoProductCatalogs' resource space. -->
    <sv:node sv:name="demoProductCatalogs">
      <sv:property sv:name="jcr:primaryType" sv:type="Name">
        <sv:value>crisp:resourceresolver</sv:value>
      </sv:property>
      <sv:property sv:name="crisp:beandefinition" sv:type="String">
        <sv:value>
          <!-- XML Bean definition here for a ResourceResolver for the resource space, 'demoProductCatalogs'. -->
        </sv:value>
      </sv:property>
      <sv:property sv:multiple="true" sv:name="crisp:propnames" sv:type="String">
        <sv:value>example.commerce.api.base.uri</sv:value>
      </sv:property>
      <sv:property sv:multiple="true" sv:name="crisp:propvalues" sv:type="String">
        <sv:value>http://localhost:8080/example-commerce/api/v1</sv:value>
      </sv:property>
    </sv:node>
  </sv:node>
</sv:node>

You can bootstrap configurations into the node, or you can update the configuration there at runtime. Any changes at runtime will be affected right away.

Before going further, let's take a look at how the configuration nodes are structured:

  • The CRISP module configuration node at /hippo:configuration/hippo:modules/crispregistry/hippo:moduleconfig must be of primary node type, crisp:moduleconfig.
  • The CRISP module configuration node has single child node named crisp:resourceresolvercontainer of primary node type, crisp:resourceresolvercontainer, that may contain zero or multiple child node(s) specifying ResourceResolvers, which primary node type is crisp:resourceresolver, for each resource space underneath. So, in the example shown above, there is only one ResourceResolver configuration for a resource named demoProductCatalogs which is going to be used when invoking ResourceServiceBroker APIs.
  • A ResourceResolver configuration node under /hippo:configuration/hippo:modules/crispregistry/hippo:moduleconfig/crisp:resourceresolvercontainer must be of primary node type, crisp:resourceresolver.
  • A ResourceResolver configuration node (of primary node type, crisp:resourceresolver) could have crisp:propnames (string multiple), crisp:propvalues (string multiple) and crisp:beandefinition (string) properties.
  • crisp:propnames (string multiple) and crisp:propvalues (string multiple) properties define pairs of variable property names and values to be interpolated in the crisp:beandefinition (string) property value. So, a management UI tool may possibly let administrator edit those pairs of variable properties without having to expose the XML bean definition in crisp:beandefinition (string) property directly.
  • crisp:beandefinition (string) property defines Spring Framework Bean definition for a ResourceResolver bean in XML format. Find the example bootstrap configurations for details in the demo project.

Adding a ResourceResolver configuration for a new resource space

You can configure a ResourceResolver in the repository configuration as explained below.

Since Bloomreach Experience Manager 12.6, you can also configure a ResourceResolver directly in a CRISP API Addon's Spring Bean assembly XML file in the delivery tier web application (e.g. /site). in which case, the ResourceResolver can be accessed only in the same delivery tier web application. The ResourceResolver cannot be accessed from other web application such as /cms if you configure it in a CRISP API Addon's Spring Bean assembly XML file of a delivery tier web application.

Adding a ResourceResolver in repository configuration

By default, there is no ResourceResolver configuration under /hippo:configuration/hippo:modules/crispregistry/hippo:moduleconfig/crisp:resourceresolvercontainer. You can add ResourceResolver configuration nodes there for your backend services.

For example, if you want to add a new resource space, 'demoProductCatalogs', then you should add a node by the resource space name, 'demoProductCatalogs' (ie, /hippo:configuration/hippo:modules/crispregistry/hippo:moduleconfig/crisp:resourceresolvercontainer/demoProductCatalogs). And the 'demoProductCatalogs' can look like the following example (in System View XML format):

<?xml version="1.0" encoding="UTF-8"?>
<sv:node sv:name="demoProductCatalogs" xmlns:sv="http://www.jcp.org/jcr/sv/1.0">
  <sv:property sv:name="jcr:primaryType" sv:type="Name">
    <sv:value>crisp:resourceresolver</sv:value>
  </sv:property>
  <sv:property sv:name="crisp:beandefinition" sv:type="String">
    <sv:value><![CDATA[<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.1.xsd">
 
  <bean parent="abstractCrispSimpleJacksonRestTemplateResourceResolver"
        class="org.onehippo.cms7.crisp.core.resource.jackson.SimpleJacksonRestTemplateResourceResolver">
    <property name="cacheEnabled" value="${cache.enabled}" />
    <property name="baseUri" value="${example.commerce.api.base.uri}" />
    <property name="restTemplate">
      <bean class="org.springframework.web.client.RestTemplate">
        <property name="requestFactory" ref="org.springframework.http.client.ClientHttpRequestFactory" />
      </bean>
    </property>
    <property name="resourceLinkResolver">
      <bean class="org.onehippo.cms7.crisp.core.resource.FreemarkerTemplateResourceLinkResolver">
        <property name="templateSource">
          <value>http://www.example.com/products/${(preview == "true")?then("staging", "current")}/sku/${resource.valueMap['SKU']!"unknown"}/overview.html</value>
        </property>
      </bean>
    </property>
    <property name="resourceDataCache">
      <bean class="org.onehippo.cms7.crisp.core.resource.SpringResourceDataCache">
        <constructor-arg>
          <bean class="org.springframework.cache.ehcache.EhCacheCache">
            <constructor-arg>
              <bean parent="abstractCrispResourceEhCache">
                <property name="cacheName" value="demoProductCatalogsCache" />
                <property name="maxEntriesLocalHeap" value="1000" />
                <property name="maxEntriesLocalDisk" value="0" />
                <property name="timeToLiveSeconds" value="60" />
                <property name="timeToIdleSeconds" value="60" />
              </bean>
            </constructor-arg>
          </bean>
        </constructor-arg>
      </bean>
    </property>
  </bean>
 
</beans>
    ]]></sv:value>
  </sv:property>
  <sv:property sv:multiple="true" sv:name="crisp:propnames" sv:type="String">
    <sv:value>cache.enabled</sv:value>
    <sv:value>example.commerce.api.base.uri</sv:value>
  </sv:property>
  <sv:property sv:multiple="true" sv:name="crisp:propvalues" sv:type="String">
    <sv:value>true<sv:value>
    <sv:value>http://localhost:8080/example-commerce/api/v1</sv:value>
  </sv:property>
</sv:node>

The example configuration shown above is going to add a ResourceResolver configuration node named demoProductCatalogs which is used as resource space name when invoking ResourceServiceBroker API.

Adding a ResourceResolver in Spring Bean assembly

Since Bloomreach Experience Manager 12.6, you can configure a ResourceResolver bean directly in a CRISP API Addon's Spring Bean XML file instead of doing that in the repository configuration.

To achieve that, define a ResourceResolver bean with a unique identifier which is used as a resource space name.

For example, if you want to define a ResourceResolver with a resource space name, "demoProductCatalogs", then you should define a bean with ID, "demoProductCatalogs" like the following in a CRISP API Addon's Spring assembly XML file (e.g, site/src/main/resources/META-INF/hst-assembly/addon/crisp/overrides/custom-resource-resolvers.xml):

<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.1.xsd">

  <bean id="demoProductCatalogs"
        parent="abstractCrispSimpleRestTemplateResourceResolver"
        class="org.onehippo.cms7.crisp.core.resource.jdom.SimpleJdomRestTemplateResourceResolver">
    <!-- SNIP -->
  </bean> 

</beans>

You can define multiple ResourceResolver beans in single Spring assembly XML file as long as each bean has a unique identifier which is used as resource space name.

The resource space by the ResourceResolver bean, which is defined in a CRISP API Addon's Spring assembly XML file in a delivery tier web application (e.g, /site), cannot be accessed from other web application (e.g, /cms). It can be used only by the delivery tier web application.

ResourceResolver Bean Definition

In the example configuration in the previous section, basically the ResourceResolver component will be instantiated and registered for demoProductCatalogs resource space name by the crisp:beandefinition property configuration in Spring Framework Bean XML configuration.

Note: CRISP Core will create a child ApplicationContext from the XML beans configuration in the crisp:beandefinition property and simply get a bean of type, org.onehippo.cms7.crisp.api.resource.ResourceResolver, to register the bean for the resource space, the name of which is specified by the ResourceResolver configuration node name. Therefore, you don't have to set id attribute of the ResourceResolver bean definition.

The crisp:beandefinition property configuration could be interpolated by the variables set by pairs of crisp:propnames and crisp:propvalues properties, which possibly enables a management UI to be able to give administrator ability to configure those configuration parameters without having to look into crisp:beandefinition XML bean configuration in detail in most cases.

In the example in the previous section, the ResourceResolver component is configured by the bean definition with class="org.onehippo.cms7.crisp.core.resource.jackson.SimpleJacksonRestTemplateResourceResolver". SimpleJacksonRestTemplateResourceResolver is a ResourceResolver implementation that handles any JSON-based REST APIs in a generic way. Also, please note that the ResourceResolver bean has parent="abstractCrispSimpleJacksonRestTemplateResourceResolver", which means the bean definition inherits all the common features provided by CRISP module library by the "parent" bean definition. If possible, it is a good practice to inherits an abstract bean definitions of CRISP module library to inherit all the goodness provided by the CRISP library wherever possible. For your information, the following abstract bean definitions for ResourceResolver components are defined by default.

<!-- SNIP -->
 
<!-- Basic HTTP Client Enabled Abstract Base Bean Definition -->
<bean id="abstractCrispHttpRequestResourceResolver" abstract="true">
  <property name="clientHttpRequestFactory"
            ref="org.springframework.http.client.ClientHttpRequestFactory" />
</bean>
 
<!-- SNIP -->
 
<!-- Basic JSON Supporting (Jackson Library based) HTTP Client Enabled Abstract Base Bean Definition -->
<bean id="abstractCrispSimpleJacksonRestTemplateResourceResolver" abstract="true"
      parent="abstractCrispHttpRequestResourceResolver">
  <property name="cacheEnabled" value="true" />
</bean>
 
<!-- SNIP -->

Configuring Http Connection Pool 

CRISP API provides the default HTTP connection pool with 600 maximum connections in total and 200 maximum connections per route, which should be good enough in most use cases.

If you want to change this default configuration, add an XML file in site/src/main/resources/META-INF/hst-assembly/addon/crisp/overrides/ folder (e.g, custom-crisp-http-client.xml) like the following example:

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:aop="http://www.springframework.org/schema/aop"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
                           http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd">

  <!-- Customizing the default CRISP HttpClientBuilderFactoryBean with custom settings. -->
  <bean id="crispHttpClientBuilder" class="org.onehippo.cms7.crisp.core.support.httpclient.DefaultHttpClientBuilderFactoryBean">
    <property name="useSystemProperties" value="true" />
    <property name="maxConnTotal" value="400" />
    <property name="maxConnPerRoute" value="200" />
    <property name="connectionTimeMillisToLive" value="3600000" />
  </bean>

</beans>

Below are details on each property:

 Property  Description  Default Value
 useSystemProperties  If this is set to true, it becomes equivalent to calling on HttpClientBuilder.useSystemProperties(), which allows passing system properties when initializing an HttpClient. See its JavaDoc for details.  true
 maxConnTotal  The maximum HTTP connections in total.  600
 maxConnPerRoute  The maximum HTTP connections per route.  200
 connectionTimeMillisToLive  The time to live milliseconds for each HTTP connection. By default, it is set to -1. If this value is not a positive number, then it means that HTTP connections will never expire.  -1
Did you find this page helpful?
How could this documentation serve you better?
On this page
    Did you find this page helpful?
    How could this documentation serve you better?