Skip to content

Commit c9970ab

Browse files
committed
Fix splitability tests for the Delta scan with deletion vectors
Signed-off-by: Jihoon Son <ghoonson@gmail.com>
1 parent 19e6502 commit c9970ab

1 file changed

Lines changed: 23 additions & 9 deletions

File tree

integration_tests/src/main/python/delta_lake_test.py

Lines changed: 23 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -282,7 +282,7 @@ def test_delta_empty_deletion_vector_read(spark_tmp_path, use_chunked_reader, us
282282
do_test_delta_deletion_vector_read(data_path, use_cdf, conf, f"SELECT * FROM delta.`{data_path}`")
283283

284284

285-
def do_test_scan_split(spark_tmp_path, enable_deletion_vectors, expected_num_partitions, post_setup_table_func=None):
285+
def do_test_scan_split(spark_tmp_path, enable_deletion_vectors, expected_num_partitions, post_setup_table_func=None, conf=None):
286286
import os
287287
import math
288288

@@ -296,8 +296,8 @@ def setup_tables(spark):
296296
post_setup_table_func(spark, data_path)
297297
target_num_row_groups = 2
298298
row_group_size = int(num_rows * 4 / target_num_row_groups) # num_rows * 4 bytes per int / target_num_row_groups
299-
conf = {"parquet.block.size": str(row_group_size)}
300-
with_cpu_session(setup_tables, conf)
299+
table_setup_conf = {"parquet.block.size": str(row_group_size)}
300+
with_cpu_session(setup_tables, table_setup_conf)
301301
# Verify that we have 1 file with 2 row groups
302302
def verify_files_and_row_groups():
303303
# list files in data_path
@@ -314,12 +314,14 @@ def verify_files_and_row_groups():
314314
data_file = verify_files_and_row_groups()
315315
file_size = os.path.getsize(data_file)
316316

317-
conf = {"spark.sql.files.maxPartitionBytes": str(math.ceil(file_size/2.0))}
317+
read_conf = {"spark.sql.files.maxPartitionBytes": str(math.ceil(file_size/2.0))}
318+
if conf:
319+
read_conf = copy_and_update(read_conf, conf)
318320

319321
def get_num_partitions(spark):
320322
df = spark.sql("SELECT * from delta.`{}`".format(data_path))
321323
return df.rdd.getNumPartitions()
322-
num_partitions = with_gpu_session(get_num_partitions, conf=conf)
324+
num_partitions = with_gpu_session(get_num_partitions, conf=read_conf)
323325
assert num_partitions == expected_num_partitions, f"Expected {expected_num_partitions} partitions for split read"
324326

325327

@@ -343,30 +345,42 @@ def test_delta_scan_split_with_DV_enabled_with_no_DV(spark_tmp_path):
343345

344346
@allow_non_gpu(*delta_meta_allow)
345347
@delta_lake
348+
@pytest.mark.parametrize("pushdown_dv_predicate", [True, False], ids=idfn)
346349
@pytest.mark.skipif(is_databricks_runtime(),
347350
reason="Deletion vector scan is not supported on Databricks")
348351
@pytest.mark.skipif(is_before_spark_353(),
349352
reason="Spark-RAPIDS supports scan with deletion vectors starting in Spark 3.5.3")
350-
def test_delta_scan_split_with_DV_enabled_with_DVs(spark_tmp_path):
353+
def test_delta_scan_split_with_DV_enabled_with_DVs(spark_tmp_path, pushdown_dv_predicate):
351354
def do_delete(spark, data_path):
352355
num_deleted = spark.sql(f"DELETE FROM delta.`{data_path}` WHERE a = 0").collect()[0][0]
353356
assert num_deleted > 0, "Expected some rows to be deleted"
354-
do_test_scan_split(spark_tmp_path, enable_deletion_vectors=True, expected_num_partitions=1, post_setup_table_func=do_delete)
357+
# The cuDF-based reader (GpuDeltaParquetFileFormat2), which is used when dv_predicate_pushdown is True, support the file split,
358+
# whereas the scala reader (GpuDeltaParquetFileFormat) does not support it.
359+
# So we expect 2 partitions when dv_predicate_pushdown is True, and 1 partition when it is False.
360+
expected_num_partitions = 2 if pushdown_dv_predicate else 1
361+
conf = {"spark.rapids.sql.delta.deletionVectors.predicatePushdown.enabled": f"{pushdown_dv_predicate}"}
362+
do_test_scan_split(spark_tmp_path, enable_deletion_vectors=True, expected_num_partitions=expected_num_partitions, post_setup_table_func=do_delete, conf=conf)
355363

356364

357365
@allow_non_gpu(*delta_meta_allow)
358366
@delta_lake
367+
@pytest.mark.parametrize("pushdown_dv_predicate", [True, False], ids=idfn)
359368
@pytest.mark.skipif(is_databricks_runtime(),
360369
reason="Deletion vector scan is not supported on Databricks")
361370
@pytest.mark.skipif(is_before_spark_353(),
362371
reason="Spark-RAPIDS supports scan with deletion vectors starting in Spark 3.5.3")
363-
def test_delta_scan_split_with_DV_disabled_with_DVs(spark_tmp_path):
372+
def test_delta_scan_split_with_DV_disabled_with_DVs(spark_tmp_path, pushdown_dv_predicate):
364373
def do_delete_and_disable_DV(spark, data_path):
365374
num_deleted = spark.sql(f"DELETE FROM delta.`{data_path}` WHERE a = 0").collect()[0][0]
366375
assert num_deleted > 0, "Expected some rows to be deleted"
367376
spark.sql(f"ALTER TABLE delta.`{data_path}` SET TBLPROPERTIES " +
368377
"('delta.enableDeletionVectors' = 'false')")
369-
do_test_scan_split(spark_tmp_path, enable_deletion_vectors=True, expected_num_partitions=1, post_setup_table_func=do_delete_and_disable_DV)
378+
# The cuDF-based reader (GpuDeltaParquetFileFormat2), which is used when dv_predicate_pushdown is True, support the file split,
379+
# whereas the scala reader (GpuDeltaParquetFileFormat) does not support it.
380+
# So we expect 2 partitions when dv_predicate_pushdown is True, and 1 partition when it is False.
381+
expected_num_partitions = 2 if pushdown_dv_predicate else 1
382+
conf = {"spark.rapids.sql.delta.deletionVectors.predicatePushdown.enabled": f"{pushdown_dv_predicate}"}
383+
do_test_scan_split(spark_tmp_path, enable_deletion_vectors=True, expected_num_partitions=expected_num_partitions, post_setup_table_func=do_delete_and_disable_DV, conf=conf)
370384

371385

372386
@allow_non_gpu(*delta_meta_allow)

0 commit comments

Comments
 (0)