when(consumer.feature(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), any(BucketIndex.class), any(Bucket.class), any(Bucket.class))).thenReturn(true); verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); verify(consumer, times(expectedDeletes)).feature((NodeRef) notNull(), (NodeRef) isNull()); verify(consumer, times(expectedAdds)).feature((NodeRef) isNull(), (NodeRef) notNull()); return sw.elapsed(TimeUnit.MILLISECONDS);
final NodeRef rroot = nodeFor(right); when(consumer.tree(eq(lroot), eq(rroot))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class))).thenReturn(false); verify(consumer, times(1)).tree(eq(lroot), eq(rroot)); verify(consumer, times(32)).bucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(0)).feature(any(NodeRef.class), any(NodeRef.class)); verify(consumer, times(32)).endBucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).endTree(eq(lroot), eq(rroot)); verifyNoMoreInteractions(consumer);
when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); visitor.walk(consumer); verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); verify(consumer, times(2)).feature(larg.capture(), rarg.capture()); assertTrue(allValuesAtTheRight.contains(nodeRefChange2)); verify(consumer, times(1)).endTree(any(NodeRef.class), any(NodeRef.class)); verifyNoMoreInteractions(consumer);
when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); visitor.walk(consumer); verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); verify(consumer, times(2)).feature(larg.capture(), rarg.capture()); assertTrue(allValuesAtTheRight.contains(nodeRefChange2)); verify(consumer, times(1)).endTree(any(NodeRef.class), any(NodeRef.class)); verifyNoMoreInteractions(consumer);
when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); visitor.walk(consumer); verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); verify(consumer, times(2)).feature(larg.capture(), rarg.capture()); assertTrue(allValuesAtTheRight.contains(nodeRefChange2)); verify(consumer, times(1)).endTree(any(NodeRef.class), any(NodeRef.class)); verifyNoMoreInteractions(consumer);
private void testLeafBucketDeeper(final int leftsize, final RevTree rightRoot, final int overlapCount) { consumer = mock(Consumer.class); when(consumer.feature(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); // right tree has feature nodes "f0" to "f<rightsize-1>" final int rightsize = (int) rightRoot.size(); // the left tree feature node names start at "f<rightsize - 100>", so there's a 100 node // overlap RevTree leftRoot = createFeaturesTree(leftSource, "f", leftsize, rightsize - overlapCount, true); PreOrderDiffWalk visitor = newVisitor(leftRoot, rightRoot); // consume all when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), any(BucketIndex.class), any(Bucket.class), any(Bucket.class))).thenReturn(true); visitor.walk(consumer); // there's only the root tree verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); // there shall be <overlapCount> calls to feature with both non null args final int totalFeatureNotifications = (rightsize + leftsize) - overlapCount; verify(consumer, times(totalFeatureNotifications)).feature(any(NodeRef.class), any(NodeRef.class)); // there shall be <overlapCount> calls to feature with both non null args verify(consumer, times(overlapCount)).feature((NodeRef) notNull(), (NodeRef) notNull()); final int expectedDeletes = leftsize - overlapCount; final int expectedAdds = rightsize - overlapCount; verify(consumer, times(expectedDeletes)).feature((NodeRef) notNull(), (NodeRef) isNull()); verify(consumer, times(expectedAdds)).feature((NodeRef) isNull(), (NodeRef) notNull()); }
when(consumer.feature(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), any(BucketIndex.class), any(Bucket.class), any(Bucket.class))).thenReturn(true); verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); verify(consumer, times(expectedDeletes)).feature((NodeRef) notNull(), (NodeRef) isNull()); verify(consumer, times(expectedAdds)).feature((NodeRef) isNull(), (NodeRef) notNull()); return sw.elapsed(TimeUnit.MILLISECONDS);
when(consumer.feature(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), any(BucketIndex.class), any(Bucket.class), any(Bucket.class))).thenReturn(true); verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); verify(consumer, times(expectedDeletes)).feature((NodeRef) notNull(), (NodeRef) isNull()); verify(consumer, times(expectedAdds)).feature((NodeRef) isNull(), (NodeRef) notNull()); return sw.elapsed(TimeUnit.MILLISECONDS);
private void testLeafBucketDeeper(final int leftsize, final RevTree rightRoot, final int overlapCount) { consumer = mock(Consumer.class); when(consumer.feature(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); // right tree has feature nodes "f0" to "f<rightsize-1>" final int rightsize = (int) rightRoot.size(); // the left tree feature node names start at "f<rightsize - 100>", so there's a 100 node // overlap RevTree leftRoot = RevObjectTestSupport.INSTANCE.createFeaturesTree(leftSource, "f", leftsize, rightsize - overlapCount, true); PreOrderDiffWalk visitor = newVisitor(leftRoot, rightRoot); // consume all when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), any(BucketIndex.class), any(Bucket.class), any(Bucket.class))).thenReturn(true); visitor.walk(consumer); // there's only the root tree verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); // there shall be <overlapCount> calls to feature with both non null args final int totalFeatureNotifications = (rightsize + leftsize) - overlapCount; verify(consumer, times(totalFeatureNotifications)).feature(any(NodeRef.class), any(NodeRef.class)); // there shall be <overlapCount> calls to feature with both non null args verify(consumer, times(overlapCount)).feature((NodeRef) notNull(), (NodeRef) notNull()); final int expectedDeletes = leftsize - overlapCount; final int expectedAdds = rightsize - overlapCount; verify(consumer, times(expectedDeletes)).feature((NodeRef) notNull(), (NodeRef) isNull()); verify(consumer, times(expectedAdds)).feature((NodeRef) isNull(), (NodeRef) notNull()); }
@Test public void testLeafLeafWithSubStrees() { // two leaf trees ObjectId metadataId = RevObjectTestSupport.hashString("fake"); RevTree left = createTreesTree(leftSource, 2, 100, metadataId); RevTree right = createTreesTree(rightSource, 3, 100, metadataId); PreOrderDiffWalk visitor = newVisitor(left, right); final NodeRef lroot = nodeFor(left); final NodeRef rroot = nodeFor(right); // consume any tree diff when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); visitor.walk(consumer); // capture calls to consumer.tree(node, node) ArgumentCaptor<NodeRef> larg = ArgumentCaptor.forClass(NodeRef.class); ArgumentCaptor<NodeRef> rarg = ArgumentCaptor.forClass(NodeRef.class); verify(consumer, times(2)).tree(larg.capture(), rarg.capture()); assertEquals(2, larg.getAllValues().size()); assertEquals("left side arg for the first tree() call is not the left root", lroot, larg.getAllValues().get(0)); assertNull("left side arg for the second tree() call should be null", larg.getAllValues().get(1)); assertEquals(2, rarg.getAllValues().size()); assertEquals(rroot, rarg.getAllValues().get(0)); assertNotNull(rarg.getAllValues().get(1)); verify(consumer, times(100)).feature((NodeRef) isNull(), any(NodeRef.class)); verify(consumer, times(2)).endTree(any(NodeRef.class), any(NodeRef.class)); verifyNoMoreInteractions(consumer); }
private void testLeafBucketDeeper(final int leftsize, final RevTree rightRoot, final int overlapCount) { consumer = mock(Consumer.class); when(consumer.feature(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); // right tree has feature nodes "f0" to "f<rightsize-1>" final int rightsize = (int) rightRoot.size(); // the left tree feature node names start at "f<rightsize - 100>", so there's a 100 node // overlap RevTree leftRoot = testSupport.createFeaturesTree(leftSource, "f", leftsize, rightsize - overlapCount, true); PreOrderDiffWalk visitor = newVisitor(leftRoot, rightRoot); // consume all when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), any(BucketIndex.class), any(Bucket.class), any(Bucket.class))).thenReturn(true); visitor.walk(consumer); // there's only the root tree verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); // there shall be <overlapCount> calls to feature with both non null args final int totalFeatureNotifications = (rightsize + leftsize) - overlapCount; verify(consumer, times(totalFeatureNotifications)).feature(any(NodeRef.class), any(NodeRef.class)); // there shall be <overlapCount> calls to feature with both non null args verify(consumer, times(overlapCount)).feature((NodeRef) notNull(), (NodeRef) notNull()); final int expectedDeletes = leftsize - overlapCount; final int expectedAdds = rightsize - overlapCount; verify(consumer, times(expectedDeletes)).feature((NodeRef) notNull(), (NodeRef) isNull()); verify(consumer, times(expectedAdds)).feature((NodeRef) isNull(), (NodeRef) notNull()); }
@Test public void testLeafLeafWithSubStrees() { // two leaf trees ObjectId metadataId = RevObjectTestSupport.hashString("fake"); RevTree left = testSupport.createTreesTree(leftSource, 2, 100, metadataId); RevTree right = testSupport.createTreesTree(rightSource, 3, 100, metadataId); PreOrderDiffWalk visitor = newVisitor(left, right); final NodeRef lroot = nodeFor(left); final NodeRef rroot = nodeFor(right); // consume any tree diff when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); visitor.walk(consumer); // capture calls to consumer.tree(node, node) ArgumentCaptor<NodeRef> larg = ArgumentCaptor.forClass(NodeRef.class); ArgumentCaptor<NodeRef> rarg = ArgumentCaptor.forClass(NodeRef.class); verify(consumer, times(2)).tree(larg.capture(), rarg.capture()); assertEquals(2, larg.getAllValues().size()); assertEquals("left side arg for the first tree() call is not the left root", lroot, larg.getAllValues().get(0)); assertNull("left side arg for the second tree() call should be null", larg.getAllValues().get(1)); assertEquals(2, rarg.getAllValues().size()); assertEquals(rroot, rarg.getAllValues().get(0)); assertNotNull(rarg.getAllValues().get(1)); verify(consumer, times(100)).feature((NodeRef) isNull(), any(NodeRef.class)); verify(consumer, times(2)).endTree(any(NodeRef.class), any(NodeRef.class)); verifyNoMoreInteractions(consumer); }
@Test public void testLeafLeafWithSubStrees() { // two leaf trees ObjectId metadataId = RevObjectTestSupport.hashString("fake"); RevTree left = RevObjectTestSupport.INSTANCE.createTreesTree(leftSource, 2, 100, metadataId); RevTree right = RevObjectTestSupport.INSTANCE.createTreesTree(rightSource, 3, 100, metadataId); PreOrderDiffWalk visitor = newVisitor(left, right); final NodeRef lroot = nodeFor(left); final NodeRef rroot = nodeFor(right); // consume any tree diff when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); visitor.walk(consumer); // capture calls to consumer.tree(node, node) ArgumentCaptor<NodeRef> larg = ArgumentCaptor.forClass(NodeRef.class); ArgumentCaptor<NodeRef> rarg = ArgumentCaptor.forClass(NodeRef.class); verify(consumer, times(2)).tree(larg.capture(), rarg.capture()); assertEquals(2, larg.getAllValues().size()); assertEquals("left side arg for the first tree() call is not the left root", lroot, larg.getAllValues().get(0)); assertNull("left side arg for the second tree() call should be null", larg.getAllValues().get(1)); assertEquals(2, rarg.getAllValues().size()); assertEquals(rroot, rarg.getAllValues().get(0)); assertNotNull(rarg.getAllValues().get(1)); verify(consumer, times(100)).feature((NodeRef) isNull(), any(NodeRef.class)); verify(consumer, times(2)).endTree(any(NodeRef.class), any(NodeRef.class)); verifyNoMoreInteractions(consumer); }
final NodeRef rroot = nodeFor(right); when(consumer.tree(eq(lroot), eq(rroot))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class))).thenReturn(false); verify(consumer, times(1)).tree(eq(lroot), eq(rroot)); verify(consumer, times(32)).bucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(0)).feature(any(NodeRef.class), any(NodeRef.class)); verify(consumer, times(32)).endBucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).endTree(eq(lroot), eq(rroot)); verifyNoMoreInteractions(consumer);
@Test public void testSkipBucket() { // two bucket trees of depth 2 final int size = CanonicalNodeNameOrder.maxBucketsForLevel(0) * CanonicalNodeNameOrder.normalizedSizeLimit(0); RevTree left = createFeaturesTree(leftSource, "f", size); RevTree right = createFeaturesTree(rightSource, "f", size, 0, true);// all features // changed assertDepth(left, leftSource, 2); assertDepth(right, rightSource, 2); PreOrderDiffWalk visitor = newVisitor(left, right); final NodeRef lroot = nodeFor(left); final NodeRef 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(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(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(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(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(NodeRef.class), any(NodeRef.class)); verify(consumer, times(32)).endBucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).endTree(eq(lroot), eq(rroot)); verifyNoMoreInteractions(consumer); }
@Test public void testBucketBucketFlatMoreDepth() { RevTree left = createFeaturesTree(leftSource, "f", CanonicalNodeNameOrder.maxBucketsForLevel(0) * CanonicalNodeNameOrder.normalizedSizeLimit(0)); RevTree right = createFeaturesTree(rightSource, "f", CanonicalNodeNameOrder.maxBucketsForLevel(0) * CanonicalNodeNameOrder.normalizedSizeLimit(0) + 1); PreOrderDiffWalk visitor = newVisitor(left, right); when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), any(BucketIndex.class), any(Bucket.class), any(Bucket.class))).thenReturn(true); visitor.walk(consumer); verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); // consumer.bucket should be called for depth 0 and then 1 verify(consumer, times(1)).bucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).bucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(1)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).feature((NodeRef) isNull(), any(NodeRef.class)); verify(consumer, times(1)).endBucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).endBucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(1)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).endTree(any(NodeRef.class), any(NodeRef.class)); verifyNoMoreInteractions(consumer); }
@Test public void testLeafLeafTwoRemoves() { // two leaf trees RevTree left = createFeaturesTree(leftSource, "f", 5); RevTree right = createFeaturesTree(rightSource, "f", 3); PreOrderDiffWalk visitor = newVisitor(left, right); final NodeRef lroot = nodeFor(left); final NodeRef rroot = nodeFor(right); when(consumer.tree(eq(lroot), eq(rroot))).thenReturn(true); visitor.walk(consumer); verify(consumer, times(1)).tree(eq(lroot), eq(rroot)); ArgumentCaptor<NodeRef> larg = ArgumentCaptor.forClass(NodeRef.class); ArgumentCaptor<NodeRef> rarg = ArgumentCaptor.forClass(NodeRef.class); verify(consumer, times(2)).feature(larg.capture(), rarg.capture()); assertEquals(2, larg.getAllValues().size()); assertNull(rarg.getAllValues().get(0)); assertNull(rarg.getAllValues().get(1)); NodeRef n1 = featureNodeRef("f", 3);// the two added nodes NodeRef n2 = featureNodeRef("f", 4); assertTrue(larg.getAllValues().contains(n1)); assertTrue(larg.getAllValues().contains(n2)); verify(consumer, times(1)).endTree(eq(lroot), eq(rroot)); verifyNoMoreInteractions(consumer); }
@Test public void testLeafBucketSimple() { final int rightsize = 1 + CanonicalNodeNameOrder.normalizedSizeLimit(0); RevTree left = createFeaturesTree(leftSource, "f", 1); RevTree right = createFeaturesTree(rightSource, "f", rightsize); PreOrderDiffWalk visitor = newVisitor(left, right); // consume all when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), any(BucketIndex.class), any(Bucket.class), any(Bucket.class))).thenReturn(true); visitor.walk(consumer); // there's only the root tree verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); // there's only one feature on the right tree, so all right trees features fall on a single // bucket final int leftBucketCount = right.buckets().size(); final int expectedBucketCalls = leftBucketCount; verify(consumer, times(expectedBucketCalls)).bucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(rightsize - 1)).feature((NodeRef) isNull(), any(NodeRef.class)); verify(consumer, times(expectedBucketCalls)).endBucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).endTree(any(NodeRef.class), any(NodeRef.class)); verifyNoMoreInteractions(consumer); }
@Test public void testBucketBucketFlatMoreDepth() { RevTree left = testSupport.createFeaturesTree(leftSource, "f", CanonicalNodeNameOrder.maxBucketsForLevel(0) * CanonicalNodeNameOrder.normalizedSizeLimit(0)); RevTree right = testSupport.createFeaturesTree(rightSource, "f", CanonicalNodeNameOrder.maxBucketsForLevel(0) * CanonicalNodeNameOrder.normalizedSizeLimit(0) + 1); PreOrderDiffWalk visitor = newVisitor(left, right); when(consumer.tree(any(NodeRef.class), any(NodeRef.class))).thenReturn(true); when(consumer.bucket(any(NodeRef.class), any(NodeRef.class), any(BucketIndex.class), any(Bucket.class), any(Bucket.class))).thenReturn(true); visitor.walk(consumer); verify(consumer, times(1)).tree(any(NodeRef.class), any(NodeRef.class)); // consumer.bucket should be called for depth 0 and then 1 verify(consumer, times(1)).bucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).bucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(1)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).feature((NodeRef) isNull(), any(NodeRef.class)); verify(consumer, times(1)).endBucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(0)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).endBucket(any(NodeRef.class), any(NodeRef.class), argThat(depthMatches(1)), any(Bucket.class), any(Bucket.class)); verify(consumer, times(1)).endTree(any(NodeRef.class), any(NodeRef.class)); verifyNoMoreInteractions(consumer); }
@Test public void testLeafLeafTwoAdds() { // two leaf trees RevTree left = testSupport.createFeaturesTree(leftSource, "f", 3); RevTree right = testSupport.createFeaturesTree(rightSource, "f", 5); PreOrderDiffWalk visitor = newVisitor(left, right); final NodeRef lroot = nodeFor(left); final NodeRef rroot = nodeFor(right); when(consumer.tree(eq(lroot), eq(rroot))).thenReturn(true); visitor.walk(consumer); verify(consumer, times(1)).tree(eq(lroot), eq(rroot)); ArgumentCaptor<NodeRef> larg = ArgumentCaptor.forClass(NodeRef.class); ArgumentCaptor<NodeRef> rarg = ArgumentCaptor.forClass(NodeRef.class); verify(consumer, times(2)).feature(larg.capture(), rarg.capture()); assertEquals(2, larg.getAllValues().size()); assertNull(larg.getAllValues().get(0)); assertNull(larg.getAllValues().get(1)); NodeRef n1 = featureNodeRef("f", 3);// the two added nodes NodeRef n2 = featureNodeRef("f", 4); assertTrue(rarg.getAllValues().contains(n1)); assertTrue(rarg.getAllValues().contains(n2)); verify(consumer, times(1)).endTree(eq(lroot), eq(rroot)); verifyNoMoreInteractions(consumer); }