On 03/28/2016 03:21 PM, Yegor Roganov wrote:
I would like to get what I described in the subject: attach an event
listener that will execute once after current transaction's successful
commit (analogue to django's on_commit
<https://docs.djangoproject.com/en/1.9/topics/db/transactions/#django.db.transaction.on_commit>
 ).
If current transaction rolls back, the event listener(s) should be
discarded.

set your own token to disable the event after the transaction ends:

@event.listens_for(sess, 'after_commit')
def foo(session):
   if "my_token" not in session.info:
       print("do my event")


@event.listens_for(sess, "after_transaction_end")
def bar(session, transaction):
   session.info["my_token"] = True





I have tried using `event.listens_for(sess, 'after_commit', once=True)`,
but probably as expected it will execute the callback if session
continues to be used after rollback. Here is a complete source that you
can play around with:
|
from sqlalchemy import Column, Integer, create_engine, event
from sqlalchemy.orm import sessionmaker
from sqlalchemy.ext.declarative import declarative_base


Base = declarative_base()

engine = create_engine('sqlite:///:memory:', echo=True)

Session = sessionmaker(bind=engine)


class User(Base):
     __tablename__ = 'users'

     id = Column(Integer, primary_key=True)

Base.metadata.create_all(engine)

sess = Session()

sess.add(User(id=1))
sess.commit()


@event.listens_for(sess, 'after_commit', once=True)
def foo(session):
     print("shouldn't be called since the transaction will be rolled back!")

sess.add(User(id=1))
try:
     sess.commit()
except:
     sess.rollback()

sess.add(User(id=2))
sess.commit()  # event callback will be called here

|

There is also an `after_transaction_end` event, but unfortunately I have
not managed to bend it to my needs as well: 1) I haven't found public
API to determine the transaction state when the callback executes 2) If
an event listener is attached in a subtransaction, the callback will get
called when the subransaction commits, while I'd like to the callback to
only get called when the 'outermost' transaction commits successfully.


Greatly appreciate any help.

--
You received this message because you are subscribed to the Google
Groups "sqlalchemy" group.
To unsubscribe from this group and stop receiving emails from it, send
an email to sqlalchemy+unsubscr...@googlegroups.com
<mailto:sqlalchemy+unsubscr...@googlegroups.com>.
To post to this group, send email to sqlalchemy@googlegroups.com
<mailto:sqlalchemy@googlegroups.com>.
Visit this group at https://groups.google.com/group/sqlalchemy.
For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to the Google Groups 
"sqlalchemy" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to sqlalchemy+unsubscr...@googlegroups.com.
To post to this group, send email to sqlalchemy@googlegroups.com.
Visit this group at https://groups.google.com/group/sqlalchemy.
For more options, visit https://groups.google.com/d/optout.

Reply via email to