Unit Testing

Overview

Unit testing focuses on verifying individual units of a module in isolation. When testing code that interacts with external backends, you can use mock objects to simulate those dependencies. This approach allows you to test your code without requiring actual backend services.

The CRISP API provides mock object support to simplify testing code that depends on CRISP API integrations.

Maven Dependency

To use the CRISP API mock objects in your unit tests, add the following Maven dependency:

<dependency> <groupId>org.onehippo.cms7</groupId> <artifactId>hippo-addon-crisp-mock</artifactId> <version>${hippo.addon-crisp.version}</version> <scope>test</scope> </dependency>

Available Mock Objects

CRISP API includes the following mock objects and helper classes for unit testing:

  • org.onehippo.cms7.crisp.mock.resource.MockJacksonResourceResolverAdapter
    Extend this adapter to create a mock ResourceResolver for backends that return JSON payloads.
  • org.onehippo.cms7.crisp.mock.resource.MockJdomResourceResolverAdapter
    Extend this adapter to create a mock ResourceResolver for backends that return XML payloads.
  • org.onehippo.cms7.crisp.mock.broker.MockResourceServiceBroker
    Use this class to create a mock ResourceServiceBroker.
  • org.onehippo.cms7.crisp.mock.module.MockCrispHstServices
    Use this helper to replace the system default ResourceServiceBroker during unit tests.

Example: Unit Test with Mock ResourceResolver

If your code interacts with a backend that returns JSON and relies on CRISP API calls, you can use MockJacksonResourceResolverAdapter to mock the backend. Register the mock ResourceResolver with a MockResourceServiceBroker, then set this broker as the system default. Your code will then use the mock objects during testing.

The following example demonstrates this approach:

public class ProductServiceTest { @Test public void testFindProducts() throws Exception { Map<String, ResourceResolver> resourceResolverMap = new HashMap<>(); // 1. Create a mock ResourceResolver for the "products" resourceSpace and add it to the map. resourceResolverMap.put("products", new MockJacksonResourceResolverAdapter() { @Override public Resource findResources(String baseAbsPath, Map<String, Object> pathVariables, ExchangeHint exchangeHint) throws ResourceException { // 2. For this test, read data from a local file in the classpath whenever findResources(...) is called. return urlToResource(ProductServiceTest.class.getResource("products-output.json")); } }); // 3. Create and register the mock ResourceServiceBroker. ResourceServiceBroker mockBroker = new MockResourceServiceBroker(resourceResolverMap); MockCrispHstServices.setDefaultResourceServiceBroker(mockBroker); // 4. Invoke the code under test. ProductService productService = new ProductService(); // getProducts() should retrieve the ResourceServiceBroker via CrispHstServices.getDefaultResourceServiceBroker(...). // It will use the mockBroker set above. // When getProducts() calls findResources("products", ...), it receives the Resource from urlToResource(...). List<Product> products = productService.getProducts(); // 5. Add assertions to validate the results. // ... } }

Summary of steps:

  1. Extend MockJacksonResourceResolverAdapter or MockJdomResourceResolverAdapter to create a mock ResourceResolver based on your backend's payload format.
  2. Create a mock ResourceServiceBroker using MockResourceServiceBroker and provide your ResourceResolver instances in the constructor map.
  3. Register the mock ResourceServiceBroker as the system default using MockCrispHstServices.setDefaultResourceServiceBroker(...). All subsequent CRISP API calls will use the mock objects.
  4. Run the code you want to test.
  5. Use assertions to verify the expected behavior.

Using a Real ResourceResolver in Tests

You may need to test code with a real backend by providing an actual ResourceResolver instance. JUnit supports conditional testing with assumptions, which you can use as needed.

MockResourceServiceBroker accepts a map of resourceSpace keys and ResourceResolver values. You can add any ResourceResolver instance for a specific resourceSpace.

For example, the Simple JSON API Example defines a ResourceResolver bean as follows:

<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> <!-- ... --> </bean>

You can create the equivalent configuration in Java for your unit tests:

public class MyExampleTest { @Test public void testFindAll() throws Exception { Map<String, ResourceResolver> resourceResolverMap = new HashMap<>(); // Create the ResourceResolver as defined in the bean configuration. SimpleJacksonRestTemplateResourceResolver resourceResolver = new SimpleJacksonRestTemplateResourceResolver(); resourceResolver.setCacheEnabled(true); resourceResolver.setBaseUri("https://commerce.example.com/api"); resourceResolver.setRestTemplate(new RestTemplate(new SimpleClientHttpRequestFactory())); // Register the ResourceResolver for the 'simpleSpace' resourceSpace. resourceResolverMap.put("simpleSpace", resourceResolver); ResourceServiceBroker mockBroker = new MockResourceServiceBroker(resourceResolverMap); MockCrispHstServices.setDefaultResourceServiceBroker(mockBroker); // ... } }

Alternatively, if you use a Spring BeanFactory such as org.springframework.context.support.ClassPathXmlApplicationContext in your unit tests, you can load and use the ResourceResolver bean directly from the application context.

Share Feedback
Page: /build/crisp-api/introduction-config/unit-testing
Section: Build
Category *
Unit Testing | Bloomreach Content Documentation