PHOENIX-1753 Query with RVC that doesn't lead with the row key can return 
incorrect results


Project: http://git-wip-us.apache.org/repos/asf/phoenix/repo
Commit: http://git-wip-us.apache.org/repos/asf/phoenix/commit/e06ceaf4
Tree: http://git-wip-us.apache.org/repos/asf/phoenix/tree/e06ceaf4
Diff: http://git-wip-us.apache.org/repos/asf/phoenix/diff/e06ceaf4

Branch: refs/heads/4.x-HBase-1.x
Commit: e06ceaf455642d92b500d0e4edc343a3342a0d93
Parents: 4bc162d
Author: James Taylor <jtay...@salesforce.com>
Authored: Thu Mar 19 18:54:57 2015 -0700
Committer: James Taylor <jtay...@salesforce.com>
Committed: Sat Mar 21 11:13:24 2015 -0700

----------------------------------------------------------------------
 .../phoenix/end2end/RowValueConstructorIT.java  | 33 +++++++++++++++++++-
 .../apache/phoenix/compile/WhereOptimizer.java  |  4 +++
 .../phoenix/compile/WhereOptimizerTest.java     | 16 ++++++++++
 3 files changed, 52 insertions(+), 1 deletion(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/phoenix/blob/e06ceaf4/phoenix-core/src/it/java/org/apache/phoenix/end2end/RowValueConstructorIT.java
----------------------------------------------------------------------
diff --git 
a/phoenix-core/src/it/java/org/apache/phoenix/end2end/RowValueConstructorIT.java
 
b/phoenix-core/src/it/java/org/apache/phoenix/end2end/RowValueConstructorIT.java
index 8d67fa4..3859785 100644
--- 
a/phoenix-core/src/it/java/org/apache/phoenix/end2end/RowValueConstructorIT.java
+++ 
b/phoenix-core/src/it/java/org/apache/phoenix/end2end/RowValueConstructorIT.java
@@ -1362,6 +1362,37 @@ public class RowValueConstructorIT extends 
BaseClientManagedTimeIT {
         conn.close();
     }
 
-
+    @Test
+    public void testRVCWithRowKeyNotLeading() throws Exception {
+        String ddl = "CREATE TABLE sorttest4 (rownum BIGINT primary key, name 
varchar(16), age integer)";
+        Connection conn = nextConnection(getUrl());
+        conn.createStatement().execute(ddl);
+        conn.close();
+        conn = nextConnection(getUrl());
+        String dml = "UPSERT INTO sorttest4 (rownum, name, age) values (?, ?, 
?)";
+        PreparedStatement stmt = conn.prepareStatement(dml);
+        stmt.setInt(1, 1);
+        stmt.setString(2, "A");
+        stmt.setInt(3, 1);
+        stmt.executeUpdate();
+        stmt.setInt(1, 2);
+        stmt.setString(2, "B");
+        stmt.setInt(3, 2);
+        stmt.executeUpdate();
+        conn.commit();
+        conn.close();
+        // the below query should only return one record -> (1, "A", 1)
+        String query = "SELECT rownum, name, age FROM sorttest4 where (age, 
rownum) < (2, 2)";
+        conn = nextConnection(getUrl());
+        ResultSet rs = conn.createStatement().executeQuery(query);
+        int numRecords = 0;
+        while (rs.next()) {
+            assertEquals(1, rs.getInt(1));
+            assertEquals("A", rs.getString(2));
+            assertEquals(1, rs.getInt(3));
+            numRecords++;
+        }
+        assertEquals(1, numRecords);
+    }
 
 }

http://git-wip-us.apache.org/repos/asf/phoenix/blob/e06ceaf4/phoenix-core/src/main/java/org/apache/phoenix/compile/WhereOptimizer.java
----------------------------------------------------------------------
diff --git 
a/phoenix-core/src/main/java/org/apache/phoenix/compile/WhereOptimizer.java 
b/phoenix-core/src/main/java/org/apache/phoenix/compile/WhereOptimizer.java
index 713076e..b03793d 100644
--- a/phoenix-core/src/main/java/org/apache/phoenix/compile/WhereOptimizer.java
+++ b/phoenix-core/src/main/java/org/apache/phoenix/compile/WhereOptimizer.java
@@ -542,6 +542,10 @@ public class WhereOptimizer {
                 int span = position - initialPosition;
                 return new SingleKeySlot(new 
RowValueConstructorKeyPart(table.getPKColumns().get(initialPosition), rvc, 
span, childSlots), initialPosition, span, EVERYTHING_RANGES);
             }
+            // If we don't clear the child list, we end up passing some of
+            // the child expressions of previous matches up the tree, causing
+            // those expressions to form the scan start/stop key. PHOENIX-1753
+            childSlots.clear();
             return null;
         }
 

http://git-wip-us.apache.org/repos/asf/phoenix/blob/e06ceaf4/phoenix-core/src/test/java/org/apache/phoenix/compile/WhereOptimizerTest.java
----------------------------------------------------------------------
diff --git 
a/phoenix-core/src/test/java/org/apache/phoenix/compile/WhereOptimizerTest.java 
b/phoenix-core/src/test/java/org/apache/phoenix/compile/WhereOptimizerTest.java
index 0ec6b45..94b25d0 100644
--- 
a/phoenix-core/src/test/java/org/apache/phoenix/compile/WhereOptimizerTest.java
+++ 
b/phoenix-core/src/test/java/org/apache/phoenix/compile/WhereOptimizerTest.java
@@ -1275,6 +1275,22 @@ public class WhereOptimizerTest extends 
BaseConnectionlessQueryTest {
     }
     
     @Test
+    public void testRVCExpressionWithNonFirstLeadingColOfRowKey() throws 
SQLException {
+        String old_value = "value";
+        String orgId = getOrganizationId();
+        
+        String query = "select * from entity_history where (old_value, 
organization_id) >= (?,?)";
+        List<Object> binds = Arrays.<Object>asList(old_value, orgId);
+        StatementContext context = compileStatement(query, binds);
+        Scan scan = context.getScan();
+        Filter filter = scan.getFilter();
+        assertNotNull(filter);
+        assertTrue(filter instanceof SingleKeyValueComparisonFilter);
+        assertArrayEquals(HConstants.EMPTY_START_ROW, scan.getStartRow());
+        assertArrayEquals(HConstants.EMPTY_END_ROW, scan.getStopRow());
+    }
+    
+    @Test
     public void testMultiRVCExpressionsCombinedWithAnd() throws SQLException {
         String lowerTenantId = "000000000000001";
         String lowerParentId = "000000000000002";

Reply via email to