public void testObsoleteThreadThenRestoreRemoveBlipDoesntDie() { WaveletBasedConversationBlip first = target.getRootThread().appendBlip(); WaveletBasedConversationThread willBecomeEmpty = first.addReplyThread(); ConversationBlip toggleBlip = willBecomeEmpty.appendBlip(); String toggleBlipId = toggleBlip.getId(); // Make the thread empty by remotely removing its blip. ManifestBlip manifestRootBlip = target.getManifest().getRootThread().getBlip(0); ManifestThread manifestReply = manifestRootBlip.getReply(0); manifestReply.removeBlip(manifestReply.getBlip(0)); assertThreadValid(willBecomeEmpty); // Re-add then remove the blip, as can happen in playback. manifestReply.appendBlip(toggleBlipId); manifestReply.removeBlip(manifestReply.getBlip(0)); }
public void testRemoveRestoreThreadAfterObsoleteThreadDoesntDie() { WaveletBasedConversationBlip first = target.getRootThread().appendBlip(); WaveletBasedConversationThread reply11 = first.addReplyThread(); ConversationBlip blip1 = reply11.appendBlip(); String blip1Id = blip1.getId(); WaveletBasedConversationThread reply2 = first.addReplyThread(); // Make first thread empty by removing its blip. ManifestBlip manifestRootBlip = target.getManifest().getRootThread().getBlip(0); ManifestThread manifestReply1 = manifestRootBlip.getReply(0); manifestReply1.removeBlip(manifestReply1.getBlip(0)); assertThreadValid(reply11); // Remove and re-add second thread, as can happen in playback. String thread2Id = reply2.getId(); ManifestThread manifestReply2 = manifestRootBlip.getReply(1); manifestRootBlip.removeReply(manifestReply2); manifestRootBlip.appendReply(thread2Id, false); assertThreadInvalid(reply2); }
/** * Very basic test to see that we can create the object with a document and use it. */ public void testSimpleUsageWithDocument() { ObservableManifestBlip blip = buildBlipElement(ConversationTestUtils.createManifestDocument(), "b+1"); assertEquals("b+1", blip.getId()); ManifestThread reply = blip.appendReply("t1", false); assertNotNull(reply); assertEquals("t1", reply.getId()); }
/** * Removes a blip from the manifest, as though a remote client had done so. */ private void remoteRemoveBlip(WaveletBasedConversationBlip blip) { ManifestThread parentThread = blip.getThread().getManifestThread(); ManifestBlip manifestBlip = blip.getManifestBlip(); parentThread.removeBlip(manifestBlip); }
/** * Test that iterating a thread whose manifest contains blips not backed by the * wavelet skips those blips. */ public void testMissingBlipIteration() { WaveletBasedConversationThread thread = target.getRootThread(); WaveletBasedConversationBlip first = thread.appendBlip(); manifestDoc.with(new Action() { @Override public <N, E extends N, T extends N> void exec(MutableDocument<N, E, T> doc) { N rootThreadNode = doc.getFirstChild(doc.getDocumentElement()); E rootThread = doc.asElement(rootThreadNode); doc.createChildElement(rootThread, "blip", Collections.singletonMap( "id", idGenerator.newBlipId())); } }); WaveletBasedConversationBlip third = thread.appendBlip(); assertEquals(3, CollectionUtils.newArrayList(thread.getManifestThread().getBlips()).size()); assertEquals(Arrays.asList(first, third), getBlipList(thread)); }
public void testConcrrentDeletionOfFinalBlipsLeavesEmptyThread() { WaveletBasedConversationBlip first = target.getRootThread().appendBlip(); WaveletBasedConversationThread replyThread = first.addReplyThread(); WaveletBasedConversationBlip b1 = replyThread.appendBlip(); WaveletBasedConversationBlip b2 = replyThread.appendBlip(); // Locally delete b1, remotely delete b2. b1.delete(); replyThread.addListener(threadListener); b2.addListener(blipListener); target.addListener(convListener); remoteRemoveBlip(b2); // Expect blip deletion events and it to be invalid. verify(blipListener).onDeleted(); verify(convListener).onBlipDeleted(b2); assertBlipInvalid(b2); assertThreadValid(replyThread); assertEquals(Arrays.asList(replyThread), CollectionUtils.newArrayList(first.getReplyThreads())); // The manifest now has a thread with no blips. assertEquals(1, first.getManifestBlip().numReplies()); assertEquals(0, first.getManifestBlip().getReply(0).numBlips()); // Still there after the next mutation. ObservableConversationBlip second = target.getRootThread().appendBlip(); assertThreadValid(replyThread); assertEquals(Arrays.asList(replyThread), CollectionUtils.newArrayList(first.getReplyThreads())); verify(convListener).onBlipAdded(second); verifyNoMoreInteractions(blipListener, threadListener, convListener); }
public void testRemoveRestoreThreadAfterObsoleteThreadDoesntDie() { WaveletBasedConversationBlip first = target.getRootThread().appendBlip(); WaveletBasedConversationThread reply11 = first.addReplyThread(); ConversationBlip blip1 = reply11.appendBlip(); String blip1Id = blip1.getId(); WaveletBasedConversationThread reply2 = first.addReplyThread(); // Make first thread empty by removing its blip. ManifestBlip manifestRootBlip = target.getManifest().getRootThread().getBlip(0); ManifestThread manifestReply1 = manifestRootBlip.getReply(0); manifestReply1.removeBlip(manifestReply1.getBlip(0)); assertThreadValid(reply11); // Remove and re-add second thread, as can happen in playback. String thread2Id = reply2.getId(); ManifestThread manifestReply2 = manifestRootBlip.getReply(1); manifestRootBlip.removeReply(manifestReply2); manifestRootBlip.appendReply(thread2Id, false); assertThreadInvalid(reply2); }
/** * Very basic test to see that we can create the object with a document and use it. */ public void testSimpleUsageWithDocument() { ObservableManifestBlip blip = buildBlipElement(ConversationTestUtils.createManifestDocument(), "b+1"); assertEquals("b+1", blip.getId()); ManifestThread reply = blip.appendReply("t1", false); assertNotNull(reply); assertEquals("t1", reply.getId()); }
/** * Removes a blip from the manifest, as though a remote client had done so. */ private void remoteRemoveBlip(WaveletBasedConversationBlip blip) { ManifestThread parentThread = blip.getThread().getManifestThread(); ManifestBlip manifestBlip = blip.getManifestBlip(); parentThread.removeBlip(manifestBlip); }
/** * Test that iterating a thread whose manifest contains blips not backed by the * wavelet skips those blips. */ public void testMissingBlipIteration() { WaveletBasedConversationThread thread = target.getRootThread(); WaveletBasedConversationBlip first = thread.appendBlip(); manifestDoc.with(new Action() { @Override public <N, E extends N, T extends N> void exec(MutableDocument<N, E, T> doc) { N rootThreadNode = doc.getFirstChild(doc.getDocumentElement()); E rootThread = doc.asElement(rootThreadNode); doc.createChildElement(rootThread, "blip", Collections.singletonMap( "id", idGenerator.newBlipId())); } }); WaveletBasedConversationBlip third = thread.appendBlip(); assertEquals(3, CollectionUtils.newArrayList(thread.getManifestThread().getBlips()).size()); assertEquals(Arrays.asList(first, third), getBlipList(thread)); }
public void testConcrrentDeletionOfFinalBlipsLeavesEmptyThread() { WaveletBasedConversationBlip first = target.getRootThread().appendBlip(); WaveletBasedConversationThread replyThread = first.addReplyThread(); WaveletBasedConversationBlip b1 = replyThread.appendBlip(); WaveletBasedConversationBlip b2 = replyThread.appendBlip(); // Locally delete b1, remotely delete b2. b1.delete(); replyThread.addListener(threadListener); b2.addListener(blipListener); target.addListener(convListener); remoteRemoveBlip(b2); // Expect blip deletion events and it to be invalid. verify(blipListener).onDeleted(); verify(convListener).onBlipDeleted(b2); assertBlipInvalid(b2); assertThreadValid(replyThread); assertEquals(Arrays.asList(replyThread), CollectionUtils.newArrayList(first.getReplyThreads())); // The manifest now has a thread with no blips. assertEquals(1, first.getManifestBlip().numReplies()); assertEquals(0, first.getManifestBlip().getReply(0).numBlips()); // Still there after the next mutation. ObservableConversationBlip second = target.getRootThread().appendBlip(); assertThreadValid(replyThread); assertEquals(Arrays.asList(replyThread), CollectionUtils.newArrayList(first.getReplyThreads())); verify(convListener).onBlipAdded(second); verifyNoMoreInteractions(blipListener, threadListener, convListener); }
public void testObsoleteThreadThenRestoreRemoveBlipDoesntDie() { WaveletBasedConversationBlip first = target.getRootThread().appendBlip(); WaveletBasedConversationThread willBecomeEmpty = first.addReplyThread(); ConversationBlip toggleBlip = willBecomeEmpty.appendBlip(); String toggleBlipId = toggleBlip.getId(); // Make the thread empty by remotely removing its blip. ManifestBlip manifestRootBlip = target.getManifest().getRootThread().getBlip(0); ManifestThread manifestReply = manifestRootBlip.getReply(0); manifestReply.removeBlip(manifestReply.getBlip(0)); assertThreadValid(willBecomeEmpty); // Re-add then remove the blip, as can happen in playback. manifestReply.appendBlip(toggleBlipId); manifestReply.removeBlip(manifestReply.getBlip(0)); }