nixspamsum
changeset 8 7f131cf431bc
parent 7 83c4798e291d
child 9 3a392067015c
equal deleted inserted replaced
7:83c4798e291d 8:7f131cf431bc
     7 __version__ = '0.1.2'
     7 __version__ = '0.1.2'
     8 __date__ = '2009-07-03'
     8 __date__ = '2009-07-03'
     9 
     9 
    10 import os
    10 import os
    11 import re
    11 import re
       
    12 import fileinput
    12 
    13 
    13 class NiXSapmSum(object):
    14 class NiXSapmSum(object):
    14     """
    15     """
    15     Small log parser class to parse and summarize NiX Spam DNSBL lookup
    16     Small log parser class to parse and summarize NiX Spam DNSBL lookup
    16     based rejects from a mail log file.
    17     based rejects from a mail log file.
    53         return self._doms
    54         return self._doms
    54 
    55 
    55     def getMXs(self):
    56     def getMXs(self):
    56         return self._mxs
    57         return self._mxs
    57 
    58 
       
    59 
    58 def getOptionParser():
    60 def getOptionParser():
    59     from optparse import OptionParser
    61     from optparse import OptionParser
    60     description = 'NiX Spam DNSBL lookup based rejects summarizer'
    62     description = 'NiX Spam DNSBL lookup based rejects summarizer'
    61     usage  = 'usage: %prog [options] maillog [maillog [...]]'
    63     usage  = 'usage: %prog [options] maillog [maillog [...]]'
    62     version = '%prog '+__version__
    64     version = '%prog '+__version__
    76             choices=('postfix',),
    78             choices=('postfix',),
    77             help='MTA that generated the maillog [default: %default]')
    79             help='MTA that generated the maillog [default: %default]')
    78     return parser
    80     return parser
    79 
    81 
    80 
    82 
    81 def openLogFile(fname):
    83 def check_files(log_files):
    82     try:
    84     """Checks that all files from *log_files* exist and all of them are
    83         fh = open(fname)
    85     readable.
    84         return fh
    86 
    85     except IOError, e:
    87     If a file doesn't exist or is not readable, it will be removed from
    86         os.sys.stderr.write('Warning: %s\nskipped file: %s\n' % (e.strerror,
    88     *log_files* set.
    87             fname))
    89 
       
    90     This function will return *True*, if at least one file has passed the
       
    91     checks. Otherwise *False* will be returned. And the *log_files* set
       
    92     will be emptied.
       
    93 
       
    94     :param log_files: set of file names
       
    95     :type log_files: set
       
    96     :rtype: bool"""
       
    97     assert isinstance(log_files, set), 'log_files argument must be a set'
       
    98     lf_copy = log_files.copy()
       
    99     for lf in lf_copy:
       
   100         if not os.path.isfile(lf):
       
   101             os.sys.stderr.write('Warning: No such file: %r\n' % lf)
       
   102             log_files.remove(lf)
       
   103         elif not os.access(lf, os.R_OK):
       
   104             os.sys.stderr.write('Warning: Cannot read file: %r\n' % lf)
       
   105             log_files.remove(lf)
       
   106 
       
   107     if log_files:
       
   108         return True
       
   109     return False
    88 
   110 
    89 
   111 
    90 def buildTable(output, domains, percent, orderBy):
   112 def buildTable(output, domains, percent, orderBy):
    91     k = 0 if orderBy == 'name' else 1
   113     k = 0 if orderBy == 'name' else 1
    92     doms = sorted(domains.items(), lambda d,c: cmp(d[k],c[k]), reverse=k)
   114     doms = sorted(domains.items(), lambda d,c: cmp(d[k],c[k]), reverse=k)
   135     print output.getvalue()
   157     print output.getvalue()
   136 
   158 
   137 def main():
   159 def main():
   138     parser = getOptionParser()
   160     parser = getOptionParser()
   139     opts, args = parser.parse_args()
   161     opts, args = parser.parse_args()
   140     if len(args) < 1:
   162     if not args:
   141         parser.error('No log file specified')
   163         parser.error('No log file specified')
       
   164     # drop duplicates
       
   165     log_files = set(args)
       
   166     # remove inexistent/unreadable files
       
   167     if not check_files(log_files):
       
   168         os.sys.stderr.write('No readable log files found\n')
       
   169         return 1
       
   170 
   142     nixss = NiXSapmSum()
   171     nixss = NiXSapmSum()
   143     nixss.setLogFormat(opts.format)
   172     nixss.setLogFormat(opts.format)
   144     for fn in args:
   173 
   145         fh = openLogFile(fn)
   174     fi = fileinput.FileInput(log_files, openhook=fileinput.hook_compressed)
   146         if fh is not None:
   175     nixss.parseLog(fi)
   147             nixss.parseLog(fh)
   176     fi.close()
   148             fh.close()
       
   149     showResult(nixss, opts)
   177     showResult(nixss, opts)
       
   178     return 0
   150 
   179 
   151 if __name__ == '__main__':
   180 if __name__ == '__main__':
   152     main()
   181     os.sys.exit(main())