fix mixing user-provided timestamps and local deletion time for #4396

This commit is contained in:
Jonathan Ellis 2012-07-10 08:35:23 -05:00
parent 5bcfcbc3ed
commit 84a1d6059b
2 changed files with 42 additions and 1 deletions

View File

@ -256,8 +256,9 @@ public abstract class AbstractColumnContainer implements IColumnContainer, IIter
if (isMarkedForDelete() && getLocalDeletionTime() < gcBefore)
return true;
long deletedAt = getMarkedForDeleteAt();
for (IColumn column : columns)
if (column.mostRecentLiveChangeAt() < getLocalDeletionTime() || column.hasIrrelevantData(gcBefore))
if (column.mostRecentLiveChangeAt() <= deletedAt || column.hasIrrelevantData(gcBefore))
return true;
return false;

View File

@ -35,11 +35,14 @@ import org.apache.cassandra.CleanupHelper;
import org.apache.cassandra.Util;
import org.apache.cassandra.config.DatabaseDescriptor;
import org.apache.cassandra.db.*;
import org.apache.cassandra.db.columniterator.IColumnIterator;
import org.apache.cassandra.db.columniterator.IdentityQueryFilter;
import org.apache.cassandra.db.compaction.OperationType;
import org.apache.cassandra.db.filter.QueryFilter;
import org.apache.cassandra.db.filter.QueryPath;
import org.apache.cassandra.io.sstable.*;
import org.apache.cassandra.utils.ByteBufferUtil;
import org.apache.cassandra.utils.FBUtilities;
public class CompactionsTest extends CleanupHelper
{
@ -128,6 +131,43 @@ public class CompactionsTest extends CleanupHelper
assertMaxTimestamp(store, maxTimestampExpected);
}
@Test
public void testSuperColumnTombstones() throws IOException, ExecutionException, InterruptedException
{
Table table = Table.open(TABLE1);
ColumnFamilyStore cfs = table.getColumnFamilyStore("Super1");
cfs.disableAutoCompaction();
DecoratedKey key = Util.dk("tskey");
ByteBuffer scName = ByteBufferUtil.bytes("TestSuperColumn");
// a subcolumn
RowMutation rm = new RowMutation(TABLE1, key.key);
rm.add(new QueryPath("Super1", scName, ByteBufferUtil.bytes(0)),
ByteBufferUtil.EMPTY_BYTE_BUFFER,
FBUtilities.timestampMicros());
rm.apply();
cfs.forceBlockingFlush();
// shadow the subcolumn with a supercolumn tombstone
rm = new RowMutation(TABLE1, key.key);
rm.delete(new QueryPath("Super1", scName), FBUtilities.timestampMicros());
rm.apply();
cfs.forceBlockingFlush();
CompactionManager.instance.performMaximal(cfs);
assertEquals(1, cfs.getSSTables().size());
// check that the shadowed column is gone
SSTableReader sstable = cfs.getSSTables().iterator().next();
SSTableScanner scanner = sstable.getScanner(new QueryFilter(null, new QueryPath("Super1", scName), new IdentityQueryFilter()));
scanner.seekTo(key);
IColumnIterator iter = scanner.next();
assertEquals(key, iter.getKey());
SuperColumn sc = (SuperColumn) iter.next();
assert sc.getSubColumns().isEmpty();
}
public void assertMaxTimestamp(ColumnFamilyStore store, long maxTimestampExpected)
{
long maxTimestampObserved = Long.MIN_VALUE;