Hi all,
I'm trying to test a model that uses the @ParentResourceValueMapValue on its properties (see snippet below)
@Model(
adaptables = {SlingHttpServletRequest.class, Resource.class},
adapters = {ArticleInfo.class, Component.class, ComponentExporter.class},
resourceType = ArticleInfoImpl.RESOURCE_TYPE,
defaultInjectionStrategy = DefaultInjectionStrategy.OPTIONAL
)
name = ExporterConstants.SLING_MODEL_EXPORTER_NAME,
extensions = ExporterConstants.SLING_MODEL_EXTENSION
)
public class ArticleInfoImpl extends com.ally.components.core.internal.models.v1.ComponentImpl implements ArticleInfo {
protected static final String RESOURCE_TYPE = "contenthub/components/content/articleinfo/v1/articleinfo";
private final Logger log = LoggerFactory.getLogger(this.getClass().getName());
private static final String DATE_FORMAT = "MM/dd/uuuu";
@ParentResourceValueMapValue
private String customPubDate;
@ParentResourceValueMapValue
private String customModDate;
@ParentResourceValueMapValue
private String contentLength;
@ParentResourceValueMapValue
private String contentType;
@ParentResourceValueMapValue
private String authorContentFragmentPath;
//For STOR-43776
//NB: The name and type may change need to work with Cherub on this
@ParentResourceValueMapValue
private String customPubDateSelection;
@ParentResourceValueMapValue
private String customModDateSelection;
private String authorName = "";
private ContentTypeConverter contentTypeConverter;
private DateService dateService;
@SlingObject
private ResourceResolver resourceResolver;
@PostConstruct
public void initModel() {
super.initModel();
if (authorContentFragmentPath != null) {
Resource pathResource = resourceResolver.getResource(authorContentFragmentPath);
ContentFragment authorFragment = pathResource.adaptTo(ContentFragment.class);
String modelPath = "global/models/person";
String[] elementNames = new String[] { "firstName", "lastName" };
if (ContentFragmentUtils.getType(authorFragment).equals(modelPath)) {
log.info("Content fragment matches specified type of " + modelPath);
DAMContentFragment authorFragmentModel = new DAMContentFragmentImpl(pathResource, contentTypeConverter, null, elementNames);
String firstName = "";
String lastName = "";
firstName = java.util.Optional.ofNullable(authorFragmentModel.getElements().get(0).getValue()).orElse("").toString();
lastName = java.util.Optional.ofNullable(authorFragmentModel.getElements().get(1).getValue()).orElse("").toString();
if(lastName == "") {
authorName = firstName;
} else {
authorName = firstName + " " + lastName;
}
} else {
log.warn("Content fragment does not match the specified type of " + modelPath);
}
}
}
When I try to setup a Junit Test for this I continue to get the following error
Unable to create model class com.ally.components.contenthub.internal.models.v1.content.ArticleInfoImpl
at org.apache.sling.models.impl.ModelAdapterFactory.internalCreateModel(ModelAdapterFactory.java:390)
...
Caused by: java.lang.IllegalArgumentException: No Sling Models Injector registered for source 'parent-valuemap-value'.
at org.apache.sling.models.impl.ModelAdapterFactory.injectElement(ModelAdapterFactory.java:502)
Here's the Unit test setup...
@TestInstance(Lifecycle.PER_CLASS)
class ArticleInfoImplTest extends ComponentTest {
protected final static String ARTICLE_PAGE_JSON = "/content/dam/ArticlePage.json";
ArticleInfo articleInfo;
AemObjectInjector aemObjectInjector = new AemObjectInjector();
@BeforeAll
void setUpBeforeClass() {
initializeAemContext();
context.addModelsForClasses(ArticleInfoImpl.class);
context.load().json(ARTICLE_PAGE_JSON, BASIC_PAGE);
context.registerService(AemObjectInjector.class, aemObjectInjector);
context.registerInjectActivateService(new DateServiceImpl());
context.registerService(ContentTypeConverter.class, new MockContentTypeConverter());
articleInfo = adaptToClass(BASIC_PAGE + "/jcr:content/root/main/article", ArticleInfo.class);
}
void test() {
assertNotNull(articleInfo);
}
}
I'm registering an injector on 4th line of the Setup.
Why does the system not recognize it per the Stack Trace?
Thanks in advance for any help.
Solved! Go to Solution.
Views
Replies
Total Likes
The ParentResourceValueMapInjector is part of ACS AEM Commons, and it is not registered as part of the AEM Mocks. You should instantiate that service and register it in the context.
The model should use adaptables either as SlingHttpServletRequest.class or Resource.class and should not use both.
The ParentResourceValueMapInjector is part of ACS AEM Commons, and it is not registered as part of the AEM Mocks. You should instantiate that service and register it in the context.
Hi,
That is actually the main issue here. I cannot figure how to register the injector from ACS AEM Commons. I'd appreciate any help with how to do that.
Thanks for your help
-Garrett
Views
Replies
Total Likes
Views
Replies
Total Likes
Hello @gdeacon ,
Can you follow this article? Hope this will serve your purpose. Especially the 2nd method(Language Navigation example)
https://sadyrifat.medium.com/aem-unit-test-case-for-sling-delegation-pattern-1f011b947fb3
Views
Likes
Replies