-
Notifications
You must be signed in to change notification settings - Fork 28.9k
[SPARK-19716][SQL] support by-name resolution for struct type elements in array #17398
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -33,6 +33,10 @@ case class StringIntClass(a: String, b: Int) | |
|
|
||
| case class ComplexClass(a: Long, b: StringLongClass) | ||
|
|
||
| case class ArrayClass(arr: Seq[StringIntClass]) | ||
|
|
||
| case class NestedArrayClass(nestedArr: Array[ArrayClass]) | ||
|
|
||
| class EncoderResolutionSuite extends PlanTest { | ||
| private val str = UTF8String.fromString("hello") | ||
|
|
||
|
|
@@ -62,6 +66,54 @@ class EncoderResolutionSuite extends PlanTest { | |
| encoder.resolveAndBind(attrs).fromRow(InternalRow(InternalRow(str, 1.toByte), 2)) | ||
| } | ||
|
|
||
| test("real type doesn't match encoder schema but they are compatible: array") { | ||
|
||
| val encoder = ExpressionEncoder[ArrayClass] | ||
| val attrs = Seq('arr.array(new StructType().add("a", "int").add("b", "int").add("c", "int"))) | ||
| val array = new GenericArrayData(Array(InternalRow(1, 2, 3))) | ||
| encoder.resolveAndBind(attrs).fromRow(InternalRow(array)) | ||
| } | ||
|
|
||
| test("real type doesn't match encoder schema but they are compatible: nested array") { | ||
| val encoder = ExpressionEncoder[NestedArrayClass] | ||
| val et = new StructType().add("arr", ArrayType( | ||
| new StructType().add("a", "int").add("b", "int").add("c", "int"))) | ||
| val attrs = Seq('nestedArr.array(et)) | ||
| val innerArr = new GenericArrayData(Array(InternalRow(1, 2, 3))) | ||
| val outerArr = new GenericArrayData(Array(InternalRow(innerArr))) | ||
| encoder.resolveAndBind(attrs).fromRow(InternalRow(outerArr)) | ||
| } | ||
|
|
||
| test("the real type is not compatible with encoder schema: non-array field") { | ||
| val encoder = ExpressionEncoder[ArrayClass] | ||
| val attrs = Seq('arr.int) | ||
| assert(intercept[AnalysisException](encoder.resolveAndBind(attrs)).message == | ||
| "need an array field but got int") | ||
| } | ||
|
|
||
| test("the real type is not compatible with encoder schema: array element type") { | ||
| val encoder = ExpressionEncoder[ArrayClass] | ||
| val attrs = Seq('arr.array(new StructType().add("c", "int"))) | ||
| assert(intercept[AnalysisException](encoder.resolveAndBind(attrs)).message == | ||
| "No such struct field a in c") | ||
| } | ||
|
|
||
| test("the real type is not compatible with encoder schema: nested array element type") { | ||
| val encoder = ExpressionEncoder[NestedArrayClass] | ||
|
|
||
| withClue("inner element is not array") { | ||
| val attrs = Seq('nestedArr.array(new StructType().add("arr", "int"))) | ||
| assert(intercept[AnalysisException](encoder.resolveAndBind(attrs)).message == | ||
| "need an array field but got int") | ||
| } | ||
|
|
||
| withClue("nested array element type is not compatible") { | ||
| val attrs = Seq('nestedArr.array(new StructType() | ||
| .add("arr", ArrayType(new StructType().add("c", "int"))))) | ||
| assert(intercept[AnalysisException](encoder.resolveAndBind(attrs)).message == | ||
| "No such struct field a in c") | ||
| } | ||
| } | ||
|
|
||
| test("nullability of array type element should not fail analysis") { | ||
| val encoder = ExpressionEncoder[Seq[Int]] | ||
| val attrs = 'a.array(IntegerType) :: Nil | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
below are style-only changes