private void reorderChildNodes()

in shared/impl-vlt/src/main/java/org/apache/sling/ide/impl/vlt/ReorderChildNodesCommand.java [72:147]


    private void reorderChildNodes(Node nodeToReorder, ResourceProxy resourceToReorder) throws RepositoryException {

        List<ResourceProxy> children = resourceToReorder.getChildren();
        ListIterator<ResourceProxy> childrenIterator = children.listIterator();

        // do not process
        if (!childrenIterator.hasNext()) {
            getLogger().trace("Resource at {0} has no children, skipping child node reordering",
                            resourceToReorder.getPath());
            return;
        }

        Set<String> resourceChildNames = new HashSet<>(children.size());
        Set<String> nodeChildNames = new HashSet<>(children.size());

        List<Node> nodeChildren = new LinkedList<>();
        NodeIterator nodeChildrenIt = nodeToReorder.getNodes();
        while (nodeChildrenIt.hasNext()) {
            Node node = nodeChildrenIt.nextNode();
            nodeChildren.add(node);
            nodeChildNames.add(node.getName());
        }

        for (ResourceProxy childResources : children) {
            resourceChildNames.add(Text.getName(childResources.getPath()));
        }
        ListIterator<Node> nodeChildrenListIt = nodeChildren.listIterator();

        // the sorting is conditioned on the local workspace and the repository having the same child names
        // if that precondition is not met abort processing since there can be no meaningful result

        traceResourcesAndNodes(children, nodeChildren);

        if (! resourceChildNames.equals(nodeChildNames)) {
            getLogger().warn(
                    "Different child names between the local workspace ( " + resourceChildNames
                            + ") and the repository (" + nodeChildNames + ") for path " + resource.getPath()
                            + ". Reordering will not be performed");
            return;
        }

        while (childrenIterator.hasNext() || nodeChildrenListIt.hasNext()) {

            ResourceProxy childResource = childrenIterator.next();
            Node childNode = nodeChildrenListIt.next();

            // order is as expected, skip reordering
            if (Text.getName(childResource.getPath()).equals(childNode.getName())) {
                // descend into covered child resources once they are properly arranged and perform reordering
                if (resourceToReorder.covers(childResource.getPath())) {
                    reorderChildNodes(childNode, childResource);
                }
                continue;
            }

            // don't perform any reordering if this particular node does not have reorderable children
            if (!nodeToReorder.getPrimaryNodeType().hasOrderableChildNodes()) {
                getLogger().trace("Node at {0} does not have orderable child nodes, skipping reordering of {1}",
                        nodeToReorder.getPath(), childResource.getPath());
                continue;
            }

            String expectedParentName;
            if (childrenIterator.hasNext()) {
                expectedParentName = Text.getName(childrenIterator.next().getPath());
                childrenIterator.previous(); // move back
            } else {
                expectedParentName = null;
            }

            getLogger().trace("For node at {0} ordering {1} before {2}", nodeToReorder.getPath(),
                    Text.getName(childResource.getPath()), expectedParentName);

            nodeToReorder.orderBefore(Text.getName(childResource.getPath()), expectedParentName);
        }
    }