def pendings (self): while self.pending.running: w = self.wait () if w is None: break agn.log (agn.LV_DEBUG, 'par', '%s: process finished' % w.description) while self.pending.queued and len (self.pending.running) < self.processes: prio = agn.Stream.of (self.pending.queued.keys ()).sorted ().first () w = self.pending.queued[prio].pop (0) if not self.pending.queued[prio]: del self.pending.queued[prio] # if w.prepare is not None: try: w.prepare (*w.args, **w.kws) except Exception as e: agn.logexc (agn.LV_ERROR, 'par', '%s: prepare fails: %s' % (w.description, e)) def starter (): self.processtitle (w.description) rc = w.method (*w.args, **w.kws) self.processtitle () return rc w.pid = self.pending.control.spawn (starter) self.pending.running.append (w) agn.log (agn.LV_DEBUG, 'par', '%s: launched' % w.description) return self.pending.running or self.pending.queued
def execute (self, size): global running for path in self.ws: ok = True try: fd = open (path, 'r') body = fd.read (size) fd.close () except IOError, e: agn.log (agn.LV_ERROR, 'child', 'Failed to open %s: %r' % (path, e.args)) ok = False if ok: try: msg = email.message_from_string (body) bav = BAV (body, msg, -1) if bav.execute_is_no_systemmail (): ok = bav.execute_filter_or_forward () else: ok = bav.execute_scan_and_unsubscribe () except Exception as e: agn.logexc (agn.LV_ERROR, 'child', 'Fatal: catched failure: %s' % e) ok = False if ok: self.ws.success (bav.sender) else: self.ws.fail () if not running: break
def wait(self, block=False): w = None while self.pending.running and w is None: rc = self.pending.control.join(block=block) if not rc.pid: break # w = (agn.Stream.of( self.pending.running).filter(lambda r: r.pid == rc.pid).first( no=None)) if w is not None: agn.log( agn.LV_DEBUG, 'par', '%s: returned with %s' % (w.description, ('exit with %d' % rc.exitcode) if rc.exitcode is not None else ('died due to signal %d' % rc.signal))) if w.finalize is not None: try: w.finalize(rc, *w.args, **w.kws) except Exception as e: agn.logexc( agn.LV_ERROR, 'per', '%s: finalize fails: %s' % (w.description, e)) self.pending.running.remove(w) self.lockTitle() return w
def run(self): """start the server""" while not self.term: try: self.server.handle_request() except select.error: pass except Exception, e: agn.logexc(agn.LV_ERROR, 'run', 'Unexpected exception caught: %s' % str(e))
def execute_filter_or_forward (self): if self.parsedEMail.ignore: parm = 'ignore' else: match = self.rule.matchHeader (self.msg, 'filter') if not match is None and not match[1].inverse: if not match[1].parm: parm = 'save' else: parm = match[1].parm else: parm = 'sent' fwd = None if parm == 'sent': if 'fwd' in self.parm: fwd = self.parm['fwd'] if self.hasSpamAssassin: fwd = self.filterWithSpamAssassin (fwd) self.saveMessage (parm) if parm == 'sent': while self.msg.has_key (BAV.x_agn): del self.msg[BAV.x_agn] if fwd is not None: sendMsg = self.enrich () self.sendmail (sendMsg, fwd) if self.parm.has_key ('ar'): ar = self.parm['ar'] if self.parm.has_key ('from') and self.headerFrom and self.headerFrom[1]: sender = self.headerFrom[1] ar = Autoresponder (ar, sender) if self.parm.has_key ('armid'): agn.log (agn.LV_INFO, 'fof', 'Trigger autoresponder message for %s' % sender) ar.triggerMessage (self.cinfo, self.parm, self.dryrun) else: nmsg = ar.createMessage (self.msg, self.parm, self.dryrun) if nmsg: agn.log (agn.LV_INFO, 'fof', 'Forward newly generated autoresponder message to %s' % sender) self.sendmail (nmsg, sender) else: agn.log (agn.LV_INFO, 'fof', 'No sender in original message found') if self.parm.has_key ('sub') and self.parm.has_key ('cid') and self.parm.has_key ('from'): try: (mlist, form) = self.parm['sub'].split (':', 1) cid = self.parm['cid'] if self.headerFrom and self.headerFrom[1]: self.subscribe (self.headerFrom[1].lower (), self.headerFrom[0], int (cid), int (mlist), int (form)) except ValueError, e: agn.logexc (agn.LV_ERROR, 'fof', 'Failed to parse subscribe parameter: %r' % (e.args, ))
def __call__ (self): rc = True if self.open (): self.ref.processtitle.push (self.name) try: self.execute () self.ref.pendings () except Exception as e: agn.logexc (agn.LV_ERROR, self.name, 'failed due to: %s' % e) rc = False finally: self.close () self.ref.processtitle.pop () self.ref.lockTitle () return rc
def scan(self): global term self.expireTracker() try: fp = agn.Filepos(self.maillog, self.saveFile, checkpoint=1000) except agn.error as e: agn.log( agn.LV_INFO, 'main', 'Unable to open %s: %s, try to gain access' % (self.maillog, e)) n = agn.call([agn.mkpath(agn.base, 'bin', 'smctrl'), 'logaccess']) if n != 0: agn.log(agn.LV_ERROR, 'main', 'Failed to gain access to %s (%d)' % (self.maillog, n)) with agn.Ignore(OSError): st = os.stat(self.saveFile) if st.st_size == 0: agn.log(agn.LV_ERROR, 'main', 'Remove corrupt empty file %s' % self.saveFile) os.unlink(self.saveFile) return self.mtrack.open() try: sp = SyslogParser() for line in fp: try: info = sp(line) if info is not None: if not self.parse(info, line): agn.log(agn.LV_WARNING, 'scan', 'Unparsable line: %s (%r)' % (line, info)) else: agn.log(agn.LV_WARNING, 'scan', 'Unparsable format: %s' % line) except Exception as e: agn.logexc(agn.LV_ERROR, 'scan', 'Failed to parse line: %s: %s' % (line, e)) if term: break finally: fp.close() self.mtrack.close() self.processCompleted()
def main(): rc = 1 (opts, param) = getopt.getopt(sys.argv[1:], 'v') for opt in opts: if opt[0] == '-v': agn.outlevel = agn.LV_DEBUG agn.outstream = sys.stderr agn.lock() agn.log(agn.LV_INFO, 'main', 'Starting up') db = agn.DBaseID() if db is not None: # db.log = lambda a: agn.log (agn.LV_DEBUG, 'db', a) curs = db.cursor() if curs is not None: softbounce = Softbounce(db, curs) if softbounce.setup(): try: softbounce.removeOldEntries() softbounce.setupTimestamp() softbounce.collectNewBounces() softbounce.finalizeTimestamp() softbounce.mergeNewBounces() softbounce.convertToHardbounce() rc = 0 except agn.error as e: agn.logexc(agn.LV_ERROR, 'main', 'Failed due to %s' % e) softbounce.ok = False softbounce.done() else: agn.log(agn.LV_ERROR, 'main', 'Setup of handling failed') curs.sync() curs.close() else: agn.log(agn.LV_ERROR, 'main', 'Failed to get database cursor') db.close() else: agn.log(agn.LV_ERROR, 'main', 'Failed to setup database interface') agn.log(agn.LV_INFO, 'main', 'Going down') agn.unlock() if rc: sys.exit(rc)
def handle_error(self, request, client_address): agn.logexc( agn.LV_ERROR, 'rq', 'Request failed for %s: %r' % (client_address[0], request))