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

hongze pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/incubator-gluten.git


The following commit(s) were added to refs/heads/main by this push:
     new 6221edddf3 [VL] gluten-it: Print error details (#10293)
6221edddf3 is described below

commit 6221edddf367ae8eb726747693e5ef5aeb96e1ad
Author: Hongze Zhang <[email protected]>
AuthorDate: Wed Aug 6 15:33:31 2025 +0200

    [VL] gluten-it: Print error details (#10293)
---
 .../apache/gluten/integration/command/Queries.java |  2 +-
 .../gluten/integration/command/QueriesCompare.java |  2 +-
 .../gluten/integration/command/QueriesMixin.java   |  7 +++
 .../apache/gluten/integration/action/Queries.scala | 27 +++++++---
 .../gluten/integration/action/QueriesCompare.scala | 60 +++++++++++++++-------
 5 files changed, 72 insertions(+), 26 deletions(-)

diff --git 
a/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/Queries.java
 
b/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/Queries.java
index 456998cb2f..56c0ff183f 100644
--- 
a/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/Queries.java
+++ 
b/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/Queries.java
@@ -55,7 +55,7 @@ public class Queries implements Callable<Integer> {
     }
     org.apache.gluten.integration.action.Queries queries =
         new 
org.apache.gluten.integration.action.Queries(dataGenMixin.getScale(), 
dataGenMixin.genPartitionedData(), queriesMixin.queries(),
-            queriesMixin.explain(), queriesMixin.iterations(), 
randomKillTasks, queriesMixin.noSessionReuse(), 
JavaConverters.asScalaBufferConverter(metricsReporters).asScala());
+            queriesMixin.explain(), queriesMixin.iterations(), 
randomKillTasks, queriesMixin.noSessionReuse(), 
queriesMixin.suppressFailureMessages(), 
JavaConverters.asScalaBufferConverter(metricsReporters).asScala());
     return mixin.runActions(ArrayUtils.addAll(dataGenMixin.makeActions(), 
queries));
   }
 }
diff --git 
a/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/QueriesCompare.java
 
b/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/QueriesCompare.java
index d194aad185..6449c060c2 100644
--- 
a/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/QueriesCompare.java
+++ 
b/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/QueriesCompare.java
@@ -40,7 +40,7 @@ public class QueriesCompare implements Callable<Integer> {
     org.apache.gluten.integration.action.QueriesCompare queriesCompare =
         new 
org.apache.gluten.integration.action.QueriesCompare(dataGenMixin.getScale(),
             dataGenMixin.genPartitionedData(), queriesMixin.queries(),
-            queriesMixin.explain(), queriesMixin.iterations(), 
queriesMixin.noSessionReuse());
+            queriesMixin.explain(), queriesMixin.iterations(), 
queriesMixin.noSessionReuse(), queriesMixin.suppressFailureMessages());
     return mixin.runActions(ArrayUtils.addAll(dataGenMixin.makeActions(), 
queriesCompare));
   }
 }
diff --git 
a/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/QueriesMixin.java
 
