From 78b89b68d9f2b3ba1fe3cb9b03d4260062af66de Mon Sep 17 00:00:00 2001 From: Liang Zhang Date: Fri, 5 Apr 2024 01:31:08 +0800 Subject: [PATCH] Remove AuditSQLException (#30777) * Refactor CDCChannelInboundHandler * Rename DMLWithoutShardingKeyException * Remove AuditSQLException * Remove AuditSQLException --- .../error-code/sql-error-code.cn.md | 2 +- .../error-code/sql-error-code.en.md | 1 + ...rdingConditionsShardingAuditAlgorithm.java | 4 +- .../audit/DMLWithoutShardingKeyException.java | 13 +++--- ...gConditionsShardingAuditAlgorithmTest.java | 4 +- .../auditor/ShardingSQLAuditorTest.java | 8 ++-- .../syntax/audit/AuditSQLException.java | 41 ------------------- .../cdc/exception/CDCExceptionWrapper.java | 9 ++-- .../netty/CDCChannelInboundHandler.java | 17 ++++---- 9 files changed, 31 insertions(+), 68 deletions(-) rename infra/common/src/main/java/org/apache/shardingsphere/infra/exception/syntax/audit/SQLAuditException.java => features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/exception/audit/DMLWithoutShardingKeyException.java (65%) delete mode 100644 infra/common/src/main/java/org/apache/shardingsphere/infra/exception/syntax/audit/AuditSQLException.java diff --git a/docs/document/content/user-manual/error-code/sql-error-code.cn.md b/docs/document/content/user-manual/error-code/sql-error-code.cn.md index 1aee36579f9b3..83e3d2dced5ee 100644 --- a/docs/document/content/user-manual/error-code/sql-error-code.cn.md +++ b/docs/document/content/user-manual/error-code/sql-error-code.cn.md @@ -65,7 +65,6 @@ SQL 错误码以标准的 SQL State,Vendor Code 和详细错误信息提供, | 12100 | 42000 | You have an error in your SQL syntax: %s | | 12101 | 42000 | Can not accept SQL type '%s'. | | 12200 | 42000 | Hint data source '%s' does not exist. | -| 12201 | 42000 | SQL audit failed, error message: %s. | ### 连接 @@ -187,6 +186,7 @@ SQL 错误码以标准的 SQL State,Vendor Code 和详细错误信息提供, | 20086 | 44000 | Some routed data sources do not belong to configured data sources. routed data sources: \`%s\`, configured data sources: \`%s\`. | | 20087 | 44000 | Please check your sharding conditions \`%s\` to avoid same record in table \`%s\` routing to multiple data nodes. | | 20088 | 44000 | Cannot found routing table factor, data source: %s, actual table: %s. | +| 20090 | 42000 | Not allow DML operation without sharding conditions. | ### 读写分离 diff --git a/docs/document/content/user-manual/error-code/sql-error-code.en.md b/docs/document/content/user-manual/error-code/sql-error-code.en.md index 1a6cbc6a42b30..66933f65737ae 100644 --- a/docs/document/content/user-manual/error-code/sql-error-code.en.md +++ b/docs/document/content/user-manual/error-code/sql-error-code.en.md @@ -187,6 +187,7 @@ SQL error codes provide by standard `SQL State`, `Vendor Code` and `Reason`, whi | 20086 | 44000 | Some routed data sources do not belong to configured data sources. routed data sources: \`%s\`, configured data sources: \`%s\`. | | 20087 | 44000 | Please check your sharding conditions \`%s\` to avoid same record in table \`%s\` routing to multiple data nodes. | | 20088 | 44000 | Cannot found routing table factor, data source: %s, actual table: %s. | +| 20090 | 42000 | Not allow DML operation without sharding conditions. | ### Readwrite-splitting diff --git a/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/algorithm/audit/DMLShardingConditionsShardingAuditAlgorithm.java b/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/algorithm/audit/DMLShardingConditionsShardingAuditAlgorithm.java index 17406a6f6d347..e35d11bb651fd 100644 --- a/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/algorithm/audit/DMLShardingConditionsShardingAuditAlgorithm.java +++ b/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/algorithm/audit/DMLShardingConditionsShardingAuditAlgorithm.java @@ -18,11 +18,11 @@ package org.apache.shardingsphere.sharding.algorithm.audit; import org.apache.shardingsphere.infra.binder.context.statement.SQLStatementContext; -import org.apache.shardingsphere.infra.exception.syntax.audit.SQLAuditException; import org.apache.shardingsphere.infra.metadata.database.ShardingSphereDatabase; import org.apache.shardingsphere.infra.metadata.database.rule.RuleMetaData; import org.apache.shardingsphere.infra.metadata.user.Grantee; import org.apache.shardingsphere.infra.exception.core.ShardingSpherePreconditions; +import org.apache.shardingsphere.sharding.exception.audit.DMLWithoutShardingKeyException; import org.apache.shardingsphere.sharding.route.engine.condition.engine.ShardingConditionEngine; import org.apache.shardingsphere.sharding.rule.ShardingRule; import org.apache.shardingsphere.sharding.spi.ShardingAuditAlgorithm; @@ -42,7 +42,7 @@ public void check(final SQLStatementContext sqlStatementContext, final List new SQLAuditException("Not allow DML operation without sharding conditions")); + DMLWithoutShardingKeyException::new); } } } diff --git a/infra/common/src/main/java/org/apache/shardingsphere/infra/exception/syntax/audit/SQLAuditException.java b/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/exception/audit/DMLWithoutShardingKeyException.java similarity index 65% rename from infra/common/src/main/java/org/apache/shardingsphere/infra/exception/syntax/audit/SQLAuditException.java rename to features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/exception/audit/DMLWithoutShardingKeyException.java index 57a444a4ed32f..ae439b239b395 100644 --- a/infra/common/src/main/java/org/apache/shardingsphere/infra/exception/syntax/audit/SQLAuditException.java +++ b/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/exception/audit/DMLWithoutShardingKeyException.java @@ -15,18 +15,19 @@ * limitations under the License. */ -package org.apache.shardingsphere.infra.exception.syntax.audit; +package org.apache.shardingsphere.sharding.exception.audit; import org.apache.shardingsphere.infra.exception.core.external.sql.sqlstate.XOpenSQLState; +import org.apache.shardingsphere.sharding.exception.ShardingSQLException; /** - * SQL audit exception. + * DML without sharding key exception. */ -public final class SQLAuditException extends AuditSQLException { +public final class DMLWithoutShardingKeyException extends ShardingSQLException { - private static final long serialVersionUID = 4183020614721058122L; + private static final long serialVersionUID = -2856743119521264343L; - public SQLAuditException(final String errorMessage) { - super(XOpenSQLState.SYNTAX_ERROR, 1, "SQL audit failed, error message: %s.", errorMessage); + public DMLWithoutShardingKeyException() { + super(XOpenSQLState.SYNTAX_ERROR, 90, "Not allow DML operation without sharding conditions."); } } diff --git a/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/algorithm/audit/DMLShardingConditionsShardingAuditAlgorithmTest.java b/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/algorithm/audit/DMLShardingConditionsShardingAuditAlgorithmTest.java index 4f18df4f7aac9..e3e0ff51964e7 100644 --- a/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/algorithm/audit/DMLShardingConditionsShardingAuditAlgorithmTest.java +++ b/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/algorithm/audit/DMLShardingConditionsShardingAuditAlgorithmTest.java @@ -18,11 +18,11 @@ package org.apache.shardingsphere.sharding.algorithm.audit; import org.apache.shardingsphere.infra.binder.context.statement.SQLStatementContext; -import org.apache.shardingsphere.infra.exception.syntax.audit.SQLAuditException; import org.apache.shardingsphere.infra.metadata.database.ShardingSphereDatabase; import org.apache.shardingsphere.infra.metadata.database.rule.RuleMetaData; import org.apache.shardingsphere.infra.metadata.user.Grantee; import org.apache.shardingsphere.infra.spi.type.typed.TypedSPILoader; +import org.apache.shardingsphere.sharding.exception.audit.DMLWithoutShardingKeyException; import org.apache.shardingsphere.sharding.rule.ShardingRule; import org.apache.shardingsphere.sharding.spi.ShardingAuditAlgorithm; import org.apache.shardingsphere.sql.parser.sql.common.statement.ddl.DDLStatement; @@ -70,6 +70,6 @@ void assertEmptyShardingConditionsCheck() { when(sqlStatementContext.getSqlStatement()).thenReturn(mock(DMLStatement.class)); when(database.getRuleMetaData()).thenReturn(new RuleMetaData(Collections.singletonList(rule))); when(rule.isShardingTable("t_order")).thenReturn(true); - assertThrows(SQLAuditException.class, () -> shardingAuditAlgorithm.check(sqlStatementContext, Collections.emptyList(), mock(Grantee.class), mock(RuleMetaData.class), database)); + assertThrows(DMLWithoutShardingKeyException.class, () -> shardingAuditAlgorithm.check(sqlStatementContext, Collections.emptyList(), mock(Grantee.class), mock(RuleMetaData.class), database)); } } diff --git a/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/auditor/ShardingSQLAuditorTest.java b/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/auditor/ShardingSQLAuditorTest.java index ae50b0abc7a89..07d1d21ea3e3a 100644 --- a/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/auditor/ShardingSQLAuditorTest.java +++ b/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/auditor/ShardingSQLAuditorTest.java @@ -18,7 +18,7 @@ package org.apache.shardingsphere.sharding.auditor; import org.apache.shardingsphere.infra.binder.context.statement.CommonSQLStatementContext; -import org.apache.shardingsphere.infra.exception.syntax.audit.SQLAuditException; +import org.apache.shardingsphere.sharding.exception.audit.DMLWithoutShardingKeyException; import org.apache.shardingsphere.infra.hint.HintValueContext; import org.apache.shardingsphere.infra.metadata.database.ShardingSphereDatabase; import org.apache.shardingsphere.infra.metadata.database.rule.RuleMetaData; @@ -97,11 +97,11 @@ void assertCheckSuccessByDisableAuditNames() { void assertCheckFailed() { ShardingAuditAlgorithm auditAlgorithm = rule.getAuditors().get("auditor_1"); RuleMetaData globalRuleMetaData = mock(RuleMetaData.class); - doThrow(new SQLAuditException("Not allow DML operation without sharding conditions")) + doThrow(new DMLWithoutShardingKeyException()) .when(auditAlgorithm).check(sqlStatementContext, Collections.emptyList(), grantee, globalRuleMetaData, databases.get("foo_db")); - SQLAuditException ex = assertThrows(SQLAuditException.class, + DMLWithoutShardingKeyException ex = assertThrows(DMLWithoutShardingKeyException.class, () -> new ShardingSQLAuditor().audit(sqlStatementContext, Collections.emptyList(), grantee, globalRuleMetaData, databases.get("foo_db"), rule, hintValueContext)); - assertThat(ex.getMessage(), is("SQL audit failed, error message: Not allow DML operation without sharding conditions.")); + assertThat(ex.getMessage(), is("Not allow DML operation without sharding conditions.")); verify(rule.getAuditors().get("auditor_1")).check(sqlStatementContext, Collections.emptyList(), grantee, globalRuleMetaData, databases.get("foo_db")); } } diff --git a/infra/common/src/main/java/org/apache/shardingsphere/infra/exception/syntax/audit/AuditSQLException.java b/infra/common/src/main/java/org/apache/shardingsphere/infra/exception/syntax/audit/AuditSQLException.java deleted file mode 100644 index 3c733fd2c7521..0000000000000 --- a/infra/common/src/main/java/org/apache/shardingsphere/infra/exception/syntax/audit/AuditSQLException.java +++ /dev/null @@ -1,41 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package org.apache.shardingsphere.infra.exception.syntax.audit; - -import com.google.common.base.Preconditions; -import org.apache.shardingsphere.infra.exception.core.external.sql.sqlstate.SQLState; -import org.apache.shardingsphere.infra.exception.core.external.sql.type.kernel.category.SyntaxSQLException; - -/** - * Audit SQL exception. - */ -public abstract class AuditSQLException extends SyntaxSQLException { - - private static final long serialVersionUID = -2464996050872874641L; - - private static final int AUDIT_CODE = 2; - - protected AuditSQLException(final SQLState sqlState, final int errorCode, final String reason, final Object... messageArgs) { - super(sqlState, getErrorCode(errorCode), reason, messageArgs); - } - - private static int getErrorCode(final int errorCode) { - Preconditions.checkArgument(errorCode >= 0 && errorCode < 100, "The value range of error code should be [0, 100)."); - return AUDIT_CODE * 100 + errorCode; - } -} diff --git a/kernel/data-pipeline/scenario/cdc/core/src/main/java/org/apache/shardingsphere/data/pipeline/cdc/exception/CDCExceptionWrapper.java b/kernel/data-pipeline/scenario/cdc/core/src/main/java/org/apache/shardingsphere/data/pipeline/cdc/exception/CDCExceptionWrapper.java index ce07aed48a32b..07b6a23f628be 100644 --- a/kernel/data-pipeline/scenario/cdc/core/src/main/java/org/apache/shardingsphere/data/pipeline/cdc/exception/CDCExceptionWrapper.java +++ b/kernel/data-pipeline/scenario/cdc/core/src/main/java/org/apache/shardingsphere/data/pipeline/cdc/exception/CDCExceptionWrapper.java @@ -18,7 +18,6 @@ package org.apache.shardingsphere.data.pipeline.cdc.exception; import lombok.Getter; -import org.apache.shardingsphere.infra.exception.core.external.sql.ShardingSphereSQLException; /** * CDC exception wrapper. @@ -30,11 +29,11 @@ public final class CDCExceptionWrapper extends RuntimeException { private final String requestId; - private final ShardingSphereSQLException exception; + private final Exception cause; - public CDCExceptionWrapper(final String requestId, final ShardingSphereSQLException exception) { - super(exception.getMessage()); + public CDCExceptionWrapper(final String requestId, final Exception cause) { + super(cause.getMessage()); this.requestId = requestId; - this.exception = exception; + this.cause = cause; } } diff --git a/proxy/frontend/core/src/main/java/org/apache/shardingsphere/proxy/frontend/netty/CDCChannelInboundHandler.java b/proxy/frontend/core/src/main/java/org/apache/shardingsphere/proxy/frontend/netty/CDCChannelInboundHandler.java index cf0b8fecc5899..c5a24a286c694 100644 --- a/proxy/frontend/core/src/main/java/org/apache/shardingsphere/proxy/frontend/netty/CDCChannelInboundHandler.java +++ b/proxy/frontend/core/src/main/java/org/apache/shardingsphere/proxy/frontend/netty/CDCChannelInboundHandler.java @@ -42,19 +42,22 @@ import org.apache.shardingsphere.data.pipeline.cdc.protocol.response.CDCResponse.Status; import org.apache.shardingsphere.data.pipeline.cdc.protocol.response.ServerGreetingResult; import org.apache.shardingsphere.data.pipeline.core.exception.param.PipelineInvalidParameterException; -import org.apache.shardingsphere.infra.exception.metadata.rule.MissingRequiredRuleException; import org.apache.shardingsphere.infra.autogen.version.ShardingSphereVersion; import org.apache.shardingsphere.infra.exception.core.ShardingSpherePreconditions; -import org.apache.shardingsphere.infra.exception.core.external.sql.ShardingSphereSQLException; import org.apache.shardingsphere.infra.exception.core.external.sql.sqlstate.XOpenSQLState; import org.apache.shardingsphere.infra.exception.core.external.sql.type.kernel.category.PipelineSQLException; -import org.apache.shardingsphere.infra.exception.syntax.audit.SQLAuditException; +import org.apache.shardingsphere.infra.exception.dialect.SQLExceptionTransformEngine; +import org.apache.shardingsphere.infra.exception.dialect.exception.syntax.database.UnknownDatabaseException; +import org.apache.shardingsphere.infra.exception.metadata.rule.MissingRequiredRuleException; +import org.apache.shardingsphere.infra.exception.mysql.exception.AccessDeniedException; import org.apache.shardingsphere.infra.metadata.user.Grantee; import org.apache.shardingsphere.infra.metadata.user.ShardingSphereUser; import org.apache.shardingsphere.proxy.backend.context.ProxyContext; +import org.apache.shardingsphere.proxy.frontend.protocol.FrontDatabaseProtocolTypeFactory; import java.net.InetSocketAddress; import java.net.SocketAddress; +import java.sql.SQLException; import java.util.Objects; import java.util.Optional; @@ -91,8 +94,8 @@ public void exceptionCaught(final ChannelHandlerContext ctx, final Throwable cau ChannelFuture channelFuture; if (cause instanceof CDCExceptionWrapper) { CDCExceptionWrapper wrapper = (CDCExceptionWrapper) cause; - ShardingSphereSQLException exception = wrapper.getException(); - channelFuture = ctx.writeAndFlush(CDCResponseUtils.failed(wrapper.getRequestId(), exception.toSQLException().getSQLState(), exception.getMessage())); + SQLException sqlException = SQLExceptionTransformEngine.toSQLException(wrapper.getCause(), FrontDatabaseProtocolTypeFactory.getDatabaseType()); + channelFuture = ctx.writeAndFlush(CDCResponseUtils.failed(wrapper.getRequestId(), sqlException.getSQLState(), sqlException.getMessage())); } else { channelFuture = ctx.writeAndFlush(CDCResponseUtils.failed("", XOpenSQLState.GENERAL_ERROR.getValue(), String.valueOf(cause.getMessage()))); } @@ -151,9 +154,9 @@ private void checkPrivileges(final String requestId, final Grantee grantee, fina AuthorityRule authorityRule = ProxyContext.getInstance().getContextManager().getMetaDataContexts().getMetaData().getGlobalRuleMetaData().findSingleRule(AuthorityRule.class) .orElseThrow(() -> new CDCExceptionWrapper(requestId, new MissingRequiredRuleException("authority"))); ShardingSpherePrivileges privileges = authorityRule.findPrivileges(grantee) - .orElseThrow(() -> new CDCExceptionWrapper(requestId, new SQLAuditException(String.format("Access denied for user '%s'", grantee)))); + .orElseThrow(() -> new CDCExceptionWrapper(requestId, new AccessDeniedException(grantee.getUsername(), grantee.getHostname(), false))); ShardingSpherePreconditions.checkState(privileges.hasPrivileges(currentDatabase), - () -> new CDCExceptionWrapper(requestId, new SQLAuditException(String.format("Unknown database '%s'", currentDatabase)))); + () -> new CDCExceptionWrapper(requestId, new UnknownDatabaseException(currentDatabase))); } private String getHostAddress(final ChannelHandlerContext context) {