【发布时间】:2020-04-10 17:18:47
【问题描述】:
我正在创建一个简单的 CRUD 应用程序。我正在使用 Flask,我决定使用 SQLAlchemy 作为 ORM,并使用 Marshmallow 来验证有效负载。
我目前的问题是尽量减少我需要编写的复制量。
在这种情况下,我们只是在处理帖子。
创建
models.py
class Post(Base):
__tablename__ = 'posts'
id = Column(UUID(as_uuid=True), primary_key=True)
user_id = Column(UUID(as_uuid=True), ForeignKey('users.id'))
title = Column(String(length=50))
schemas.py
class CreatePostSchema(Schema):
title = fields.Str(required=True)
我不需要id 和user_id,因为它们将由后端创建/找到,但所有其他字段都是必需的。
我正在使用 BluePrints,与帖子创建相关的路由/端点之一将具有 post() 方法。
我可以创建装饰器以首先确保架构正确,获取用户并将其传递给 post 方法:
@auth_required()
@validate_schema(CreatePostSchema)
def post(request, user_id, cleaned_schema):
create_post(cleaned_schema)
return 200
现在,我可以编写 create_post() 函数而无需硬编码键,例如:
def create_post(user_id, **clean_data)
post = models.Post(**clean_data)
post.user_id = user_id
但这是好的做法吗?或者我应该明确说明如下键:
def create_post(user_id, title)
post = models.Post(title=title)
post.user_id = user_id
post.id = uuid4()
return post
然后我还有一个问题,在哪个阶段进行验证。验证应该在post() 方法之前进行,还是在创建帖子期间进行?例如,我可以这样做:
def create_post(user_id, **data):
clean_data = CreatePostSchema.load(**data)
post = models.Post(**clean_data)
session.add(post)
session.commit()
return
这样我可以删除额外的@has_schema() 装饰器。
更新
更新是一种无需重复键即可编写的不同野兽。假设我们只有 1 个字段和 EditPostSchema = CreatePostSchema。实际上,我会拥有更多,例如创建日期、更新日期、描述等
clean_data = EditPostSchema.load(**data)
id = clean_data.pop('id')
update_post(id, clean_data)
def update_post(id, **clean_data):
session.query(Post).get(id).update(**clean_data, synchronize_session=False)
return
所以本质上,我认为Schemas 应该已经解释了我需要用于 CRUD 的字段,所以我不需要重复它们。我说的对吗?
【问题讨论】:
标签: python sqlalchemy marshmallow