和SQLAlchemy联接,我们没有外键

问题描述

| 在MySQL中假设以下内容:
CREATE TABLE users (
  id integer auto_increment primary key,username varchar(30),active enum(\'N\',\'Y\'),created_on int(11),updated_on int(11),points int(10),// other fields
);

CREATE TABLE comments (
  id integer auto_increment primary key,user_id integer,forum_id integer,favorited integer,// other fields
);
请注意,没有正式的外键约束添加到表中。这是我继承的东西,在当前设置中无法更改。 (我们正在对整个系统进行大修,但与此同时,我必须处理自己得到的内容) 当在表之间没有建立正式的外键时,我很难解决SQLalchemy的联接问题。 实际上,我想执行以下操作:
SELECT 
  u.username,c.forum_id,count(c.id)
FROM 
  users u
  JOIN comments c ON u.id=c.user_id
WHERE
  u.id = 1234
GROUP BY
  u.username,c.forum_id;
我拥有的代码包括以下内容:
mapper(Users,users,primary_key=[users.c.id],include_properties=[\'user_id\',\'username\',\'active\',\'created_on\',\'updated_on\',\'points\'])
mapper(Comments,comments,primary_key=[comments.c.id],include_properties=[\'active\',\'user_id\',\'favorited\',\'forum_id\'])

j = join(users,comments)
mapper(UserComments,j,properties={\'user_id\': [users.c.id,comments.c.user_id]})

session = create_session()
query = session.query(UserComments).filter(users.cid == 1234)
rdata = run(query)
for row in rdata:
    print row
...当然会失败:
sqlalchemy.exc.ArgumentError: Can\'t find any foreign key relationships
between \'users\' and \'comments\'.
当我们没有外键时,我不确定如何解决此问题。我还要如何定义关系?我认为这是mapper()调用的一部分:
mapper(UserComments,comments.c.user_id]})
...但是显然我误读了文档。 在此先感谢您的帮助。     

解决方法

        您有两个选择。您可以在
join
中传递加入条件,如下所示:
j = join(users,comments,onclause=users.c.id == commends.c.user_id)
如果您是根据
orm.relationship
属性定义的,则关键字参数将是
primaryjoin
而不是
onclause
。 但是,我更喜欢撒谎。通知SQLAlchemy有一个外键,即使没有。
comments = Table(\'comments\',metadata,Column(\'id\',Integer,primary_key=True),Column(\'user_id\',ForeignKey(\'users.id\')),...
)
即使实际的数据库没有外键,SQLAlchemy也会像实际存在外键一样继续进行操作。当然,如果违反了隐含的前键约束,您可能会遇到麻烦(如果没有相应的
users.id
,则为
comments.user_id
),但是您仍然可能会遇到麻烦。     

相关问答

错误1:Request method ‘DELETE‘ not supported 错误还原:...
错误1:启动docker镜像时报错:Error response from daemon:...
错误1:private field ‘xxx‘ is never assigned 按Alt...
报错如下,通过源不能下载,最后警告pip需升级版本 Requirem...