Casting to a struct type with repeated field names fails with "ArrowArray struct has 2 children (expected 1)"
メンテナーはふだん 1 日以内に返信
評価
- 難易度
- 2/5
- 見積もり時間
- 1〜3時間
- 初心者へのやさしさ
- 68/100
調査の方向性
CometCast.isSupported の struct ブランチを読み、すでに重複フィールド名を拒否する CometCreateNamedStruct と比較します。array と map のブランチはそこへ再帰するため、1 つのチェックで repro SQL 内のネストしたケースをカバーします。失敗する 3 つの CAST クエリと通過する 2 つのコントロールで再現し、次に修正によって cast がフォールバックして結果が Spark と一致することを確認します。完了は、cast テストスイートで重複する struct フィールド名をカバーする新しいケースと、NativeUtil.importVector からの IllegalStateException がないことのように見えます。
索引モデルが issue の本文から書いたものです。
説明
Describe the bug
A cast whose target struct type repeats a field name fails the task when Comet runs it natively. Spark allows the cast as long as each pair of fields casts, so CAST(s AS STRUCT<x: INT, x: INT>) over a STRUCT<p: INT, q: INT> column returns {1, 10}. Comet's native cast_struct_to_struct builds the result with the target fields, and the projection itself works: to_json over the cast matches Spark with {"x":1,"x":10}. Importing the result on the JVM then fails, because Java Arrow keys struct children by name and the two x children collapse into one:
java.lang.IllegalStateException: ArrowArray struct has 2 children (expected 1)
at org.apache.arrow.util.Preconditions.checkState(Preconditions.java:562)
at org.apache.arrow.c.ArrayImporter.doImport(ArrayImporter.java:92)
at org.apache.arrow.c.ArrayImporter.importChild(ArrayImporter.java:83)
at org.apache.arrow.c.ArrayImporter.doImport(ArrayImporter.java:101)
at org.apache.arrow.c.ArrayImporter.importArray(ArrayImporter.java:68)
at org.apache.arrow.c.ArrowImporter.importVector(ArrowImporter.java:62)
at org.apache.comet.vector.NativeUtil.importVector(NativeUtil.scala:264)
at org.apache.comet.vector.NativeUtil.getNextBatch(NativeUtil.scala:211)
at org.apache.comet.CometExecIterator.getNextBatch(CometExecIterator.scala:236)
The same happens when the struct is nested in an array or a map value.
Steps to reproduce
Default configs, reproduced on main at fef94f6cd with Spark 4.1.3:
CREATE TABLE ts (
s STRUCT<p: INT, q: INT>,
arr ARRAY<STRUCT<p: INT, q: INT>>,
m MAP<STRING, STRUCT<p: INT, q: INT>>) USING parquet;
INSERT INTO ts VALUES
(named_struct('p', 1, 'q', 10), array(named_struct('p', 1, 'q', 10)),
map('k', named_struct('p', 1, 'q', 10))),
(named_struct('p', 2, 'q', NULL), array(), map()),
(NULL, NULL, NULL);
SELECT CAST(s AS STRUCT<x: INT, x: INT>) FROM ts; -- IllegalStateException
SELECT CAST(arr AS ARRAY<STRUCT<x: INT, x: INT>>) FROM ts; -- IllegalStateException
SELECT CAST(m AS MAP<STRING, STRUCT<x: INT, x: INT>>) FROM ts; -- IllegalStateException
SELECT CAST(s AS STRUCT<x: INT, y: INT>) FROM ts; -- matches Spark
SELECT to_json(CAST(s AS STRUCT<x: INT, x: INT>)) FROM ts; -- matches Spark
The plan is CometProject over CometNativeScan. Spark returns {1, 10}, {2, null} and null for the first query.
Expected behavior
Either match Spark or fall back. The smallest fix is probably for the struct branch of CometCast.isSupported to return Unsupported when the target struct repeats a field name, the same way CometCreateNamedStruct declines repeated names. The array and map branches already recurse into the struct branch, so one check there also covers the nested cases.
Additional context
This is the same Java Arrow limitation as #6251 (arrays_zip, fix in #6324), #5605 and #1015. Main declines structs with repeated field names wherever they would cross into Java Arrow: the shuffle and row conversion checks (#5866), the codegen dispatcher (#5766) and the cache serializer (#6004). Those checks guard the paths that bring a struct into Comet, though, and a native cast creates one. The broadcast exchange admits these types too (CometSink.convert calls supportedDataType with the default allowDuplicateStructFieldNames = true), so declining in the serde that produces the struct is what keeps it out.
Found while checking whether anything in #5603 was worth keeping.
- 主要言語
- Scala
- スター
- 1.3k
- フォーク
- 387
- 平均マージ
- 2日 4時間
- マージ済み PR(30日)
- 413
環境構築
- Dockerfile・Docker Compose ファイルなし
- プルリクエストのテンプレートあり
- コントリビューションガイドを読む
はじめの一歩
- issue を最後まで読み、次にプロジェクトのコントリビューションガイドを読みます。
- 着手することを issue にコメントします — 二人が同じ作業をするのを防げます。
- リポジトリをフォークし、ブランチを切って変更します。
- issue 番号を参照したプルリクエストを送ります。
apache/datafusion-comet のほかの issue
-
Iceberg data tables whose names end with a metadata-table name fall back to Spark対応中かも @aryan9948 が 3 日前に担当しました。 オープンrequires-triage
難易度 2/5 1〜3時間 初心者へのやさしさ 75/100
apache/datafusion-comet#6719 · コメント 1 件 ·
メンテナーはふだん 1 日以内に返信
-
ANSI integral SUM overflow reports "integer overflow" without Spark's try_add suggestion対応中かも @0lai0 が 3 日前に担当しました。 オープンarea:aggregation bug priority:medium
難易度 2/5 1〜3時間 初心者へのやさしさ 82/100
apache/datafusion-comet#6661 · コメント 1 件 · 担当者 1 名 ·
メンテナーはふだん 1 日以内に返信
-
Native from_json with a schema that repeats a field name fails with "ArrowArray struct has 2 children (expected 1)"対応中かも @Samearth17 が 4 日前に担当しました。 オープンarea:expressions area:ffi bug good first issue priority:medium
難易度 2/5 1〜3時間 初心者へのやさしさ 70/100
apache/datafusion-comet#6592 ·
メンテナーはふだん 1 日以内に返信
-
arrays_zip with two same-named inputs fails with "ArrowArray struct has 2 children (expected 1)"対応中かも @mohitgurav20 が 11 日前に担当しました。 オープンarea:expressions area:ffi bug priority:high
難易度 2/5 1〜3時間 初心者へのやさしさ 78/100
apache/datafusion-comet#6251 · コメント 4 件 · 担当者 1 名 ·
メンテナーはふだん 1 日以内に返信
-
ci: a transient Maven Central failure in lint-java is reported as a scalafix violation対応中かも @andygrove が 19 日前に担当しました。 オープンarea:ci bug priority:low
難易度 2/5 1〜3時間 初心者へのやさしさ 84/100
apache/datafusion-comet#6060 ·
メンテナーはふだん 1 日以内に返信
apache/datafusion-comet の issue をすべて見る
似ている issue
-
Fix Math.ceilDiv wrong result for exact positive divisions対応中かも @pamod-madubashana が今日担当しました。 オープン
難易度 2/5 1〜3時間 初心者へのやさしさ 88/100
scala-native/scala-native#5094 ·
メンテナーはふだん 1 日以内に返信
-
"Show threat" doesn't show the evaluation of the threat対応中かも @Zinkelburger が今日担当しました。 オープン
難易度 2/5 1〜3時間 初心者へのやさしさ 62/100
lichess-org/lila#22008 · コメント 1 件 ·
メンテナーはふだん 1 日以内に返信
-
C21 publishes `reactivemongo/core/SSL` as Java 23 bytecode — TLS connections fail on any JDK < 23オープン
難易度 2/5 1〜3時間 初心者へのやさしさ 74/100
ReactiveMongo/ReactiveMongo#1520 ·
メンテナーはふだん 1 日以内に返信
-
module: memory type: bug/reported
難易度 1/5 1時間未満 初心者へのやさしさ 78/100
OpenXiangShan/XiangShan#6688 · コメント 2 件 ·
メンテナーはふだん 2 日以内に返信
-
難易度 2/5 1〜3時間 初心者へのやさしさ 78/100
disneystreaming/smithy4s#2011 ·