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

Support for Optional types as X | None #399

Open
santigandolfo opened this issue Dec 26, 2023 · 1 comment
Open

Support for Optional types as X | None #399

santigandolfo opened this issue Dec 26, 2023 · 1 comment
Labels
bug Something isn't working

Comments

@santigandolfo
Copy link

I'm trying to update my code to Odmantic 1.0.0, Pydantic 2.5.2 and also start using Python 3.11, but when I define one of my classes like this:

from typing import Optional
from odmantic import Model
from pydantic import EmailStr
class User(Model):
    firebase_uid: str
    permissions: list[str] = []
    name: str | None = None
    email: str | None= None

I'm getting this error:

webhook-1  |   File "/app/app/domain/entities.py", line 8, in <module>
webhook-1  |     class User(Model):
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/odmantic/model.py", line 488, in __new__
webhook-1  |     return super().__new__(mcs, name, bases, namespace, **kwargs)
webhook-1  |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/odmantic/model.py", line 406, in __new__
webhook-1  |     cls = super().__new__(mcs, name, bases, namespace, **kwargs)
webhook-1  |           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/pydantic/_internal/_model_construction.py", line 181, in __new__
webhook-1  |     set_model_fields(cls, bases, config_wrapper, types_namespace)
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/pydantic/_internal/_model_construction.py", line 426, in set_model_fields
webhook-1  |     fields, class_vars = collect_model_fields(cls, bases, config_wrapper, types_namespace, typevars_map=typevars_map)
webhook-1  |                          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/pydantic/_internal/_fields.py", line 120, in collect_model_fields
webhook-1  |     type_hints = get_cls_type_hints_lenient(cls, types_namespace)
webhook-1  |                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/pydantic/_internal/_typing_extra.py", line 212, in get_cls_type_hints_lenient
webhook-1  |     hints[name] = eval_type_lenient(value, globalns, localns)
webhook-1  |                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/pydantic/_internal/_typing_extra.py", line 224, in eval_type_lenient
webhook-1  |     return typing._eval_type(value, globalns, localns)  # type: ignore
webhook-1  |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
webhook-1  |   File "/usr/local/lib/python3.11/typing.py", line 392, in _eval_type
webhook-1  |     t = t.__origin__[args]
webhook-1  |         ~~~~~~~~~~~~^^^^^^
webhook-1  | TypeError: type 'types.UnionType' is not subscriptable

How can I define the entity?
If I define it like this it works, but I'm using ruff and it automatically suggests the other format (and I personally prefer it):

class User(Model):
    firebase_uid: str
    permissions: list[str] = []
    name: Optional[str] = None
    email: Optional[str]= None

I'm also having problems if instead of the email being of type str I use EmailStr:

class User(Model):
    firebase_uid: str
    permissions: list[str] = []
    name: Optional[str] = None
    email: Optional[EmailStr]= None

In that case I get this error when I do users = await self.engine.find(User):

webhook-1  |   File "/app/app/domain/usecases/users_usecases.py", line 23, in list_users
webhook-1  |     users = await self.engine.find(User)
webhook-1  |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/odmantic/engine.py", line 110, in __await__
webhook-1  |     instances.append(self._parse_document(raw_doc))
webhook-1  |                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/odmantic/engine.py", line 83, in _parse_document
webhook-1  |     instance = self._model.model_validate_doc(raw_doc)
webhook-1  |                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/odmantic/model.py", line 806, in model_validate_doc
webhook-1  |     raise DocumentParsingError(
webhook-1  |           ^^^^^^^^^^^^^^^^^^^^^
webhook-1  |   File "/usr/local/lib/python3.11/site-packages/odmantic/exceptions.py", line 111, in __init__
webhook-1  |     self.inner = ValidationError.from_exception_data(
webhook-1  |                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
webhook-1  | TypeError: ValueError: 'error' required in context

If I define it like this there are no errors:

class User(Model):
    firebase_uid: str
    permissions: list[str] = []
    name: str
    email: EmailStr
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

2 participants