Skip to content

Add Hadoop config option to auto-derive Parquet list encoding from writer schema#1341

Open
clairemcginty wants to merge 3 commits into
mainfrom
auto-derive-list-encoding
Open

Add Hadoop config option to auto-derive Parquet list encoding from writer schema#1341
clairemcginty wants to merge 3 commits into
mainfrom
auto-derive-list-encoding

Conversation

@clairemcginty

@clairemcginty clairemcginty commented Jun 23, 2026

Copy link
Copy Markdown
Contributor

(branched off #1340; once that's merged I'll update the base ref)

Adds a hadoop configuration flag parquet.type.read.auto-detect-list-encoding that will instruct ParquetType to auto-detect list encoding based off writer schema.

todo: update benchmarks to check added ms cost per file


override private[parquet] def properties: MagnolifyParquetProperties =
propertiesWithAvroImportCompat
override private[parquet] def updateProperties(

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this feels like a very non-idiomatic way to achieve this in Scala, but couldn't think of a better option that wouldn't break API compat

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe a private apply would seem nicer?

Base automatically changed from repeated-schema-compat-check to main June 29, 2026 15:32

@regadas regadas left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

one thing worth confirming before moving ahead.

Comment thread docs/parquet.md

val reader = pt
.readBuilder(...)
+ .withConf(ParquetConfiguration.of("parquet.type.read.auto-detect-list-encoding" -> true)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: missing )

Suggested change
+ .withConf(ParquetConfiguration.of("parquet.type.read.auto-detect-list-encoding" -> true)
+ .withConf(ParquetConfiguration.of("parquet.type.read.auto-detect-list-encoding" -> true))

Comment on lines +98 to +136
def detectArrayEncoding(schema: Type): Option[ArrayEncoding] = {
val encodings = scala.collection.mutable.Set.empty[ArrayEncoding]

def visit(t: Type): Unit = t match {
case g: GroupType if g.getLogicalTypeAnnotation == LogicalTypeAnnotation.listType() =>
g.getFields.asScala.headOption match {
case Some(child) if child.getName == "list" =>
encodings += ArrayEncoding.ThreeLevelList
case Some(child) if child.getName == "array" =>
encodings += ArrayEncoding.ThreeLevelArray
case Some(_) =>
throw new InvalidRecordException(
s"Schema contained unsupported list encoding ```$t```;" +
s" child element of LIST annotation must be one of: [list, array]`"
)
case None =>
}
g.getFields.asScala.foreach(visit)
case g: GroupType =>
g.getFields.asScala.foreach(visit)
case t: PrimitiveType if t.getRepetition == Repetition.REPEATED =>
encodings += ArrayEncoding.Ungrouped
case _ =>
}

schema match {
case g: GroupType => g.getFields.asScala.foreach(visit)
case _ =>
}

if (encodings.size > 1) {
throw new InvalidRecordException(
s"Multiple list encodings detected in writer schema: ${encodings.mkString(", ")}. " +
"Cannot auto-detect list encoding."
)
}

encodings.headOption
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

hmm maybe I'm wrong but the current 2-level-array test fixtures use a group element, so we're missing a primitive-element unit test + roundtrip? If so I think this path might be broken for 2-level array encoding over primitive elements ... throwing "Multiple list encodings".

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants