chore: import upstream snapshot with attribution

This commit is contained in:
wehub-resource-sync
2026-07-13 13:17:40 +08:00
commit f1825c8ceb
10096 changed files with 2364182 additions and 0 deletions
@@ -0,0 +1,213 @@
import os
import pandas as pd
import pyarrow as pa
import pyarrow.parquet as pq
import pytest
from packaging.version import Version
import ray
from ray.data import Schema
from ray.data._internal.util import rows_same
from ray.data.block import BlockAccessor
from ray.data.datasource.path_util import _unwrap_protocol
from ray.data.tests.conftest import * # noqa
from ray.data.tests.mock_http_server import * # noqa
from ray.tests.conftest import * # noqa
def df_to_csv(dataframe, path, **kwargs):
dataframe.to_csv(path, **kwargs)
def test_csv_read(
ray_start_regular_shared, tmp_path, target_max_block_size_infinite_or_default
):
# Single file.
df1 = pd.DataFrame({"one": [1, 2, 3], "two": ["a", "b", "c"]})
path1 = os.path.join(tmp_path, "test1.csv")
df1.to_csv(path1, index=False)
ds = ray.data.read_csv(path1, partitioning=None)
dsdf = ds.to_pandas().sort_values(by=["one", "two"]).reset_index(drop=True)
pd.testing.assert_frame_equal(df1.astype(dsdf.dtypes.to_dict()), dsdf)
# Test metadata ops.
assert ds.count() == 3
assert ds.input_files() == [_unwrap_protocol(path1)]
assert ds.schema() == Schema(pa.schema([("one", pa.int64()), ("two", pa.string())]))
# Two files, override_num_blocks=2.
df2 = pd.DataFrame({"one": [4, 5, 6], "two": ["e", "f", "g"]})
path2 = os.path.join(tmp_path, "test2.csv")
df2.to_csv(path2, index=False)
ds = ray.data.read_csv([path1, path2], override_num_blocks=2, partitioning=None)
dsdf = ds.to_pandas().sort_values(by=["one", "two"]).reset_index(drop=True)
df = pd.concat([df1, df2], ignore_index=True)
pd.testing.assert_frame_equal(df.astype(dsdf.dtypes.to_dict()), dsdf)
# Test metadata ops.
for entry in ds._execute().blocks:
assert (
# pyrefly: ignore[no-matching-overload]
BlockAccessor.for_block(ray.get(entry.ref)).size_bytes()
== entry.metadata.size_bytes
)
# Three files, override_num_blocks=2.
df3 = pd.DataFrame({"one": [7, 8, 9], "two": ["h", "i", "j"]})
path3 = os.path.join(tmp_path, "test3.csv")
df3.to_csv(path3, index=False)
ds = ray.data.read_csv(
[path1, path2, path3],
override_num_blocks=2,
partitioning=None,
)
df = pd.concat([df1, df2, df3], ignore_index=True)
dsdf = ds.to_pandas().sort_values(by=["one", "two"]).reset_index(drop=True)
pd.testing.assert_frame_equal(df.astype(dsdf.dtypes.to_dict()), dsdf)
def test_csv_write(
ray_start_regular_shared, tmp_path, target_max_block_size_infinite_or_default
):
input_df = pd.DataFrame({"id": [0]})
ds = ray.data.from_blocks([input_df])
ds.write_csv(tmp_path)
output_df = pd.concat(
[
pd.read_csv(os.path.join(tmp_path, filename))
for filename in os.listdir(tmp_path)
]
)
assert rows_same(input_df, output_df)
@pytest.mark.parametrize("override_num_blocks", [None, 2])
def test_csv_roundtrip(
ray_start_regular_shared,
tmp_path,
override_num_blocks,
target_max_block_size_infinite_or_default,
):
df = pd.DataFrame({"one": [1, 2, 3], "two": ["a", "b", "c"]})
ds = ray.data.from_pandas([df], override_num_blocks=override_num_blocks)
ds.write_csv(tmp_path)
ds2 = ray.data.read_csv(tmp_path)
ds2df = ds2.to_pandas()
assert rows_same(ds2df, df)
for entry in ds2._execute().blocks:
# pyrefly: ignore[no-matching-overload]
assert (
BlockAccessor.for_block(ray.get(entry.ref)).size_bytes()
== entry.metadata.size_bytes
)
def test_csv_read_invalid_format(ray_start_regular_shared, tmp_path):
df = pd.DataFrame({"one": [1, 2, 3], "two": ["a", "b", "c"]})
# Setup: CSV and Parquet files in the same directory.
csv_path = os.path.join(tmp_path, "test.csv")
df.to_csv(csv_path, index=False)
table = pa.Table.from_pandas(df)
parquet_path = os.path.join(tmp_path, "test.parquet")
pq.write_table(table, parquet_path)
# Test 1: CSV parser should fail on Parquet file.
error_message = "Failed to read CSV file"
with pytest.raises(ValueError, match=error_message):
ray.data.read_csv(parquet_path).materialize()
# Test 2: CSV parser should fail when directory contains non-CSV files.
with pytest.raises(ValueError, match=error_message):
ray.data.read_csv(tmp_path).materialize()
def test_csv_read_no_header(ray_start_regular_shared, tmp_path):
from pyarrow import csv
file_path = os.path.join(tmp_path, "test.csv")
df = pd.DataFrame({"one": [1, 2, 3], "two": ["a", "b", "c"]})
df.to_csv(file_path, index=False, header=False)
ds = ray.data.read_csv(
file_path,
read_options=csv.ReadOptions(column_names=["one", "two"]),
)
out_df = ds.to_pandas()
pd.testing.assert_frame_equal(df.astype(out_df.dtypes.to_dict()), out_df)
def test_csv_read_with_column_type_specified(ray_start_regular_shared, tmp_path):
from pyarrow import csv
file_path = os.path.join(tmp_path, "test.csv")
df = pd.DataFrame({"one": [1, 2, 3e1], "two": ["a", "b", "c"]})
df.to_csv(file_path, index=False)
# Incorrect to parse scientific notation in int64 as PyArrow represents
# it as double.
with pytest.raises(ValueError):
ray.data.read_csv(
file_path,
convert_options=csv.ConvertOptions(
column_types={"one": "int64", "two": "string"}
),
).schema()
# Parsing scientific notation in double should work.
ds = ray.data.read_csv(
file_path,
convert_options=csv.ConvertOptions(
column_types={"one": "float64", "two": "string"}
),
)
expected_df = pd.DataFrame({"one": [1.0, 2.0, 30.0], "two": ["a", "b", "c"]})
actual_df = ds.to_pandas()
pd.testing.assert_frame_equal(
expected_df.astype(actual_df.dtypes.to_dict()), actual_df
)
@pytest.mark.skipif(
Version(pa.__version__) < Version("7.0.0"),
reason="invalid_row_handler was added in pyarrow 7.0.0",
)
def test_csv_invalid_file_handler(
ray_start_regular_shared, tmp_path, target_max_block_size_infinite_or_default
):
from pyarrow import csv
invalid_txt = "f1,f2\n2,3\nx\n4,5"
invalid_file = os.path.join(tmp_path, "invalid.csv")
with open(invalid_file, "wt") as f:
f.write(invalid_txt)
ray.data.read_csv(
invalid_file,
parse_options=csv.ParseOptions(
delimiter=",", invalid_row_handler=lambda i: "skip"
),
)
def test_read_example_data(ray_start_regular_shared, tmp_path):
ds = ray.data.read_csv("example://iris.csv")
assert ds.count() == 150
assert ds.take(1) == [
{
"sepal.length": 5.1,
"sepal.width": 3.5,
"petal.length": 1.4,
"petal.width": 0.2,
"variety": "Setosa",
}
]
if __name__ == "__main__":
import sys
sys.exit(pytest.main(["-v", __file__]))