Expand my Community achievements bar.

Where to Add Custom Oak Indexes in AEM as a Cloud Service?

Avatar

Level 4

 

Hi AEM Community,

We are trying to add a custom Oak index in our AEM as a Cloud Service project. We tried adding the index in both:

  1. ui.apps package

  2. ui.apps/structure (we created a structure folder inside ui.apps)

However, our Maven build fails with multiple errors and warnings. Here is the relevant part of the log:

 

 
[WARNING] ValidationViolation: Filter root's ancestor '/content/dam' is not covered by any of the specified dependencies nor a valid root. @ META-INF\vault\filter.xml, validator: jackrabbit-filter [WARNING] ValidationViolation: Package of type 'MIXED' is legacy. Use one of the other types instead! @ META-INF\vault\properties.xml, validator: jackrabbit-packagetype [ERROR] ValidationViolation: Invalid XML found: Given root node name 'oak:index' (implicitly given via filename) cannot be resolved. The prefix used in the filename must be declared as XML namespace in the child docview XML as well! @ jcr_root\_oak_index\.content.xml, validator: jackrabbit-docviewparser, JCR node path: /oak:index [WARNING] ValidationViolation: Found orphaned filter entries: entry with root '/apps', entry with root '/apps/customproject', entry with root '/apps/sling', entry with root '/apps/cq', entry with root '/apps/dam', entry with root '/apps/wcm', entry with root '/apps/msm', entry with root '/apps/settings', entry with root '/content/dam/customproject', validator: jackrabbit-filter [ERROR] ValidationViolation: Node 'cqPageLucene-custom-1 [oak:QueryIndexDefinition]' is not allowed as child of node with types [nt:folder]: Node type does not allow arbitrary child nodes and does not allow this specific name and node type either! @ jcr_root\_oak_index\cqPageLucene-custom-1, validator: jackrabbit-nodetypes, JCR node path: /oak:index/cqPageLucene-custom-1

 

 

Additional Info:

  • Our custom Oak index file _oak_index/cqPageLucene-custom-1/.content.xml looks like this:

 

 
<?xml version="1.0" encoding="UTF-8"?> <jcr:root xmlns:jcr="http://www.jcp.org/jcr/1.0" xmlns:nt="http://www.jcp.org/jcr/nt/1.0" xmlns:oak="http://jackrabbit.apache.org/oak/ns/1.0" xmlns:cq="http://www.day.com/jcr/cq/1.0" jcr:primaryType="oak:QueryIndexDefinition" type="lucene" async="[async,nrt]" compatVersion="{Long}2" evaluatePathRestrictions="{Boolean}true" includedPaths="[/content/project]" queryPaths="[/content/project]" tags="[PageSearch]" reindex="{Boolean}true" reindexCount="{Long}1"> <aggregates jcr:primaryType="nt:unstructured"> <cq:Page jcr:primaryType="nt:unstructured"> <include0 jcr:primaryType="nt:unstructured" path="jcr:content" relativeNode="{Boolean}true"/> </cq:Page> <cq:PageContent jcr:primaryType="nt:unstructured"> <include0 jcr:primaryType="nt:unstructured" path="*"/> <include1 jcr:primaryType="nt:unstructured" path="*/*"/> <include2 jcr:primaryType="nt:unstructured" path="*/*/*"/> </cq:PageContent> </aggregates> <indexRules jcr:primaryType="nt:unstructured"> <cq:Page jcr:primaryType="nt:unstructured"> <properties jcr:primaryType="nt:unstructured"> <allProps jcr:primaryType="nt:unstructured" name=".*" isRegexp="{Boolean}true" nodeScopeIndex="{Boolean}true" analyzed="{Boolean}true" useInSpellcheck="{Boolean}true"/> <cqTags jcr:primaryType="nt:unstructured" name="jcr:content/cq:tags" nodeScopeIndex="{Boolean}true" propertyIndex="{Boolean}true" analyzed="{Boolean}false" type="String"/> </properties> </cq:Page> </indexRules> </jcr:root>
 

