This is an automated email from the ASF dual-hosted git repository.
dongjoon pushed a commit to branch branch-4.0
in repository https://gitbox.apache.org/repos/asf/spark.git
The following commit(s) were added to refs/heads/branch-4.0 by this push:
new d31d2f60b258 [SPARK-53667][SQL] Fix EXPLAIN for CALL with IDENTIFIER
d31d2f60b258 is described below
commit d31d2f60b2588df2ebe17150cfe4e304e32ea794
Author: Anton Okolnychyi <[email protected]>
AuthorDate: Wed Sep 24 08:58:32 2025 -0700
[SPARK-53667][SQL] Fix EXPLAIN for CALL with IDENTIFIER
### What changes were proposed in this pull request?
This PR fixes EXPLAIN for CALL with IDENTIFIER.
### Why are the changes needed?
These changes are needed to avoid MatchError exceptions for CALL statements
with `PlanWithUnresolvedIdentifier` in parsed (not analyzed) plan in EXPLAIN
output.
### Does this PR introduce _any_ user-facing change?
No.
### How was this patch tested?
This PR comes with tests.
### Was this patch authored or co-authored using generative AI tooling?
No.
Closes #52424 from aokolnychyi/spark-53667.
Authored-by: Anton Okolnychyi <[email protected]>
Signed-off-by: Dongjoon Hyun <[email protected]>
(cherry picked from commit 466c608b1b8070a88d4232c38f7ab04d35b3cf48)
Signed-off-by: Dongjoon Hyun <[email protected]>
---
.../spark/sql/catalyst/plans/logical/v2Commands.scala | 13 ++++++++++---
.../org/apache/spark/sql/connector/ProcedureSuite.scala | 13 +++++++++++++
2 files changed, 23 insertions(+), 3 deletions(-)
diff --git
a/sql/catalyst/src/main/scala/org/apache/spark/sql/catalyst/plans/logical/v2Commands.scala
b/sql/catalyst/src/main/scala/org/apache/spark/sql/catalyst/plans/logical/v2Commands.scala
index f8c1b2a90145..f5c8f08ce87b 100644
---
a/sql/catalyst/src/main/scala/org/apache/spark/sql/catalyst/plans/logical/v2Commands.scala
+++
b/sql/catalyst/src/main/scala/org/apache/spark/sql/catalyst/plans/logical/v2Commands.scala
@@ -1654,12 +1654,19 @@ case class Call(
}
override def simpleString(maxFields: Int): String = {
- val name = procedure match {
+ procedure match {
case ResolvedProcedure(catalog, ident, _) =>
- s"${quoteIfNeeded(catalog.name)}.${ident.quoted}"
+ val name = s"${quoteIfNeeded(catalog.name)}.${ident.quoted}"
+ simpleString(name, maxFields)
case UnresolvedProcedure(nameParts) =>
- nameParts.quoted
+ val name = nameParts.quoted
+ simpleString(name, maxFields)
+ case _ =>
+ super.simpleString(maxFields)
}
+ }
+
+ private def simpleString(name: String, maxFields: Int): String = {
val argsString = truncatedString(args, ", ", maxFields)
s"Call $name($argsString)"
}
diff --git
a/sql/core/src/test/scala/org/apache/spark/sql/connector/ProcedureSuite.scala
b/sql/core/src/test/scala/org/apache/spark/sql/connector/ProcedureSuite.scala
index ae11699f8c6d..7578b7b86843 100644
---
a/sql/core/src/test/scala/org/apache/spark/sql/connector/ProcedureSuite.scala
+++
b/sql/core/src/test/scala/org/apache/spark/sql/connector/ProcedureSuite.scala
@@ -117,6 +117,19 @@ class ProcedureSuite extends QueryTest with
SharedSparkSession with BeforeAndAft
Row(3) :: Nil)
}
+ test("IDENTIFIER inside EXPLAIN") {
+ catalog.createProcedure(Identifier.of(Array("ns"), "sum"), UnboundSum)
+ val explain1 = spark.sql(
+ "EXPLAIN CALL IDENTIFIER(:p1)(5, 3)",
+ Map("p1" -> "cat.ns.sum")).head().getString(0)
+ assert(explain1.contains("Call cat.ns.sum(5, 3)"))
+ val explain2 = spark.sql(
+ "EXPLAIN EXTENDED CALL IDENTIFIER(:p1)(10, 10)",
+ Map("p1" -> "cat.ns.sum")).head().getString(0)
+ assert(explain2.contains("'NameParameterizedQuery [p1], [cat.ns.sum]"))
+ assert(explain2.contains("Call cat.ns.sum(10, 10)"))
+ }
+
test("parameterized statements") {
catalog.createProcedure(Identifier.of(Array("ns"), "sum"), UnboundSum)
checkAnswer(
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]