1#!/usr/bin/env python 2 3""" 4Extract iperf data from json blob and format for gnuplot. 5""" 6 7import json 8import os 9import sys 10 11import os.path 12from optparse import OptionParser 13 14import pprint 15# for debugging, so output to stderr to keep verbose 16# output out of any redirected stdout. 17pp = pprint.PrettyPrinter(indent=4, stream=sys.stderr) 18 19def generate_output(iperf, options): 20 for i in iperf.get('intervals'): 21 for ii in i.get('streams'): 22 if options.verbose: pp.pprint(ii) 23 row = '{0} {1} {2} {3} {4}\n'.format( 24 round(float(ii.get('start')), 4), 25 ii.get('bytes'), 26 # to Gbits/sec 27 round(float(ii.get('bits_per_second')) / (1000*1000*1000), 3), 28 ii.get('retransmits'), 29 round(float(ii.get('snd_cwnd')) / (1000*1000), 2) 30 ) 31 yield row 32 33def main(): 34 usage = '%prog [ -f FILE | -o OUT | -v ]' 35 parser = OptionParser(usage=usage) 36 parser.add_option('-f', '--file', metavar='FILE', 37 type='string', dest='filename', 38 help='Input filename.') 39 parser.add_option('-o', '--output', metavar='OUT', 40 type='string', dest='output', 41 help='Optional file to append output to.') 42 parser.add_option('-v', '--verbose', 43 dest='verbose', action='store_true', default=False, 44 help='Verbose debug output to stderr.') 45 options, args = parser.parse_args() 46 47 if not options.filename: 48 parser.error('Filename is required.') 49 50 file_path = os.path.normpath(options.filename) 51 52 if not os.path.exists(file_path): 53 parser.error('{f} does not exist'.format(f=file_path)) 54 55 with open(file_path,'r') as fh: 56 data = fh.read() 57 58 try: 59 iperf = json.loads(data) 60 except Exception as e: 61 parser.error('Could not parse JSON from file (ex): {0}'.format(str(e))) 62 63 if options.output: 64 absp = os.path.abspath(options.output) 65 d,f = os.path.split(absp) 66 if not os.path.exists(d): 67 parser.error('Output file directory path {0} does not exist'.format(d)) 68 fh = open(absp, 'a') 69 else: 70 fh = sys.stdout 71 72 for i in generate_output(iperf, options): 73 fh.write(i) 74 75 76if __name__ == '__main__': 77 main()