#!/usr/bin/env python
#------------------------------------------------------------------------------
# @(#) $Id: ACSPerfReportGen.py,v 1.3 2004/10/15 22:16:35 dfugate Exp $
#
# ALMA - Atacama Large Millimiter Array
# (c) Associated Universities, Inc. Washington DC, USA, 2001
# (c) European Southern Observatory, 2002
# Copyright by ESO (in the framework of the ALMA collaboration)
# and Cosylab 2002, All rights reserved
#
# This library is free software; you can redistribute it and/or
# modify it under the terms of the GNU Lesser General Public
# License as published by the Free Software Foundation; either
# version 2.1 of the License, or (at your option) any later version.
#
# This library is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public
# License along with this library; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
#------------------------------------------------------------------------------
'''
TODO:
- all
'''
#------------------------------------------------------------------------------
__version__ = "$Id: ACSPerfReportGen.py,v 1.3 2004/10/15 22:16:35 dfugate Exp $"
#------------------------------------------------------------------------------
from sys import argv, stdout
from copy import deepcopy
import anydbm
import time
from AcsutilPy.FindFile import findFile
#------------------------------------------------------------------------------
htmlBegin='''
ACS Performance Analysis Report
ACS Performance Analysis Report
'''
msgBegin='''
%s
'''
htmlEnd='''
This report was generated on: %s
'''
testMachineInfo = {}
specialKeys = ['cpu', 'mem' ]
#------------------------------------------------------------------------------
def getDBasDict(dbName):
'''
Helper function returns an ACS performance database as a Python dictionary.
In this dict, the keys are the test type and the values are lists of tests.
'''
if findFile(dbName)[0]!="":
dbName=findFile(dbName)[0]
DB = anydbm.open(DBNAME, 'r')
retVal = {}
#get each and every individual test from the database
for key in DB.keys():
#turn the value back into a Python dictionary
tDict = eval(DB[key])
#now figure out what type of performance test we're dealing with...
msg = tDict['msg']
#add this type of performance test to the return dictionary if it has
#not been encountered previously
if not retVal.has_key(msg):
retVal[msg]=[]
#add the dictionary describing the test to the return value
retVal[msg].append(tDict)
DB.close()
return retVal
#------------------------------------------------------------------------------
def sortDict(inDict):
'''
Sorts a dictionary (of the same type returned by the getDBasDict function).
'''
#sort each value (e.g., list)
for key in inDict.keys():
inDict[key].sort(performanceSort)
#------------------------------------------------------------------------------
def performanceSort(a,b):
'''
Helper function used by sortDict function to sort two dictionaries describing
a performance test. Sorts based on hostname first and then date.
'''
#run from the same host
if a['ip']==b['ip'] and a['date'] < b['date']:
return -1
elif a['ip'] < b['ip']:
return -1
else:
return 1
#------------------------------------------------------------------------------
def generateHTML(inDict, outFile=stdout):
'''
Helper function generates an HTML report based on a dictionary returned by
getDBasDict function.
'''
#make a deepcopy of this so we can do with it as we please!
inDict = deepcopy(inDict)
#sort it
sortDict(inDict)
#print out the HTML tags all reports will begin with
print>>outFile, htmlBegin
for msg in inDict.keys():
print>>outFile, msgBegin % (msg)
genHTMLForMsg(inDict[msg], outFile)
#print out remaining HTML
printMachineInfo(outFile)
print>>outFile, htmlEnd % (time.asctime())
#------------------------------------------------------------------------------
def genHTMLForMsg(inList, outFile=stdout):
'''
'''
tList = []
for tDict in inList:
#remove this key
del tDict['msg']
#get a list of all remaining keys
realKeys = inList[0].keys()
#rearrange the list of keys
keys = ['ip', 'lang', 'date', 'runs', 'avg', 'mindur', 'maxdur', 'cpu', 'mem', 'units']
#strip out duplicated keys
for key in keys:
try:
realKeys.remove(key)
except:
pass
#merge the two lists
keys = keys + realKeys
#remove cpu and mem
keys.remove('cpu')
keys.remove('mem')
#print out an initial row full of column descriptions
print>>outFile, ''
for key in keys:
print>>outFile, ' %s | ' % (getNiceColHeader(key))
print>>outFile, '
'
#print out the rest of the rows
for tDict in inList:
print>>outFile, ''
for key in keys:
print>>outFile, ' %s | ' % (tDict[key])
if not testMachineInfo.has_key(tDict['ip']):
testMachineInfo[tDict['ip']] = { 'cpu':tDict['cpu'], 'mem':tDict['mem'] }
if testMachineInfo[tDict['ip']]['cpu'] == "Unknown":
testMachineInfo[tDict['ip']]['cpu'] = tDict['cpu']
if testMachineInfo[tDict['ip']]['mem'] == "Unknown":
testMachineInfo[tDict['ip']]['mem'] = tDict['mem']
print>>outFile, '
'
#print out remaining HTML
print>>outFile, msgEnd
#------------------------------------------------------------------------------
def getNiceColHeader(origHeader):
'''
Helper function returns a more descriptive column header or just the original
header if no alternative is known.
'''
tDict = { 'msg' : "Description",
'avg' : "Average
Time to
Complete",
'runs' : "Number
of
Runs",
'mindur' : "Min.
Run
Time",
'maxdur' : "Max.
Run
Time",
'cpu' : "PC
Speed",
'mem' : "PC
Memory",
'date' : "Date
of
Run",
'ip' : "PC
Name",
'lang' : "Prog.
Lang",
'units' : "Time
Units"
}
if tDict.has_key(origHeader):
return tDict[origHeader]
else:
return origHeader
#------------------------------------------------------------------------------
def printMachineInfo(outFile):
'''
'''
print>>outFile, msgBegin % ("General Info on Test Machines")
#print out an initial row full of column descriptions
print>>outFile, ' %s | ' % ("PC Name")
for key in specialKeys:
print>>outFile, ' %s | ' % (getNiceColHeader(key))
print>>outFile, '
'
#print out the rest of the rows
for machineName in testMachineInfo.keys():
print>>outFile, ' %s | ' % (machineName)
tDict = testMachineInfo[machineName]
for key in specialKeys:
print>>outFile, ' %s | ' % (tDict[key])
print>>outFile, '
'
print '''
'''
#------------------------------------------------------------------------------
if __name__=="__main__":
DBNAME = argv[1] #name of the database
#open the database
joe = getDBasDict(DBNAME)
generateHTML(joe)