ComparableMerger implements MigoriMerger { @Override public RevValue merge(MigoriDatastore store, Index index, Collection<RevValue> heads) throws IOException, NigoriCryptographyException, UnauthorisedException { assert heads.size() > 1; List<T> items = new ArrayList<T>(heads.size()); Map<T, RevValue> mapBack = new HashMap<T, RevValue>(); for (RevValue value : heads) { T item; try { item = converter.fromBytes(index, value.getValue()); } catch (ConversionException e) { throw new IOException(e); } items.add(item); mapBack.put(item, value); } findEquivalences(store, index, items, mapBack); T latest = items.get(items.size() - 1); if (items.size() == 1) { return mapBack.get(latest); } T newItem = converter.fromLatest(latest); return store.put(index, converter.toBytes(newItem), map(items, mapBack) .toArray(new RevValue[0])); } ComparableMerger(Converter<T> converter); @Override RevValue merge(MigoriDatastore store, Index index, Collection<RevValue> heads);  }
@Test public void mergeTwoEquiv() throws IOException, NigoriCryptographyException, UnauthorisedException { Collection<RevValue> heads = new ArrayList<RevValue>(); byte[] test = MessageLibrary.toBytes("test"); RevValue rv = new RevValue(Revision.EMPTY, test); RevValue rv1 = new RevValue(Revision.EMPTY, test); heads.add(rv); heads.add(rv1); MigoriDatastore store = createMock(MigoriDatastore.class); expect(store.put(eq(INDEX), aryEq(test), eq(rv), eq(rv1))).andReturn(rv); replay(store); RevValue value = merger.merge(store, INDEX, heads); verify(store); assertEquals(rv, value); }
@Test public void mergeTwoEquivOneGreater() throws IOException, NigoriCryptographyException, UnauthorisedException { Collection<RevValue> heads = new ArrayList<RevValue>(); byte[] test = MessageLibrary.toBytes("test"); byte[] test1 = MessageLibrary.toBytes("test1"); RevValue rv = new RevValue(Revision.EMPTY, test); RevValue rv1 = new RevValue(Revision.EMPTY, test); RevValue rv2 = new RevValue(Revision.EMPTY, test1); heads.add(rv); heads.add(rv1); heads.add(rv2); MigoriDatastore store = createMock(MigoriDatastore.class); expect(store.put(eq(INDEX), aryEq(test), eq(rv), eq(rv1))).andReturn(rv); expect(store.put(eq(INDEX), aryEq(test1), eq(rv), eq(rv2))).andReturn(rv2); replay(store); RevValue value = merger.merge(store, INDEX, heads); verify(store); assertEquals(rv2, value); }
@Test public void mergeTwoDiff() throws IOException, NigoriCryptographyException, UnauthorisedException { Collection<RevValue> heads = new ArrayList<RevValue>(); byte[] test = MessageLibrary.toBytes("test"); byte[] test1 = MessageLibrary.toBytes("test1"); RevValue rv = new RevValue(Revision.EMPTY, test); RevValue rv1 = new RevValue(Revision.EMPTY, test1); heads.add(rv); heads.add(rv1); MigoriDatastore store = createMock(MigoriDatastore.class); expect(store.put(eq(INDEX), aryEq(test1), eq(rv), eq(rv1))).andReturn(rv1); replay(store); RevValue value = merger.merge(store, INDEX, heads); verify(store); assertEquals(rv1, value); }