Search in sources :

Example 16 with Bucket

use of org.locationtech.geogig.api.Bucket in project GeoGig by boundlessgeo.

the class PreOrderDiffWalkTest method testSkipBucket.

@Test
public void testSkipBucket() {
    // two bucket trees of depth 2
    final int size = RevTree.MAX_BUCKETS * RevTree.NORMALIZED_SIZE_LIMIT;
    RevTree left = createFeaturesTree(leftSource, "f", size).build();
    // all features
    RevTree right = createFeaturesTree(rightSource, "f", size, 0, true).build();
    // changed
    assertDepth(left, leftSource, 2);
    assertDepth(right, rightSource, 2);
    PreOrderDiffWalk visitor = new PreOrderDiffWalk(left, right, leftSource, rightSource);
    final Node lroot = nodeFor(left);
    final Node rroot = nodeFor(right);
    // consume the root tree
    when(consumer.tree(eq(lroot), eq(rroot))).thenReturn(true);
    // skip all buckets of depth 0
    when(consumer.bucket(anyInt(), eq(0), any(Bucket.class), any(Bucket.class))).thenReturn(false);
    visitor.walk(consumer);
    verify(consumer, times(1)).tree(eq(lroot), eq(rroot));
    verify(consumer, times(32)).bucket(anyInt(), eq(0), any(Bucket.class), any(Bucket.class));
    // should not be any call to consumer.features as we skipped all buckets of depth 0 (which
    // point to leaf trees)
    verify(consumer, times(0)).feature(any(Node.class), any(Node.class));
    verify(consumer, times(32)).endBucket(anyInt(), eq(0), any(Bucket.class), any(Bucket.class));
    verify(consumer, times(1)).endTree(eq(lroot), eq(rroot));
    verifyNoMoreInteractions(consumer);
}
Also used : Bucket(org.locationtech.geogig.api.Bucket) Node(org.locationtech.geogig.api.Node) TreeTestSupport.featureNode(org.locationtech.geogig.api.plumbing.diff.TreeTestSupport.featureNode) RevTree(org.locationtech.geogig.api.RevTree) Test(org.junit.Test)

Example 17 with Bucket

use of org.locationtech.geogig.api.Bucket in project GeoGig by boundlessgeo.

the class DepthSearch method getDirectChild.

/**
     * @param parent
     * @param directChildName
     * @return
     */
public Optional<Node> getDirectChild(RevTree parent, String directChildName, final int subtreesDepth) {
    if (parent.isEmpty()) {
        return Optional.absent();
    }
    if (parent.trees().isPresent() || parent.features().isPresent()) {
        if (parent.trees().isPresent()) {
            ImmutableList<Node> refs = parent.trees().get();
            for (int i = 0; i < refs.size(); i++) {
                if (directChildName.equals(refs.get(i).getName())) {
                    return Optional.of(refs.get(i));
                }
            }
        }
        if (parent.features().isPresent()) {
            ImmutableList<Node> refs = parent.features().get();
            for (int i = 0; i < refs.size(); i++) {
                if (directChildName.equals(refs.get(i).getName())) {
                    return Optional.of(refs.get(i));
                }
            }
        }
        return Optional.absent();
    }
    Integer bucket = refOrder.bucket(directChildName, subtreesDepth);
    ImmutableSortedMap<Integer, Bucket> buckets = parent.buckets().get();
    Bucket subtreeBucket = buckets.get(bucket);
    if (subtreeBucket == null) {
        return Optional.absent();
    }
    RevTree subtree = objectDb.get(subtreeBucket.id(), RevTree.class);
    return getDirectChild(subtree, directChildName, subtreesDepth + 1);
}
Also used : Bucket(org.locationtech.geogig.api.Bucket) Node(org.locationtech.geogig.api.Node) RevTree(org.locationtech.geogig.api.RevTree)

Example 18 with Bucket

use of org.locationtech.geogig.api.Bucket in project GeoGig by boundlessgeo.

the class FormatCommonV1 method readTree.

