[teiid-commits] teiid SVN: r2280 - in trunk/engine/src: test/java/org/teiid/query/optimizer and 1 other directory.

teiid-commits at lists.jboss.org teiid-commits at lists.jboss.org
Tue Jun 22 15:56:42 EDT 2010


Author: shawkins
Date: 2010-06-22 15:56:42 -0400 (Tue, 22 Jun 2010)
New Revision: 2280

Modified:
   trunk/engine/src/main/java/org/teiid/query/optimizer/relational/rules/RuleRaiseAccess.java
   trunk/engine/src/test/java/org/teiid/query/optimizer/TestJoinOptimization.java
   trunk/engine/src/test/java/org/teiid/query/optimizer/TestOptimizer.java
Log:
TEIID-1107 adding the ability to raise criteria if it's been pushed too far.

Modified: trunk/engine/src/main/java/org/teiid/query/optimizer/relational/rules/RuleRaiseAccess.java
===================================================================
--- trunk/engine/src/main/java/org/teiid/query/optimizer/relational/rules/RuleRaiseAccess.java	2010-06-22 19:24:56 UTC (rev 2279)
+++ trunk/engine/src/main/java/org/teiid/query/optimizer/relational/rules/RuleRaiseAccess.java	2010-06-22 19:56:42 UTC (rev 2280)
@@ -164,10 +164,66 @@
                 return performRaise(rootNode, accessNode, parentNode);
             case NodeConstants.Types.SELECT:            
             {
-                if (!parentNode.hasBooleanProperty(NodeConstants.Info.IS_DEPENDENT_SET) && canRaiseOverSelect(accessNode, metadata, capFinder, parentNode)) {
+            	if (parentNode.hasBooleanProperty(NodeConstants.Info.IS_DEPENDENT_SET)) {
+            		return null;
+            	}
+            	if (canRaiseOverSelect(accessNode, metadata, capFinder, parentNode)) {
                     RulePushSelectCriteria.satisfyAccessPatterns(parentNode, accessNode);
                     return performRaise(rootNode, accessNode, parentNode);                      
-                }
+            	}
+            	//determine if we should push the select back up
+            	if (parentNode.getParent() == null) {
+            		return null;
+            	}
+        		PlanNode selectRoot = parentNode;
+        		while (selectRoot.getParent() != null && selectRoot.getParent().getType() == NodeConstants.Types.SELECT) {
+        			selectRoot = selectRoot.getParent();
+        		}
+        		if (selectRoot.getParent() == null || selectRoot.getParent().getType() == NodeConstants.Types.PROJECT) {
+        			return null;
+        		}
+    			PlanNode grandParent = selectRoot.getParent();
+    			boolean isLeft = false;
+				isLeft = grandParent.getFirstChild() == selectRoot;
+				if (grandParent.getType() == NodeConstants.Types.JOIN) {
+					JoinType jt = (JoinType)grandParent.getProperty(NodeConstants.Info.JOIN_TYPE);
+					if (jt == JoinType.JOIN_FULL_OUTER || (jt == JoinType.JOIN_LEFT_OUTER && !isLeft)) {
+						return null;
+					}
+				}
+				grandParent.removeChild(selectRoot);
+				if (isLeft) {
+					grandParent.addFirstChild(accessNode);
+				} else {
+					grandParent.addLastChild(accessNode);
+				}
+    			PlanNode newParent = grandParent.getParent();
+				//TODO: use costing or heuristics instead of always raising
+    			PlanNode newRoot = raiseAccessNode(rootNode, accessNode, metadata, capFinder, afterJoinPlanning);
+    			if (newRoot == null) {
+					//return the tree to its original state
+    				parentNode.addFirstChild(accessNode);
+    				if (isLeft) {
+    					grandParent.addFirstChild(selectRoot);
+    				} else {
+    					grandParent.addLastChild(selectRoot);
+    				}
+    			} else {
+    				//attach the select nodes above the access node
+    				accessNode = grandParent.getParent();
+					if (newParent != null) {
+    					isLeft = newParent.getFirstChild() == accessNode;
+    					if (isLeft) {
+    						newParent.addFirstChild(selectRoot);
+    					} else {
+    						newParent.addLastChild(selectRoot);
+    					}
+    				} else {
+    					newRoot = selectRoot;
+    				}
+					parentNode.addFirstChild(accessNode);
+    				return newRoot;
+    			}
                 return null;
             }   
             case NodeConstants.Types.SOURCE:

Modified: trunk/engine/src/test/java/org/teiid/query/optimizer/TestJoinOptimization.java
===================================================================
--- trunk/engine/src/test/java/org/teiid/query/optimizer/TestJoinOptimization.java	2010-06-22 19:24:56 UTC (rev 2279)
+++ trunk/engine/src/test/java/org/teiid/query/optimizer/TestJoinOptimization.java	2010-06-22 19:56:42 UTC (rev 2280)
@@ -922,5 +922,84 @@
                 0       // UnionAll
     	});
     }
