PageRenderTime 72ms CodeModel.GetById 47ms app.highlight 20ms RepoModel.GetById 1ms app.codeStats 1ms

/Demo/scripts/ftpstats.py

http://unladen-swallow.googlecode.com/
Python | 145 lines | 116 code | 10 blank | 19 comment | 29 complexity | 710d30da42671b2022512b9c95e10708 MD5 | raw file
  1#! /usr/bin/env python
  2
  3# Extract statistics from ftp daemon log.
  4
  5# Usage:
  6# ftpstats [-m maxitems] [-s search] [file]
  7# -m maxitems: restrict number of items in "top-N" lists, default 25.
  8# -s string:   restrict statistics to lines containing this string.
  9# Default file is /usr/adm/ftpd;  a "-" means read standard input.
 10
 11# The script must be run on the host where the ftp daemon runs.
 12# (At CWI this is currently buizerd.)
 13
 14import os
 15import sys
 16import re
 17import string
 18import getopt
 19
 20pat = '^([a-zA-Z0-9 :]*)!(.*)!(.*)!([<>].*)!([0-9]+)!([0-9]+)$'
 21prog = re.compile(pat)
 22
 23def main():
 24    maxitems = 25
 25    search = None
 26    try:
 27        opts, args = getopt.getopt(sys.argv[1:], 'm:s:')
 28    except getopt.error, msg:
 29        print msg
 30        print 'usage: ftpstats [-m maxitems] [file]'
 31        sys.exit(2)
 32    for o, a in opts:
 33        if o == '-m':
 34            maxitems = string.atoi(a)
 35        if o == '-s':
 36            search = a
 37    file = '/usr/adm/ftpd'
 38    if args: file = args[0]
 39    if file == '-':
 40        f = sys.stdin
 41    else:
 42        try:
 43            f = open(file, 'r')
 44        except IOError, msg:
 45            print file, ':', msg
 46            sys.exit(1)
 47    bydate = {}
 48    bytime = {}
 49    byfile = {}
 50    bydir = {}
 51    byhost = {}
 52    byuser = {}
 53    bytype = {}
 54    lineno = 0
 55    try:
 56        while 1:
 57            line = f.readline()
 58            if not line: break
 59            lineno = lineno + 1
 60            if search and string.find(line, search) < 0:
 61                continue
 62            if prog.match(line) < 0:
 63                print 'Bad line', lineno, ':', repr(line)
 64                continue
 65            items = prog.group(1, 2, 3, 4, 5, 6)
 66            (logtime, loguser, loghost, logfile, logbytes,
 67             logxxx2) = items
 68##                      print logtime
 69##                      print '-->', loguser
 70##                      print '--> -->', loghost
 71##                      print '--> --> -->', logfile
 72##                      print '--> --> --> -->', logbytes
 73##                      print '--> --> --> --> -->', logxxx2
 74##                      for i in logtime, loghost, logbytes, logxxx2:
 75##                              if '!' in i: print '???', i
 76            add(bydate, logtime[-4:] + ' ' + logtime[:6], items)
 77            add(bytime, logtime[7:9] + ':00-59', items)
 78            direction, logfile = logfile[0], logfile[1:]
 79            # The real path probably starts at the last //...
 80            while 1:
 81                i = string.find(logfile, '//')
 82                if i < 0: break
 83                logfile = logfile[i+1:]
 84            add(byfile, logfile + ' ' + direction, items)
 85            logdir = os.path.dirname(logfile)
 86##              logdir = os.path.normpath(logdir) + '/.'
 87            while 1:
 88                add(bydir, logdir + ' ' + direction, items)
 89                dirhead = os.path.dirname(logdir)
 90                if dirhead == logdir: break
 91                logdir = dirhead
 92            add(byhost, loghost, items)
 93            add(byuser, loguser, items)
 94            add(bytype, direction, items)
 95    except KeyboardInterrupt:
 96        print 'Interrupted at line', lineno
 97    show(bytype, 'by transfer direction', maxitems)
 98    show(bydir, 'by directory', maxitems)
 99    show(byfile, 'by file', maxitems)
100    show(byhost, 'by host', maxitems)
101    show(byuser, 'by user', maxitems)
102    showbar(bydate, 'by date')
103    showbar(bytime, 'by time of day')
104
105def showbar(dict, title):
106    n = len(title)
107    print '='*((70-n)//2), title, '='*((71-n)//2)
108    list = []
109    keys = dict.keys()
110    keys.sort()
111    for key in keys:
112        n = len(str(key))
113        list.append((len(dict[key]), key))
114    maxkeylength = 0
115    maxcount = 0
116    for count, key in list:
117        maxkeylength = max(maxkeylength, len(key))
118        maxcount = max(maxcount, count)
119    maxbarlength = 72 - maxkeylength - 7
120    for count, key in list:
121        barlength = int(round(maxbarlength*float(count)/maxcount))
122        bar = '*'*barlength
123        print '%5d %-*s %s' % (count, maxkeylength, key, bar)
124
125def show(dict, title, maxitems):
126    if len(dict) > maxitems:
127        title = title + ' (first %d)'%maxitems
128    n = len(title)
129    print '='*((70-n)//2), title, '='*((71-n)//2)
130    list = []
131    keys = dict.keys()
132    for key in keys:
133        list.append((-len(dict[key]), key))
134    list.sort()
135    for count, key in list[:maxitems]:
136        print '%5d %s' % (-count, key)
137
138def add(dict, key, item):
139    if dict.has_key(key):
140        dict[key].append(item)
141    else:
142        dict[key] = [item]
143
144if __name__ == "__main__":
145    main()