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]