+    
+
+    /**
+     * Test for Case 836073: 
+     */
+    @Test public void testForCase836073_1() {
+        String sql = "select bqt1.smalla.intkey, bqt1.smallb.intkey from bqt1.smalla, bqt1.smallb WHERE formatdate(bqt1.smalla.DateValue,'yyyyMM') = '200309' AND bqt1.smalla.intkey = bqt1.smallb.intkey"; //$NON-NLS-1$
+             
+        // Plan query
+        ProcessorPlan plan = TestOptimizer.helpPlan(sql, FakeMetadataFactory.exampleBQTCached(), new String[] {"SELECT bqt1.smalla.DateValue, bqt1.smalla.intkey, bqt1.smallb.intkey FROM bqt1.smalla, bqt1.smallb WHERE bqt1.smalla.intkey = bqt1.smallb.intkey"}); //$NON-NLS-1$
+
+        TestOptimizer.checkNodeTypes(plan, new int[] {
+            1,      // Access
+            0,      // DependentAccess
+            0,      // DependentSelect
+            0,      // DependentProject
+            0,      // DupRemove
+            0,      // Grouping
+            0,      // Join
+            0,      // MergeJoin
+            0,      // Null
+            0,      // PlanExecution
+            1,      // Project
+            1,      // Select
+            0,      // Sort
+            0       // UnionAll
+        });
+    }
+    
+    @Test public void testForCase836073_2() {
+        String sql = "select bqt1.smalla.intkey, bqt1.smallb.intkey from bqt1.smalla left outer join bqt1.smallb on bqt1.smalla.intkey = bqt1.smallb.intkey WHERE formatdate(bqt1.smalla.DateValue,'yyyyMM') = '200309'"; //$NON-NLS-1$
         
+        // Plan query
+        ProcessorPlan plan = TestOptimizer.helpPlan(sql, FakeMetadataFactory.exampleBQTCached(), new String[] {"SELECT bqt1.smalla.DateValue, bqt1.smalla.intkey, bqt1.smallb.intkey FROM bqt1.smalla LEFT OUTER JOIN bqt1.smallb ON bqt1.smalla.intkey = bqt1.smallb.intkey"}); //$NON-NLS-1$ 
+
+        TestOptimizer.checkNodeTypes(plan, new int[] {
+            1,      // Access
+            0,      // DependentAccess
+            0,      // DependentSelect
+            0,      // DependentProject
+            0,      // DupRemove
+            0,      // Grouping
+            0,      // Join
+            0,      // MergeJoin
+            0,      // Null
+            0,      // PlanExecution
+            1,      // Project
+            1,      // Select
+            0,      // Sort
+            0       // UnionAll
+        });
+    }
+    
+    /**
+     * Note that we don't allow pushdown here because the criteria placement matters
+     */
+    @Test public void testForCase836073_3() {
+        String sql = "select bqt1.smalla.intkey, b.intkey from bqt1.smalla left outer join (select * from bqt1.smallb where formatdate(bqt1.smallb.DateValue,'yyyyMM') = '200309') b on bqt1.smalla.intkey = b.intkey"; //$NON-NLS-1$
+        
+        // Plan query
+        ProcessorPlan plan = TestOptimizer.helpPlan(sql, FakeMetadataFactory.exampleBQTCached(), new String[] {"SELECT g_0.intkey AS c_0 FROM bqt1.smalla AS g_0 ORDER BY c_0", "SELECT g_0.DateValue AS c_0, g_0.IntKey AS c_1 FROM bqt1.smallb AS g_0 ORDER BY c_1"}); //$NON-NLS-1$ //$NON-NLS-2$
+
+        TestOptimizer.checkNodeTypes(plan, new int[] {
+            2,      // Access
+            0,      // DependentAccess
+            0,      // DependentSelect
+            0,      // DependentProject
+            0,      // DupRemove
+            0,      // Grouping
+            0,      // Join
+            1,      // MergeJoin
+            0,      // Null
+            0,      // PlanExecution
+            1,      // Project
+            1,      // Select
+            0,      // Sort
+            0       // UnionAll
+        });
+    }
+        
 }

Modified: trunk/engine/src/test/java/org/teiid/query/optimizer/TestOptimizer.java
===================================================================
--- trunk/engine/src/test/java/org/teiid/query/optimizer/TestOptimizer.java	2010-06-22 19:24:56 UTC (rev 2279)
+++ trunk/engine/src/test/java/org/teiid/query/optimizer/TestOptimizer.java	2010-06-22 19:56:42 UTC (rev 2280)
@@ -4386,17 +4386,17 @@
             "SELECT BQT1.SmallA.IntKey FROM BQT1.SmallA, BQT1.SmallB WHERE (BQT1.SmallA.IntKey = lookup('BQT1.SmallB', 'IntKey', 'StringKey', BQT1.SmallB.StringKey)) AND (BQT1.SmallA.IntKey = 1)",  //$NON-NLS-1$
             metadata,
             null, capFinder,
-            new String[] {"SELECT BQT1.SmallA.IntKey FROM BQT1.SmallA WHERE BQT1.SmallA.IntKey = 1", "SELECT BQT1.SmallB.StringKey FROM BQT1.SmallB"}, //$NON-NLS-1$ //$NON-NLS-2$
+            new String[] {"SELECT g_1.StringKey, g_0.IntKey FROM BQT1.SmallA AS g_0, BQT1.SmallB AS g_1 WHERE g_0.IntKey = 1"}, //$NON-NLS-1$ //$NON-NLS-2$
             SHOULD_SUCCEED );
 
         checkNodeTypes(plan, new int[] {
-            2,      // Access
+            1,      // Access
             0,      // DependentAccess
             0,      // DependentSelect
             0,      // DependentProject
             0,      // DupRemove
             0,      // Grouping
-            1,      // NestedLoopJoinStrategy
+            0,      // NestedLoopJoinStrategy
             0,      // MergeJoinStrategy
             0,      // Null
             0,      // PlanExecution



More information about the teiid-commits mailing list