public static RevTree readTree(ObjectId id, DataInput in) throws IOException {
    final long size = in.readLong();
    final int treeCount = in.readInt();
    final ImmutableList.Builder<Node> featuresBuilder = new ImmutableList.Builder<Node>();
    final ImmutableList.Builder<Node> treesBuilder = new ImmutableList.Builder<Node>();
    final SortedMap<Integer, Bucket> buckets = new TreeMap<Integer, Bucket>();
    final int nFeatures = in.readInt();
    for (int i = 0; i < nFeatures; i++) {
        Node n = readNode(in);
        if (n.getType() != RevObject.TYPE.FEATURE) {
            throw new IllegalStateException("Non-feature node in tree's feature list.");
        }
        featuresBuilder.add(n);
    }
    final int nTrees = in.readInt();
    for (int i = 0; i < nTrees; i++) {
        Node n = readNode(in);
        if (n.getType() != RevObject.TYPE.TREE) {
            throw new IllegalStateException("Non-tree node in tree's subtree list.");
        }
        treesBuilder.add(n);
    }
    final int nBuckets = in.readInt();
    for (int i = 0; i < nBuckets; i++) {
        int key = in.readInt();
        Bucket bucket = readBucket(in);
        buckets.put(key, bucket);
    }
    ImmutableList<Node> trees = treesBuilder.build();
    ImmutableList<Node> features = featuresBuilder.build();
    if (nTrees == 0 && nFeatures == 0 && nBuckets == 0) {
        return RevTree.EMPTY;
    } else if (trees.isEmpty() && features.isEmpty()) {
        return RevTreeImpl.createNodeTree(id, size, treeCount, buckets);
    } else if (buckets.isEmpty()) {
        return RevTreeImpl.createLeafTree(id, size, features, trees);
    } else {
        throw new IllegalArgumentException("Tree has mixed buckets and nodes; this is not supported.");
    }
}
Also used : ImmutableList(com.google.common.collect.ImmutableList) SimpleFeatureTypeBuilder(org.geotools.feature.simple.SimpleFeatureTypeBuilder) Builder(com.google.common.collect.ImmutableList.Builder) Node(org.locationtech.geogig.api.Node) TreeMap(java.util.TreeMap) Bucket(org.locationtech.geogig.api.Bucket)

Example 19 with Bucket

use of org.locationtech.geogig.api.Bucket in project GeoGig by boundlessgeo.

the class FormatCommonV2 method writeTree.

public static void writeTree(RevTree tree, DataOutput data) throws IOException {
    writeUnsignedVarLong(tree.size(), data);
    writeUnsignedVarInt(tree.numTrees(), data);
    Envelope envBuff = new Envelope();
    final int nFeatures = tree.features().isPresent() ? tree.features().get().size() : 0;
    writeUnsignedVarInt(nFeatures, data);
    if (nFeatures > 0) {
        for (Node feature : tree.features().get()) {
            writeNode(feature, data, envBuff);
        }
    }
    final int nTrees = tree.trees().isPresent() ? tree.trees().get().size() : 0;
    writeUnsignedVarInt(nTrees, data);
    if (nTrees > 0) {
        for (Node subTree : tree.trees().get()) {
            writeNode(subTree, data, envBuff);
        }
    }
    final int nBuckets = tree.buckets().isPresent() ? tree.buckets().get().size() : 0;
    writeUnsignedVarInt(nBuckets, data);
    if (tree.buckets().isPresent()) {
        ImmutableSortedMap<Integer, Bucket> buckets = tree.buckets().get();
        for (Map.Entry<Integer, Bucket> bucket : buckets.entrySet()) {
            writeBucket(bucket.getKey(), bucket.getValue(), data, envBuff);
        }
    }
}
Also used : Bucket(org.locationtech.geogig.api.Bucket) Node(org.locationtech.geogig.api.Node) Envelope(com.vividsolutions.jts.geom.Envelope) Map(java.util.Map) SortedMap(java.util.SortedMap) ImmutableSortedMap(com.google.common.collect.ImmutableSortedMap) TreeMap(java.util.TreeMap)

Example 20 with Bucket

use of org.locationtech.geogig.api.Bucket in project GeoGig by boundlessgeo.

the class PreOrderDiffWalk method traverseLeafBucket.

/**
     * Compares a bucket tree (i.e. its size is greater than {@link RevTree#NORMALIZED_SIZE_LIMIT}
     * and hence has been split into buckets) at the right side of the comparison, and a the
     * {@link RevTree#children() children} nodes of a leaf tree at the left side of the comparison.
     * <p>
     * This happens when the right tree is much larger than the left tree
     * <p>
     * This traversal is symmetric to {@link #traverseBucketLeaf} so be careful that any change made
     * to this method shall have a matching change at {@link #traverseBucketLeaf}
     * 
     * @precondition {@code right.buckets().isPresent()}
     */
private void traverseLeafBucket(final Consumer consumer, final Iterator<Node> left, final RevTree right, final int bucketDepth) {
    checkState(right.buckets().isPresent());
    final SortedMap<Integer, Bucket> rightBuckets = right.buckets().get();
    final ListMultimap<Integer, Node> nodesByBucket = splitNodesToBucketsAtDepth(left, bucketDepth);
    final SortedSet<Integer> bucketIndexes = Sets.newTreeSet(Sets.union(rightBuckets.keySet(), nodesByBucket.keySet()));
    // get all buckets at once, to leverage ObjectDatabase optimizations
    final Map<ObjectId, RevObject> bucketTrees;
    bucketTrees = uniqueIndex(rightSource.getAll(transform(rightBuckets.values(), BUCKET_ID)), OBJECT_ID);
    for (Integer bucketIndex : bucketIndexes) {
        Bucket rightBucket = rightBuckets.get(bucketIndex);
        // never returns null, but empty
        List<Node> leftNodes = nodesByBucket.get(bucketIndex);
        if (null == rightBucket) {
            traverseLeafLeaf(consumer, leftNodes.iterator(), Iterators.<Node>emptyIterator());
        } else if (leftNodes.isEmpty()) {
            if (consumer.bucket(bucketIndex, bucketDepth, null, rightBucket)) {
                RevTree rightTree = (RevTree) bucketTrees.get(rightBucket.id());
                // traverseBucketBucket(consumer, RevTree.EMPTY, rightTree, bucketDepth);
                traverseTree(consumer, RevTree.EMPTY, rightTree, bucketDepth + 1);
            }
            consumer.endBucket(bucketIndex, bucketDepth, null, rightBucket);
        } else {
            RevTree rightTree = (RevTree) bucketTrees.get(rightBucket.id());
            if (rightTree.buckets().isPresent()) {
                traverseLeafBucket(consumer, leftNodes.iterator(), rightTree, bucketDepth + 1);
            } else {
                traverseLeafLeaf(consumer, leftNodes.iterator(), rightTree.children());
            }
        }
    }
}
Also used : Bucket(org.locationtech.geogig.api.Bucket) ObjectId(org.locationtech.geogig.api.ObjectId) RevObject(org.locationtech.geogig.api.RevObject) Node(org.locationtech.geogig.api.Node) RevTree(org.locationtech.geogig.api.RevTree)

Aggregations

Bucket (org.locationtech.geogig.api.Bucket)23 Node (org.locationtech.geogig.api.Node)18 RevTree (org.locationtech.geogig.api.RevTree)15 Test (org.junit.Test)8 TreeTestSupport.featureNode (org.locationtech.geogig.api.plumbing.diff.TreeTestSupport.featureNode)8 ObjectId (org.locationtech.geogig.api.ObjectId)6 Envelope (com.vividsolutions.jts.geom.Envelope)3 TreeMap (java.util.TreeMap)3 Bounded (org.locationtech.geogig.api.Bounded)3 Predicate (com.google.common.base.Predicate)2 ImmutableList (com.google.common.collect.ImmutableList)2 Builder (com.google.common.collect.ImmutableList.Builder)2 Map (java.util.Map)2 Nullable (javax.annotation.Nullable)2 SimpleFeatureTypeBuilder (org.geotools.feature.simple.SimpleFeatureTypeBuilder)2 RevObject (org.locationtech.geogig.api.RevObject)2 DiffEntry (org.locationtech.geogig.api.plumbing.diff.DiffEntry)2 ImmutableSortedMap (com.google.common.collect.ImmutableSortedMap)1 HashSet (java.util.HashSet)1 Iterator (java.util.Iterator)1