Questions:

  1. Where is the correct location for custom Oak indexes in AEM as a Cloud Service?

  2. Do we need a separate structure package, or can it exist inside ui.apps?

  3. How do we avoid the validation errors when packaging _oak_index with Maven?

Any guidance or examples of a working structure for custom Oak indexes in AEM Cloud Service would be greatly appreciated.

Thank you in advance!

2 Replies

Avatar

Level 10

Custom Oak indexes should be placed in the ui.apps package under the path ui.apps/src/main/content/jcr_root/_oak_index/. This is the correct location, and you don't need a separate structure package for Oak indexes.

This page explains everything about preparing the new index definition, deploying custom index definitions, and the project configurations: https://experienceleague.adobe.com/en/docs/experience-manager-cloud-service/content/operations/index... 

 

IMO to resolve your validation errors, you need to update your Maven POM files with specific configurations:

1) Add the following to your root pom.xml to support the filevault-package-maven-plugin (version 1.3.2 or higher recommended):

 
<plugin>
    <groupId>org.apache.jackrabbit</groupId>
    <artifactId>filevault-package-maven-plugin</artifactId>
    <version>1.3.2</version>
    <configuration>
        <validatorsSettings>
            <jackrabbit-packagetype>
                <options>
                    <immutableRootNodeNames>apps,libs,oak:index</immutableRootNodeNames>
                </options>
            </jackrabbit-packagetype>
        </validatorsSettings>
    </configuration>
</plugin>
 
2) In your ui.apps/pom.xml, add these critical properties:
 
<plugin>
    <groupId>org.apache.jackrabbit</groupId>
    <artifactId>filevault-package-maven-plugin</artifactId>
    <configuration>
        <allowIndexDefinitions>true</allowIndexDefinitions>
        <properties>
            <cloudManagerTarget>none</cloudManagerTarget>
            <noIntermediateSaves>true</noIntermediateSaves>
        </properties>
    </configuration>
</plugin>

The allowIndexDefinitions=true property is essential to allow Oak index definitions in the package.

3) Update your filter.xml to include the specific index path:

<?xml version="1.0" encoding="UTF-8"?>
<workspaceFilter version="1.0">
    <filter root="/oak:index/cqPageLucene-custom-1"/>
</workspaceFilter>

4) Ensure your <package_name>/META-INF/vault/properties.xml contains these required properties:

noIntermediateSaves=true 
allowIndexDefinitions=true

The warning about /content/dam not being covered suggests you have a filter entry pointing to content areas. Oak indexes should only reference /oak:index paths in your filters.

 

Avatar

Employee Advisor

Hello @georhe6 ,

 

My findings and the required fixes for the custom Oak index issue :

  1. Correct Location for Custom Oak Indexes:
    Custom Oak index definitions must be placed inside a content package that deploys to /oak:index.
    Recommended structure:
    ui.apps.structure/src/main/content/jcr_root/_oak_index/<index-name>/.content.xml
    (Alternatively, placing this under ui.apps/src/main/content/jcr_root/_oak_index also works.)

  2. Package Type Requirement:
    The module containing the index must produce a content package. Using the older MIXED package type leads to validation errors.
    Please ensure the module POM is configured with: packaging = content-package

  3. Required Vault Filter:
    The filter.xml must explicitly include the index root. For example:

    <filter root="/oak:index/<index-name>"/>
  4. Reason for the Maven Build Failures:

  • The index .content.xml must declare the oak namespace (xmlns:oak).

  • The parent node of the index cannot be typed as nt:folder, otherwise the index node type oak:QueryIndexDefinition is rejected.

  • FileVault validates prefixes strictly; since the folder name encodes “oak:”, the XML must declare that prefix.

  • Orphaned filter warnings occur when filter entries do not match the package roots.

  1. Correct Index Definition Requirements:
    Each index folder under _oak_index must contain a .content.xml with:

  1. Recommended Best Practice:
    We suggest placing all custom Oak indexes inside a dedicated ui.apps.structure module. This keeps system-level content separate from application code and avoids packaging conflicts.

  2. Expected Result:
    Implementing the above changes will resolve:

  • XML namespace validation errors

  • Node type violations

  • Orphaned filter warnings

  • MIXED package-type warnings