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

Add support for conversion from str in pydantic-settings #296

Open
BartSchuurmans opened this issue Oct 8, 2024 · 2 comments
Open

Add support for conversion from str in pydantic-settings #296

BartSchuurmans opened this issue Oct 8, 2024 · 2 comments
Labels
enhancement 🚀 New feature or request

Comments

@BartSchuurmans
Copy link

from pathlib import Path
from upath import UPath
from pydantic_settings import BaseSettings

class Settings(BaseSettings):
    my_path: Path
    my_upath: UPath

settings = Settings(my_path="/tmp", my_upath="/tmp")
❯ python example.py
Traceback (most recent call last):
  File "/home/bart/src/proj/example.py", line 9, in <module>
    settings = Settings(my_path="/tmp", my_upath="/tmp")
               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/bart/src/proj/.venv/lib/python3.12/site-packages/pydantic_settings/main.py", line 152, in __init__
    super().__init__(
  File "/home/bart/src/proj/.venv/lib/python3.12/site-packages/pydantic/main.py", line 212, in __init__
    validated_self = self.__pydantic_validator__.validate_python(data, self_instance=self)
                     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
pydantic_core._pydantic_core.ValidationError: 1 validation error for Settings
my_upath
  Input should be an instance of UPath [type=is_instance_of, input_value='/tmp', input_type=str]
    For further information visit https://errors.pydantic.dev/2.9/v/is_instance_of

When reading through some older (solved) issues, I got the impression that this used to work. Should this work out of the box?

pydantic                  2.9.2          Data validation using Python type ...
pydantic-core             2.23.4         Core functionality for Pydantic va...
pydantic-settings         2.5.2          Settings management using Pydantic
universal-pathlib         0.2.5          pathlib api extended to use fsspec...
@BartSchuurmans BartSchuurmans changed the title Integration with pydantic-settings broken(?) Conversion from str in pydantic-settings broken(?) Oct 8, 2024
@ap--
Copy link
Collaborator

ap-- commented Oct 8, 2024

Hi @BartSchuurmans

Regarding the implementation, imo behavior here is correct. This only works for your pathlib.Path attributes because of lax mode: https://docs.pydantic.dev/latest/concepts/conversion_table/#__tabbed_1_1

See:

>>> from pathlib import Path
... from pydantic import ConfigDict
... from pydantic_settings import BaseSettings
... 
>>> class Settings(BaseSettings):
...     model_config = ConfigDict(strict=True)
...     my_path: Path
...     
>>> Settings(my_path="/tmp")
Traceback (most recent call last):
  File "<python-input-4>", line 1, in <module>
    Settings(my_path="/tmp")
    ~~~~~~~~^^^^^^^^^^^^^^^^
  File "/Users/andreaspoehlmann/Development/universal_pathlib/venv313/lib/python3.13/site-packages/pydantic_settings/main.py", line 144, in __init__
    super().__init__(
    ~~~~~~~~~~~~~~~~^
        **__pydantic_self__._settings_build_values(
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    ...<20 lines>...
        )
        ^
    )
    ^
  File "/Users/andreaspoehlmann/Development/universal_pathlib/venv313/lib/python3.13/site-packages/pydantic/main.py", line 211, in __init__
    validated_self = self.__pydantic_validator__.validate_python(data, self_instance=self)
pydantic_core._pydantic_core.ValidationError: 1 validation error for Settings
my_path
  Input should be an instance of Path [type=is_instance_of, input_value='/tmp', input_type=str]
    For further information visit https://errors.pydantic.dev/2.9/v/is_instance_of

I can see how users would expect to be able to just cast from string by default though. You can do this right now via: https://docs.pydantic.dev/latest/concepts/validators/#before-after-wrap-and-plain-validators . But I agree, that this should be more convenient. We should make sure to expose storage_options in some way to pydantic too.

@ap-- ap-- added the enhancement 🚀 New feature or request label Oct 8, 2024
@ap-- ap-- changed the title Conversion from str in pydantic-settings broken(?) Add support for conversion from str in pydantic-settings Oct 8, 2024
@BartSchuurmans
Copy link
Author

@ap-- Thanks for your quick response!

I am using the PlainValidator now to support converting str to UPath:

from typing import Annotated
from pydantic import PlainValidator
from upath import UPath
from pydantic_settings import BaseSettings

class Settings(BaseSettings):
    my_upath: Annotated[UPath, PlainValidator(lambda x: UPath(x))]

settings = Settings(my_upath="/tmp")

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement 🚀 New feature or request
Projects
None yet
Development

No branches or pull requests

2 participants