Testing Components that Extend Core Component via Sling Delegation Pattern | Community
Skip to main content
July 30, 2021

Testing Components that Extend Core Component via Sling Delegation Pattern

  • July 30, 2021
  • 2 replies
  • 2708 views

Hello All, 

 

I am using AEM as a cloud service and am using the AEM specific cloud jar file for my local instances. I am trying to test a component which uses the Sling Delegation Pattern for adding new functionality to an AEM core component. 

 

My model looks something like this:

 

@Model(adaptables = SlingHttpServletRequest.class, adapters = {List.class}, resourceType = TeaserListModel.TEASER_LIST_RESOURCE_TYPE,defaultInjectionStrategy = DefaultInjectionStrategy.OPTIONAL)
public class TeaserListModel implements List {
@Self
@Via(type = ResourceSuperType.class)
private List list; // Expect V1 of ListImpl from core components to be injected here
}


My test looks like this:

public class TeaserListModelTest implements List {

private static final String TEST_BASE = "/teaserlist";
private static final String CONTENT_ROOT = "/content";
private static final String CURRENT_PAGE = "/content/list";
private static final String CONTEXT_PATH = "/context";
private static final String LIST_1 = CURRENT_PAGE + "/jcr:content/root/staticListType";
private static final String LIST_2 = CURRENT_PAGE + "/jcr:content/root/staticWithVanityPaths";

public final AemContext context = CoreComponentTestContext.newAemContext();

@BeforeEach
public void setUp() {
context.load().json(TEST_BASE + CoreComponentTestContext.TEST_CONTENT_JSON, CONTENT_ROOT);
}

@Test
void testTeaserListModelValues() {
Resource currentResource = context.currentResource("/content/list/jcr:content/root/staticListType");
TeaserListModel model = context.request().adaptTo(TeaserListModel.class);
assertNotNull(model);
}
}

 

Here is all my test-content.json (lots of different items here since I've been trying different things)

{
"teaserlist": {
"jcr:primaryType": "nt:unstructured",
"showModificationDate": true,
"tagsMatch": "any",
"linkItems": true,
"orderBy": "originalPublishDate",
"jcr:lastModifiedBy": "admin",
"jcr:created": "Tue Jul 20 2021 16:03:08 GMT+0530",
"parentPage": "/content/tsc/en",
"sortOrder": "desc",
"maxItems": "6",
"showDescription": true,
"sling:resourceType": "mycompany/components/template/teaserlist",
"childDepth": "1",
"listFrom": "children",
"dateFormat": "yyyy-MM-dd"
},
"teaserTestPage": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "JCR Title",
"teaserlist": {
"jcr:primaryType": "nt:unstructured",
"showModificationDate": "true",
"jcr:createdBy": "admin",
"tagsMatch": "any",
"linkItems": "true",
"orderBy": "originalPublishDate",
"jcr:lastModifiedBy": "admin",
"jcr:created": "Wed Jul 28 2021 09:57:54 GMT-0400",
"parentPage": "/content/teaserTestPage",
"sortOrder": "asc",
"id": "345",
"maxItems": "5",
"showDescription": "true",
"jcr:lastModified": "Thu Jul 29 2021 04:19:44 GMT-0400",
"sling:resourceType": "mycompany/components/content/teaserlist",
"sling:resourceSuperType": "core/wcm/components/list",
"childDepth": "5",
"listFrom": "children"
}
},
"list": {
"jcr:primaryType": "nt:unstructured",
"showModificationDate": "false",
"jcr:createdBy": "admin",
"tagsMatch": "any",
"linkItems": "true",
"jcr:lastModifiedBy": "admin",
"jcr:created": "Wed Jul 07 2021 14:01:33 GMT-0400",
"sortOrder": "asc",
"showDescription": "true",
"jcr:lastModified": "Sun Jul 11 2021 20:39:28 GMT-0400",
"sling:resourceType": "mycompany/components/content/list",
"childDepth": "1",
"listFrom": "children"
}
},
"list": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "List Page",
"root": {
"jcr:primaryType": "nt:unstructured",
"sling:resourceType": "wcm/foundation/components/responsivegrid",
"illegalListType": {
"jcr:primaryType": "nt:unstructured",
"sling:resourceType": "core/wcm/components/list",
"listFrom": "nonExisting"
},
"staticListType": {
"jcr:primaryType": "nt:unstructured",
"sling:resourceType": "core/wcm/components/list/v2/list",
"listFrom": "static",
"showThumbnail": "true",
"linkItems": "true",
"showDescription": "true",
"showModificationDate": "true",
"pages": [
"/content/list/pages/page_1",
"/content/list/pages/page_2"
]
},
"staticWithVanityPaths": {
"jcr:primaryType": "nt:unstructured",
"sling:resourceType": "core/wcm/components/list/v2/list",
"listFrom": "static",
"showThumbnail": "true",
"linkItems": "true",
"showDescription": "true",
"showModificationDate": "true",
"orderBy": "title",
"pages": [
"/content/list/pages/page_3",
"/content/list/pages/page_4"
]
}
}
},
"pages": {
"page_1": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "Page 1",
"cq:lastModified": "2016-09-23T16:12:45.000-07:00"
},
"page_1_1": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "Page 1.1"
}
},
"page_1_2": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "Page 1.2"
},
"page_1_2_1": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "Page 1.2.1"
},
"page_1_2_1_1": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "Page 1.2.1.1"
}
}
}
},
"page_1_3": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "Page 1.3",
"cq:tags": [
"list:test_category/test_tag"
]
}
}
},
"page_2": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "Page 2",
"cq:lastModified": "2016-09-21T16:12:45.000-07:00"
}
},
"page_3": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "Page 3",
"sling:vanityPath": "/page_3.html"
}
},
"page_4": {
"jcr:primaryType": "cq:Page",
"jcr:content": {
"jcr:primaryType": "cq:PageContent",
"jcr:title": "Page 4",
"sling:vanityPath": "/4_page.html"
}
}
}
}
}


My issue is that during testing, the list property of the TeaserListModel is instead of type TeaserListModel instead of ListImpl. If I omit the sling:resourceSuperType in the resources json, then list is type null. I also cannot import of the ListImpl classes since they are hidden in the internal folder of AEM core components. What I would like is the list property of TeaserListModel to be v1 of ListImpl from core components. 

When deploying to my local instance, I do see that the list property of TeaserListModel is set to the core components v1 ListImpl. Its only during testing does it seem to not find the v1 ListImpl to inject, and instead either marks the field as null, or adapts it to the TeaserListModel. 

 

Has anyone else ran into this issue before? I am also using Junit 5 with the v3.0.2 of io-mocks. 

This post is no longer active and is closed to new replies. Need help? Start a new post to ask your question.

2 replies

arunpatidar
Community Advisor
Community Advisor
August 1, 2021
Adobe Employee
August 5, 2021

You test content is not properly setup. You will need to include your component definition (in /apps/...) as well as define there the sling:resourceSuperType for it.

 

For an example of how to load test content in apps, have a look at https://github.com/adobe/aem-core-wcm-components/blob/master/bundles/core/src/test/java/com/adobe/cq/wcm/core/components/internal/models/v1/ProgressBarImplTest.java#L49 and https://github.com/adobe/aem-core-wcm-components/blob/master/bundles/core/src/test/resources/progressbar/test-apps.json#L9

sreenu539
May 19, 2023

I tried having /apps, /mysite jsons with actual component definitions with sling:resourceSuperType, as well in /content json sling:resourceType, sling:resourceSuperType. No success in injecting @self @2434638 ResourceSuperType or through adaptTo

 

If you have any successful code example, can you please provide.