logide-parsimine/bin/top4

69 lines
2.1 KiB
Python
Executable File

#!/usr/bin/python
# encoding: utf-8
"""
Skript:
PATH=path/to/bin:$PATH
cat access.log | top4 | head
"""
# Loo tühi dict tüüpi objekt, siia korjame kokku URL -> mitu korda külastati vastendused
hits = {}
try:
import sys
filename = sys.argv[1]
if filename.endswith(".gz"):
import gzip
stream = gzip.open(filename)
else:
stream = open(filename)
except IndexError:
stream = sys.stdin
sys.stderr.write("Loen standardsisendist...\n")
# Käi ridahaaval fail läbi
for line in stream:
# Kui rea sees ei esine sõnet GET siis jäta vahele
if "GET" not in line:
# Hüppa järgmise tsükli algusse
continue
# Rea sees oli GET, nüüd võime proovida lõpikuda rida tühikute järgi massiiviks
fields = line.split()
# Massiivi indeksid algavad nullist, seitsmenda tulba indeks on 6
path = fields[6]
# Kontrollime kas URL on juba võtmena kasutuses dict objektis
if path in hits:
# Kui on siis lisame ühe juurde
hits[path] = hits[path] + 1
else:
# Kui ei ole siis määra väärtuseks 1
hits[path] = 1
# Kuna dict tüüpi objekti ei saa sorteerida tuleb ta kõigepealt viia sorteeritavale kujule
# nagu nt list:
hits = hits.items()
# Nüüd hits on massiiv kahestest massiividest (path, count)
# Sellise asja sorteerimiseks saab kasutada list objekti funktsiooni sort
# Sorteerimisel on vaja ette anda ka funktsioon mis nopib välja asja mille järgi sorteerida
# See on siin argument nimega key, millele on väärtuseks antud
# nimetu (anonüümne, lambda) funktsioon mis massiivi iga elemendi (path, count)
# kohta tagastab count negatiivse väärtuse
hits.sort(key=lambda (path,count):-count)
# Massiiv on nüüd sorteeritud, esimese 10 vaste kuvamiseks saame massiviist võtta alammassiivi [:10]
# Süntaks [algus:lõpp] kehtib samamoodi nii massiividel (list, tuple) kui ka sõnedel
# Kui algus jäetakse vahele asendatakse see algusega
# Kui lõpp jäetakse vahele asendatakse see lõpuga
# Indeksid võivad negatiivsed olla
for path, count in hits:
print "% 9d %s" % (count, path)