-
Notifications
You must be signed in to change notification settings - Fork 1k
PHOENIX-7593: Enable CompactionScanner for flushes #2134
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Changes from 3 commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -60,6 +60,7 @@ | |
| import org.apache.hadoop.hbase.io.ImmutableBytesWritable; | ||
| import org.apache.hadoop.hbase.ipc.RpcControllerFactory; | ||
| import org.apache.hadoop.hbase.ipc.controller.InterRegionServerIndexRpcControllerFactory; | ||
| import org.apache.hadoop.hbase.regionserver.FlushLifeCycleTracker; | ||
| import org.apache.hadoop.hbase.regionserver.InternalScanner; | ||
| import org.apache.hadoop.hbase.regionserver.MiniBatchOperationInProgress; | ||
| import org.apache.hadoop.hbase.regionserver.Region; | ||
|
|
@@ -611,6 +612,29 @@ private boolean areMutationsInSameTable(Table targetHTable, Region region) { | |
| region.getTableDescriptor().getTableName().getName()) == 0); | ||
| } | ||
|
|
||
| @Override | ||
| public InternalScanner preFlush(ObserverContext<RegionCoprocessorEnvironment> c, Store store, | ||
| InternalScanner scanner, FlushLifeCycleTracker tracker) | ||
| throws IOException { | ||
| if (!isPhoenixTableTTLEnabled(c.getEnvironment().getConfiguration())) { | ||
|
||
| return scanner; | ||
| } else { | ||
| return User.runAsLoginUser(new PrivilegedExceptionAction<InternalScanner>() { | ||
| @Override public InternalScanner run() throws Exception { | ||
| String tableName = c.getEnvironment().getRegion().getRegionInfo().getTable() | ||
| .getNameAsString(); | ||
| Configuration conf = c.getEnvironment().getConfiguration(); | ||
| long maxLookbackInMillis = | ||
| BaseScannerRegionObserverConstants.getMaxLookbackInMillis(conf); | ||
| maxLookbackInMillis = CompactionScanner.getMaxLookbackInMillis(tableName, | ||
| store.getColumnFamilyName(), maxLookbackInMillis); | ||
| return new CompactionScanner(c.getEnvironment(), store, scanner, | ||
| maxLookbackInMillis, false, true, null); | ||
| } | ||
| }); | ||
| } | ||
| } | ||
|
|
||
| @Override | ||
| public InternalScanner preCompact(ObserverContext<RegionCoprocessorEnvironment> c, Store store, | ||
| InternalScanner scanner, ScanType scanType, CompactionLifeCycleTracker tracker, | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -604,8 +604,67 @@ public void testRetainingLastRowVersion() throws Exception { | |
| TestUtil.dumpTable(conn, dataTableName); | ||
| ResultSet rs = stmt.executeQuery("select * from " + dataTableName + " where id = 'a'"); | ||
| while(rs.next()) { | ||
| assertNotNull(rs.getString(3)); | ||
| assertNotNull(rs.getString(4)); | ||
| assertEquals("abc", rs.getString(3)); | ||
| assertEquals("abcd", rs.getString(4)); | ||
| } | ||
| } | ||
| } | ||
|
|
||
| @Test(timeout=60000) | ||
| public void testRetainingLastRowVersionForFlushes() throws Exception { | ||
| try(Connection conn = DriverManager.getConnection(getUrl())) { | ||
| String tableName = generateUniqueName(); | ||
| createTable(tableName); | ||
| long timeIntervalBetweenTwoUpserts = (ttl / 2) + 1; | ||
| injectEdge.setValue(System.currentTimeMillis()); | ||
| EnvironmentEdgeManager.injectEdge(injectEdge); | ||
| TableName dataTableName = TableName.valueOf(tableName); | ||
| injectEdge.incrementValue(1); | ||
| Statement stmt = conn.createStatement(); | ||
| stmt.execute("upsert into " + tableName + " values ('a', 'ab', 'abc', 'abcd')"); | ||
| conn.commit(); | ||
| injectEdge.incrementValue(timeIntervalBetweenTwoUpserts * 1000); | ||
| stmt.execute("upsert into " + tableName + " values ('a', 'ab1')"); | ||
| conn.commit(); | ||
| injectEdge.incrementValue(timeIntervalBetweenTwoUpserts * 1000); | ||
| stmt.execute("upsert into " + tableName + " values ('a', 'ab2')"); | ||
| conn.commit(); | ||
| injectEdge.incrementValue(timeIntervalBetweenTwoUpserts * 1000); | ||
| stmt.execute("upsert into " + tableName + " values ('a', 'ab3')"); | ||
| conn.commit(); | ||
| injectEdge.incrementValue(MAX_LOOKBACK_AGE * 1000); | ||
|
|
||
| TestUtil.dumpTable(conn, dataTableName); | ||
| byte[] rowKey = Bytes.toBytes("a"); | ||
| int rawCellCount = TestUtil.getRawCellCount(conn, dataTableName, rowKey); | ||
| // 6 non-empty cells (ab3, ab2, ab1, ab, abc, abcd) + 4 empty cells (for 4 upserts) | ||
| assertEquals(10, rawCellCount); | ||
|
|
||
| TestUtil.flush(utility, dataTableName); | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Let's use TestUtil.getRawCellCount and verify that extra row versions are removed. |
||
| injectEdge.incrementValue(1); | ||
| rawCellCount = TestUtil.getRawCellCount(conn, dataTableName, rowKey); | ||
| // 1 non-empty cell (ab3) and 1 empty cell in max lookback window are | ||
| // immediately retained. | ||
| // 3 non-empty cells outside max lookback window will be retained (ab2, abc, abcd) | ||
| // 3 (for multi-CF)/ 2 (single-CF) empty cells will be retained outside | ||
| // max lookback window | ||
| assertEquals(multiCF ? 8 : 7, rawCellCount); | ||
| TestUtil.dumpTable(conn, dataTableName); | ||
|
|
||
| majorCompact(dataTableName); | ||
| injectEdge.incrementValue(1); | ||
| rawCellCount = TestUtil.getRawCellCount(conn, dataTableName, rowKey); | ||
| // 1 non-empty cell (ab3) and 1 empty cell at the edge of max lookback window will be | ||
| // retained | ||
| // 2 non-empty cells outside max lookback window will be retained (abc, abcd) | ||
| // 2 empty cells will be retained outside max lookback window | ||
| assertEquals(6, rawCellCount); | ||
| TestUtil.dumpTable(conn, dataTableName); | ||
|
|
||
| ResultSet rs = stmt.executeQuery("select * from " + dataTableName + " where id = 'a'"); | ||
| while(rs.next()) { | ||
| assertEquals("abc", rs.getString(3)); | ||
| assertEquals("abcd", rs.getString(4)); | ||
| } | ||
| } | ||
| } | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -128,8 +128,8 @@ public static synchronized Collection<Object[]> data() { | |
| { false, false, KeepDeletedCells.FALSE, 1, 100, null}, | ||
| { false, false, KeepDeletedCells.TRUE, 5, 50, null}, | ||
| { false, false, KeepDeletedCells.TTL, 1, 25, null}, | ||
| { true, false, KeepDeletedCells.FALSE, 5, 50, null}, | ||
| { true, false, KeepDeletedCells.TRUE, 1, 25, null}, | ||
| { true, false, KeepDeletedCells.FALSE, 5, 50, 0}, | ||
| { true, false, KeepDeletedCells.TRUE, 1, 25, 0}, | ||
| { true, false, KeepDeletedCells.TTL, 5, 100, null}, | ||
| { false, false, KeepDeletedCells.FALSE, 1, 100, 0}, | ||
| { false, false, KeepDeletedCells.TRUE, 5, 50, 0}, | ||
|
|
@@ -246,7 +246,7 @@ public void testMaskingAndMajorCompaction() throws Exception { | |
| } | ||
|
|
||
| @Test | ||
| public void testMinorCompactionShouldNotRetainCellsWhenMaxLookbackIsDisabled() | ||
| public void testMinorCompactionAndFlushesShouldNotRetainCellsWhenMaxLookbackIsDisabled() | ||
| throws Exception { | ||
| if (tableLevelMaxLookback == null || tableLevelMaxLookback != 0) { | ||
| return; | ||
|
|
@@ -273,15 +273,31 @@ public void testMinorCompactionShouldNotRetainCellsWhenMaxLookbackIsDisabled() | |
| Thread.sleep(1); | ||
| } | ||
| flush(TableName.valueOf(tableName)); | ||
| // Flushes dump and retain all the cells to HFile. | ||
| // Doing MAX_COLUMN_INDEX + 1 to account for empty cells | ||
| assertEquals(TestUtil.getRawCellCount(conn, TableName.valueOf(tableName), row), | ||
| rowUpdateCounter * (MAX_COLUMN_INDEX + 1)); | ||
| // At every flush, extra cell versions should be removed. | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We need to rename this test method to testMinorCompactionAndFlushShouldNotRetainCellsWhenMaxLookbackIsDisabled |
||
| // MAX_COLUMN_INDEX table columns will be retained for each row version. | ||
| int expectedMaxRawCellCount; | ||
| if (multiCF) { | ||
| // All empty cells are retained for multiCF tables for flushes and minor | ||
| // compactions | ||
| expectedMaxRawCellCount = | ||
| ((i + 1) * MAX_COLUMN_INDEX * versions) + rowUpdateCounter; | ||
| } | ||
| else { | ||
| // Only empty column is retained for each row version | ||
| expectedMaxRawCellCount = (i + 1) * (MAX_COLUMN_INDEX + 1) * versions; | ||
| } | ||
| int rawCellCount = TestUtil.getRawCellCount( | ||
| conn, TableName.valueOf(tableName), row); | ||
| // Need inequality check here as a minor compaction could have happened | ||
| assertTrue(rawCellCount <= expectedMaxRawCellCount); | ||
| } | ||
| // Run one minor compaction (in case no minor compaction has happened yet) | ||
| TestUtil.minorCompact(utility, TableName.valueOf(tableName)); | ||
| assertEquals(TestUtil.getRawCellCount(conn, TableName.valueOf(tableName), | ||
| Bytes.toBytes("a")), (MAX_COLUMN_INDEX + 1) * versions); | ||
| int rawCellCount = TestUtil.getRawCellCount(conn, TableName.valueOf(tableName), | ||
| Bytes.toBytes("a")); | ||
| int expectedRawCellCount = (MAX_COLUMN_INDEX * versions) | ||
| + (multiCF ? rowUpdateCounter : versions); | ||
| assertEquals(expectedRawCellCount, rawCellCount); | ||
| } catch (AssertionError e) { | ||
| TestUtil.dumpTable(conn, TableName.valueOf(tableName)); | ||
| throw e; | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For not emptycfstore aren't we doing this check on every row
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, will fix that. Thanks