Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Test regressions with pytest 8.0.0 #8674

Closed
1 task done
mgorny opened this issue Jan 30, 2024 · 3 comments · Fixed by #8678
Closed
1 task done

Test regressions with pytest 8.0.0 #8674

mgorny opened this issue Jan 30, 2024 · 3 comments · Fixed by #8678
Assignees
Labels
bug V2 Bug related to Pydantic V2

Comments

@mgorny
Copy link
Contributor

mgorny commented Jan 30, 2024

Initial Checks

  • I confirm that I'm using Pydantic V2

Description

When running the test suite using pytest 8.0.0, the following test regressions are seen:

FAILED tests/test_validators.py::test_use_bare - Failed: DID NOT WARN. No warnings of type (<class 'pydantic.warnings.PydanticDeprecatedSince20'>,) were emitted.
FAILED tests/test_validators.py::test_use_no_fields - Failed: DID NOT WARN. No warnings of type (<class 'pydantic.warnings.PydanticDeprecatedSince20'>,) were emitted.
FAILED tests/test_validators.py::test_validator_bad_fields_throws_configerror - Failed: DID NOT WARN. No warnings of type (<class 'pydantic.warnings.PydanticDeprecatedSince20'>,) were emitted.
FAILED tests/test_validators.py::test_assert_raises_validation_error - assert [{'ctx': {'er...+ snap', ...}] == [{'ctx': {'er...+ snap', ...}]
Full output
$ python -m pytest -Wdefault  
========================================================= test session starts =========================================================
platform linux -- Python 3.11.7, pytest-8.0.0, pluggy-1.4.0
benchmark: 4.0.0 (defaults: timer=time.perf_counter disable_gc=False min_rounds=5 min_time=0.000005 max_time=1.0 calibration_precision=10 warmup=True warmup_iterations=100000)
rootdir: /tmp/pydantic
configfile: pyproject.toml
testpaths: tests
plugins: benchmark-4.0.0, examples-0.0.10, mock-3.12.0, Faker-22.6.0
collected 4902 items                                                                                                                  

tests/benchmarks/test_fastapi_startup_generics.py .                                                                             [  0%]
tests/benchmarks/test_fastapi_startup_simple.py .                                                                               [  0%]
tests/benchmarks/test_north_star.py ........                                                                                    [  0%]
tests/mypy/test_mypy.py ssssssssssssssssssssssssssssssssssssssssssssssssssssss                                                  [  1%]
tests/plugin/test_plugin.py s                                                                                                   [  1%]
tests/test_abc.py .s                                                                                                            [  1%]
tests/test_aliases.py ......................................................                                                    [  2%]
tests/test_annotated.py .............................                                                                           [  3%]
tests/test_assert_in_validators.py .                                                                                            [  3%]
tests/test_callable.py ........                                                                                                 [  3%]
tests/test_color.py ..........................................................................................                  [  5%]
tests/test_computed_fields.py ....................sss....x...                                                                   [  5%]
tests/test_config.py .................................................................                                          [  7%]
tests/test_construction.py ..............................................                                                       [  7%]
tests/test_create_model.py ............................................                                                         [  8%]
tests/test_dataclasses.py ..................................................................................................... [ 10%]
.........s.....................ss.....................................................................                          [ 13%]
tests/test_datetime.py ........................................................................................................ [ 15%]
........................................................................................                                        [ 16%]
tests/test_decorators.py ......                                                                                                 [ 17%]
tests/test_deprecated.py ...............................................                                                        [ 18%]
tests/test_deprecated_validate_arguments.py .....................                                                               [ 18%]
tests/test_discriminated_union.py ..........................................................                                    [ 19%]
tests/test_docs.py ssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssss [ 21%]
sssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssss [ 24%]
sssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssss [ 27%]
sssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssssss [ 29%]
sssssssssssssssssssssssssssssssss..                                                                                             [ 30%]
tests/test_docs_extraction.py .............                                                                                     [ 30%]
tests/test_edge_cases.py ...................................................................................................... [ 32%]
............s...................................sss...................                                                          [ 34%]
tests/test_errors.py ...                                                                                                        [ 34%]
tests/test_exports.py ......................................................................................................... [ 36%]
.................................                                                                                               [ 36%]
tests/test_fastapi_json_schema.py ..                                                                                            [ 37%]
tests/test_fields.py .......                                                                                                    [ 37%]
tests/test_forward_ref.py ...........................................                                                           [ 38%]
tests/test_generics.py ..................................s.........s............................................sx.......xx.... [ 40%]
........                                                                                                                        [ 40%]
tests/test_internal.py .........s.                                                                                              [ 40%]
tests/test_json.py ......................................................                                                       [ 41%]
tests/test_json_schema.py ..................................................................................................... [ 43%]
............................................................................................................................... [ 46%]
.................................................................................x............................................. [ 48%]
....................                                                                                                            [ 49%]
tests/test_main.py ....................................................................................................ssssssss [ 51%]
sssssssssssssssss.........................................................................................................      [ 53%]
tests/test_migration.py ....................................................................................................... [ 56%]
.............................................................................................................................   [ 58%]
tests/test_model_signature.py .............s.                                                                                   [ 58%]
tests/test_model_validator.py ........                                                                                          [ 59%]
tests/test_networks.py ........................................................................................................ [ 61%]
.................................................x............................................................................. [ 63%]
s.                                                                                                                              [ 63%]
tests/test_networks_ipaddress.py .............................................................................................. [ 65%]
.....................................................................                                                           [ 67%]
tests/test_parse.py ...........                                                                                                 [ 67%]
tests/test_pickle.py .....................                                                                                      [ 67%]
tests/test_plugins.py .............                                                                                             [ 68%]
tests/test_private_attributes.py ........................                                                                       [ 68%]
tests/test_rich_repr.py ..                                                                                                      [ 68%]
tests/test_root_model.py .........................................................................                              [ 70%]
tests/test_serialize.py ............................................................................                            [ 71%]
tests/test_strict.py ......                                                                                                     [ 71%]
tests/test_structural_pattern_matching.py .                                                                                     [ 71%]
tests/test_tools.py .........                                                                                                   [ 71%]
tests/test_type_adapter.py ....................x...........................                                                     [ 72%]
tests/test_type_alias_type.py ........x....                                                                                     [ 73%]
tests/test_types.py ..................................................s........................................................ [ 75%]
............................................................................................................................... [ 78%]
..................................................x......ss.................................................................... [ 80%]
............................................................................................................................... [ 83%]
............................................................................................................................... [ 85%]
............................................................................................................................... [ 88%]
....................................                                                                                            [ 89%]
tests/test_types_namedtuple.py ..........                                                                                       [ 89%]
tests/test_types_payment_card_number.py ..............................................                                          [ 90%]
tests/test_types_typeddict.py ..s.s.s.s.s.s.s.s.s.s.s.s..s.s.s.s.s.sss..........s.s.s.s.s.s.......                              [ 91%]
tests/test_typing.py ............s                                                                                              [ 91%]
tests/test_utils.py ..............................................................................s............................ [ 94%]
.................................................................                                                               [ 95%]
tests/test_v1.py ..                                                                                                             [ 95%]
tests/test_validate_call.py .......................................                                                             [ 96%]
tests/test_validators.py ............................F.F.F...................................F................................. [ 98%]
...............................................................                                                                 [ 99%]
tests/test_validators_dataclass.py ........                                                                                     [ 99%]
tests/test_version.py ......                                                                                                    [ 99%]
tests/test_warnings.py .....                                                                                                    [100%]

============================================================== FAILURES ===============================================================
____________________________________________________________ test_use_bare ____________________________________________________________

    class Model(BaseModel):
        a: str
    
        with pytest.warns(PydanticDeprecatedSince20, match=V1_VALIDATOR_DEPRECATION_MATCH):
    
>           @validator

tests/test_validators.py:537: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _

__field = <function test_use_bare.<locals>.Model.checker at 0x7fd4605e1bc0>, pre = False, each_item = False, always = False
check_fields = None

    def validator(
        __field: str,
        *fields: str,
        pre: bool = False,
        each_item: bool = False,
        always: bool = False,
        check_fields: bool | None = None,
        allow_reuse: bool = False,
    ) -> Callable[[_V1ValidatorType], _V1ValidatorType]:
        """Decorate methods on the class indicating that they should be used to validate fields.
    
        Args:
            __field (str): The first field the validator should be called on; this is separate
                from `fields` to ensure an error is raised if you don't pass at least one.
            *fields (str): Additional field(s) the validator should be called on.
            pre (bool, optional): Whether this validator should be called before the standard
                validators (else after). Defaults to False.
            each_item (bool, optional): For complex objects (sets, lists etc.) whether to validate
                individual elements rather than the whole object. Defaults to False.
            always (bool, optional): Whether this method and other validators should be called even if
                the value is missing. Defaults to False.
            check_fields (bool | None, optional): Whether to check that the fields actually exist on the model.
                Defaults to None.
            allow_reuse (bool, optional): Whether to track and raise an error if another validator refers to
                the decorated function. Defaults to False.
    
        Returns:
            Callable: A decorator that can be used to decorate a
                function to be used as a validator.
        """
        if allow_reuse is True:  # pragma: no cover
            warn(_ALLOW_REUSE_WARNING_MESSAGE, DeprecationWarning)
        fields = tuple((__field, *fields))
        if isinstance(fields[0], FunctionType):
>           raise PydanticUserError(
                '`@validator` should be used with fields and keyword arguments, not bare. '
                "E.g. usage should be `@validator('<field_name>', ...)`",
                code='validator-no-fields',
E               pydantic.errors.PydanticUserError: `@validator` should be used with fields and keyword arguments, not bare. E.g. usage should be `@validator('<field_name>', ...)`
E               
E               For further information visit https://errors.pydantic.dev/2.6/u/validator-no-fields

pydantic/deprecated/class_validators.py:116: PydanticUserError

During handling of the above exception, another exception occurred:

    def test_use_bare():
        with pytest.raises(TypeError, match='`@validator` should be used with fields'):
    
>           class Model(BaseModel):

tests/test_validators.py:532: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _

    class Model(BaseModel):
        a: str
    
>       with pytest.warns(PydanticDeprecatedSince20, match=V1_VALIDATOR_DEPRECATION_MATCH):
E       Failed: DID NOT WARN. No warnings of type (<class 'pydantic.warnings.PydanticDeprecatedSince20'>,) were emitted.
E        Emitted warnings: [].

tests/test_validators.py:535: Failed
_________________________________________________________ test_use_no_fields __________________________________________________________

    class Model(BaseModel):
        a: str
    
        with pytest.warns(PydanticDeprecatedSince20, match=V1_VALIDATOR_DEPRECATION_MATCH):
    
>           @validator()
E           TypeError: validator() missing 1 required positional argument: '__field'

tests/test_validators.py:561: TypeError

During handling of the above exception, another exception occurred:

    def test_use_no_fields():
        with pytest.raises(TypeError, match=re.escape("validator() missing 1 required positional argument: '__field'")):
    
>           class Model(BaseModel):

tests/test_validators.py:556: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _

    class Model(BaseModel):
        a: str
    
>       with pytest.warns(PydanticDeprecatedSince20, match=V1_VALIDATOR_DEPRECATION_MATCH):
E       Failed: DID NOT WARN. No warnings of type (<class 'pydantic.warnings.PydanticDeprecatedSince20'>,) were emitted.
E        Emitted warnings: [].

tests/test_validators.py:559: Failed
____________________________________________ test_validator_bad_fields_throws_configerror _____________________________________________

    class Model(BaseModel):
        a: str
        b: str
    
        with pytest.warns(PydanticDeprecatedSince20, match=V1_VALIDATOR_DEPRECATION_MATCH):
    
>           @validator(['a', 'b'])

tests/test_validators.py:592: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _

__field = ['a', 'b'], pre = False, each_item = False, always = False, check_fields = None

    def validator(
        __field: str,
        *fields: str,
        pre: bool = False,
        each_item: bool = False,
        always: bool = False,
        check_fields: bool | None = None,
        allow_reuse: bool = False,
    ) -> Callable[[_V1ValidatorType], _V1ValidatorType]:
        """Decorate methods on the class indicating that they should be used to validate fields.
    
        Args:
            __field (str): The first field the validator should be called on; this is separate
                from `fields` to ensure an error is raised if you don't pass at least one.
            *fields (str): Additional field(s) the validator should be called on.
            pre (bool, optional): Whether this validator should be called before the standard
                validators (else after). Defaults to False.
            each_item (bool, optional): For complex objects (sets, lists etc.) whether to validate
                individual elements rather than the whole object. Defaults to False.
            always (bool, optional): Whether this method and other validators should be called even if
                the value is missing. Defaults to False.
            check_fields (bool | None, optional): Whether to check that the fields actually exist on the model.
                Defaults to None.
            allow_reuse (bool, optional): Whether to track and raise an error if another validator refers to
                the decorated function. Defaults to False.
    
        Returns:
            Callable: A decorator that can be used to decorate a
                function to be used as a validator.
        """
        if allow_reuse is True:  # pragma: no cover
            warn(_ALLOW_REUSE_WARNING_MESSAGE, DeprecationWarning)
        fields = tuple((__field, *fields))
        if isinstance(fields[0], FunctionType):
            raise PydanticUserError(
                '`@validator` should be used with fields and keyword arguments, not bare. '
                "E.g. usage should be `@validator('<field_name>', ...)`",
                code='validator-no-fields',
            )
        elif not all(isinstance(field, str) for field in fields):
>           raise PydanticUserError(
                '`@validator` fields should be passed as separate string args. '
                "E.g. usage should be `@validator('<field_name_1>', '<field_name_2>', ...)`",
                code='validator-invalid-fields',
            )
E           pydantic.errors.PydanticUserError: `@validator` fields should be passed as separate string args. E.g. usage should be `@validator('<field_name_1>', '<field_name_2>', ...)`
E           
E           For further information visit https://errors.pydantic.dev/2.6/u/validator-invalid-fields

pydantic/deprecated/class_validators.py:122: PydanticUserError

During handling of the above exception, another exception occurred:

    def test_validator_bad_fields_throws_configerror():
        """
        Attempts to create a validator with fields set as a list of strings,
        rather than just multiple string args. Expects ConfigError to be raised.
        """
        with pytest.raises(TypeError, match='`@validator` fields should be passed as separate string args.'):
    
>           class Model(BaseModel):

tests/test_validators.py:586: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _

    class Model(BaseModel):
        a: str
        b: str
    
>       with pytest.warns(PydanticDeprecatedSince20, match=V1_VALIDATOR_DEPRECATION_MATCH):
E       Failed: DID NOT WARN. No warnings of type (<class 'pydantic.warnings.PydanticDeprecatedSince20'>,) were emitted.
E        Emitted warnings: [].

tests/test_validators.py:590: Failed
_________________________________________________ test_assert_raises_validation_error _________________________________________________

    def test_assert_raises_validation_error():
        class Model(BaseModel):
            a: str
    
            @field_validator('a')
            @classmethod
            def check_a(cls, v: Any):
                assert v == 'a', 'invalid a'
                return v
    
        Model(a='a')
    
        with pytest.raises(ValidationError) as exc_info:
            Model(a='snap')
        injected_by_pytest = "assert 'snap' == 'a'\n  - a\n  + snap"
>       assert exc_info.value.errors(include_url=False) == [
            {
                'ctx': {'error': HasRepr(repr(AssertionError("invalid a\nassert 'snap' == 'a'\n  - a\n  + snap")))},
                'input': 'snap',
                'loc': ('a',),
                'msg': f'Assertion failed, invalid a\n{injected_by_pytest}',
                'type': 'assertion_error',
            }
        ]
E       assert [{'ctx': {'er...+ snap', ...}] == [{'ctx': {'er...+ snap', ...}]
E         
E         At index 0 diff: {'type': 'assertion_error', 'loc': ('a',), 'msg': "Assertion failed, invalid a\nassert 'snap' == 'a'\n  \n  - a\n  + snap", 'input': 'snap', 'ctx': {'error': AssertionError("invalid a\nassert 'snap' == 'a'\n  \n  - a\n  + snap")}} != {'ctx': {'error': HasRepr('AssertionError("invalid a\\nassert \'snap\' == \'a\'\\n  - a\\n  + snap")')}, 'input': 'snap', 'loc': ('a',), 'msg': "Assertion failed, invalid a\nassert 'snap' == 'a'\n  - a\n  + snap", 'type': 'assertion_error'}
E         Use -v to get more diff

tests/test_validators.py:1311: AssertionError
========================================================== warnings summary ===========================================================
tests/test_annotated.py::test_annotated_instance_exceptions[<lambda>-value0-empty_init_ctx0]
  /tmp/pydantic/.venv/lib/python3.11/site-packages/_pytest/_code/code.py:703: DeprecationWarning: PYDANTIC_ERRORS_OMIT_URL is deprecated, use PYDANTIC_ERRORS_INCLUDE_URL instead
    str(exc),

tests/test_config.py::TestsBaseConfig::test_config_class_is_deprecated
  /tmp/pydantic/tests/test_config.py:353: PydanticDeprecatedSince20: BaseConfig is deprecated. Use the `pydantic.ConfigDict` instead. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    class Config(BaseConfig):

tests/test_config.py::TestsBaseConfig::test_config_class_attributes_are_deprecated
  /tmp/pydantic/tests/test_config.py:367: PydanticDeprecatedSince20: BaseConfig is deprecated. Use the `pydantic.ConfigDict` instead. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    assert BaseConfig().validate_assignment is False

tests/test_config.py::TestsBaseConfig::test_config_class_attributes_are_deprecated
  /tmp/pydantic/tests/test_config.py:374: PydanticDeprecatedSince20: BaseConfig is deprecated. Use the `pydantic.ConfigDict` instead. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    class Config(BaseConfig):

tests/test_deprecated.py::test_parse_raw_pass
tests/test_deprecated.py::test_parse_raw_pass_fail
  /tmp/pydantic/pydantic/main.py:1098: PydanticDeprecatedSince20: `load_str_bytes` is deprecated. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    obj = parse.load_str_bytes(

tests/test_deprecated.py::test_field_include_deprecation
  /tmp/pydantic/pydantic/fields.py:754: PydanticDeprecatedSince20: Using extra keyword arguments on `Field` is deprecated and will be removed. Use `json_schema_extra` instead. (Extra keys: 'include'). Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    warn(

tests/test_deprecated.py::test_parse_file
  /tmp/pydantic/pydantic/main.py:1150: PydanticDeprecatedSince20: `load_file` is deprecated. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    obj = parse.load_file(

tests/test_deprecated.py::test_parse_file
tests/test_deprecated.py::test_deprecated_module
  /tmp/pydantic/pydantic/deprecated/parse.py:78: PydanticDeprecatedSince20: `load_str_bytes` is deprecated. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    return load_str_bytes(

tests/test_deprecated.py::test_parse_file
  /tmp/pydantic/pydantic/main.py:1070: PydanticDeprecatedSince20: The `parse_obj` method is deprecated; use `model_validate` instead. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    warnings.warn(

tests/test_deprecated.py::test_deprecated_module
  /tmp/pydantic/pydantic/deprecated/tools.py:101: PydanticDeprecatedSince20: `schema_of` is deprecated. Use `pydantic.TypeAdapter.json_schema` instead. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    schema_of(type_, title=title, by_alias=by_alias, ref_template=ref_template, schema_generator=schema_generator),

tests/test_deprecated.py::test_deprecated_module
  /tmp/pydantic/pydantic/deprecated/json.py:131: PydanticDeprecatedSince20: `pydantic_encoder` is deprecated, use `pydantic_core.to_jsonable_python` instead. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    return pydantic_encoder(obj)

tests/test_json_schema.py::test_callable_fallback_with_non_serializable_default[Cannot generate a JsonSchema for core_schema.CallableSchema \\[skipped-choice\\]]
  /tmp/pydantic/pydantic/json_schema.py:2099: PydanticJsonSchemaWarning: Default value <function test_callable_fallback_with_non_serializable_default.<locals>.Model.<lambda> at 0x7fd463bac2c0> is not JSON serializable; excluding default from JSON schema [non-serializable-default]
    warnings.warn(message, PydanticJsonSchemaWarning)

tests/test_json_schema.py::test_callable_fallback_with_non_serializable_default[Default value .* is not JSON serializable; excluding default from JSON schema \\[non-serializable-default\\]]
  /tmp/pydantic/pydantic/json_schema.py:2099: PydanticJsonSchemaWarning: Cannot generate a JsonSchema for core_schema.CallableSchema [skipped-choice]
    warnings.warn(message, PydanticJsonSchemaWarning)

tests/test_validators.py::test_root_validator_allow_reuse_same_field
  /tmp/pydantic/tests/test_validators.py:2516: PydanticDeprecatedSince20: Pydantic V1 style `@root_validator` validators are deprecated. You should migrate to Pydantic V2 style `@model_validator` validators, see the migration guide for more details. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    @root_validator(skip_on_failure=True)

tests/test_validators.py::test_root_validator_allow_reuse_same_field
  /tmp/pydantic/tests/test_validators.py:2521: PydanticDeprecatedSince20: Pydantic V1 style `@root_validator` validators are deprecated. You should migrate to Pydantic V2 style `@model_validator` validators, see the migration guide for more details. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/. Deprecated in Pydantic V2.0 to be removed in V3.0. See Pydantic V2 Migration Guide at https://errors.pydantic.dev/2.6/migration/
    @root_validator(skip_on_failure=True)

-- Docs: https://docs.pytest.org/en/stable/how-to/capture-warnings.html
======================================================= short test summary info =======================================================
FAILED tests/test_validators.py::test_use_bare - Failed: DID NOT WARN. No warnings of type (<class 'pydantic.warnings.PydanticDeprecatedSince20'>,) were emitted.
FAILED tests/test_validators.py::test_use_no_fields - Failed: DID NOT WARN. No warnings of type (<class 'pydantic.warnings.PydanticDeprecatedSince20'>,) were emitted.
FAILED tests/test_validators.py::test_validator_bad_fields_throws_configerror - Failed: DID NOT WARN. No warnings of type (<class 'pydantic.warnings.PydanticDeprecatedSince20'>,) were emitted.
FAILED tests/test_validators.py::test_assert_raises_validation_error - assert [{'ctx': {'er...+ snap', ...}] == [{'ctx': {'er...+ snap', ...}]
================================ 4 failed, 4239 passed, 650 skipped, 9 xfailed, 17 warnings in 15.50s =================================

Example Code

No response

Python, Pydantic & OS Version

pydantic version: 2.6.0
        pydantic-core version: 2.16.1
          pydantic-core build: profile=release pgo=true
                 install path: /tmp/pydantic/pydantic
               python version: 3.11.7 (main, Dec 26 2023, 16:39:22) [GCC 13.2.1 20231216]
                     platform: Linux-6.7.2-gentoo-dist-x86_64-AMD_Ryzen_5_3600_6-Core_Processor-with-glibc2.38
             related packages: typing_extensions-4.9.0 email-validator-2.1.0.post1
                       commit: c1dff153
@mgorny mgorny added bug V2 Bug related to Pydantic V2 pending Awaiting a response / confirmation labels Jan 30, 2024
@mgorny
Copy link
Contributor Author

mgorny commented Jan 30, 2024

For the record, I've seen a similar issue with one more package but here it looks it could actually be a pytest bug. I've gotta leave right now but I'll take another look when I get home.

@mgorny
Copy link
Contributor Author

mgorny commented Jan 30, 2024

Ok, I think this is actually a bug in the test suite.

if isinstance(fields[0], FunctionType):
raise PydanticUserError(
'`@validator` should be used with fields and keyword arguments, not bare. '
"E.g. usage should be `@validator('<field_name>', ...)`",
code='validator-no-fields',
)
elif not all(isinstance(field, str) for field in fields):
raise PydanticUserError(
'`@validator` fields should be passed as separate string args. '
"E.g. usage should be `@validator('<field_name_1>', '<field_name_2>', ...)`",
code='validator-invalid-fields',
)
warn(
'Pydantic V1 style `@validator` validators are deprecated.'
' You should migrate to Pydantic V2 style `@field_validator` validators,'
' see the migration guide for more details',
DeprecationWarning,
stacklevel=2,
)

Unless I'm missing something, the exception is thrown before the warning is emitted.

def test_use_bare():
with pytest.raises(TypeError, match='`@validator` should be used with fields'):
class Model(BaseModel):
a: str
with pytest.warns(PydanticDeprecatedSince20, match=V1_VALIDATOR_DEPRECATION_MATCH):
@validator
def checker(cls, v):
return v

I'm guessing that with pytest-7, the pytest.warns() assertion was ignored because of the exception raised but now it's respected.

@mgorny
Copy link
Contributor Author

mgorny commented Jan 30, 2024

I'm preparing a pull request to address at last some of the failures.

mgorny added a commit to mgorny/pydantic that referenced this issue Jan 30, 2024
Fix `tests/test_validators.py::test_use_no_fields` not to check
for a warning that can't be emitted because calling the decorator
fails with a `TypeError`.  Starting with pytest 8.0.0 (due to
pytest-dev/pytest#9036 fix), `pytest.warns()` assertions are enforced
even if an exception is raised and consumed by `pytest.raises()`.

Bug pydantic#8674
mgorny added a commit to mgorny/pydantic that referenced this issue Jan 30, 2024
Emit Pydantic V1 style `@validator` deprecation warnings before raising
`PydanticUserError` about incorrect use.  This is one of the possible
solutions to test failures introduced with pytest 8.0.0, as now
`pytest.warns()` assertions are enforced even if an exception raised
and caught by `pytest.raises()` (this is pytest-dev/pytest#9036).

The alternate possibility would be to remove `pytest.warns()` from
respective test functions but I think it's reasonable to emit these
warnings, to warn the users that they ought to consider upgrading
the code to Pydantic V2 API rather than fixing the immediate issue.

Bug pydantic#8674
@sydney-runkle sydney-runkle removed the pending Awaiting a response / confirmation label Jan 30, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug V2 Bug related to Pydantic V2
Projects
None yet
2 participants