def onFailure(self, transaction, th_q, args, kw): th_q.join() results = transaction.results if errors.hasFailed(results): transaction.state = 2 eventname = self.name failed_apps = dict () #rollback_candidates = [s for s in self.subscribers_s + self.subscribers if not s.ignore_old_failures and s.name in results] rollback_candidates = [s for s in self.subscribers_s + self.subscribers if s.name in results] logger.debug("Begin rollback") for subscriber in rollback_candidates: f = getattr(subscriber, eventname, getattr(subscriber, "onAnyEvent", None)) rollback = getattr(f, "rollback", None) if rollback: logger.debug("ateempting rollback for %s" % subscriber.name) try: rollback(subscriber, *args, **kw) except Exception, err: msg = "Rollback failed for %s:%s (%s)" % (subscriber.name, eventname, err) logger.exception(msg) if errors.isError(results[subscriber.name]): failed_apps[subscriber.name] = results[subscriber.name] if subscriber.adminemail: recipient = subscriber.adminemail appname = subscriber.name err = utils.sendAlert(locals()) if err: logger.warn(err)
def __call__(self, initiator, sid, *args, **kw): logger.info('Syncer publishing event: \"(%s)%s\"' % (initiator, self.name)) args = [cPickle.loads(arg) for arg in args] kw = dict(((cPickle.loads(k), cPickle.loads(v)) for (k,v) in kw.items())) th_q = Queue() __failed = False if not sid: sid = sessions.genVisitId(self.name, args, kw) with threading.Lock(): session = transactions.session() transaction = transactions.newTransaction(self, initiator, *self.argsfilterer(args, kw)) if self.transactional: session.add(transaction) session.commit() tr_id = transaction.id logger.debug("Transaction (%s): Begin" % transaction.id) for subscriber in self.subscribers_s: if not initiator == subscriber.name or self.name == 'onSignon': self.runInThread(sid, transaction, subscriber, args, kw, th_q, True) if errors.hasFailed(transaction.results): __failed = True break results = copy.copy(transaction.results) if __failed: self.onFailure(transaction, th_q, args, kw) else: for subscriber in self.subscribers: if not initiator == subscriber.name: self.runInThread(sid, transaction, subscriber, args, kw, th_q) def thCleanup(transaction, th_q): th_q.join() transaction.state = 2 #transactions.commit() session.commit() session.close() #transactions.session.close() if self.join: print "I'm asked to wait" threading.Thread(target=thCleanup, args=(transaction, th_q)).run() print "My wait is over" else: threading.Thread(target=thCleanup, args=(transaction, th_q)).start() #print '========================================' #print sessions #print results #print '========================================' return tr_id, results