2017-07-19 55 views
0

我想存儲對SQL數據庫的額外表中的數據庫條目的引用與通用目的。有沒有一種有效的方法來創建一個對象,並立即獲得在SQLAlchemy中新創建的對象的自動增加的ID

在SQLAlchemy中我的數據模型是這樣的:

class Entity(db.Model): 
    id = db.Column(db.Integer, primary_key = True) 
    name = db.Column(db.String(10)) 

    def __init__(self, name): 
     self.name = name 


class Entry(db.Model): 
    id = db.Column(db.Integer, primary_key=True) 
    name= db.Column(db.String(10)) 

    entity_id = db.Column(db.Integer, db.ForeignKey('entity.id')) 

    def __init__(self, name, entity_id): 
     self.name = name 
     self.entity_id = entity_id 


class Thing(db.Model): 
    id = db.Column(db.Integer, primary_key=True) 
    name= db.Column(db.String(10)) 

    entity_id = db.Column(db.Integer, db.ForeignKey('entity.id')) 

    def __init__(self, name, entity_id): 
     self.name = name 
     self.entity_id = entity_id 

只要一個事情創建,應該有參考ENTITY_ID在新創建的條目實體。爲了解決這個問題,我先創建一個實體,將其提交,然後從新創建的實體中獲取ID,並使用抓取的ID創建條目東西

# Create a new Entity object 
entity = Entity(entity_title) 

# Commit the entity 
db.session.add(entity) 
db.session.commit() 

# Get the entity ID 
entity_id = Entity.query.filter_by(name=entity_title).first().id 

# Create a new Entry/Thing object 
entry= Entry(name, entity_id) 

# Commit the entry 
db.session.add(task) 
db.session.commit() 

這種方式似乎相當低效。有沒有其他辦法可以解決這個問題?

回答

0

而不是手動處理外鍵,relationships服務於這個確切目的,允許您處理對象及其關係的內存表示,而不必按正確的順序執行flush() es以找出您應該將外鍵放在哪裏。

class Entry(db.Model): 
    id = db.Column(db.Integer, primary_key=True) 
    name= db.Column(db.String(10)) 

    entity_id = db.Column(db.Integer, db.ForeignKey('entity.id')) 
    entity = relationship(Entity) 

entry = Entry(name="foo", entity=Entry(name="foo")) 
db.session.add(entry) 
db.session.commit() 

注意如何你不必應付entity_id呢?

在你的特殊情況,你也可以找到inheritance有用:

class Entity(db.Model): 
    __tablename__ = "entities" 

    id = db.Column(db.Integer, primary_key = True) 
    name = db.Column(db.String(10)) 
    type = db.Column(db.Enum("entry", "thing")) 

    def __init__(self, name): 
     self.name = name 

    __mapper_args__ = { 
     "polymorphic_on": type, 
    } 

class Entry(Entity): 
    __tablename__ = "entries" 

    id = db.Column(db.Integer, db.ForeignKey('entity.id') primary_key=True) 

class Thing(Entity): 
    __tablename__ = "things" 

    id = db.Column(db.Integer, db.ForeignKey('entity.id') primary_key=True) 

entry = Entry(name="foo") # automatically deals with the entities table 
db.session.add(entry) 
db.session.commit() 
0

您可以使用調用Session.flush()

entity = Entity(entity_title) 

# Commit the entity 
db.session.add(entity) 
db.session.flush() 

之後,你可能有ID在entity.id session.flush()只有「製造」一個實例,但它actualy沒有提交你的會話 你的情況

# Create a new Entity object 
entity = Entity(entity_title) 

# Commit the entity 
db.session.add(entity) 
db.session.flush() 

# Didn't need 
# Get the entity ID 
# entity_id = Entity.query.filter_by(name=entity_title).first().id 

# Create a new Entry/Thing object 
entry= Entry(name, entity.id) 

# Commit the entry 
db.session.add(task) 
db.session.commit() 

這裏文檔 http://docs.sqlalchemy.org/en/latest/orm/session_api.html#sqlalchemy.orm.session.Session.flush

+0

謝謝!這正是我想要的。 – heribert

相關問題