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

panjuan 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 a38e7e2  For #11013, drop resource can ignore single tables. (#12837)
a38e7e2 is described below

commit a38e7e2b149933958dc2d00253ef6174cf0fcd49
Author: Raigor <[email protected]>
AuthorDate: Thu Sep 30 12:35:17 2021 +0800

    For #11013, drop resource can ignore single tables. (#12837)
---
 .../src/main/antlr4/imports/Keyword.g4             | 12 ++++++
 .../src/main/antlr4/imports/RDLStatement.g4        |  6 ++-
 .../core/common/CommonDistSQLStatementVisitor.java |  3 +-
 .../statement/rdl/drop/DropResourceStatement.java  |  2 +
 .../rdl/resource/DropResourceBackendHandler.java   | 27 ++++++++++---
 .../resource/DropResourceBackendHandlerTest.java   | 47 +++++++++++++++++++++-
 .../rdl/drop/DropResourceStatementAssert.java      |  1 +
 .../rdl/drop/DropResourceStatementTestCase.java    |  3 ++
 .../src/main/resources/case/rdl/drop.xml           |  7 ++++
 .../src/main/resources/sql/supported/rdl/drop.xml  |  1 +
 10 files changed, 100 insertions(+), 9 deletions(-)

diff --git 
a/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/antlr4/imports/Keyword.g4
 
b/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/antlr4/imports/Keyword.g4
index ab033ce..eca6f46 100644
--- 
a/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/antlr4/imports/Keyword.g4
+++ 
b/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/antlr4/imports/Keyword.g4
@@ -114,3 +114,15 @@ INSTANCE
 IP
     : I P
     ;
+
+IGNORE
+    : I G N O R E
+    ;
+
+SINGLE
+    : S I N G L E
+    ;
+
+TABLES
+    : T A B L E S
+    ;
diff --git 
a/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/antlr4/imports/RDLStatement.g4
 
b/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/antlr4/imports/RDLStatement.g4
index 7104bcf..a8e5dac 100644
--- 
a/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/antlr4/imports/RDLStatement.g4
+++ 
b/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/antlr4/imports/RDLStatement.g4
@@ -28,7 +28,7 @@ alterResource
     ;
 
 dropResource
-    : DROP RESOURCE IDENTIFIER (COMMA IDENTIFIER)*
+    : DROP RESOURCE IDENTIFIER (COMMA IDENTIFIER)* ignoreSingleTables?
     ;
 
 dataSource
@@ -86,3 +86,7 @@ poolProperties
 poolProperty
     : key=(IDENTIFIER | STRING) EQ value=(INT | IDENTIFIER | STRING)
     ;
+
+ignoreSingleTables
+    : IGNORE SINGLE TABLES
+    ;
diff --git 
a/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/java/org/apache/shardingsphere/distsql/parser/core/common/CommonDistSQLStatementVisitor.java
 
b/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/java/org/apache/shardingsphere/distsql/parser/core/common/CommonDistSQLStatementVisitor.java
index 8a82fb4..656faa4 100644
--- 
a/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/java/org/apache/shardingsphere/distsql/parser/core/common/CommonDistSQLStatementVisitor.java
+++ 
b/shardingsphere-distsql-parser/shardingsphere-distsql-parser-engine/src/main/java/org/apache/shardingsphere/distsql/parser/core/common/CommonDistSQLStatementVisitor.java
@@ -109,7 +109,8 @@ public final class CommonDistSQLStatementVisitor extends 
CommonDistSQLStatementB
     
     @Override
     public ASTNode visitDropResource(final DropResourceContext ctx) {
-        return new 
DropResourceStatement(ctx.IDENTIFIER().stream().map(ParseTree::getText).collect(Collectors.toList()));
+        boolean ignoreSingleTables = null != ctx.ignoreSingleTables();
+        return new 
DropResourceStatement(ctx.IDENTIFIER().stream().map(ParseTree::getText).collect(Collectors.toList()),
 ignoreSingleTables);
     }
     
     @Override
diff --git 
a/shardingsphere-distsql-parser/shardingsphere-distsql-parser-statement/src/main/java/org/apache/shardingsphere/distsql/parser/statement/rdl/drop/DropResourceStatement.java
 
b/shardingsphere-distsql-parser/shardingsphere-distsql-parser-statement/src/main/java/org/apache/shardingsphere/distsql/parser/statement/rdl/drop/DropResourceStatement.java
index 1e87582..e595829 100644
--- 
a/shardingsphere-distsql-parser/shardingsphere-distsql-parser-statement/src/main/java/org/apache/shardingsphere/distsql/parser/statement/rdl/drop/DropResourceStatement.java
+++ 
b/shardingsphere-distsql-parser/shardingsphere-distsql-parser-statement/src/main/java/org/apache/shardingsphere/distsql/parser/statement/rdl/drop/DropResourceStatement.java
@@ -31,4 +31,6 @@ import java.util.Collection;
 public final class DropResourceStatement extends ResourceDefinitionStatement {
     
     private final Collection<String> names;
+    
+    private final boolean ignoreSingleTables;
 }
diff --git 
a/shardingsphere-proxy/shardingsphere-proxy-backend/src/main/java/org/apache/shardingsphere/proxy/backend/text/distsql/rdl/resource/DropResourceBackendHandler.java
 
b/shardingsphere-proxy/shardingsphere-proxy-backend/src/main/java/org/apache/shardingsphere/proxy/backend/text/distsql/rdl/resource/DropResourceBackendHandler.java
index 2a6af01..bcd7934 100644
--- 
a/shardingsphere-proxy/shardingsphere-proxy-backend/src/main/java/org/apache/shardingsphere/proxy/backend/text/distsql/rdl/resource/DropResourceBackendHandler.java
+++ 
b/shardingsphere-proxy/shardingsphere-proxy-backend/src/main/java/org/apache/shardingsphere/proxy/backend/text/distsql/rdl/resource/DropResourceBackendHandler.java
@@ -32,6 +32,7 @@ import 
org.apache.shardingsphere.proxy.backend.context.ProxyContext;
 import org.apache.shardingsphere.proxy.backend.response.header.ResponseHeader;
 import 
org.apache.shardingsphere.proxy.backend.response.header.update.UpdateResponseHeader;
 import 
org.apache.shardingsphere.proxy.backend.text.SchemaRequiredBackendHandler;
+import org.apache.shardingsphere.singletable.rule.SingleTableRule;
 
 import javax.sql.DataSource;
 import java.util.Collection;
@@ -52,7 +53,7 @@ public final class DropResourceBackendHandler extends 
SchemaRequiredBackendHandl
     @Override
     public ResponseHeader execute(final String schemaName, final 
DropResourceStatement sqlStatement) throws ResourceDefinitionViolationException 
{
         Collection<String> toBeDroppedResourceNames = sqlStatement.getNames();
-        check(schemaName, toBeDroppedResourceNames);
+        check(schemaName, toBeDroppedResourceNames, 
sqlStatement.isIgnoreSingleTables());
         drop(schemaName, toBeDroppedResourceNames);
         // TODO update meta data context in memory
         
ProxyContext.getInstance().getContextManager().getMetaDataContexts().getMetaDataPersistService().ifPresent(
@@ -60,9 +61,9 @@ public final class DropResourceBackendHandler extends 
SchemaRequiredBackendHandl
         return new UpdateResponseHeader(sqlStatement);
     }
     
-    private void check(final String schemaName, final Collection<String> 
toBeDroppedResourceNames) throws RequiredResourceMissedException, 
ResourceInUsedException {
+    private void check(final String schemaName, final Collection<String> 
toBeDroppedResourceNames, final boolean ignoreSingleTables) throws 
RequiredResourceMissedException, ResourceInUsedException {
         checkResourceNameExisted(schemaName, toBeDroppedResourceNames);
-        checkResourceNameNotInUse(schemaName, toBeDroppedResourceNames);
+        checkResourceNameNotInUse(schemaName, toBeDroppedResourceNames, 
ignoreSingleTables);
     }
     
     private void checkResourceNameExisted(final String schemaName, final 
Collection<String> resourceNames) throws RequiredResourceMissedException {
@@ -73,13 +74,27 @@ public final class DropResourceBackendHandler extends 
SchemaRequiredBackendHandl
         }
     }
     
-    private void checkResourceNameNotInUse(final String schemaName, final 
Collection<String> toBeDroppedResourceNames) throws ResourceInUsedException {
+    private void checkResourceNameNotInUse(final String schemaName, final 
Collection<String> toBeDroppedResourceNames, final boolean ignoreSingleTables) 
throws ResourceInUsedException {
         Multimap<String, String> inUsedMultimap = 
getInUsedResources(schemaName);
         Collection<String> inUsedResourceNames = inUsedMultimap.keySet();
         inUsedResourceNames.retainAll(toBeDroppedResourceNames);
         if (!inUsedResourceNames.isEmpty()) {
-            String firstResource = inUsedResourceNames.iterator().next();
-            throw new ResourceInUsedException(firstResource, 
inUsedMultimap.get(firstResource));
+            if (ignoreSingleTables) {
+                checkResourceNameNotInUseIgnoreSingleTableRule(new 
HashSet<>(inUsedResourceNames), inUsedMultimap);
+            } else {
+                String firstResource = inUsedResourceNames.iterator().next();
+                throw new ResourceInUsedException(firstResource, 
inUsedMultimap.get(firstResource));
+            }
+        }
+    }
+    
+    private void checkResourceNameNotInUseIgnoreSingleTableRule(final 
Collection<String> inUsedResourceNames, final Multimap<String, String> 
inUsedMultimap) throws ResourceInUsedException {
+        for (String each : inUsedResourceNames) {
+            Collection<String> inUsedRules = inUsedMultimap.get(each);
+            inUsedRules.remove(SingleTableRule.class.getSimpleName());
+            if (!inUsedRules.isEmpty()) {
+                throw new ResourceInUsedException(each, inUsedRules);
+            }
         }
     }
     
diff --git 
a/shardingsphere-proxy/shardingsphere-proxy-backend/src/test/java/org/apache/shardingsphere/proxy/backend/text/distsql/rdl/resource/DropResourceBackendHandlerTest.java
 
b/shardingsphere-proxy/shardingsphere-proxy-backend/src/test/java/org/apache/shardingsphere/proxy/backend/text/distsql/rdl/resource/DropResourceBackendHandlerTest.java
index 7633388..bb986cb 100644
--- 
a/shardingsphere-proxy/shardingsphere-proxy-backend/src/test/java/org/apache/shardingsphere/proxy/backend/text/distsql/rdl/resource/DropResourceBackendHandlerTest.java
+++ 
b/shardingsphere-proxy/shardingsphere-proxy-backend/src/test/java/org/apache/shardingsphere/proxy/backend/text/distsql/rdl/resource/DropResourceBackendHandlerTest.java
@@ -18,6 +18,8 @@
 package org.apache.shardingsphere.proxy.backend.text.distsql.rdl.resource;
 
 import 
org.apache.shardingsphere.distsql.parser.statement.rdl.drop.DropResourceStatement;
+import org.apache.shardingsphere.infra.datanode.DataNode;
+import 
org.apache.shardingsphere.infra.distsql.exception.resource.ResourceDefinitionViolationException;
 import org.apache.shardingsphere.mode.manager.ContextManager;
 import org.apache.shardingsphere.mode.metadata.MetaDataContexts;
 import org.apache.shardingsphere.infra.distsql.exception.DistSQLException;
@@ -29,6 +31,7 @@ import 
org.apache.shardingsphere.proxy.backend.context.ProxyContext;
 import org.apache.shardingsphere.proxy.backend.response.header.ResponseHeader;
 import 
org.apache.shardingsphere.proxy.backend.response.header.update.UpdateResponseHeader;
 import org.apache.shardingsphere.shadow.rule.ShadowRule;
+import org.apache.shardingsphere.singletable.rule.SingleTableRule;
 import org.junit.Before;
 import org.junit.Test;
 import org.junit.runner.RunWith;
@@ -39,6 +42,7 @@ import javax.sql.DataSource;
 import java.sql.SQLException;
 import java.util.Collections;
 import java.util.HashMap;
+import java.util.LinkedHashMap;
 import java.util.Map;
 
 import static org.hamcrest.CoreMatchers.is;
@@ -73,6 +77,9 @@ public final class DropResourceBackendHandlerTest {
     @Mock
     private ShadowRule shadowRule;
     
+    @Mock
+    private SingleTableRule singleTableRule;
+    
     private DropResourceBackendHandler dropResourceBackendHandler;
     
     @Before
@@ -121,7 +128,45 @@ public final class DropResourceBackendHandlerTest {
         }
     }
     
+    @Test
+    public void assertResourceNameInUseWithoutIgnoreSingleTables() {
+        
when(ruleMetaData.getRules()).thenReturn(Collections.singleton(singleTableRule));
+        when(singleTableRule.getType()).thenReturn("SingleTableRule");
+        DataNode dataNode = mock(DataNode.class);
+        when(dataNode.getDataSourceName()).thenReturn("test0");
+        
when(singleTableRule.getAllDataNodes()).thenReturn(Collections.singletonMap("", 
Collections.singleton(dataNode)));
+        
when(resource.getDataSources()).thenReturn(Collections.singletonMap("test0", 
dataSource));
+        try {
+            dropResourceBackendHandler.execute("test", 
createDropResourceStatement());
+        } catch (final SQLException ex) {
+            assertThat(ex.getMessage(), is("Resource [test0] is still used by 
[SingleTableRule]."));
+        }
+    }
+    
+    @Test
+    public void assertResourceNameInUseIgnoreSingleTables() throws 
ResourceDefinitionViolationException {
+        
when(ruleMetaData.getRules()).thenReturn(Collections.singleton(singleTableRule));
+        when(singleTableRule.getType()).thenReturn("SingleTableRule");
+        DataNode dataNode = mock(DataNode.class);
+        when(dataNode.getDataSourceName()).thenReturn("test0");
+        
when(singleTableRule.getAllDataNodes()).thenReturn(Collections.singletonMap("", 
Collections.singleton(dataNode)));
+        
when(resource.getDataSources()).thenReturn(getDataSourceMapForSupportRemove());
+        ResponseHeader responseHeader = 
dropResourceBackendHandler.execute("test", 
createDropResourceStatementIgnoreSingleTables());
+        assertTrue(responseHeader instanceof UpdateResponseHeader);
+        assertNull(resource.getDataSources().get("test0"));
+    }
+    
+    private Map<String, DataSource> getDataSourceMapForSupportRemove() {
+        Map<String, DataSource> result = new LinkedHashMap<>();
+        result.put("test0", dataSource);
+        return result;
+    }
+    
     private DropResourceStatement createDropResourceStatement() {
-        return new DropResourceStatement(Collections.singleton("test0"));
+        return new DropResourceStatement(Collections.singleton("test0"), 
false);
+    }
+    
+    private DropResourceStatement 
createDropResourceStatementIgnoreSingleTables() {
+        return new DropResourceStatement(Collections.singleton("test0"), true);
     }
 }
diff --git 
a/shardingsphere-test/shardingsphere-parser-test/src/main/java/org/apache/shardingsphere/test/sql/parser/parameterized/asserts/statement/distsql/rdl/drop/DropResourceStatementAssert.java
 
b/shardingsphere-test/shardingsphere-parser-test/src/main/java/org/apache/shardingsphere/test/sql/parser/parameterized/asserts/statement/distsql/rdl/drop/DropResourceStatementAssert.java
index ef8e169..47f21a9 100644
--- 
a/shardingsphere-test/shardingsphere-parser-test/src/main/java/org/apache/shardingsphere/test/sql/parser/parameterized/asserts/statement/distsql/rdl/drop/DropResourceStatementAssert.java
+++ 
b/shardingsphere-test/shardingsphere-parser-test/src/main/java/org/apache/shardingsphere/test/sql/parser/parameterized/asserts/statement/distsql/rdl/drop/DropResourceStatementAssert.java
@@ -45,6 +45,7 @@ public final class DropResourceStatementAssert {
             assertNull(assertContext.getText("Actual resource should not 
exist."), actual);
         } else {
             assertThat(assertContext.getText("resource assertion error: "), 
actual.getNames(), is(expected.getDataSources()));
+            assertThat(assertContext.getText("resource assertion error: "), 
actual.isIgnoreSingleTables(), 
is(expected.getIgnoreSingleTables().iterator().next()));
         }
     }
 }
diff --git 
a/shardingsphere-test/shardingsphere-parser-test/src/main/java/org/apache/shardingsphere/test/sql/parser/parameterized/jaxb/cases/domain/statement/distsql/rdl/drop/DropResourceStatementTestCase.java
 
b/shardingsphere-test/shardingsphere-parser-test/src/main/java/org/apache/shardingsphere/test/sql/parser/parameterized/jaxb/cases/domain/statement/distsql/rdl/drop/DropResourceStatementTestCase.java
index ef623ea..ae0c3b8 100644
--- 
a/shardingsphere-test/shardingsphere-parser-test/src/main/java/org/apache/shardingsphere/test/sql/parser/parameterized/jaxb/cases/domain/statement/distsql/rdl/drop/DropResourceStatementTestCase.java
+++ 
b/shardingsphere-test/shardingsphere-parser-test/src/main/java/org/apache/shardingsphere/test/sql/parser/parameterized/jaxb/cases/domain/statement/distsql/rdl/drop/DropResourceStatementTestCase.java
@@ -34,4 +34,7 @@ public final class DropResourceStatementTestCase extends 
SQLParserTestCase {
     
     @XmlElement(name = "data-source")
     private final List<String> dataSources = new LinkedList<>();
+    
+    @XmlElement(name = "ignore-single-tables")
+    private final List<Boolean> ignoreSingleTables = new LinkedList<>();
 }
diff --git 
a/shardingsphere-test/shardingsphere-parser-test/src/main/resources/case/rdl/drop.xml
 
b/shardingsphere-test/shardingsphere-parser-test/src/main/resources/case/rdl/drop.xml
index ed0c03c..af16286 100644
--- 
a/shardingsphere-test/shardingsphere-parser-test/src/main/resources/case/rdl/drop.xml
+++ 
b/shardingsphere-test/shardingsphere-parser-test/src/main/resources/case/rdl/drop.xml
@@ -20,6 +20,13 @@
     <drop-resource sql-case-id="drop-resource">
         <data-source>ds_0</data-source>
         <data-source>ds_1</data-source>
+        <ignore-single-tables>false</ignore-single-tables>
+    </drop-resource>
+
+    <drop-resource sql-case-id="drop-resource-ignore-single-tables">
+        <data-source>ds_0</data-source>
+        <data-source>ds_1</data-source>
+        <ignore-single-tables>true</ignore-single-tables>
     </drop-resource>
     
     <drop-sharding-table-rule sql-case-id="drop-sharding-table-rule" />
diff --git 
a/shardingsphere-test/shardingsphere-parser-test/src/main/resources/sql/supported/rdl/drop.xml
 
b/shardingsphere-test/shardingsphere-parser-test/src/main/resources/sql/supported/rdl/drop.xml
index fcf730e..9705923 100644
--- 
a/shardingsphere-test/shardingsphere-parser-test/src/main/resources/sql/supported/rdl/drop.xml
+++ 
b/shardingsphere-test/shardingsphere-parser-test/src/main/resources/sql/supported/rdl/drop.xml
@@ -18,6 +18,7 @@
 
 <sql-cases>
     <distsql-case id="drop-resource" value="DROP RESOURCE ds_0,ds_1" />
+    <distsql-case id="drop-resource-ignore-single-tables" value="DROP RESOURCE 
ds_0,ds_1 ignore single tables;" />
     <distsql-case id="drop-sharding-table-rule" value="DROP SHARDING TABLE 
RULE t_order,t_order_item" />
     <distsql-case id="drop-sharding-binding-table-rules" value="DROP SHARDING 
BINDING TABLE RULES" />
     <distsql-case id="drop-sharding-broadcast-table-rules" value="DROP 
SHARDING BROADCAST TABLE RULES" />

Reply via email to