This is an automated email from the ASF dual-hosted git repository.

kgyrtkirk pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/hive.git


The following commit(s) were added to refs/heads/master by this push:
     new 621bfd1  HIVE-25822: Unexpected result rows in case of outer join 
contains conditions only affecting one side (#2891) (Zoltan Haindrich reviewed 
by Stamatis Zampetakis, Aman Sinha)
621bfd1 is described below

commit 621bfd164f018063fe5e03d9f7a7d990ce22691a
Author: Zoltan Haindrich <k...@rxd.hu>
AuthorDate: Tue Dec 21 11:50:45 2021 +0100

    HIVE-25822: Unexpected result rows in case of outer join contains 
conditions only affecting one side (#2891) (Zoltan Haindrich reviewed by 
Stamatis Zampetakis, Aman Sinha)
---
 .../java/org/apache/hadoop/hive/conf/HiveConf.java |  2 +
 .../hive/ql/exec/CommonMergeJoinOperator.java      | 80 ++++++++++++++++--
 .../clientpositive/outer_join_unexpected_rows.q    | 17 ++++
 .../test/results/clientpositive/llap/join46.q.out  |  4 +-
 .../results/clientpositive/llap/join_1to1.q.out    | 64 +--------------
 .../clientpositive/llap/join_emit_interval.q.out   |  6 +-
 .../results/clientpositive/llap/mapjoin2.q.out     |  2 +-
 .../llap/outer_join_unexpected_rows.q.out          | 95 ++++++++++++++++++++++
 .../llap/vector_full_outer_join2.q.out             | 18 ++--
 9 files changed, 208 insertions(+), 80 deletions(-)