b/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/QueriesMixin.java
index 64e4b32eca..a053e34e09 100644
--- 
a/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/QueriesMixin.java
+++ 
b/tools/gluten-it/common/src/main/java/org/apache/gluten/integration/command/QueriesMixin.java
@@ -45,6 +45,9 @@ public class QueriesMixin {
   @CommandLine.Option(names = {"--no-session-reuse"}, description = "Recreate 
new Spark session each time a query is about to run", defaultValue = "false")
   private boolean noSessionReuse;
 
+  @CommandLine.Option(names = {"--suppress-failure-messages"}, description = 
"Do not printing failures on error", defaultValue = "false")
+  private boolean suppressFailureMessages;
+
   public boolean explain() {
     return explain;
   }
@@ -57,6 +60,10 @@ public class QueriesMixin {
     return noSessionReuse;
   }
 
+  public boolean suppressFailureMessages() {
+    return suppressFailureMessages;
+  }
+
   public Actions.QuerySelector queries() {
     return new Actions.QuerySelector() {
       @Override
diff --git 
a/tools/gluten-it/common/src/main/scala/org/apache/gluten/integration/action/Queries.scala
 
b/tools/gluten-it/common/src/main/scala/org/apache/gluten/integration/action/Queries.scala
index bfcb1aafd1..7144c97d00 100644
--- 
a/tools/gluten-it/common/src/main/scala/org/apache/gluten/integration/action/Queries.scala
+++ 
b/tools/gluten-it/common/src/main/scala/org/apache/gluten/integration/action/Queries.scala
@@ -33,6 +33,7 @@ case class Queries(
     iterations: Int,
     randomKillTasks: Boolean,
     noSessionReuse: Boolean,
+    suppressFailureMessages: Boolean,
     metricsReporters: Seq[PlanMetric.Reporter])
   extends Action {
   import Queries._
@@ -68,7 +69,21 @@ case class Queries(
 
     val passedCount = results.count(l => l.queryResult.succeeded())
     val count = results.count(_ => true)
-    val succeeded = results.filter(_.queryResult.succeeded())
+    val succeededQueries = results.filter(_.queryResult.succeeded())
+    val failedQueries = results.filter(!_.queryResult.succeeded())
+
+    println()
+
+    if (failedQueries.nonEmpty) {
+      println(s"There are failed queries.")
+      if (!suppressFailureMessages) {
+        println()
+        failedQueries.foreach {
+          failedQuery =>
+            println(s"Query ${failedQuery.queryResult.caseId()} failed by 
error: ${failedQuery.queryResult.asFailure().error}")
+        }
+      }
+    }
 
     // RAM stats
     println("Performing GC to collect RAM statistics... ")
@@ -82,7 +97,7 @@ case class Queries(
     )
     println("")
 
-    val sqlMetrics = 
succeeded.flatMap(_.queryResult.asSuccess().runResult.sqlMetrics)
+    val sqlMetrics = 
succeededQueries.flatMap(_.queryResult.asSuccess().runResult.sqlMetrics)
     metricsReporters.foreach {
       r =>
         val report = r.toString(sqlMetrics)
@@ -94,17 +109,17 @@ case class Queries(
     println("")
     printf("Summary: %d out of %d queries passed. \n", passedCount, count)
     println("")
-    val all = succeeded.map(_.queryResult).asSuccesses().agg("all").map(s => 
TestResultLine(s))
-    Queries.printResults(succeeded ++ all)
+    val all = 
succeededQueries.map(_.queryResult).asSuccesses().agg("all").map(s => 
TestResultLine(s))
+    Queries.printResults(succeededQueries ++ all)
     println("")
 
-    if (passedCount == count) {
+    if (failedQueries.isEmpty) {
       println("No failed queries. ")
       println("")
     } else {
       println("Failed queries: ")
       println("")
-      Queries.printResults(results.filter(!_.queryResult.succeeded()))
+      Queries.printResults(failedQueries)
       println("")
     }
 
diff --git 
a/tools/gluten-it/common/src/main/scala/org/apache/gluten/integration/action/QueriesCompare.scala
 
b/tools/gluten-it/common/src/main/scala/org/apache/gluten/integration/action/QueriesCompare.scala
index 804f1fbd79..fcc8fb9036 100644
--- 
a/tools/gluten-it/common/src/main/scala/org/apache/gluten/integration/action/QueriesCompare.scala
+++ 
b/tools/gluten-it/common/src/main/scala/org/apache/gluten/integration/action/QueriesCompare.scala
@@ -16,14 +16,13 @@
  */
 package org.apache.gluten.integration.action
 
-import org.apache.commons.lang3.exception.ExceptionUtils
 import org.apache.gluten.integration.QueryRunner.QueryResult
 import org.apache.gluten.integration.action.Actions.QuerySelector
 import org.apache.gluten.integration.action.QueriesCompare.TestResultLine
 import 
org.apache.gluten.integration.action.TableRender.RowParser.FieldAppender.RowAppender
 import org.apache.gluten.integration.stat.RamStat
-import org.apache.gluten.integration.{QueryRunner, Suite, TableCreator}
-import org.apache.spark.sql.{RunResult, SparkSession, SparkSessionSwitcher, 
TestUtils}
+import org.apache.gluten.integration.{QueryRunner, Suite}
+import org.apache.spark.sql.{SparkSession, TestUtils}
 
 case class QueriesCompare(
     scale: Double,
@@ -31,7 +30,8 @@ case class QueriesCompare(
     queries: QuerySelector,
     explain: Boolean,
     iterations: Int,
-    noSessionReuse: Boolean)
+    noSessionReuse: Boolean,
+    suppressFailureMessages: Boolean)
     extends Action {
 
   override def execute(suite: Suite): Boolean = {
@@ -89,8 +89,23 @@ case class QueriesCompare(
       TestResultLine(b.caseId(), b, t)
     }
 
-    val passedCount = results.count(l => l.testPassed)
+    val passedCount = results.count(l => l.testPassed())
     val count = results.count(_ => true)
+    val succeededQueries = results.filter(_.testPassed())
+    val failedQueries = results.filter(!_.testPassed)
+
+    println()
+
+    if (failedQueries.nonEmpty) {
+      println(s"There are failed queries.")
+      if (!suppressFailureMessages) {
+        println()
+        failedQueries.foreach {
+          failedQuery =>
+            println(s"Query ${failedQuery.queryId} failed by error: 
${failedQuery.error()}")
+        }
+      }
+    }
 
     // RAM stats
     println("Performing GC to collect RAM statistics... ")
@@ -107,25 +122,24 @@ case class QueriesCompare(
     println("")
     printf("Summary: %d out of %d queries passed. \n", passedCount, count)
     println("")
-    val succeeded = results.filter(_.testPassed)
-    val all = succeeded match {
+    val all = succeededQueries match {
       case Nil => None
       case several =>
         val allExpected = several.map(_.expected).asSuccesses().agg("all 
expected").get
         val allActual = several.map(_.actual).asSuccesses().agg("all 
actual").get
         Some(TestResultLine("all", allExpected, allActual))
     }
-    QueriesCompare.printResults(succeeded ++ all)
+    QueriesCompare.printResults(succeededQueries ++ all)
     println("")
 
-    if (passedCount == count) {
+    if (failedQueries.isEmpty) {
       println("No failed queries. ")
       println("")
     } else {
       println(
         "Failed queries (a failed query with correct row count indicates value 
mismatches): ")
       println("")
-      QueriesCompare.printResults(results.filter(!_.testPassed))
+      QueriesCompare.printResults(failedQueries)
       println("")
     }
 
@@ -138,15 +152,25 @@ case class QueriesCompare(
 
 object QueriesCompare {
   case class TestResultLine(queryId: String, expected: QueryResult, actual: 
QueryResult) {
-    val testPassed: Boolean = {
-      expected.succeeded() && actual.succeeded() &&
+    private def tryGetError(): Option[String] = {
+      if (!expected.succeeded()) {
+        return Some(expected.asFailure().error.toString)
+      }
+      if (!actual.succeeded()) {
+        return Some(actual.asFailure().error.toString)
+      }
       TestUtils
-        .compareAnswers(
-          expected.asSuccess().runResult.rows,
-          actual.asSuccess().runResult.rows,
-          sort = true)
-        .isEmpty
+          .compareAnswers(
+            expected.asSuccess().runResult.rows,
+            actual.asSuccess().runResult.rows,
+            sort = true)
     }
+
+    private val maybeError = tryGetError()
+
+    def testPassed(): Boolean = maybeError.isEmpty
+
+    def error(): String = maybeError.get
   }
 
   object TestResultLine {
@@ -154,7 +178,7 @@ object QueriesCompare {
       override def parse(rowAppender: RowAppender, line: TestResultLine): Unit 
= {
         val inc = rowAppender.incremental()
         inc.next().write(line.queryId)
-        inc.next().write(line.testPassed)
+        inc.next().write(line.testPassed())
         
inc.next().write(line.expected.asSuccessOption().map(_.runResult.rows.size))
         
inc.next().write(line.actual.asSuccessOption().map(_.runResult.rows.size))
         
inc.next().write(line.expected.asSuccessOption().map(_.runResult.planningTimeMillis))


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to