You are viewing a plain text version of this content. The canonical link for it is here.
Posted to notifications@shardingsphere.apache.org by tu...@apache.org on 2022/12/09 03:18:07 UTC

[shardingsphere] branch master updated: Fix wrong decide result when execute same sharding condition subquery with sql federation (#22754)

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

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


The following commit(s) were added to refs/heads/master by this push:
     new 631fdf40f87 Fix wrong decide result when execute same sharding condition subquery with sql federation (#22754)
631fdf40f87 is described below

commit 631fdf40f87223e176abe5c851a51b3287b4d6de
Author: Zhengqiang Duan <du...@apache.org>
AuthorDate: Fri Dec 9 11:17:52 2022 +0800

    Fix wrong decide result when execute same sharding condition subquery with sql federation (#22754)
    
    * Fix wrong decide result when execute same sharding condition subquery with sql federation
    
    * Fix wrong decide result when execute same sharding condition subquery with sql federation
---
 .../decider/ShardingSQLFederationDecider.java      | 10 ++++--
 .../decider/ShardingSQLFederationDeciderTest.java  | 37 ++++++++++++++++++++--
 2 files changed, 41 insertions(+), 6 deletions(-)

diff --git a/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/decider/ShardingSQLFederationDecider.java b/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/decider/ShardingSQLFederationDecider.java
index 3c1984d34c4..101082c60e7 100644
--- a/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/decider/ShardingSQLFederationDecider.java
+++ b/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/decider/ShardingSQLFederationDecider.java
@@ -47,7 +47,7 @@ public final class ShardingSQLFederationDecider implements SQLFederationDecider<
             return;
         }
         addTableDataNodes(deciderContext, rule, tableNames);
-        ShardingConditions shardingConditions = createShardingConditions(queryContext, database, rule);
+        ShardingConditions shardingConditions = getMergedShardingConditions(queryContext, database, rule);
         if (shardingConditions.isNeedMerge() && shardingConditions.isSameShardingCondition()) {
             return;
         }
@@ -69,10 +69,14 @@ public final class ShardingSQLFederationDecider implements SQLFederationDecider<
     }
     
     @SuppressWarnings({"unchecked", "rawtypes"})
-    private static ShardingConditions createShardingConditions(final QueryContext queryContext, final ShardingSphereDatabase database, final ShardingRule rule) {
+    private static ShardingConditions getMergedShardingConditions(final QueryContext queryContext, final ShardingSphereDatabase database, final ShardingRule rule) {
         ShardingConditionEngine shardingConditionEngine = ShardingConditionEngineFactory.createShardingConditionEngine(queryContext, database, rule);
         List<ShardingCondition> shardingConditions = shardingConditionEngine.createShardingConditions(queryContext.getSqlStatementContext(), queryContext.getParameters());
-        return new ShardingConditions(shardingConditions, queryContext.getSqlStatementContext(), rule);
+        ShardingConditions result = new ShardingConditions(shardingConditions, queryContext.getSqlStatementContext(), rule);
+        if (result.isNeedMerge()) {
+            result.merge();
+        }
+        return result;
     }
     
     @Override
diff --git a/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/decider/ShardingSQLFederationDeciderTest.java b/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/decider/ShardingSQLFederationDeciderTest.java
index 5931abf6613..76f8d504185 100644
--- a/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/decider/ShardingSQLFederationDeciderTest.java
+++ b/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/decider/ShardingSQLFederationDeciderTest.java
@@ -25,12 +25,20 @@ import org.apache.shardingsphere.infra.database.DefaultDatabase;
 import org.apache.shardingsphere.infra.database.type.dialect.PostgreSQLDatabaseType;
 import org.apache.shardingsphere.infra.datanode.DataNode;
 import org.apache.shardingsphere.infra.metadata.database.ShardingSphereDatabase;
+import org.apache.shardingsphere.sharding.route.engine.condition.ShardingCondition;
+import org.apache.shardingsphere.sharding.route.engine.condition.engine.ShardingConditionEngineFactory;
+import org.apache.shardingsphere.sharding.route.engine.condition.engine.impl.WhereClauseShardingConditionEngine;
+import org.apache.shardingsphere.sharding.route.engine.condition.value.ListShardingConditionValue;
+import org.apache.shardingsphere.sharding.rule.BindingTableRule;
 import org.apache.shardingsphere.sharding.rule.ShardingRule;
 import org.apache.shardingsphere.sharding.rule.TableRule;
 import org.junit.Test;
+import org.mockito.MockedStatic;
 
+import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collections;
+import java.util.List;
 import java.util.Optional;
 import java.util.Properties;
 
@@ -38,8 +46,10 @@ import static org.hamcrest.MatcherAssert.assertThat;
 import static org.hamcrest.Matchers.is;
 import static org.junit.Assert.assertFalse;
 import static org.junit.Assert.assertTrue;
+import static org.mockito.ArgumentMatchers.any;
 import static org.mockito.Mockito.RETURNS_DEEP_STUBS;
 import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.mockStatic;
 import static org.mockito.Mockito.when;
 
 public final class ShardingSQLFederationDeciderTest {
@@ -58,17 +68,33 @@ public final class ShardingSQLFederationDeciderTest {
     }
     
     @Test
-    public void assertDecideWhenContainsPagination() {
+    public void assertDecideWhenContainsSameShardingCondition() {
         SelectStatementContext select = createStatementContext();
-        when(select.getPaginationContext().isHasPagination()).thenReturn(true);
+        when(select.isContainsSubquery()).thenReturn(true);
         QueryContext queryContext = new QueryContext(select, "", Collections.emptyList());
         SQLFederationDeciderContext actual = new SQLFederationDeciderContext();
         ShardingSQLFederationDecider federationDecider = new ShardingSQLFederationDecider();
-        federationDecider.decide(actual, queryContext, createDatabase(), createShardingRule(), new ConfigurationProperties(new Properties()));
+        try (MockedStatic<ShardingConditionEngineFactory> shardingConditionEngineFactory = mockStatic(ShardingConditionEngineFactory.class)) {
+            WhereClauseShardingConditionEngine shardingConditionEngine = mock(WhereClauseShardingConditionEngine.class);
+            when(shardingConditionEngine.createShardingConditions(any(), any())).thenReturn(createShardingConditions());
+            shardingConditionEngineFactory.when(() -> ShardingConditionEngineFactory.createShardingConditionEngine(any(QueryContext.class), any(), any())).thenReturn(shardingConditionEngine);
+            federationDecider.decide(actual, queryContext, createDatabase(), createShardingRule(), new ConfigurationProperties(new Properties()));
+        }
         assertThat(actual.getDataNodes().size(), is(4));
         assertFalse(actual.isUseSQLFederation());
     }
     
+    private List<ShardingCondition> createShardingConditions() {
+        List<ShardingCondition> result = new ArrayList<>();
+        ShardingCondition shardingCondition1 = new ShardingCondition();
+        shardingCondition1.getValues().add(new ListShardingConditionValue<>("order_id", "t_order", Collections.singletonList(1)));
+        result.add(shardingCondition1);
+        ShardingCondition shardingCondition2 = new ShardingCondition();
+        shardingCondition2.getValues().add(new ListShardingConditionValue<>("order_id", "t_order_item", Collections.singletonList(1)));
+        result.add(shardingCondition2);
+        return result;
+    }
+    
     @Test
     public void assertDecideWhenContainsSubquery() {
         SelectStatementContext select = createStatementContext();
@@ -198,6 +224,11 @@ public final class ShardingSQLFederationDeciderTest {
                 new DataNode("ds_0", "t_order"), new DataNode("ds_1", "t_order"),
                 new DataNode("ds_0", "t_order_item"), new DataNode("ds_1", "t_order_item")));
         when(result.findTableRule("t_order")).thenReturn(Optional.of(tableRule));
+        BindingTableRule bindingTableRule = mock(BindingTableRule.class);
+        when(bindingTableRule.hasLogicTable("t_order")).thenReturn(true);
+        when(bindingTableRule.hasLogicTable("t_order_item")).thenReturn(true);
+        when(result.findBindingTableRule("t_order")).thenReturn(Optional.of(bindingTableRule));
+        when(result.findBindingTableRule("t_order_item")).thenReturn(Optional.of(bindingTableRule));
         return result;
     }
 }