Python 使用sqlalchemy向MySQL数据库添加相关数据

Python 使用sqlalchemy向MySQL数据库添加相关数据,python,mysql,sqlalchemy,Python,Mysql,Sqlalchemy,我创建了一些类,用于创建表和使用sqlalchemy向MySQL数据库添加数据。我现在面临的问题如下 如果我想在表c中添加一个条目,我所需要的就是这样的代码 class A(Base): __tablename__ = 'a' id = Column(Integer, primary_key=True) name = Column(String(1000)) class B(Base): __tablename__ = 'b' id = Colum

我创建了一些类,用于创建表和使用sqlalchemy向MySQL数据库添加数据。我现在面临的问题如下

如果我想在表c中添加一个条目,我所需要的就是这样的代码

class A(Base):
     __tablename__ = 'a'

    id = Column(Integer, primary_key=True)
    name = Column(String(1000))

class B(Base):
    __tablename__ = 'b'

    id = Column(Integer, primary_key=True)
    name = Column(String(1000))

class C(Base):
    __tablename__ = 'c'

    id = Column(Integer, primary_key=True)
    b_id = Column(Integer, ForeignKey('b.id'))
    name = Column(String(1000))
    a_id = Column(Integer, ForeignKey('a.id'))

    b = relationship('B', backref=backref('cb'), foreign_keys = b_id)
    a = relationship('A', backref=backref('ca'), foreign_keys = a_id)

connect = engine.connect()
Base.metadata.create_all(bind=engine)
这一切都按照我所需要的方式工作,c条目中b_id和a_id的外键与a和b中相应id的外键匹配

但是,假设在提交到数据库并关闭会话之后,我现在决定向c“c2”添加另一个条目。我希望此条目与表a和表b的关系与我的第一个条目相同(以便a_id和b_id与名为“c1”的条目相同)。但是,如果我使用与第一个条目类似的代码,sqlalchemy只会在表a和表b中创建名称为“a1”和“b1”的重复条目,id号为2而不是1。然后,表c中的条目将具有正确的id号,但它们将链接到重复条目

我希望能够将一个条目添加到c中,无论我选择多少次,并将其与表a和b关联,而不必每次在a和b中创建新条目。如何避免这种冗余?

试着这样做:

c_ent = C(name = 'c1')
a1 = A(name = 'a1')
b1 = B(name = 'b1')

a1.ca = [c_ent]
b1.cb = [c_ent]

list1 = [a1, b1]

sess = create_session(name)
for i in list1:
    sess.add(i)

sess.commit()
sess.close()
使用sqlite的完整代码:

c2 = C(name='c2')
c2.a = a1
c2.b = b1

sess = create_session(name)
sess.add(c2)
sess.commit()
sess.close()
执行后:

from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy import Column, Integer, String, ForeignKey, create_engine
from sqlalchemy.orm import relationship, backref, sessionmaker


Base = declarative_base()


class A(Base):
    __tablename__ = 'a'

    id = Column(Integer, primary_key=True)
    name = Column(String(1000))


class B(Base):
    __tablename__ = 'b'

    id = Column(Integer, primary_key=True)
    name = Column(String(1000))


class C(Base):
    __tablename__ = 'c'

    id = Column(Integer, primary_key=True)
    b_id = Column(Integer, ForeignKey('b.id'))
    name = Column(String(1000))
    a_id = Column(Integer, ForeignKey('a.id'))

    b = relationship('B', backref=backref('cb'), foreign_keys=b_id)
    a = relationship('A', backref=backref('ca'), foreign_keys=a_id)

engine = create_engine('sqlite:////tmp/temp.db')

connect = engine.connect()
Base.metadata.create_all(bind=engine)

Session = sessionmaker(bind=engine)
sess = Session()

c_ent = C(name='c1')
a1 = A(name='a1')
b1 = B(name='b1')

a1.ca = [c_ent]
b1.cb = [c_ent]

list1 = [a1, b1]

for i in list1:
    sess.add(i)
sess.commit()

c2 = C(name='c2')
c2.a = a1
c2.b = b1
sess.add(c2)
sess.commit()

sess.close()

正如您所看到的,没有重复的数据。您在表
a
中只有一个条目,在表
b
中只有一个条目。此方法仍然存在与原始方法相同的问题,但感谢您的帮助。此问题在哪里?您的问题是创建新条目。在我的代码中,我没有创建A和B的新条目,我只使用了您已有的条目。对不起,我可能不够具体。我并不担心代码中有新条目,而是担心代码在实际数据库中创建的新条目。
$ sqlite3 /tmp/temp.db 
SQLite version 3.8.2 2013-12-06 14:53:30
Enter ".help" for instructions
Enter SQL statements terminated with a ";"
sqlite> SELECT * FROM c;
1|1|c1|1
2|1|c2|1
sqlite> SELECT * FROM a;
1|a1
sqlite> SELECT * FROM b;
1|b1