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

jerryshao pushed a commit to branch branch-1.3
in repository https://gitbox.apache.org/repos/asf/gravitino.git


The following commit(s) were added to refs/heads/branch-1.3 by this push:
     new 4c4f367c1e [Cherry-pick to branch-1.3] [#13343] fix(doris): handle 
missing-table errors from DROP TABLE (#13344) (#13345)
4c4f367c1e is described below

commit 4c4f367c1e3f2c1bffed06e4aa476bc90850812f
Author: github-actions[bot] 
<41898282+github-actions[bot]@users.noreply.github.com>
AuthorDate: Sun Sep 20 17:10:42 2026 +0800

    [Cherry-pick to branch-1.3] [#13343] fix(doris): handle missing-table 
errors from DROP TABLE (#13344) (#13345)
    
    **Cherry-pick Information:**
    - Original commit: f02f537c7a252a8a94f37468a6af3a53a6eb82e5
    - Target branch: `branch-1.3`
    - Status: ✅ Clean cherry-pick (no conflicts)
    
    Co-authored-by: Qi Yu <[email protected]>
---
 .../doris/converter/DorisExceptionConverter.java   | 47 +++++++++++++++-------
 .../converter/TestDorisExceptionConverter.java     | 32 +++++++++++++++
 .../doris/integration/test/CatalogDorisIT.java     |  6 +++
 3 files changed, 70 insertions(+), 15 deletions(-)

diff --git 
a/catalogs/catalog-jdbc-doris/src/main/java/org/apache/gravitino/catalog/doris/converter/DorisExceptionConverter.java
 
b/catalogs/catalog-jdbc-doris/src/main/java/org/apache/gravitino/catalog/doris/converter/DorisExceptionConverter.java
index bbd4e5099e..0c19f360aa 100644
--- 
a/catalogs/catalog-jdbc-doris/src/main/java/org/apache/gravitino/catalog/doris/converter/DorisExceptionConverter.java
+++ 
b/catalogs/catalog-jdbc-doris/src/main/java/org/apache/gravitino/catalog/doris/converter/DorisExceptionConverter.java
@@ -20,6 +20,7 @@ package org.apache.gravitino.catalog.doris.converter;
 
 import com.google.common.annotations.VisibleForTesting;
 import java.sql.SQLException;
+import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 import org.apache.gravitino.catalog.jdbc.converter.JdbcExceptionConverter;
 import org.apache.gravitino.exceptions.ConnectionFailedException;
@@ -67,11 +68,14 @@ public class DorisExceptionConverter extends 
JdbcExceptionConverter {
       Pattern.compile(UNKNOWN_DATABASE_PATTERN_STRING);
 
   private static final String TABLE_NOT_EXIST_PATTERN_STRING =
-      ".*detailMessage = Unknown table '.*' in .*:.*";
+      ".*detailMessage = Unknown table (?:'[^']+'|\\S+) in \\S+.*";
 
   private static final Pattern TABLE_NOT_EXIST_PATTERN =
       Pattern.compile(TABLE_NOT_EXIST_PATTERN_STRING);
 
+  private static final Pattern DUPLICATED_ERROR_PREFIX_PATTERN =
+      Pattern.compile("^(errCode = \\d+, detailMessage = )\\1");
+
   private static final String DELETE_NON_EXISTING_PARTITION_STRING =
       ".*?detailMessage = Error in list of partitions to .*?";
 
@@ -93,29 +97,30 @@ public class DorisExceptionConverter extends 
JdbcExceptionConverter {
   @SuppressWarnings("FormatStringAnnotation")
   @Override
   public GravitinoRuntimeException toGravitinoException(SQLException se) {
+    String message = removeDuplicatedErrorPrefix(se.getMessage());
     int errorCode = se.getErrorCode();
     if (errorCode == CODE_OTHER) {
-      errorCode = getErrorCodeFromMessage(se.getMessage());
+      errorCode = getErrorCodeFromMessage(message);
     }
 
     switch (errorCode) {
       case CODE_DATABASE_EXISTS:
-        return new SchemaAlreadyExistsException(se, se.getMessage());
+        return new SchemaAlreadyExistsException(se, message);
       case CODE_TABLE_EXISTS:
-        return new TableAlreadyExistsException(se, se.getMessage());
+        return new TableAlreadyExistsException(se, message);
       case CODE_DATABASE_NOT_EXISTS:
       case CODE_UNKNOWN_DATABASE:
-        return new NoSuchSchemaException(se, se.getMessage());
+        return new NoSuchSchemaException(se, message);
       case CODE_NO_SUCH_TABLE:
-        return new NoSuchTableException(se, se.getMessage());
+        return new NoSuchTableException(se, message);
       case CODE_UNAUTHORIZED:
-        return new UnauthorizedException(se, se.getMessage());
+        return new UnauthorizedException(se, message);
       case CODE_NO_SUCH_COLUMN:
-        return new NoSuchColumnException(se, se.getMessage());
+        return new NoSuchColumnException(se, message);
       case CODE_DELETE_NON_EXISTING_PARTITION:
-        return new NoSuchPartitionException(se, se.getMessage());
+        return new NoSuchPartitionException(se, message);
       case CODE_PARTITION_ALREADY_EXISTS:
-        return new PartitionAlreadyExistsException(se, se.getMessage());
+        return new PartitionAlreadyExistsException(se, message);
       case CODE_BUCKETS_AUTO_NOT_SUPPORTED:
         String bucketsAutoMessage =
             String.format(
@@ -123,19 +128,31 @@ public class DorisExceptionConverter extends 
JdbcExceptionConverter {
                     + "BUCKETS AUTO was introduced in Doris 1.2.2. "
                     + "Please either upgrade to Doris 1.2.2+ or specify a 
specific bucket number instead of AUTO. "
                     + "Original error: %s",
-                se.getMessage());
+                message);
         return new GravitinoRuntimeException(se, bucketsAutoMessage);
       default:
-        if (se.getMessage() != null && se.getMessage().contains("Access 
denied")) {
-          return new ConnectionFailedException(se, se.getMessage());
+        if (message != null && message.contains("Access denied")) {
+          return new ConnectionFailedException(se, message);
         }
-        return new GravitinoRuntimeException(se, se.getMessage());
+        return new GravitinoRuntimeException(se, message);
+    }
+  }
+
+  private static String removeDuplicatedErrorPrefix(String message) {
+    if (message == null) {
+      return null;
+    }
+    Matcher matcher = DUPLICATED_ERROR_PREFIX_PATTERN.matcher(message);
+    while (matcher.find()) {
+      message = matcher.replaceFirst("$1");
+      matcher = DUPLICATED_ERROR_PREFIX_PATTERN.matcher(message);
     }
+    return message;
   }
 
   @VisibleForTesting
   static int getErrorCodeFromMessage(String message) {
-    if (message.isEmpty()) {
+    if (message == null || message.isEmpty()) {
       return CODE_OTHER;
     }
     if (DATABASE_ALREADY_EXISTS_PATTERN.matcher(message).matches()) {
diff --git 
a/catalogs/catalog-jdbc-doris/src/test/java/org/apache/gravitino/catalog/doris/converter/TestDorisExceptionConverter.java
 
b/catalogs/catalog-jdbc-doris/src/test/java/org/apache/gravitino/catalog/doris/converter/TestDorisExceptionConverter.java
index b365eb2d73..0133a99f73 100644
--- 
a/catalogs/catalog-jdbc-doris/src/test/java/org/apache/gravitino/catalog/doris/converter/TestDorisExceptionConverter.java
+++ 
b/catalogs/catalog-jdbc-doris/src/test/java/org/apache/gravitino/catalog/doris/converter/TestDorisExceptionConverter.java
@@ -18,10 +18,42 @@
  */
 package org.apache.gravitino.catalog.doris.converter;
 
+import java.sql.SQLException;
+import org.apache.gravitino.exceptions.GravitinoRuntimeException;
+import org.apache.gravitino.exceptions.NoSuchTableException;
 import org.junit.jupiter.api.Assertions;
 import org.junit.jupiter.api.Test;
 
 public class TestDorisExceptionConverter {
+  @Test
+  public void testUnknownTableWithoutQuotes() {
+    String message = "errCode = 2, detailMessage = Unknown table 
no_such_table_xyz in s_12412";
+    SQLException sqlException =
+        new SQLException(message, "HY000", DorisExceptionConverter.CODE_OTHER);
+
+    GravitinoRuntimeException converted =
+        new DorisExceptionConverter().toGravitinoException(sqlException);
+
+    Assertions.assertTrue(converted instanceof NoSuchTableException);
+    Assertions.assertEquals(message, converted.getMessage());
+    Assertions.assertSame(sqlException, converted.getCause());
+  }
+
+  @Test
+  public void testRepeatedErrorPrefixIsRemoved() {
+    String prefix = "errCode = 2, detailMessage = ";
+    String detail = "Unknown table no_such_table_xyz in s_12412";
+    SQLException sqlException =
+        new SQLException(prefix + prefix + detail, "HY000", 
DorisExceptionConverter.CODE_OTHER);
+
+    GravitinoRuntimeException converted =
+        new DorisExceptionConverter().toGravitinoException(sqlException);
+
+    Assertions.assertTrue(converted instanceof NoSuchTableException);
+    Assertions.assertEquals(prefix + detail, converted.getMessage());
+    Assertions.assertSame(sqlException, converted.getCause());
+  }
+
   @Test
   public void testGetErrorCodeFromMessage() {
     String msg =
diff --git 
a/catalogs/catalog-jdbc-doris/src/test/java/org/apache/gravitino/catalog/doris/integration/test/CatalogDorisIT.java
 
b/catalogs/catalog-jdbc-doris/src/test/java/org/apache/gravitino/catalog/doris/integration/test/CatalogDorisIT.java
index d67e2d2ed2..9b33c4eded 100644
--- 
a/catalogs/catalog-jdbc-doris/src/test/java/org/apache/gravitino/catalog/doris/integration/test/CatalogDorisIT.java
+++ 
b/catalogs/catalog-jdbc-doris/src/test/java/org/apache/gravitino/catalog/doris/integration/test/CatalogDorisIT.java
@@ -195,6 +195,12 @@ public class CatalogDorisIT extends BaseIT {
     Assertions.assertDoesNotThrow(() -> metalake.testConnection(catalogName));
   }
 
+  @Test
+  void testDropMissingTableReturnsFalse() {
+    String missingTable = GravitinoITUtils.genRandomName("missing_table");
+    
assertFalse(catalog.asTableCatalog().dropTable(NameIdentifier.of(schemaName, 
missingTable)));
+  }
+
   private void createSchema() {
     NameIdentifier ident = NameIdentifier.of(metalakeName, catalogName, 
schemaName);
     String propKey = "key";

Reply via email to