diff --git a/common/src/java/org/apache/hadoop/hive/conf/HiveConf.java 
b/common/src/java/org/apache/hadoop/hive/conf/HiveConf.java
index fd95070..b0b9b4f 100644
--- a/common/src/java/org/apache/hadoop/hive/conf/HiveConf.java
+++ b/common/src/java/org/apache/hadoop/hive/conf/HiveConf.java
@@ -1836,6 +1836,8 @@ public class HiveConf extends Configuration {
     HIVEALIAS("hive.alias", "", ""),
     HIVEMAPSIDEAGGREGATE("hive.map.aggr", true, "Whether to use map-side 
aggregation in Hive Group By queries"),
     HIVEGROUPBYSKEW("hive.groupby.skewindata", false, "Whether there is skew 
in data to optimize group by queries"),
+    HIVE_JOIN_SHORTCUT_UNMATCHED_ROWS("hive.join.shortcut.unmatched.rows", 
true,
+        "Enables to shortcut processing of known filtered rows in merge joins. 
internal use only. may affect correctness"),
     HIVEJOINEMITINTERVAL("hive.join.emit.interval", 1000,
         "How many rows in the right-most join operand Hive should buffer 
before emitting the join result."),
     HIVEJOINCACHESIZE("hive.join.cache.size", 25000,
diff --git 
a/ql/src/java/org/apache/hadoop/hive/ql/exec/CommonMergeJoinOperator.java 
b/ql/src/java/org/apache/hadoop/hive/ql/exec/CommonMergeJoinOperator.java
index e574fb9..0044a04 100644
--- a/ql/src/java/org/apache/hadoop/hive/ql/exec/CommonMergeJoinOperator.java
+++ b/ql/src/java/org/apache/hadoop/hive/ql/exec/CommonMergeJoinOperator.java
@@ -42,12 +42,12 @@ import org.apache.hadoop.hive.ql.metadata.HiveException;
 import org.apache.hadoop.hive.ql.plan.CommonMergeJoinDesc;
 import org.apache.hadoop.hive.ql.plan.ExprNodeDesc;
 import org.apache.hadoop.hive.ql.plan.JoinCondDesc;
+import org.apache.hadoop.hive.ql.plan.JoinDesc;
 import org.apache.hadoop.hive.ql.plan.OperatorDesc;
 import org.apache.hadoop.hive.ql.plan.api.OperatorType;
 import org.apache.hadoop.hive.serde2.objectinspector.ObjectInspectorUtils;
 import 
org.apache.hadoop.hive.serde2.objectinspector.ObjectInspectorUtils.ObjectInspectorCopyOption;
 import org.apache.hadoop.hive.serde2.objectinspector.StructObjectInspector;
-import org.apache.hadoop.io.WritableComparable;
 import org.apache.hadoop.io.WritableComparator;
 
 /*
@@ -74,6 +74,7 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
   transient List<Object>[] nextKeyWritables;
   transient RowContainer<List<Object>>[] nextGroupStorage;
   transient RowContainer<List<Object>>[] candidateStorage;
+  transient RowContainer<List<Object>>[] unmatchedStorage;
 
   transient String[] tagToAlias;
   private transient boolean[] fetchDone;
@@ -94,6 +95,7 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
   transient InterruptibleProcessing interruptChecker;
 
   transient NullOrdering nullOrdering;
+  transient private boolean shortcutUnmatchedRows;
 
   /** Kryo ctor. */
   protected CommonMergeJoinOperator() {
@@ -121,6 +123,7 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
 
     nextGroupStorage = new RowContainer[maxAlias];
     candidateStorage = new RowContainer[maxAlias];
+    unmatchedStorage = new RowContainer[maxAlias];
     keyWritables = new ArrayList[maxAlias];
     nextKeyWritables = new ArrayList[maxAlias];
     fetchDone = new boolean[maxAlias];
@@ -134,6 +137,8 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
     int bucketSize;
 
     int oldVar = HiveConf.getIntVar(hconf, 
HiveConf.ConfVars.HIVEMAPJOINBUCKETCACHESIZE);
+    shortcutUnmatchedRows = HiveConf.getBoolVar(hconf, 
HiveConf.ConfVars.HIVE_JOIN_SHORTCUT_UNMATCHED_ROWS);
+
     if (oldVar != 100) {
       bucketSize = oldVar;
     } else {
@@ -149,6 +154,9 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
           JoinUtil.getRowContainer(hconf, 
rowContainerStandardObjectInspectors[pos], pos,
               bucketSize, spillTableDesc, conf, !hasFilter(pos), reporter);
       candidateStorage[pos] = candidateRC;
+      RowContainer<List<Object>> unmatchedRC = JoinUtil.getRowContainer(hconf,
+          rowContainerStandardObjectInspectors[pos], pos, bucketSize, 
spillTableDesc, conf, !hasFilter(pos), reporter);
+      unmatchedStorage[pos] = unmatchedRC;
     }
 
     for (byte pos = 0; pos < order.length; pos++) {
@@ -240,6 +248,18 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
 
     byte alias = (byte) tag;
     List<Object> value = getFilteredValue(alias, row);
+
+    if (isOuterJoinUnmatchedRow(tag, value)) {
+      int type = condn[0].getType();
+      if (tag == 0 && (type == JoinDesc.LEFT_OUTER_JOIN || type == 
JoinDesc.FULL_OUTER_JOIN)) {
+        unmatchedStorage[tag].addRow(value);
+      }
+      if (tag == 1 && (type == JoinDesc.RIGHT_OUTER_JOIN || type == 
JoinDesc.FULL_OUTER_JOIN)) {
+        unmatchedStorage[tag].addRow(value);
+      }
+      emitUnmatchedRows(tag, false);
+      return;
+    }
     // compute keys and values as StandardObjects
     List<Object> key = mergeJoinComputeKeys(row, alias);
     // Fetch the first group for all small table aliases.
@@ -302,7 +322,50 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
 
     assert !nextKeyGroup;
     candidateStorage[tag].addRow(value);
+  }
+
+  private void emitUnmatchedRows(int tag, boolean force) throws HiveException {
+    if (unmatchedStorage[tag].rowCount() == 0 || (!force && 
unmatchedStorage[tag].rowCount() < joinEmitInterval)) {
+      return;
+    }
+    for (byte i = 0; i < order.length; i++) {
+      if (i == tag) {
+        storage[i] = unmatchedStorage[i];
+      } else {
+        putDummyOrEmpty(i);
+      }
+    }
+    checkAndGenObject();
+    unmatchedStorage[tag].clearRows();
+  }
 
+  /**
+   * Decides if the actual row must be an unmatched row.
+   *
+   * Unmatched rows are those which are not part of the inner-join.
+   * The current implementation has issues processing filtered rows in FOJ 
conditions.
+   * Putting them in a separate group also reduces processing done for them.
+   */
+  private boolean isOuterJoinUnmatchedRow(int tag, List<Object> value) {
+    if (!shortcutUnmatchedRows || condn.length != 1) {
+      return false;
+    }
+    switch (condn[0].getType()) {
+    case JoinDesc.INNER_JOIN:
+    case JoinDesc.LEFT_OUTER_JOIN:
+    case JoinDesc.RIGHT_OUTER_JOIN:
+    case JoinDesc.FULL_OUTER_JOIN:
+      break;
+    default:
+      return false;
+    }
+    if (hasFilter(tag)) {
+      short filterTag = getFilterTag(value);
+      if (JoinUtil.isFiltered(filterTag, 1 - tag)) {
+        return true;
+      }
+    }
+    return false;
   }
 
   private List<Byte> joinOneGroup() throws HiveException {
@@ -310,6 +373,9 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
   }
 
   private List<Byte> joinOneGroup(boolean clear) throws HiveException {
+    for (int pos = 0; pos < order.length; pos++) {
+      emitUnmatchedRows(pos, true);
+    }
     int[] smallestPos = findSmallestKey();
     List<Byte> listOfNeedFetchNext = null;
     if (smallestPos != null) {
@@ -430,7 +496,7 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
       this.nextKeyWritables[t] = null;
     }
   }
-  
+
   @Override
   public void close(boolean abort) throws HiveException {
     joinFinalLeftData(); // Do this WITHOUT checking for parents
@@ -530,7 +596,9 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
   }
 
   private void doFirstFetchIfNeeded() throws HiveException {
-    if (firstFetchHappened) return;
+    if (firstFetchHappened) {
+      return;
+    }
     firstFetchHappened = true;
     for (byte pos = 0; pos < order.length; pos++) {
       if (pos != posBigTable) {
@@ -541,7 +609,9 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
 
   private boolean allFetchDone() {
     for (byte pos = 0; pos < order.length; pos++) {
-      if (pos != posBigTable && !fetchDone[pos]) return false;
+      if (pos != posBigTable && !fetchDone[pos]) {
+        return false;
+      }
     }
     return true;
   }
@@ -638,7 +708,7 @@ public class CommonMergeJoinOperator extends 
AbstractMapJoinOperator<CommonMerge
       ObjectInspectorUtils.partialCopyToStandardObject(key, row,
           Utilities.ReduceField.KEY.position, 1, (StructObjectInspector) 
inputObjInspectors[alias],
           ObjectInspectorCopyOption.WRITABLE);
-      return (List<Object>) key.get(0); // this is always 0, even if 
KEY.position is not 
+      return (List<Object>) key.get(0); // this is always 0, even if 
KEY.position is not
     }
   }
 
diff --git a/ql/src/test/queries/clientpositive/outer_join_unexpected_rows.q 
b/ql/src/test/queries/clientpositive/outer_join_unexpected_rows.q
new file mode 100644
index 0000000..57c4409
--- /dev/null
+++ b/ql/src/test/queries/clientpositive/outer_join_unexpected_rows.q
@@ -0,0 +1,17 @@
+
+with
+t_y as (select col1 as id,col2 as s from (VALUES(0,'a'),(1,'y')) as c),
+t_xy as (select col1 as id,col2 as s from (VALUES(1,'x'),(1,'y')) as c) 
+select * from t_xy l full outer join t_y r on (l.id=r.id and l.s='y');
+
+create table t_y (id integer,s string);
+create table t_xy (id integer,s string);
+
+insert into t_y values(0,'a'),(1,'y'),(1,'x');
+insert into t_xy values(1,'x'),(1,'y');
+
+select * from t_xy l full outer join t_y r on (l.id=r.id and l.s='y');
+set hive.auto.convert.join=true;
+select * from t_xy l full outer join t_y r on (l.id=r.id and l.s='y');
+set hive.cbo.enable=false;
+select * from t_xy l full outer join t_y r on (l.id=r.id and l.s='y');
diff --git a/ql/src/test/results/clientpositive/llap/join46.q.out 
b/ql/src/test/results/clientpositive/llap/join46.q.out
index e4f393e..a938989 100644
--- a/ql/src/test/results/clientpositive/llap/join46.q.out
+++ b/ql/src/test/results/clientpositive/llap/join46.q.out
@@ -278,11 +278,11 @@ POSTHOOK: Input: default@test1_n2
 POSTHOOK: Input: default@test2_n0
 #### A masked pattern was here ####
 99     0       Alice   NULL    NULL    NULL
-100    1       Bob     NULL    NULL    NULL
 99     2       Mat     NULL    NULL    NULL
-101    2       Car     102     2       Del
+100    1       Bob     NULL    NULL    NULL
 NULL   NULL    None    NULL    NULL    NULL
 98     NULL    None    NULL    NULL    NULL
+101    2       Car     102     2       Del
 Warning: Shuffle Join MERGEJOIN[11][tables = [$hdt$_0, $hdt$_1]] in Stage 
'Reducer 2' is a cross product
 PREHOOK: query: EXPLAIN
 SELECT *
diff --git a/ql/src/test/results/clientpositive/llap/join_1to1.q.out 
b/ql/src/test/results/clientpositive/llap/join_1to1.q.out
index 8495894..1ccb613 100644
--- a/ql/src/test/results/clientpositive/llap/join_1to1.q.out
+++ b/ql/src/test/results/clientpositive/llap/join_1to1.q.out
@@ -373,9 +373,6 @@ NULL        NULL    NULL    25      10025   66
 NULL   NULL    NULL    30      10030   88
 NULL   NULL    NULL    35      10035   88
 NULL   NULL    NULL    40      10040   88
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    70      10040   88
 NULL   NULL    NULL    70      10040   88
@@ -466,9 +463,6 @@ NULL        NULL    NULL    25      10025   66
 NULL   NULL    NULL    30      10030   88
 NULL   NULL    NULL    35      10035   88
 NULL   NULL    NULL    40      10040   88
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    70      10040   88
 NULL   NULL    NULL    70      10040   88
@@ -589,6 +583,7 @@ POSTHOOK: Input: default@join_1to1_2
 60     10040   66      60      10040   66
 60     10040   66      60      10040   66
 70     10040   66      NULL    NULL    NULL
+70     10040   66      NULL    NULL    NULL
 80     10040   88      NULL    NULL    NULL
 80     10040   88      NULL    NULL    NULL
 NULL   10050   66      NULL    NULL    NULL
@@ -597,22 +592,10 @@ NULL      NULL    NULL    10      10010   66
 NULL   NULL    NULL    25      10025   66
 NULL   NULL    NULL    30      10030   88
 NULL   NULL    NULL    35      10035   88
-NULL   NULL    NULL    40      10040   66
 NULL   NULL    NULL    40      10040   88
-NULL   NULL    NULL    40      10040   88
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    50      10050   88
-NULL   NULL    NULL    50      10050   88
-NULL   NULL    NULL    70      10040   88
 NULL   NULL    NULL    70      10040   88
 NULL   NULL    NULL    70      10040   88
-NULL   NULL    NULL    70      10040   88
-NULL   NULL    NULL    80      10040   66
-NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    NULL    10050   66
@@ -690,6 +673,7 @@ POSTHOOK: Input: default@join_1to1_2
 60     10040   66      60      10040   66
 60     10040   66      60      10040   66
 70     10040   66      NULL    NULL    NULL
+70     10040   66      NULL    NULL    NULL
 80     10040   88      NULL    NULL    NULL
 80     10040   88      NULL    NULL    NULL
 NULL   10050   66      NULL    NULL    NULL
@@ -698,22 +682,10 @@ NULL      NULL    NULL    10      10010   66
 NULL   NULL    NULL    25      10025   66
 NULL   NULL    NULL    30      10030   88
 NULL   NULL    NULL    35      10035   88
-NULL   NULL    NULL    40      10040   66
-NULL   NULL    NULL    40      10040   88
 NULL   NULL    NULL    40      10040   88
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   88
-NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    70      10040   88
 NULL   NULL    NULL    70      10040   88
-NULL   NULL    NULL    70      10040   88
-NULL   NULL    NULL    70      10040   88
-NULL   NULL    NULL    80      10040   66
-NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    NULL    10050   66
@@ -1061,9 +1033,6 @@ NULL      NULL    NULL    25      10025   66
 NULL   NULL    NULL    30      10030   88
 NULL   NULL    NULL    35      10035   88
 NULL   NULL    NULL    40      10040   88
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    70      10040   88
 NULL   NULL    NULL    70      10040   88
@@ -1154,9 +1123,6 @@ NULL      NULL    NULL    25      10025   66
 NULL   NULL    NULL    30      10030   88
 NULL   NULL    NULL    35      10035   88
 NULL   NULL    NULL    40      10040   88
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    70      10040   88
 NULL   NULL    NULL    70      10040   88
@@ -1277,6 +1243,7 @@ POSTHOOK: Input: default@join_1to1_2
 60     10040   66      60      10040   66
 60     10040   66      60      10040   66
 70     10040   66      NULL    NULL    NULL
+70     10040   66      NULL    NULL    NULL
 80     10040   88      NULL    NULL    NULL
 80     10040   88      NULL    NULL    NULL
 NULL   10050   66      NULL    NULL    NULL
@@ -1285,22 +1252,10 @@ NULL    NULL    NULL    10      10010   66
 NULL   NULL    NULL    25      10025   66
 NULL   NULL    NULL    30      10030   88
 NULL   NULL    NULL    35      10035   88
-NULL   NULL    NULL    40      10040   66
 NULL   NULL    NULL    40      10040   88
-NULL   NULL    NULL    40      10040   88
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    50      10050   88
-NULL   NULL    NULL    50      10050   88
-NULL   NULL    NULL    70      10040   88
 NULL   NULL    NULL    70      10040   88
 NULL   NULL    NULL    70      10040   88
-NULL   NULL    NULL    70      10040   88
-NULL   NULL    NULL    80      10040   66
-NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    NULL    10050   66
@@ -1378,6 +1333,7 @@ POSTHOOK: Input: default@join_1to1_2
 60     10040   66      60      10040   66
 60     10040   66      60      10040   66
 70     10040   66      NULL    NULL    NULL
+70     10040   66      NULL    NULL    NULL
 80     10040   88      NULL    NULL    NULL
 80     10040   88      NULL    NULL    NULL
 NULL   10050   66      NULL    NULL    NULL
@@ -1386,22 +1342,10 @@ NULL    NULL    NULL    10      10010   66
 NULL   NULL    NULL    25      10025   66
 NULL   NULL    NULL    30      10030   88
 NULL   NULL    NULL    35      10035   88
-NULL   NULL    NULL    40      10040   66
-NULL   NULL    NULL    40      10040   88
 NULL   NULL    NULL    40      10040   88
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   66
-NULL   NULL    NULL    50      10050   88
-NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    50      10050   88
 NULL   NULL    NULL    70      10040   88
 NULL   NULL    NULL    70      10040   88
-NULL   NULL    NULL    70      10040   88
-NULL   NULL    NULL    70      10040   88
-NULL   NULL    NULL    80      10040   66
-NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    80      10040   66
 NULL   NULL    NULL    NULL    10050   66
diff --git a/ql/src/test/results/clientpositive/llap/join_emit_interval.q.out 
b/ql/src/test/results/clientpositive/llap/join_emit_interval.q.out
index b4b320b..996a740 100644
--- a/ql/src/test/results/clientpositive/llap/join_emit_interval.q.out
+++ b/ql/src/test/results/clientpositive/llap/join_emit_interval.q.out
@@ -155,12 +155,12 @@ POSTHOOK: Input: default@test1_n7
 POSTHOOK: Input: default@test2_n4
 #### A masked pattern was here ####
 99     0       Alice   NULL    NULL    NULL
-100    1       Bob     NULL    NULL    NULL
 99     2       Mat     NULL    NULL    NULL
-101    2       Car     102     2       Del
-101    2       Car     103     2       Ema
+100    1       Bob     NULL    NULL    NULL
 NULL   NULL    None    NULL    NULL    NULL
 98     NULL    None    NULL    NULL    NULL
+101    2       Car     102     2       Del
+101    2       Car     103     2       Ema
 Warning: Shuffle Join MERGEJOIN[9][tables = [$hdt$_0, $hdt$_1]] in Stage 
'Reducer 2' is a cross product
 PREHOOK: query: EXPLAIN
 SELECT *
diff --git a/ql/src/test/results/clientpositive/llap/mapjoin2.q.out 
b/ql/src/test/results/clientpositive/llap/mapjoin2.q.out
index 4285ac1..814344f 100644
--- a/ql/src/test/results/clientpositive/llap/mapjoin2.q.out
+++ b/ql/src/test/results/clientpositive/llap/mapjoin2.q.out
@@ -337,8 +337,8 @@ POSTHOOK: query: select isnull(a.n), isnull(a.t), 
isnull(b.n), isnull(b.t) from
 POSTHOOK: type: QUERY
 POSTHOOK: Input: default@tbl_n1
 #### A masked pattern was here ####
-false  false   true    true
 true   true    false   false
+false  false   true    true
 Warning: Map Join MAPJOIN[9][bigTable=?] in task 'Map 1' is a cross product
 PREHOOK: query: explain
 select a.key, a.a_one, b.b_one, a.a_zero, b.b_zero from ( SELECT 11 key, 0 
confuse_you, 1 a_one, 0 a_zero ) a join ( SELECT 11 key, 0 confuse_you, 1 
b_one, 0 b_zero ) b on a.key = b.key
diff --git 
a/ql/src/test/results/clientpositive/llap/outer_join_unexpected_rows.q.out 
b/ql/src/test/results/clientpositive/llap/outer_join_unexpected_rows.q.out
new file mode 100644
index 0000000..4b1dbd7
--- /dev/null
+++ b/ql/src/test/results/clientpositive/llap/outer_join_unexpected_rows.q.out
@@ -0,0 +1,95 @@
+PREHOOK: query: with
+t_y as (select col1 as id,col2 as s from (VALUES(0,'a'),(1,'y')) as c),
+t_xy as (select col1 as id,col2 as s from (VALUES(1,'x'),(1,'y')) as c) 
+select * from t_xy l full outer join t_y r on (l.id=r.id and l.s='y')
+PREHOOK: type: QUERY
+PREHOOK: Input: _dummy_database@_dummy_table
+#### A masked pattern was here ####
+POSTHOOK: query: with
+t_y as (select col1 as id,col2 as s from (VALUES(0,'a'),(1,'y')) as c),
+t_xy as (select col1 as id,col2 as s from (VALUES(1,'x'),(1,'y')) as c) 
+select * from t_xy l full outer join t_y r on (l.id=r.id and l.s='y')
+POSTHOOK: type: QUERY
+POSTHOOK: Input: _dummy_database@_dummy_table
+#### A masked pattern was here ####
+1      x       NULL    NULL
+NULL   NULL    0       a
+1      y       1       y
+PREHOOK: query: create table t_y (id integer,s string)
+PREHOOK: type: CREATETABLE
+PREHOOK: Output: database:default
+PREHOOK: Output: default@t_y
+POSTHOOK: query: create table t_y (id integer,s string)
+POSTHOOK: type: CREATETABLE
+POSTHOOK: Output: database:default
+POSTHOOK: Output: default@t_y
+PREHOOK: query: create table t_xy (id integer,s string)
+PREHOOK: type: CREATETABLE
+PREHOOK: Output: database:default
+PREHOOK: Output: default@t_xy
+POSTHOOK: query: create table t_xy (id integer,s string)
+POSTHOOK: type: CREATETABLE
+POSTHOOK: Output: database:default
+POSTHOOK: Output: default@t_xy
+PREHOOK: query: insert into t_y values(0,'a'),(1,'y'),(1,'x')
+PREHOOK: type: QUERY
+PREHOOK: Input: _dummy_database@_dummy_table
+PREHOOK: Output: default@t_y
+POSTHOOK: query: insert into t_y values(0,'a'),(1,'y'),(1,'x')
+POSTHOOK: type: QUERY
+POSTHOOK: Input: _dummy_database@_dummy_table
+POSTHOOK: Output: default@t_y
+POSTHOOK: Lineage: t_y.id SCRIPT []
+POSTHOOK: Lineage: t_y.s SCRIPT []
+PREHOOK: query: insert into t_xy values(1,'x'),(1,'y')
+PREHOOK: type: QUERY
+PREHOOK: Input: _dummy_database@_dummy_table
+PREHOOK: Output: default@t_xy
+POSTHOOK: query: insert into t_xy values(1,'x'),(1,'y')
+POSTHOOK: type: QUERY
+POSTHOOK: Input: _dummy_database@_dummy_table
+POSTHOOK: Output: default@t_xy
+POSTHOOK: Lineage: t_xy.id SCRIPT []
+POSTHOOK: Lineage: t_xy.s SCRIPT []
+PREHOOK: query: select * from t_xy l full outer join t_y r on (l.id=r.id and 
l.s='y')
+PREHOOK: type: QUERY
+PREHOOK: Input: default@t_xy
+PREHOOK: Input: default@t_y
+#### A masked pattern was here ####
+POSTHOOK: query: select * from t_xy l full outer join t_y r on (l.id=r.id and 
l.s='y')
+POSTHOOK: type: QUERY
+POSTHOOK: Input: default@t_xy
+POSTHOOK: Input: default@t_y
+#### A masked pattern was here ####
+1      x       NULL    NULL
+NULL   NULL    0       a
+1      y       1       y
+1      y       1       x
+PREHOOK: query: select * from t_xy l full outer join t_y r on (l.id=r.id and 
l.s='y')
+PREHOOK: type: QUERY
+PREHOOK: Input: default@t_xy
+PREHOOK: Input: default@t_y
+#### A masked pattern was here ####
+POSTHOOK: query: select * from t_xy l full outer join t_y r on (l.id=r.id and 
l.s='y')
+POSTHOOK: type: QUERY
+POSTHOOK: Input: default@t_xy
+POSTHOOK: Input: default@t_y
+#### A masked pattern was here ####
+1      x       NULL    NULL
+NULL   NULL    0       a
+1      y       1       y
+1      y       1       x
+PREHOOK: query: select * from t_xy l full outer join t_y r on (l.id=r.id and 
l.s='y')
+PREHOOK: type: QUERY
+PREHOOK: Input: default@t_xy
+PREHOOK: Input: default@t_y
+#### A masked pattern was here ####
+POSTHOOK: query: select * from t_xy l full outer join t_y r on (l.id=r.id and 
l.s='y')
+POSTHOOK: type: QUERY
+POSTHOOK: Input: default@t_xy
+POSTHOOK: Input: default@t_y
+#### A masked pattern was here ####
+1      x       NULL    NULL
+NULL   NULL    0       a
+1      y       1       y
+1      y       1       x
diff --git 
a/ql/src/test/results/clientpositive/llap/vector_full_outer_join2.q.out 
b/ql/src/test/results/clientpositive/llap/vector_full_outer_join2.q.out
index b764fe5..ea54dd6 100644
--- a/ql/src/test/results/clientpositive/llap/vector_full_outer_join2.q.out
+++ b/ql/src/test/results/clientpositive/llap/vector_full_outer_join2.q.out
@@ -75,17 +75,17 @@ POSTHOOK: Input: default@t_letters
 POSTHOOK: Input: default@t_roman
 #### A masked pattern was here ####
 one            1       50      NULL    NULL    NULL
-NULL   NULL    NULL    I               1       50
 two            2       30      NULL    NULL    NULL
-NULL   NULL    NULL    II              2       30
 three          3       30      NULL    NULL    NULL
+NULL   NULL    NULL    I               1       50
+NULL   NULL    NULL    II              2       30
+NULL   NULL    NULL    IV              4       60
+NULL   NULL    NULL    V               5       70
+NULL   NULL    NULL    VI              6       80
 NULL   NULL    NULL    III             3       30
 four           4       60      NULL    NULL    NULL
-NULL   NULL    NULL    IV              4       60
 five           5       70      NULL    NULL    NULL
-NULL   NULL    NULL    V               5       70
 six            6       80      NULL    NULL    NULL
-NULL   NULL    NULL    VI              6       80
 PREHOOK: query: select x1.`z`, x1.`x`, x1.`y`,
        x2.`z`, x2.`x`, x2.`y`
 from t_letters x1 full outer join t_roman x2 on (x1.`x` > 2) and (x2.`x` < 4) 
and (x1.`x` = x2.`x`)
@@ -101,13 +101,13 @@ POSTHOOK: Input: default@t_letters
 POSTHOOK: Input: default@t_roman
 #### A masked pattern was here ####
 one            1       50      NULL    NULL    NULL
-NULL   NULL    NULL    I               1       50
 two            2       30      NULL    NULL    NULL
+NULL   NULL    NULL    I               1       50
 NULL   NULL    NULL    II              2       30
+NULL   NULL    NULL    IV              4       60
+NULL   NULL    NULL    V               5       70
+NULL   NULL    NULL    VI              6       80
 three          3       30      III             3       30
 four           4       60      NULL    NULL    NULL
-NULL   NULL    NULL    IV              4       60
 five           5       70      NULL    NULL    NULL
-NULL   NULL    NULL    V               5       70
 six            6       80      NULL    NULL    NULL
-NULL   NULL    NULL    VI              6       80

Reply via email to