sqlalchemy 能通过 dict 添加纪录吗?

2015-01-01 13:19:54 +08:00
 yakczh
比如文章表的字段有标题,作者,内容,发布时间,发布状态 ,但是其中发布时间,发布状态是有默认值的
如果用
session.add( User('tittle','autrho','content','2015-01-01',0') ) 这种方式必须每个值都得写上,如果数据库表增加了字段,又要修改代码

如果用diCt只传必要的数据,我试了下
data={"title":"xxxx","author":"oooo","content":"ksjfosjfos"}

session.add(Article(data))
提示
TypeError: __init__() takes exactly 1 argument (2 given)

这个新增的字段必须写死吗? 能不能实现只传必须的字段?
3622 次点击
所在节点    问与答
5 条回复
Cynic222
2015-01-01 13:34:38 +08:00
没试过,但我猜可以session.add(Article(**data))
timonwong
2015-01-01 13:36:21 +08:00
http://docs.sqlalchemy.org/en/rel_0_9/orm/tutorial.html#create-an-instance-of-the-mapped-class
如果你没有自定义 __init__ 方法,那么SQLAlchemy已经提供了一个keyword arguments的调用方法,你的代码就只需要:
Article(**data) 就可以了

但是如果你自定义了__init__ 就不行了,要写个包装函数,比如from_dict

PS, 这个是默认 __init__ 的实现:

```
def _declarative_constructor(self, **kwargs):
"""A simple constructor that allows initialization from kwargs.

Sets attributes on the constructed instance using the names and
values in ``kwargs``.

Only keys that are present as
attributes of the instance's class are allowed. These could be,
for example, any mapped columns or relationships.
"""
cls_ = type(self)
for k in kwargs:
if not hasattr(cls_, k):
raise TypeError(
"%r is an invalid keyword argument for %s" %
(k, cls_.__name__))
setattr(self, k, kwargs[k])
_declarative_constructor.__name__ = '__init__'
```
timonwong
2015-01-01 13:37:14 +08:00
yakczh
2015-01-01 17:46:40 +08:00
@timonwong

articles_table = Table('articles',metadata,
Column('id',Integer,primary_key=True),
Column('title',String(40)),
Column('author',String(40)),
Column('content',String(40)),
Column('ctime',Integer,default=0),
Column('status',Integer,default=0),


)
class Article(object):
>>def __repr__(self):

>>>>return "<Article('%s','%s','%s')>" % (self.title,self.author,self.content)
mapper(Article,articles_table)
data={"title":"xxxx","author":"oooo","content":"ksjfosjfos"}
u=Article(**data)
session.add(u)

运行提示:
u=Article(**data)
TypeError: __init__() got an unexpected keyword argument 'content'


很奇怪不报 title,author出错
timonwong
2015-01-01 18:31:17 +08:00
@yakczh
你用的是classic 的mapper,自然用不了 declarative mapper 的方法

declarative mapper 会自然的把 default constructor 给实现一次,classic 的就需要自行手动实现。

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/158416

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX