From 95fae93ec856072460a1270909cccc19c9a34d7b Mon Sep 17 00:00:00 2001 From: dsgibbons Date: Tue, 3 Sep 2024 21:10:58 +0930 Subject: [PATCH 1/2] chore: ignore UP007 --- pyproject.toml | 1 + src/patito/_pydantic/column_info.py | 10 ++++---- tests/test_model.py | 20 ++++++++-------- tests/test_validators.py | 36 ++++++++++++++--------------- 4 files changed, 34 insertions(+), 33 deletions(-) diff --git a/pyproject.toml b/pyproject.toml index fe25ba5..dd1c878 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -133,6 +133,7 @@ extend-exclude= ["tests/__init__.py"] [tool.ruff.lint] select = ["E4", "E7", "E9", "F", "I", "B", "D", "UP"] +ignore = ["UP007"] [tool.ruff.lint.pydocstyle] convention = "google" diff --git a/src/patito/_pydantic/column_info.py b/src/patito/_pydantic/column_info.py index 4838688..260a4cd 100644 --- a/src/patito/_pydantic/column_info.py +++ b/src/patito/_pydantic/column_info.py @@ -97,20 +97,20 @@ class ColumnInfo(BaseModel, arbitrary_types_allowed=True): """ - allow_missing: Optional[bool] = None # noqa: UP007 + allow_missing: Optional[bool] = None dtype: Annotated[ - Optional[Union[DataTypeClass, DataType]], # noqa: UP007 + Optional[Union[DataTypeClass, DataType]], BeforeValidator(dtype_deserializer), ] = None constraints: Annotated[ - Optional[Union[pl.Expr, list[pl.Expr]]], # noqa: UP007 + Optional[Union[pl.Expr, list[pl.Expr]]], BeforeValidator(expr_deserializer), ] = None derived_from: Annotated[ - Optional[Union[str, pl.Expr]], # noqa: UP007 + Optional[Union[str, pl.Expr]], BeforeValidator(expr_or_col_name_deserializer), ] = None - unique: Optional[bool] = None # noqa : UP007 + unique: Optional[bool] = None def __repr__(self) -> str: """Print only Field attributes whose values are not default (mainly None).""" diff --git a/tests/test_model.py b/tests/test_model.py index 2d47498..0d0d73b 100644 --- a/tests/test_model.py +++ b/tests/test_model.py @@ -252,11 +252,11 @@ def test_model_joins() -> None: class Left(pt.Model): left: int = pt.Field(gt=20) - opt_left: Optional[int] = None # noqa: UP007 + opt_left: Optional[int] = None class Right(pt.Model): right: int = pt.Field(gt=20) - opt_right: Optional[int] = None # noqa: UP007 + opt_right: Optional[int] = None def test_model_validator(model: type[pt.Model]) -> None: """Test if all field validators have been included correctly.""" @@ -295,7 +295,7 @@ def test_model_selects() -> None: """It should produce models compatible with select statements.""" class MyModel(pt.Model): - a: Optional[int] # noqa: UP007 + a: Optional[int] b: int = pt.Field(gt=10) MySubModel = MyModel.select("b") @@ -321,7 +321,7 @@ def test_model_prefix_and_suffix() -> None: """It should produce models where all fields have been prefixed/suffixed.""" class MyModel(pt.Model): - a: Optional[int] # noqa: UP007 + a: Optional[int] b: str NewModel = MyModel.prefix("pre_").suffix("_post") @@ -333,7 +333,7 @@ def test_model_field_renaming() -> None: """It should be able to change its field names.""" class MyModel(pt.Model): - a: Optional[int] # noqa: UP007 + a: Optional[int] b: str NewModel = MyModel.rename({"b": "B"}) @@ -425,7 +425,7 @@ def validate_model_schema(schema) -> None: class ParentModel(pt.Model): a: int b: Model - c: Optional[float] = None # noqa: UP007 + c: Optional[float] = None schema = ParentModel.model_schema validate_model_schema( @@ -445,13 +445,13 @@ def test_nullable_columns() -> None: """Ensure columns are correctly nullable.""" class Test1(pt.Model): - foo: Optional[str] = pt.Field(dtype=pl.String) # noqa: UP007 + foo: Optional[str] = pt.Field(dtype=pl.String) assert Test1.nullable_columns == {"foo"} assert set(Test1.valid_dtypes["foo"]) == {pl.String} class Test2(pt.Model): - foo: Optional[int] = pt.Field(dtype=pl.UInt32) # noqa: UP007 + foo: Optional[int] = pt.Field(dtype=pl.UInt32) assert Test2.nullable_columns == {"foo"} assert set(Test2.valid_dtypes["foo"]) == {pl.UInt32} @@ -476,7 +476,7 @@ class Test2(pt.Model): with pytest.raises(ValueError, match="Invalid dtype UInt32"): class Test3(pt.Model): - foo: Optional[str] = pt.Field(dtype=pl.UInt32) # noqa: UP007 + foo: Optional[str] = pt.Field(dtype=pl.UInt32) Test3.validate_schema() @@ -536,7 +536,7 @@ class SubModel(pt.Model): class Test(pt.Model): a: int b: int - c: Optional[SubModel] # noqa: UP007 + c: Optional[SubModel] df = Test.examples({"a": range(5), "c": None}) Test.validate(df.cast()) diff --git a/tests/test_validators.py b/tests/test_validators.py index 86b6430..1826ce3 100644 --- a/tests/test_validators.py +++ b/tests/test_validators.py @@ -33,12 +33,12 @@ def test_is_optional() -> None: ) def test_is_optional_with_pipe_operator() -> None: """It should return True for optional types.""" - assert is_optional(Optional[int]) # noqa: UP007 + assert is_optional(Optional[int]) def test_dewrap_optional() -> None: """It should return the inner type of Optional types.""" - assert unwrap_optional(Optional[int]) is int # noqa: UP007 + assert unwrap_optional(Optional[int]) is int assert unwrap_optional(Union[int, None]) is int assert unwrap_optional(int) is int @@ -50,7 +50,7 @@ def test_dewrap_optional() -> None: def test_dewrap_optional_with_pipe_operator() -> None: """It should return the inner type of Optional types.""" assert ( - unwrap_optional(Optional[int]) is int # noqa: UP007 + unwrap_optional(Optional[int]) is int ) @@ -150,7 +150,7 @@ class OuterModel(pt.Model): OuterModel.validate(df_missing_nested_column_2) class OuterModelWithOptionalInner(pt.Model): - inner: Optional[InnerModel] # noqa: UP007 + inner: Optional[InnerModel] other: str df_missing_nested_column_2 = pl.DataFrame( @@ -176,7 +176,7 @@ class OuterModelWithListInner(pt.Model): OuterModelWithListInner.validate(df_missing_nested_column_2) class OuterModelWithOptionalListInner(pt.Model): - inner: Optional[list[InnerModel]] # noqa: UP007 + inner: Optional[list[InnerModel]] other: str df_missing_nested_column_2 = pl.DataFrame( @@ -188,7 +188,7 @@ class OuterModelWithOptionalListInner(pt.Model): OuterModelWithOptionalListInner.validate(df_missing_nested_column_2) class OuterModelWithListOptionalInner(pt.Model): - inner: list[Optional[InnerModel]] # noqa: UP007 + inner: list[Optional[InnerModel]] other: str df_missing_nested_column_2 = pl.DataFrame( @@ -203,7 +203,7 @@ class OuterModelWithListOptionalInner(pt.Model): OuterModelWithListOptionalInner.validate(df_missing_nested_column_2) class OuterModelWithOptionalListOptionalInner(pt.Model): - inner: Optional[list[Optional[InnerModel]]] # noqa: UP007 + inner: Optional[list[Optional[InnerModel]]] other: str df_missing_nested_column_2 = pl.DataFrame( @@ -276,7 +276,7 @@ def test_validate_non_nullable_columns() -> None: class SmallModel(pt.Model): column_1: int - column_2: Optional[int] = None # noqa: UP007 + column_2: Optional[int] = None # We insert nulls into a non-optional column, causing an exception wrong_nulls_df = pl.DataFrame().with_columns( @@ -496,7 +496,7 @@ class ABCEnum(enum.Enum): THREE = "c" class EnumModel(pt.Model): - column: Optional[ABCEnum] # noqa: UP007 + column: Optional[ABCEnum] valid_df = pl.DataFrame({"column": ["a", "b", "b", "c"]}) validate(dataframe=valid_df, schema=EnumModel) @@ -554,7 +554,7 @@ def test_optional_literal_enum_validation() -> None: """Test validation of optional typing.Literal-typed fields.""" class EnumModel(pt.Model): - column: Optional[Literal["a", "b", "c"]] # noqa: UP007 + column: Optional[Literal["a", "b", "c"]] valid_df = pl.DataFrame({"column": ["a", "b", "b", "c"]}) validate(dataframe=valid_df, schema=EnumModel) @@ -906,7 +906,7 @@ def test_optional_enum() -> None: class OptionalEnumModel(pt.Model): # Old type annotation syntax - optional_enum: Optional[Literal["A", "B"]] # noqa: UP007 + optional_enum: Optional[Literal["A", "B"]] df = pl.DataFrame({"optional_enum": ["A", "B", None]}) OptionalEnumModel.validate(df) @@ -921,9 +921,9 @@ def test_optional_pipe_operator() -> None: class OptionalEnumModel(pt.Model): # Old type annotation syntax - optional_enum_1: Optional[Literal["A", "B"]] # noqa: UP007 + optional_enum_1: Optional[Literal["A", "B"]] # New type annotation syntax - optional_enum_2: Optional[Literal["A", "B"]] # noqa: UP007 + optional_enum_2: Optional[Literal["A", "B"]] df = pl.DataFrame( { @@ -945,9 +945,9 @@ def test_validation_of_list_dtypes() -> None: class ListModel(pt.Model): int_list: list[int] - int_or_null_list: list[Optional[int]] # noqa: UP007 - nullable_int_list: Optional[list[int]] # noqa: UP007 - nullable_int_or_null_list: Optional[list[Optional[int]]] # noqa: UP007 + int_or_null_list: list[Optional[int]] + nullable_int_list: Optional[list[int]] + nullable_int_or_null_list: Optional[list[Optional[int]]] valid_df = pl.DataFrame( { @@ -987,7 +987,7 @@ class Outer(pt.Model): id: str code: str label: str - inner_types: Optional[list[Inner]] # noqa: UP007 + inner_types: Optional[list[Inner]] good_df = pl.DataFrame( { @@ -1025,7 +1025,7 @@ def test_nested_field_attrs() -> None: """Ensure that constraints are respected even when embedded inside 'anyOf'.""" class Test(pt.Model): - foo: Optional[int] = pt.Field( # noqa: UP007 + foo: Optional[int] = pt.Field( dtype=pl.Int64, ge=0, le=100, constraints=pt.field.sum() == 100 ) From 3dd17a2f4e3f902c0fbc48e8381386dca3109cf0 Mon Sep 17 00:00:00 2001 From: dsgibbons Date: Tue, 3 Sep 2024 21:12:26 +0930 Subject: [PATCH 2/2] chore: ruff --- tests/test_validators.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/tests/test_validators.py b/tests/test_validators.py index 1826ce3..2a3403f 100644 --- a/tests/test_validators.py +++ b/tests/test_validators.py @@ -49,9 +49,7 @@ def test_dewrap_optional() -> None: ) def test_dewrap_optional_with_pipe_operator() -> None: """It should return the inner type of Optional types.""" - assert ( - unwrap_optional(Optional[int]) is int - ) + assert unwrap_optional(Optional[int]) is int def test_validation_returns_df() -> None: