FastAPI学习笔记(一)-2.初识Pydantic
作者:互联网
一、使用Python的类型注释type hints 来进行数据校验 和 setting管理。
1 ''' 2 @author:invoker 3 @project:fastapi202108 4 @file: pydantic_tutorial.py 5 @contact:invoker2021@126.com 6 @descript: 7 @Date:2021/8/4 18:05 8 @version: Python 3.7.8 9 ''' 10 11 """ 12 一、使用Python的类型注释type hints 来进行数据校验 和 setting管理。 13 二、Pydantic可以在代码运行时提供类型提示,数据校验失败时提供友好的错误提示 14 三、定义输入应该如何在纯规范的Python代码中保存,并用Pydantic验证他。 15 """ 16 17 from pydantic import BaseModel 18 from datetime import datetime 19 from typing import List 20 from typing import Optional 21 22 print("\033[31m1. -----Pydantic的基本用法------------------\033[0m") 23 24 25 class User(BaseModel): 26 id: int # 没有给默认值则是必填字段 27 name: str = "John snow" # 有默认值则是选填字段 28 signup_ts: Optional[datetime] = None # 使用Optional表示是选填字段,不填就是None 29 friends: List[int] = [] # 列表中元素是int类型或则可以直接转换成int类型 30 31 32 external_data = { 33 "id": '1', 34 "signup_ts": "2021-08-04 18:00", 35 "friends": [1, 2, "3"] # "3"可以int("3")的 36 } 37 38 # python的解包,将字典的值分别赋值给对象中的属性 39 user = User(**external_data) 40 # 每个字段单独输出 41 print(user.id, user.name, user.signup_ts, user.friends) 42 # 时间字段按照原类型输出 43 print(repr(user.signup_ts)) 44 # 将该对象以字典方式输出 45 print(user.dict())View Code
执行结果:
二、Pydantic可以在代码运行时提供类型提示,数据校验失败时提供友好的错误提示
1 ''' 2 @author:invoker 3 @project:fastapi202108 4 @file: pydantic_tutorial.py 5 @contact:invoker2021@126.com 6 @descript: 7 @Date:2021/8/4 18:05 8 @version: Python 3.7.8 9 ''' 10 11 """ 12 一、使用Python的类型注释type hints 来进行数据校验 和 setting管理。 13 二、Pydantic可以在代码运行时提供类型提示,数据校验失败时提供友好的错误提示 14 三、定义输入应该如何在纯规范的Python代码中保存,并用Pydantic验证他。 15 """ 16 17 from pydantic import BaseModel 18 from datetime import datetime 19 from typing import List 20 from typing import Optional 21 22 print("\033[31m1. -----Pydantic的基本用法------------------\033[0m") 23 24 25 class User(BaseModel): 26 id: int # 没有给默认值则是必填字段,非int型可以转换成int型 27 name: str = "John snow" # 有默认值则是选填字段 28 signup_ts: Optional[datetime] = None # 使用Optional表示是选填字段,不填就是None 29 friends: List[int] = [] # 列表中元素是int类型或则可以直接转换成int类型 30 31 32 external_data = { 33 "id": 'a', 34 "signup_ts": "2021-08-04 18:00", 35 "friends": [1, 2, "3a"] # "3"可以int("3")的 36 } 37 38 # python的解包,将字典的值分别赋值给对象中的属性 39 user = User(**external_data) 40 # 每个字段单独输出 41 print(user.id, user.name, user.signup_ts, user.friends) 42 # 时间字段按照原类型输出 43 print(repr(user.signup_ts)) 44 # 将该对象以字典方式输出 45 print(user.dict())View Code
如果输入参数格式不正确。则会提示错误。
2.2 捕获异常
1 ''' 2 @author:invoker 3 @project:fastapi202108 4 @file: pydantic_tutorial.py 5 @contact:invoker2021@126.com 6 @descript: 7 @Date:2021/8/4 18:05 8 @version: Python 3.7.8 9 ''' 10 11 """ 12 一、使用Python的类型注释type hints 来进行数据校验 和 setting管理。 13 二、Pydantic可以在代码运行时提供类型提示,数据校验失败时提供友好的错误提示 14 三、定义输入应该如何在纯规范的Python代码中保存,并用Pydantic验证他。 15 """ 16 17 from pydantic import BaseModel, ValidationError 18 from datetime import datetime 19 from typing import List 20 from typing import Optional 21 22 print("\033[33;1m1. -----Pydantic的基本用法------------------\033[33;0m") 23 24 25 class User(BaseModel): 26 id: int # 没有给默认值则是必填字段,非int型可以转换成int型 27 name: str = "John snow" # 有默认值则是选填字段 28 signup_ts: Optional[datetime] = None # 使用Optional表示是选填字段,不填就是None 29 friends: List[int] = [] # 列表中元素是int类型或则可以直接转换成int类型 30 31 32 external_data = { 33 "id": '1', 34 "signup_ts": "2021-08-04 18:00", 35 "friends": [1, 2, "3"] # "3"可以int("3")的 36 } 37 38 # python的解包,将字典的值分别赋值给对象中的属性 39 user = User(**external_data) 40 # 每个字段单独输出 41 print(user.id, user.name, user.signup_ts, user.friends) 42 # 时间字段按照原类型输出 43 print(repr(user.signup_ts)) 44 # 将该对象以字典方式输出 45 print(user.dict()) 46 47 print("\033[33;1m2. -----------校验失败错误处理------------\033[33;0m") 48 49 try: 50 User(id=1, signup_ts=datetime.today(), friends=[1, 2, 'not number']) 51 except ValidationError as e: 52 print(e.json())View Code
三、BaseModel类的属性和方法
1 ''' 2 @author:invoker 3 @project:fastapi202108 4 @file: pydantic_tutorial.py 5 @contact:invoker2021@126.com 6 @descript: 7 @Date:2021/8/4 18:05 8 @version: Python 3.7.8 9 ''' 10 11 """ 12 一、使用Python的类型注释type hints 来进行数据校验 和 setting管理。 13 二、Pydantic可以在代码运行时提供类型提示,数据校验失败时提供友好的错误提示 14 三、定义输入应该如何在纯规范的Python代码中保存,并用Pydantic验证他。 15 """ 16 17 from pydantic import BaseModel, ValidationError 18 from datetime import datetime 19 from typing import List 20 from typing import Optional 21 from pathlib import Path 22 23 print("\033[33;1m1. -----Pydantic的基本用法------------------\033[33;0m") 24 25 26 class User(BaseModel): 27 id: int # 没有给默认值则是必填字段,非int型可以转换成int型 28 name: str = "John snow" # 有默认值则是选填字段 29 signup_ts: Optional[datetime] = None # 使用Optional表示是选填字段,不填就是None 30 friends: List[int] = [] # 列表中元素是int类型或则可以直接转换成int类型 31 32 33 external_data = { 34 "id": '1', 35 "signup_ts": "2021-08-04 18:00", 36 "friends": [1, 2, "3"] # "3"可以int("3")的 37 } 38 39 # python的解包,将字典的值分别赋值给对象中的属性 40 user = User(**external_data) 41 # 每个字段单独输出 42 print(user.id, user.name, user.signup_ts, user.friends) 43 # 时间字段按照原类型输出 44 print(repr(user.signup_ts)) 45 # 将该对象以字典方式输出 46 print(user.dict()) 47 48 print("\033[33;1m2. -----------校验失败错误处理------------\033[33;0m") 49 50 try: 51 User(id=1, signup_ts=datetime.today(), friends=[1, 2, 'not number']) 52 except ValidationError as e: 53 print(e.json()) 54 55 print("\033[33;1m3. -----------BaseModel类的属性和方法------------\033[33;0m") 56 # 1.以字典格式输出 57 print(f'以字典格式输出:{user.dict()}') 58 print(f'type:{type(user.dict())}') # dict 59 # 2.以json格式输出 60 print(f'以json格式输出:{user.json()}') 61 print(f'type:{type(user.json())}') # str 62 # 3.浅拷贝 63 print(f'浅拷贝:{user.copy()}') 64 print(f'type:{type(user.copy())}') # User 65 # 4.解析数据的方法 66 # 4.1 67 print(f'解析数据的方法1:{User.parse_obj(obj=external_data)}') 68 print(f'type{type(User.parse_obj(obj=external_data))}') # User 69 # 4.2 70 print(f'解析数据方法2:{User(**external_data)}') 71 print(f'type:{type(User(**external_data))}') # User 72 # 4.3 73 print(f'解析数据的方法3:解析规范的原生str数据') 74 print(User.parse_raw('{"id": 1, "name": "John snow", "signup_ts": "2021-08-04T18:00:00", "friends": [1, 2, 3]}')) 75 # 4.4 解析文件 76 print(f'解析数据的方法4:解析文件') 77 path = Path('pydantic_tutorial.json') 78 path.write_text('{"id": 1, "name": "John snow", "signup_ts": "2021-08-04T18:00:00", "friends": [1, 2, 3]}') 79 print(User.parse_file(path)) 80 81 # 5 数据格式 82 print(user.schema()) 83 print(user.schema_json()) 84 85 # 6 construct 不校验数据创建BaseModel对象实例,此方法只在特殊场景使用。 86 user_data = {"id": 'error', "name": "John snow", "signup_ts": "2021-08-04T18:00:00", "friends": [1, 2, 3]} 87 print(user.construct(**user_data)) 88 print(type(user.construct(**user_data))) 89 90 # 7 字段顺序 91 print(User.__fields__.keys()) # 只要在定义模型类时,所有字段都注明类型,字段顺序就不会乱View Code
四、递归模型(嵌套:一个模型内调用另一个模型)
引用场景不太清楚???
1 ''' 2 @author:invoker 3 @project:fastapi202108 4 @file: pydantic_tutorial.py 5 @contact:invoker2021@126.com 6 @descript: 7 @Date:2021/8/4 18:05 8 @version: Python 3.7.8 9 ''' 10 11 """ 12 一、使用Python的类型注释type hints 来进行数据校验 和 setting管理。 13 二、Pydantic可以在代码运行时提供类型提示,数据校验失败时提供友好的错误提示 14 三、定义输入应该如何在纯规范的Python代码中保存,并用Pydantic验证他。 15 """ 16 17 from pydantic import BaseModel, ValidationError 18 from datetime import datetime, date 19 from typing import List 20 from typing import Optional 21 from pathlib import Path 22 23 print("\033[33;1m1. -----Pydantic的基本用法------------------\033[33;0m") 24 25 26 class User(BaseModel): 27 id: int # 没有给默认值则是必填字段,非int型可以转换成int型 28 name: str = "John snow" # 有默认值则是选填字段 29 signup_ts: Optional[datetime] = None # 使用Optional表示是选填字段,不填就是None 30 friends: List[int] = [] # 列表中元素是int类型或则可以直接转换成int类型 31 32 33 external_data = { 34 "id": '1', 35 "signup_ts": "2021-08-04 18:00", 36 "friends": [1, 2, "3"] # "3"可以int("3")的 37 } 38 39 # python的解包,将字典的值分别赋值给对象中的属性 40 user = User(**external_data) 41 # 每个字段单独输出 42 print(user.id, user.name, user.signup_ts, user.friends) 43 # 时间字段按照原类型输出 44 print(repr(user.signup_ts)) 45 # 将该对象以字典方式输出 46 print(user.dict()) 47 48 print("\033[33;1m2. -----------校验失败错误处理------------\033[33;0m") 49 50 try: 51 User(id=1, signup_ts=datetime.today(), friends=[1, 2, 'not number']) 52 except ValidationError as e: 53 print(e.json()) 54 55 print("\033[33;1m3. -----------BaseModel类的属性和方法------------\033[33;0m") 56 # 1.以字典格式输出 57 print(f'以字典格式输出:{user.dict()}') 58 print(f'type:{type(user.dict())}') # dict 59 # 2.以json格式输出 60 print(f'以json格式输出:{user.json()}') 61 print(f'type:{type(user.json())}') # str 62 # 3.浅拷贝 63 print(f'浅拷贝:{user.copy()}') 64 print(f'type:{type(user.copy())}') # User 65 # 4.解析数据的方法 66 # 4.1 67 print(f'解析数据的方法1:{User.parse_obj(obj=external_data)}') 68 print(f'type{type(User.parse_obj(obj=external_data))}') # User 69 # 4.2 70 print(f'解析数据方法2:{User(**external_data)}') 71 print(f'type:{type(User(**external_data))}') # User 72 # 4.3 73 print(f'解析数据的方法3:解析规范的原生str数据') 74 print(User.parse_raw('{"id": 1, "name": "John snow", "signup_ts": "2021-08-04T18:00:00", "friends": [1, 2, 3]}')) 75 # 4.4 解析文件 76 print(f'解析数据的方法4:解析文件') 77 path = Path('pydantic_tutorial.json') 78 path.write_text('{"id": 1, "name": "John snow", "signup_ts": "2021-08-04T18:00:00", "friends": [1, 2, 3]}') 79 print(User.parse_file(path)) 80 81 # 5 数据格式 82 print(user.schema()) 83 print(user.schema_json()) 84 85 # 6 construct 不校验数据创建BaseModel对象实例,此方法只在特殊场景使用。 86 user_data = {"id": 'error', "name": "John snow", "signup_ts": "2021-08-04T18:00:00", "friends": [1, 2, 3]} 87 print(user.construct(**user_data)) 88 print(type(user.construct(**user_data))) 89 90 # 7 字段顺序 91 print(User.__fields__.keys()) # 只要在定义模型类时,所有字段都注明类型,字段顺序就不会乱 92 93 print("\033[33;1m4. -----------递归模型(嵌套:在一个模型内调用另一个模型)------------\033[33;0m") 94 95 96 class Sound(BaseModel): 97 sound: str 98 99 100 class Dog(BaseModel): 101 birthday: date 102 weight2: Optional[float] = None 103 sound: List[Sound] 104 105 dogs = Dog(birthday=date.today(), weight2=2.22, sound=[{"sound": "wang!"}, {"sound": "o!"}]) 106 print(dogs.dict())View Code
如果传入值是sound1,则会报错
1 ''' 2 @author:invoker 3 @project:fastapi202108 4 @file: pydantic_tutorial.py 5 @contact:invoker2021@126.com 6 @descript: 7 @Date:2021/8/4 18:05 8 @version: Python 3.7.8 9 ''' 10 11 """ 12 一、使用Python的类型注释type hints 来进行数据校验 和 setting管理。 13 二、Pydantic可以在代码运行时提供类型提示,数据校验失败时提供友好的错误提示 14 三、定义输入应该如何在纯规范的Python代码中保存,并用Pydantic验证他。 15 """ 16 17 from pydantic import BaseModel, ValidationError 18 from datetime import datetime, date 19 from typing import List 20 from typing import Optional 21 from pathlib import Path 22 23 print("\033[33;1m1. -----Pydantic的基本用法------------------\033[33;0m") 24 25 26 class User(BaseModel): 27 id: int # 没有给默认值则是必填字段,非int型可以转换成int型 28 name: str = "John snow" # 有默认值则是选填字段 29 signup_ts: Optional[datetime] = None # 使用Optional表示是选填字段,不填就是None 30 friends: List[int] = [] # 列表中元素是int类型或则可以直接转换成int类型 31 32 33 external_data = { 34 "id": '1', 35 "signup_ts": "2021-08-04 18:00", 36 "friends": [1, 2, "3"] # "3"可以int("3")的 37 } 38 39 # python的解包,将字典的值分别赋值给对象中的属性 40 user = User(**external_data) 41 # 每个字段单独输出 42 print(user.id, user.name, user.signup_ts, user.friends) 43 # 时间字段按照原类型输出 44 print(repr(user.signup_ts)) 45 # 将该对象以字典方式输出 46 print(user.dict()) 47 48 print("\033[33;1m2. -----------校验失败错误处理------------\033[33;0m") 49 50 try: 51 User(id=1, signup_ts=datetime.today(), friends=[1, 2, 'not number']) 52 except ValidationError as e: 53 print(e.json()) 54 55 print("\033[33;1m3. -----------BaseModel类的属性和方法------------\033[33;0m") 56 # 1.以字典格式输出 57 print(f'以字典格式输出:{user.dict()}') 58 print(f'type:{type(user.dict())}') # dict 59 # 2.以json格式输出 60 print(f'以json格式输出:{user.json()}') 61 print(f'type:{type(user.json())}') # str 62 # 3.浅拷贝 63 print(f'浅拷贝:{user.copy()}') 64 print(f'type:{type(user.copy())}') # User 65 # 4.解析数据的方法 66 # 4.1 67 print(f'解析数据的方法1:{User.parse_obj(obj=external_data)}') 68 print(f'type{type(User.parse_obj(obj=external_data))}') # User 69 # 4.2 70 print(f'解析数据方法2:{User(**external_data)}') 71 print(f'type:{type(User(**external_data))}') # User 72 # 4.3 73 print(f'解析数据的方法3:解析规范的原生str数据') 74 print(User.parse_raw('{"id": 1, "name": "John snow", "signup_ts": "2021-08-04T18:00:00", "friends": [1, 2, 3]}')) 75 # 4.4 解析文件 76 print(f'解析数据的方法4:解析文件') 77 path = Path('pydantic_tutorial.json') 78 path.write_text('{"id": 1, "name": "John snow", "signup_ts": "2021-08-04T18:00:00", "friends": [1, 2, 3]}') 79 print(User.parse_file(path)) 80 81 # 5 数据格式 82 print(user.schema()) 83 print(user.schema_json()) 84 85 # 6 construct 不校验数据创建BaseModel对象实例,此方法只在特殊场景使用。 86 user_data = {"id": 'error', "name": "John snow", "signup_ts": "2021-08-04T18:00:00", "friends": [1, 2, 3]} 87 print(user.construct(**user_data)) 88 print(type(user.construct(**user_data))) 89 90 # 7 字段顺序 91 print(User.__fields__.keys()) # 只要在定义模型类时,所有字段都注明类型,字段顺序就不会乱 92 93 print("\033[33;1m4. -----------递归模型(嵌套:在一个模型内调用另一个模型)------------\033[33;0m") 94 95 96 class Sound(BaseModel): 97 sound: str 98 99 100 class Dog(BaseModel): 101 birthday: date 102 weight2: Optional[float] = None 103 sound: List[Sound] 104 105 dogs = Dog(birthday=date.today(), weight2=2.22, sound=[{"sound1": "wang!"}, {"sound": "o!"}]) 106 print(dogs.dict())View Code
五、创建ORM模型
1 ''' 2 @author:invoker 3 @project:fastapi202108 4 @file: orm.py 5 @contact:invoker2021@126.com 6 @descript: 7 @Date:2021/8/5 10:21 8 @version: Python 3.7.8 9 ''' 10 # SQLAlchemy==1.3.22 11 from sqlalchemy import Column, Integer, String 12 from sqlalchemy.dialects.postgresql import ARRAY 13 from sqlalchemy.ext.declarative import declarative_base 14 # pydantic==1.7.3 15 from pydantic import BaseModel, constr 16 # python自带类型 17 from typing import List 18 19 print("\033[33;1m1. -----------------ORM模型:从类实例创建ORM对象的模型------------------\033[33;0m") 20 21 Base = declarative_base() 22 23 24 class CompanyOrm(Base): 25 __tablename__ = "companies" 26 id = Column(Integer, primary_key=True, nullable=False) 27 public_key = Column(String(20), index=True, nullable=False, unique=True) 28 name = Column(String(63), unique=True) 29 domains = Column(ARRAY(String(255))) 30 31 32 class CompanyMode(BaseModel): 33 id: int 34 public_key: constr(max_length=20) 35 name: constr(max_length=63) 36 domains: List[constr(max_length=255)] 37 38 class Config: 39 orm_mode = True 40 41 42 co_orm = CompanyOrm( 43 id=123, 44 public_key='foobar', 45 name='testing', 46 domains=['invoker.com', 'test.com'] 47 ) 48 49 print(CompanyMode.from_orm(co_orm)) 50 print(type(CompanyMode.from_orm(co_orm)))View Code
标签:int,FastAPI,ts,初识,user,print,type,Pydantic,User 来源: https://www.cnblogs.com/invoker2021/p/15102362.html