Ignore:
Timestamp:
05/16/13 08:56:59 (11 years ago)
Author:
dennis
Message:

The following has changed for new_rack_pbsmon.py and sara_nodes.py

  • Removed dependicy PBSAdvancedParser.py
  • Switched from OptionParser? to argparse
  • Added a _print function which will work with all Python versions
File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/examples/new_rack_pbsmon.py

    r288 r294  
    1313
    1414"""
    15 Usage: pbsmon [hosts]....
    16 
    17 Specifying hostnames:
     15specifying hostnames:
    1816  To specify a range use the [] to indicate a range, a couple of examples:
    1917
     
    3432import re
    3533import types
    36 from optparse import OptionParser
    3734
    3835import pbs
    39 from PBSAdvancedParser import AdvancedParser
    4036from PBSQuery import PBSQuery
    4137from PBSQuery import PBSError
     
    10298}
    10399
     100####
     101## Rewriting the print function, so it will work with all versions of Python
     102def _print(*args, **kwargs):
     103    '''A wrapper function to make the functionality for the print function the same for Python2.4 and higher'''
     104    ## First try if we are running in Python3 and higher
     105    try:
     106        Print = eval('print')
     107        Print(*args, **kwargs)
     108    except SyntaxError:
     109        ## Then Python2.6 and Python2.7
     110        try:
     111            D = dict()
     112            exec('from __future__ import print_function\np=print', D)
     113            D['p'](*args, **kwargs)
     114            del D
     115        ## Finally Python2.5 or lower
     116        except SyntaxError:
     117            del D
     118            fout    = kwargs.get('file', sys.stdout)
     119            write   = fout.write
     120            if args:
     121                write(str(args[0]))
     122                sep = kwargs.get('sep', ' ')
     123                for arg in args[1:]:
     124                    write(sep)
     125                    write(str(a))
     126                write(kwargs.get('end', '\n'))
     127
     128## Import argparse here, as I need the _print function
     129try:
     130    import argparse
     131except ImportError:
     132    _print('Cannot find argparse module', file=sys.stderror)
     133    sys.exit(1)
     134
     135####
     136## BEGIN functions for hostrange parsing
     137def l_range(start, end):
     138    '''The equivalent for the range function, but then with letters, uses the ord function'''
     139    start = ord(start)
     140    end   = ord(end)
     141    rlist = list()
     142
     143    ## A ord number must be between 96 (a == 97) and 122 (z == 122)
     144    if start < 96 or start > 122 and end < 96 or end > 122:
     145        raise Exception('You can only use letters a to z')
     146    ## If start is greater then end, then the range is invalid
     147    elif start > end:
     148        raise Exception('The first letter must be smaller then the second one')
     149    ## Just revert the ord number to the char
     150    for letter in range(start, end + 1):
     151        rlist.append(chr(letter))
     152    return rlist
     153
     154def return_range(string):
     155    '''This function will return the possible values for the given ranges'''
     156
     157    ## First check if the first char is valid
     158    if string.startswith(',') or string.startswith('-'):
     159        raise Exception('Given pattern is invalid, you can\'t use , and - at the beginning')
     160
     161    numbers_chars        = list()
     162    equal_width_length  = 0
     163
     164    ## First splitup the sections (divided by ,)
     165    for section in string.split(','):
     166        ## Within a section you can have a range, max two values
     167        chars = section.split('-')
     168        if len(chars) == 2:
     169            ## When range is a digit, simply use the range function
     170            if chars[0].isdigit() and chars[1].isdigit():
     171                ## Owke, check for equal_width_length
     172                if chars[0][0] == '0' or chars[1][0] == '0':
     173                    if len(chars[0]) >= len(chars[1]):
     174                        equal_width_length = len(chars[0])
     175                    else:
     176                        equal_width_length = len(chars[1])
     177                ## Don't forget the +1
     178                numbers_chars += range(int(chars[0]), int(chars[1])+1)
     179            ## If one of the two is a digit, raise an exceptio
     180            elif chars[0].isdigit() or chars[1].isdigit():
     181                raise Exception('I can\'t combine integers with letters, change your range please')
     182            ## Else use the l_range
     183            else:
     184                numbers_chars += l_range(chars[0], chars[1])
     185        else:
     186            ## If the value of the section is a integer value, check if it has a 0
     187            if section.isdigit() and section[0] == '0':
     188                if len(section) > equal_width_length:
     189                    equal_width_length = len(section)
     190            numbers_chars.append(section)
     191
     192        ## if the equal_width length is greater then 0, rebuild the list
     193        ## 01, 02, 03, ... 10
     194        if equal_width_length > 0:
     195            tmp_list = list()
     196            for number_char in numbers_chars:
     197                if type(number_char) is types.IntType or number_char.isdigit():
     198                    tmp_list.append('%0*d' % ( equal_width_length, int(number_char)))
     199                else:
     200                    tmp_list.append(number_char)
     201            numbers_chars = tmp_list
     202
     203    return numbers_chars
     204
     205def product(*args, **kwargs):
     206    '''Taken from the python docs, does the same as itertools.product,
     207    but this also works for py2.5'''
     208    pools = map(tuple, args) * kwargs.get('repeat', 1)
     209    result = [[]]
     210    for pool in pools:
     211        result = [x+[y] for x in result for y in pool]
     212    for prod in result:
     213        yield tuple(prod)
     214
     215def parse_args(args):
     216    rlist = list()
     217    for arg in args:
     218        parts = re.findall(HOSTRANGE, arg)
     219        if parts:
     220            ## create a formatter string, sub the matched patternn with %s
     221            string_format = re.sub(HOSTRANGE, '%s', arg)
     222            ranges = list()
     223
     224            ## detect the ranges in the parts
     225            for part in parts:
     226                ranges.append(return_range(part))
     227           
     228            ## produce the hostnames
     229            for combination in product(*ranges):
     230                rlist.append(string_format % combination)
     231        else:
     232            rlist.append(arg)
     233    return rlist
     234
     235## END functions for hostrange parsing
     236####
     237
    104238def sanitize_jobs( jobs ):
    105239
     
    141275            p = PBSQuery( OPT_SERVERNAME )
    142276    except PBSError, reason:
    143         print 'Error: %s' % reason
     277        _print('Error: %s' % reason)
    144278        sys.exit( -1 )
    145279
     
    151285        nodes = p.getnodes( attr )
    152286    except PBSError, reason:
    153         print 'Error: %s' % reason
     287        _print('Error: %s' % reason)
    154288        sys.exit( -1 )
    155289
     
    264398    save_column = None
    265399   
    266     print   
    267     print '  ',
     400    _print()   
     401    _print('  ', end=' ')
    268402    for rack in xrange( START_RACK, racknr + 1 ):
    269403       
     
    279413                    char = save_column
    280414                    save_column = None
    281                 print char,
    282         else:
    283             print char,
    284     print   
    285 
    286     print '  ',
     415                _print(char, end=' ')
     416        else:
     417            _print(char, end=' ')
     418    _print()   
     419
     420    _print('  ', end=' ')
    287421    for rack in xrange( START_RACK, racknr + 1 ):
    288422       
     
    290424        if OPT_SKIP_EMPTY_RACKS:
    291425            if nodes.has_key( rack ):
    292                 print char,
    293         else:
    294             print char,
    295     print
     426                _print(char, end=' ')
     427        else:
     428            _print(char, end=' ')
     429    _print()
    296430
    297431    for node in xrange( 1, nodenr + 1 ):
    298         print '%2d' % node,
     432        _print('%2d' % node, end=' ')
    299433
    300434        for rack in xrange( START_RACK, racknr + 1 ):
     
    303437                    continue
    304438            try:
    305                 print nodes[ rack ][ node ][ 'state_char' ],
     439                _print(nodes[ rack ][ node ][ 'state_char' ], end=' ')
    306440            except KeyError:
    307                 print ' ',
    308         print
    309     print
     441                _print(' ', end=' ')
     442        _print()
     443    _print()
    310444
    311445def print_table_summary():
     
    319453            p = PBSQuery( OPT_SERVERNAME )
    320454    except PBSError, reason:
    321         print 'error: %s' % reason
     455        _print('error: %s' % reason)
    322456        sys.exit(-1)
    323457
     
    327461        nodes = p.getnodes(attr)
    328462    except PBSError, reason:
    329         print 'error: %s' % reason
     463        _print('error: %s' % reason)
    330464        sys.exit(-1)
    331465
     
    351485        if node.is_free():                          # can happen for single CPU jobs
    352486            if node.has_job():
    353 #               print 'TD: %s' % nodename, node
     487#               _print('TD: %s' % nodename, node)
    354488                state_char = PBS_STATES[pbs_ND_single]
    355489                count_states[pbs.ND_free] -=  1
     
    363497                #   count_states[pbs_ND_free_serial] +=  1
    364498               
    365 #       print 'TD: %s %s' % (nodename, state_char)
     499#       print_('TD: %s %s' % (nodename, state_char))
    366500        dummy = nodename.split('-')
    367501        if len( dummy ) > 1:
     
    375509    n = 0
    376510    for state in legend:
    377         print '  %s  %-13s : %-5d' % (PBS_STATES[state], state, count_states[state]),
     511        _print('  %s  %-13s : %-5d' % (PBS_STATES[state], state, count_states[state]), end=' ')
    378512
    379513        n = n + 1
    380514        if not (n & 1):
    381             print
     515            _print()
    382516
    383517def print_extended( hosts=None ):
     
    402536        rows_str.append( row_str )
    403537
    404     print
    405     print row_header
    406     print EXTENDED_PATTERNS[ 'line' ] % ( EXTENDED_PATTERNS[ 'line_char' ] * LENGTH_ROW )
    407     print '\n'.join( rows_str )
    408     print
     538    _print()
     539    _print(row_header)
     540    _print(EXTENDED_PATTERNS[ 'line' ] % ( EXTENDED_PATTERNS[ 'line_char' ] * LENGTH_ROW ))
     541    _print('\n'.join( rows_str ))
     542    _print()
    409543
    410544if __name__ == '__main__':
    411545   
    412     parser = AdvancedParser(usage=__doc__)
    413 
    414     parser.add_option( "-t", "--table", dest="table", action="store_true", help="Show an table" )
    415     parser.add_option( "-l", "--list", dest="extended", action="store_true", help="Show node rows with state and jobinfo" )
    416     parser.add_option( "-s", "--summary", dest="summary", action="store_true", help="Display a short summary" )
    417     parser.add_option( "-a", "--all", dest="summary", action="store_true", help="Display a short summary" )
    418 
    419     parser.add_option( "-w", "--wide", dest="wide", action="store_true", help="Wide display for node status ( only when -t is used )" )
    420     parser.add_option( "-S", "--servername", dest="servername", help="Change the default servername" )
    421 
    422     parser.set_defaults( table=PRINT_TABLE )
    423     parser.set_defaults( summary=False )
    424     parser.set_defaults( extended=PRINT_EXTENDED )
    425     parser.set_defaults( servername=None )
    426 
    427     ( options, args ) = parser.parse_args()
    428 
    429     if options.servername:
    430         OPT_SERVERNAME = options.servername
    431 
    432     if options.wide:
     546    parser = argparse.ArgumentParser(
     547        formatter_class=argparse.RawDescriptionHelpFormatter,
     548        description=__doc__,
     549    )
     550
     551    parser.add_argument('nodes', metavar='NODES', nargs='*', type=str)
     552    parser.add_argument( "-t", "--table", dest="table", action="store_true", help="Show an table", default=PRINT_TABLE )
     553    parser.add_argument( "-l", "--list", dest="extended", action="store_true", help="Show node rows with state and jobinfo", default=PRINT_EXTENDED )
     554    parser.add_argument( "-s", "--summary", dest="summary", action="store_true", help="Display a short summary", default=False )
     555    parser.add_argument( "-a", "--all", dest="summary", action="store_true", help="Display a short summary" )
     556    parser.add_argument( "-w", "--wide", dest="wide", action="store_true", help="Wide display for node status ( only when -t is used )" )
     557    parser.add_argument( "-S", "--servername", dest="servername", help="Change the default servername", default=None )
     558
     559    args = parser.parse_args()
     560    if args.nodes:
     561        args.nodes = parse_args(args.nodes)
     562
     563    if args.servername:
     564        OPT_SERVERNAME = args.servername
     565
     566    if args.wide:
    433567        OPT_SKIP_EMPTY_RACKS = False
    434568
    435     if args:
    436         options.extended = True
    437 
    438     if options.extended and PRINT_TABLE:
    439         options.table = False
    440 
    441     if options.table and PRINT_EXTENDED:
    442         options.extended = False
    443 
    444     if options.extended:
    445         print_extended( args )
    446     elif options.table:
     569    if args.nodes:
     570        args.extended = True
     571
     572    if args.extended and PRINT_TABLE:
     573        args.table = False
     574
     575    if args.table and PRINT_EXTENDED:
     576        args.extended = False
     577
     578    if args.extended:
     579        print_extended( args.nodes )
     580    elif args.table:
    447581        print_table()
    448582    else:
    449         print 'Something is wrong, bye!'
     583        _print('Something is wrong, bye!', file=sys.stderr)
    450584        sys.exit( -1 )
    451585
    452     if options.summary:
     586    if args.summary:
    453587        print_table_summary()
Note: See TracChangeset for help on using the changeset viewer.