This is an automated email from the ASF dual-hosted git repository. rombert pushed a commit to branch issue/SLING-12469 in repository https://gitbox.apache.org/repos/asf/sling-org-apache-sling-feature-cpconverter.git
commit b094a2600c81685b38ae926b400648f649e28719 Author: Robert Munteanu <[email protected]> AuthorDate: Tue Nov 5 14:51:29 2024 +0100 SLING-12469 - Index definitions are not extracted when individual definitions are defined in the filter.xml as roots --- .../handlers/IndexDefinitionsEntryHandler.java | 43 ++++++++++++++++++++-- .../handlers/IndexDefinitionsEntryHandlerTest.java | 22 +++++++++++ .../index/full_aggregate/META-INF/vault/filter.xml | 20 ++++++++++ .../jcr_root/_oak_index/.content.xml | 19 ++++++++++ .../jcr_root/_oak_index/jcrCreated.xml | 23 ++++++++++++ 5 files changed, 123 insertions(+), 4 deletions(-) diff --git a/src/main/java/org/apache/sling/feature/cpconverter/handlers/IndexDefinitionsEntryHandler.java b/src/main/java/org/apache/sling/feature/cpconverter/handlers/IndexDefinitionsEntryHandler.java index 2da38f2..d83052b 100644 --- a/src/main/java/org/apache/sling/feature/cpconverter/handlers/IndexDefinitionsEntryHandler.java +++ b/src/main/java/org/apache/sling/feature/cpconverter/handlers/IndexDefinitionsEntryHandler.java @@ -16,12 +16,17 @@ */ package org.apache.sling.feature.cpconverter.handlers; +import static java.lang.String.format; + import java.io.IOException; import java.io.InputStream; import java.util.Optional; import javax.jcr.RepositoryException; +import org.apache.jackrabbit.spi.Name; +import org.apache.jackrabbit.spi.NameFactory; +import org.apache.jackrabbit.spi.commons.name.NameFactoryImpl; import org.apache.jackrabbit.util.Text; import org.apache.jackrabbit.vault.fs.api.WorkspaceFilter; import org.apache.jackrabbit.vault.fs.io.Archive; @@ -61,7 +66,21 @@ public class IndexDefinitionsEntryHandler extends AbstractRegexEntryHandler { String.join("|", EXCLUDED_EXTENSIONS) + ")$)[^.]+$"; // match everything else + private static final String EXTENSION_XML = ".xml"; + + // we hardcode the node type name to avoid a dependency on oak-core + private static final String NODETYPE_OAK_QUERY_INDEX_DEFINITION = "oak:QueryIndexDefinition"; + + private static final String removeXmlExtension(String input) { + if ( !input.endsWith(EXTENSION_XML) ) + throw new IllegalArgumentException(format("Input string '%s' does not end in '%s'", input, EXTENSION_XML)); + + return input.substring(0, input.length() - EXTENSION_XML.length()); + + } + private final class IndexDefinitionsParserHandler implements DocViewParserHandler { + private final WorkspaceFilter filter; private IndexDefinitions definitions; @@ -71,12 +90,28 @@ public class IndexDefinitionsEntryHandler extends AbstractRegexEntryHandler { } @Override - public void startDocViewNode(@NotNull String nodePath, @NotNull DocViewNode2 docViewNode, - @NotNull Optional<DocViewNode2> parentDocViewNode, int line, int column) + public void startDocViewNode(@NotNull final String nodePath, @NotNull final DocViewNode2 docViewNode, + @NotNull final Optional<DocViewNode2> parentDocViewNode, final int line, final int column) throws IOException, RepositoryException { + + DocViewNode2 effectiveNode = docViewNode; + String effectivePath = nodePath; + String primaryType = docViewNode.getPrimaryType().orElse(null); + + // SLING-12469 - support index definitions serialized as full coverage aggregates + if ( NODETYPE_OAK_QUERY_INDEX_DEFINITION.equals(primaryType) + && nodePath.endsWith(EXTENSION_XML)) { + effectivePath = removeXmlExtension(nodePath); + + NameFactory nameFactory = NameFactoryImpl.getInstance(); + + final Name oldName = docViewNode.getName(); + Name newName = nameFactory.create(oldName.getNamespaceURI(), removeXmlExtension(oldName.getLocalName())); + effectiveNode = new DocViewNode2(newName, docViewNode.getIndex(), docViewNode.getProperties()); + } - if ( nodePath.contains(IndexDefinitions.OAK_INDEX_PATH) && filter.contains(nodePath) ) { - definitions.addNode(Text.getRelativeParent(nodePath, 1), docViewNode); + if ( effectivePath.contains(IndexDefinitions.OAK_INDEX_PATH) && filter.contains(effectivePath) ) { + definitions.addNode(Text.getRelativeParent(effectivePath, 1), effectiveNode); } } diff --git a/src/test/java/org/apache/sling/feature/cpconverter/handlers/IndexDefinitionsEntryHandlerTest.java b/src/test/java/org/apache/sling/feature/cpconverter/handlers/IndexDefinitionsEntryHandlerTest.java index e724dd4..218c218 100644 --- a/src/test/java/org/apache/sling/feature/cpconverter/handlers/IndexDefinitionsEntryHandlerTest.java +++ b/src/test/java/org/apache/sling/feature/cpconverter/handlers/IndexDefinitionsEntryHandlerTest.java @@ -255,6 +255,28 @@ public class IndexDefinitionsEntryHandlerTest { traverseForIndexing(manager, "index_missing_namespaces"); } + + @Test + public void handleIndexDefinitionsAsFullAggregates() throws IOException, ConverterException { + + DefaultIndexManager manager = new DefaultIndexManager(); + + traverseForIndexing(manager, "full_aggregate"); + + IndexDefinitions defs = manager.getIndexes(); + Map<String, List<DocViewNode2>> indexes = defs.getIndexes(); + + assertThat(indexes).as("index definitions") + .hasSize(1) + .containsKey("/oak:index"); + + List<DocViewNode2> rootIndexes = indexes.get("/oak:index"); + assertThat(rootIndexes).as("root oak indexes") + .hasSize(1) + .element(0) + .has( Conditions.localName("jcrCreated") ) + .has( Conditions.property("type", "property") ); + } private void assertIsValidXml(byte[] tikeConfig) throws ParserConfigurationException, SAXException, IOException { diff --git a/src/test/resources/org/apache/sling/feature/cpconverter/handlers/index/full_aggregate/META-INF/vault/filter.xml b/src/test/resources/org/apache/sling/feature/cpconverter/handlers/index/full_aggregate/META-INF/vault/filter.xml new file mode 100644 index 0000000..dd1b898 --- /dev/null +++ b/src/test/resources/org/apache/sling/feature/cpconverter/handlers/index/full_aggregate/META-INF/vault/filter.xml @@ -0,0 +1,20 @@ +<?xml version="1.0" encoding="UTF-8"?> +<!-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + --> +<workspaceFilter version="1.0"> + <filter root="/oak:index/jcrCreated"/> +</workspaceFilter> \ No newline at end of file diff --git a/src/test/resources/org/apache/sling/feature/cpconverter/handlers/index/full_aggregate/jcr_root/_oak_index/.content.xml b/src/test/resources/org/apache/sling/feature/cpconverter/handlers/index/full_aggregate/jcr_root/_oak_index/.content.xml new file mode 100644 index 0000000..bbb035e --- /dev/null +++ b/src/test/resources/org/apache/sling/feature/cpconverter/handlers/index/full_aggregate/jcr_root/_oak_index/.content.xml @@ -0,0 +1,19 @@ +<?xml version="1.0" encoding="UTF-8"?> +<!-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + --> +<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" + jcr:primaryType="nt:unstructured"/> \ No newline at end of file diff --git a/src/test/resources/org/apache/sling/feature/cpconverter/handlers/index/full_aggregate/jcr_root/_oak_index/jcrCreated.xml b/src/test/resources/org/apache/sling/feature/cpconverter/handlers/index/full_aggregate/jcr_root/_oak_index/jcrCreated.xml new file mode 100644 index 0000000..c52c115 --- /dev/null +++ b/src/test/resources/org/apache/sling/feature/cpconverter/handlers/index/full_aggregate/jcr_root/_oak_index/jcrCreated.xml @@ -0,0 +1,23 @@ +<?xml version="1.0" encoding="UTF-8"?> +<!-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + --> +<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" + jcr:primaryType="oak:QueryIndexDefinition" + propertyNames="{Name}[jcr:created]" + reindex="{Boolean}false" + reindexCount="{Long}1" + type="property"/> \ No newline at end of file
