I would like to create pydantic model to validate users form. one of my model values should be validated from a list of names. I succeed to create the model using enum as follow:
from enum import Enum
class Fruit(str, Enum):
APPLE = 'apple'
BANANA = 'banana'
MELON = 'melon'
from pydantic import BaseModel
class UserForm(BaseModel):
fruit: Fruit
name: str
Now I would like to switch the enum to a list of values in my code:
fruit = ['apple','banana','melon']
How can I manage to do so?
tnx
You can use validator
in the following way:
from pydantic import BaseModel, ValidationError, validator
class UserForm(BaseModel):
fruit: str
name: str
@validator('fruit')
def fruit_must_be_in_fruits(cls,fruit):
fruits=['apple','banana','melon']
if fruit not in fruits:
raise ValueError(f'must be in {fruits}')
return fruit
try:
UserForm(fruit="apple",name="apple")
except ValidationError as e:
print(e)
It will raise a validation error if it doesn't match the criteria.
You could do this also by means of a list of Literal
type. Like so:
import pydantic
from typing import Literal, List
class M(pydantic.BaseModel):
fruits: List[Literal["apple", "orange"]]
print(M.parse_obj({"fruits":["apple", "orange"]})) # OK fruits=['apple', 'orange']
print(M.parse_obj({"fruits":["apple", "orange", "potato"]})) # Error unexpected value potato
You can get informations about the enum by its .__members__
dictionary - here you can simply iterate it keys though:
from enum import Enum
class Fruit(str, Enum):
APPLE = 'apple'
BANANA = 'banana'
MELON = 'melon'
# only need __members__ if you need more infos about it
print(Fruit.__members__)
# you do not need the __members__ if you just want the keys
print([name.lower() for name in Fruit])
Output:
# enums __members__ dictionary
{'APPLE': <Fruit.APPLE: 'apple'>,
'BANANA': <Fruit.BANANA: 'banana'>,
'MELON': <Fruit.MELON: 'melon'>}
# lower keys
['apple', 'banana', 'melon']
I am proposing an elegant solution.
from pydantic import BaseModel
from typing import List
from enum import Enum
class Fruit(str, Enum):
APPLE = 'apple'
BANANA = 'banana'
MELON = 'melon'
class UserForm(BaseModel):
fruits: List[Fruit]
name: str
And that's it.
Check the above code:
put the above code in a file main.py
.
Run
python -i main.py
>>> uf = UserForm(fruits=['apple','banana'],name='hello')
>>> uf
UserForm(fruits=[<Fruit.APPLE: 'apple'>, <Fruit.BANANA: 'banana'>], name='hello')
>>> af = UserForm(fruits=['monkey','apple'],name='hello')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "pydantic/main.py", line 400, in pydantic.main.BaseModel.__init__
pydantic.error_wrappers.ValidationError: 1 validation error for UserForm
fruits -> 0
value is not a valid enumeration member; permitted: 'apple', 'banana', 'melon' (type=type_error.enum; enum_values=[<Fruit.APPLE: 'apple'>, <Fruit.BANANA: 'banana'>, <Fruit.MELON: 'melon'>])
>>>
pydantic will raise an error, as monkey
is not in fruits.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.