spark-test commented on code in PR #59657:
URL: https://github.com/apache/spark/pull/59657#discussion_r4358967426


##########
sql/core/src/test/scala/org/apache/spark/sql/execution/datasources/parquet/ParquetVectorizedSuite.scala:
##########
@@ -1040,6 +1127,66 @@ class ParquetVectorizedSuite extends ParquetTest with 
SharedSparkSession {
     }
   }
 
+  private def createVectorizedReader(
+      file: String,
+      readSchema: StructType,
+      offheapEnabled: Boolean): VectorizedParquetRecordReader = {
+    val conf = spark.sessionState.conf
+    val hadoopConf = spark.sessionState.newHadoopConf()
+    hadoopConf.set(ParquetInputFormat.READ_SUPPORT_CLASS, 
classOf[ParquetReadSupport].getName)
+    hadoopConf.set(ParquetReadSupport.SPARK_ROW_REQUESTED_SCHEMA, 
readSchema.json)
+    Seq(
+      SQLConf.CASE_SENSITIVE,
+      SQLConf.PARQUET_BINARY_AS_STRING,
+      SQLConf.PARQUET_INT96_AS_TIMESTAMP,
+      SQLConf.PARQUET_INFER_TIMESTAMP_NTZ_ENABLED,
+      SQLConf.LEGACY_PARQUET_NANOS_AS_LONG
+    ).foreach { entry =>
+      hadoopConf.set(entry.key, conf.getConfString(entry.key))
+    }
+
+    val split = new FileSplit(new Path(file), 0, new File(file).length(), 
Array.empty[String])
+    val context = new TaskAttemptContextImpl(hadoopConf, new TaskAttemptID())
+    val reader = new VectorizedParquetRecordReader(
+      offheapEnabled,
+      conf.parquetVectorizedReaderBatchSize
+    )
+
+    try {
+      reader.enableReturningBatches()
+      reader.initialize(split, context)
+    } catch {
+      case _: Throwable =>

Review Comment:
   **Nit (P3):** If `enableReturningBatches()` or `initialize()` throws, this 
handler closes the reader but neither rethrows nor fails, and the helper 
returns the closed reader. Both SPARK-60098 tests then call `nextKeyValue()` on 
it, which fails later with an unrelated error: an `AssertionError` in 
`truncateType` or an NPE in `allocateColumns` when `sparkSchema` was never set, 
or an NPE in `loadNextRowGroup()` because `close()` nulled the row-group 
reader. A regression in the struct-clipping or shredded-variant setup these 
tests exercise would then be reported as that secondary error, and the root 
cause would be lost. Matching `Throwable` also swallows fatal errors such as 
`OutOfMemoryError` and `InterruptedException`.
   
   Consider rethrowing after cleanup, e.g. `case NonFatal(e) => reader.close(); 
throw e`.
   
   **Verification:**
   - **Regression:** A reader-initialization failure inside the closure tests' 
reader-construction helper surfaces as the original initialization exception, 
with the reader closed, rather than as a secondary error from using a closed 
reader.
   - **Behavior:** The missing-struct-fields and shredded-variant closure tests 
still pass and still assert that all value, definition-level and 
repetition-level vectors are released after reader close, in both on-heap and 
off-heap modes.



##########
sql/core/src/main/java/org/apache/spark/sql/execution/vectorized/WritableColumnVector.java:
##########
@@ -120,6 +129,11 @@ public void closeIfFreeable() {
     // no-op
   }
 
+  /**
+   * Returns true if this column vector holds no reference to data buffers.
+   */
+  public abstract boolean isFree();

Review Comment:
   **Nit (P3):** `isFree()` is only called by the new `checkIsClosed` 
assertions in `ParquetVectorizedSuite`, yet it is added as an unmarked `public 
abstract` member of this production base class. Other test-only members of 
these classes carry `@VisibleForTesting` (`MAX_CAPACITY` here, 
`OffHeapColumnVector.valuesNativeAddress()`). The Javadoc also reads as a 
whole-vector property, but both implementations check only this vector's own 
buffers (`nulls`, data, lengths/offsets) and ignore `childColumns`, reserved 
columns and `dictionaryIds`. The tests are fine today, because `close()` 
releases those vectors before `releaseMemory()`. However, a future caller could 
read the method as a full-release check for a nested or string vector. Suggest 
marking it test-only and narrowing the doc:
   
   ```suggestion
     /**
      * Returns true if this vector's own data buffers are released; vectors it 
owns are not checked.
      */
     @VisibleForTesting
     public abstract boolean isFree();
   ```
   
   **Verification:**
   - **Inspection:** The isFree() declaration on the vector base class carries 
the test-only marker, and its documentation describes the own-buffers-only 
scope that both implementations check.
   - **Regression:** The vectorized Parquet closure assertions that rely on 
isFree() still pass for on-heap and off-heap readers.



##########
sql/core/src/test/scala/org/apache/spark/sql/execution/datasources/parquet/ParquetTestAccess.scala:
##########
@@ -244,6 +245,10 @@ object ParquetTestAccess {
     f
   }
 
+  def columnVectors(reader: VectorizedParquetRecordReader): 
Array[ParquetColumnVector] = {
+    columnVectorsField.get(reader).asInstanceOf[Array[ParquetColumnVector]]

Review Comment:
   **Nit (P3):** This casts to (and returns) the package-private 
`ParquetColumnVector`, which this object's header rules out: "a package-private 
class is looked up by name here, never named in a `classOf` or a cast." The 
bridge exists for split-classloader runs (`spark-submit --jars`, e.g. the 
benchmarks). There this cast would fail with `IllegalAccessError`, even though 
the header now lists the field as bridged. It works today only because 
`ParquetVectorizedSuite` runs in a single classloader and already names the 
type directly.
   
   Suggest returning `Array[AnyRef]`, as `columnReadersHeld` does for the same 
field, and doing the typed cast in the suite's `checkColumnVectorsAreClosed`.
   
   **Verification:**
   - **Inspection:** The reflective Parquet test bridge contains no type, 
classOf or cast that names a package-private parquet class; such classes appear 
only in by-name lookups, consistent with its header.
   - **Regression:** The vectorized Parquet closure tests still pass and still 
assert release of every reserved vector after reader close.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to