Which is correct? I know the first will work but I suspect it's more work for the DB than is possibly necessary. Will the second work just as well but with less work for the DB? I'm using MySQL FWIW.
for item in items:
db.session.add(item)
db.session.commit()
or
for item in items:
db.session.add(item)
db.session.commit()
commit() commits (persists) those changes to the database. flush() is always called as part of a call to commit() (1). When you use a Session object to query the database, the query will return results both from the database and from the flushed parts of the uncommitted transaction it holds.
connection() method at the start of a transaction: from sqlalchemy. orm import Session # assume session just constructed sess = Session(bind=engine) # call connection() with options before any other operations proceed. # this will procure a new connection from the bound engine and begin a real # database transaction.
Session. commit() means that the changes made to the objects in the Session so far will be persisted into the database while Session. rollback() means those changes will be discarded. Session.
sqlalchemy. A scoped_session is constructed by calling it, passing it a factory which can create new Session objects. A factory is just something that produces a new object when called, and in the case of Session , the most common factory is the sessionmaker , introduced earlier in this section.
I think your second solution is better but it depends on how you have configured your Session. Specifically the autoflush and autocommit settings. Also you should be using an engine that has good support for transactions, such as innodb.
Assuming you have autocommit and autoflush both off then you would be flushing your insert to the server, committing the prior transaction and then creating another transaction on every iteration which is creating a lot of unnecessary work both in SQLAlchemy and MySQL.
I would recommend using add_all if you have a simple list of items to add as in your example, otherwise if you do need the loop then definitely apply the commit outside the loop.
http://docs.sqlalchemy.org/en/latest/orm/session.html#sqlalchemy.orm.session.Session.add_all
db.session.add_all(items) db.session.commit()
An additional note, if something were to go wrong part way through the loop your transaction would rollback writes only to your prior commit in the loop which probably isn't what you want if you are using transactions. For example only half your items in the list might be written to the database if an error occurs half way through your loop. Whereas calling commit outside the loop guarantees that your loop has finished and will be ALL committed or ALL rolled back.
To add on the solution: This is how you can use add_all()
user1 = User(name='user1') user2 = User(name='user2') session.add(user1) session.add(user2) session.commit() # write changes to the database
Instead of the two add lines use
session.add_all([user1, user2])
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With