1*9c5db199SXin Li# 2*9c5db199SXin Li# Copyright 2008 Google Inc. All Rights Reserved. 3*9c5db199SXin Li 4*9c5db199SXin Li""" 5*9c5db199SXin LiThe label module contains the objects and methods used to 6*9c5db199SXin Limanage labels in Autotest. 7*9c5db199SXin Li 8*9c5db199SXin LiThe valid actions are: 9*9c5db199SXin Liadd: adds label(s), or hosts to an LABEL 10*9c5db199SXin Liremove: deletes label(s), or hosts from an LABEL 11*9c5db199SXin Lilist: lists label(s) 12*9c5db199SXin Li 13*9c5db199SXin LiThe common options are: 14*9c5db199SXin Li--blist / -B: file containing a list of LABELs 15*9c5db199SXin Li 16*9c5db199SXin LiSee topic_common.py for a High Level Design and Algorithm. 17*9c5db199SXin Li""" 18*9c5db199SXin Li 19*9c5db199SXin Liimport sys 20*9c5db199SXin Lifrom autotest_lib.cli import topic_common, action_common 21*9c5db199SXin Li 22*9c5db199SXin Li 23*9c5db199SXin Liclass label(topic_common.atest): 24*9c5db199SXin Li """Label class 25*9c5db199SXin Li atest label [create|delete|list|add|remove] <options>""" 26*9c5db199SXin Li usage_action = '[create|delete|list|add|remove]' 27*9c5db199SXin Li topic = msg_topic = 'label' 28*9c5db199SXin Li msg_items = '<labels>' 29*9c5db199SXin Li 30*9c5db199SXin Li def __init__(self): 31*9c5db199SXin Li """Add to the parser the options common to all the 32*9c5db199SXin Li label actions""" 33*9c5db199SXin Li super(label, self).__init__() 34*9c5db199SXin Li 35*9c5db199SXin Li self.parser.add_option('-B', '--blist', 36*9c5db199SXin Li help='File listing the labels', 37*9c5db199SXin Li type='string', 38*9c5db199SXin Li default=None, 39*9c5db199SXin Li metavar='LABEL_FLIST') 40*9c5db199SXin Li 41*9c5db199SXin Li self.topic_parse_info = topic_common.item_parse_info( 42*9c5db199SXin Li attribute_name='labels', 43*9c5db199SXin Li filename_option='blist', 44*9c5db199SXin Li use_leftover=True) 45*9c5db199SXin Li 46*9c5db199SXin Li 47*9c5db199SXin Li def get_items(self): 48*9c5db199SXin Li return self.labels 49*9c5db199SXin Li 50*9c5db199SXin Li 51*9c5db199SXin Liclass label_help(label): 52*9c5db199SXin Li """Just here to get the atest logic working. 53*9c5db199SXin Li Usage is set by its parent""" 54*9c5db199SXin Li pass 55*9c5db199SXin Li 56*9c5db199SXin Li 57*9c5db199SXin Liclass label_list(action_common.atest_list, label): 58*9c5db199SXin Li """atest label list [--platform] [--all] 59*9c5db199SXin Li [--valid-only] [--machine <machine>] 60*9c5db199SXin Li [--blist <file>] [<labels>]""" 61*9c5db199SXin Li def __init__(self): 62*9c5db199SXin Li super(label_list, self).__init__() 63*9c5db199SXin Li 64*9c5db199SXin Li self.parser.add_option('-t', '--platform-only', 65*9c5db199SXin Li help='Display only platform labels', 66*9c5db199SXin Li action='store_true') 67*9c5db199SXin Li 68*9c5db199SXin Li self.parser.add_option('-d', '--valid-only', 69*9c5db199SXin Li help='Display only valid labels', 70*9c5db199SXin Li action='store_true') 71*9c5db199SXin Li 72*9c5db199SXin Li self.parser.add_option('-a', '--all', 73*9c5db199SXin Li help=('Display both normal & ' 74*9c5db199SXin Li 'platform labels'), 75*9c5db199SXin Li action='store_true') 76*9c5db199SXin Li 77*9c5db199SXin Li self.parser.add_option('-m', '--machine', 78*9c5db199SXin Li help='List LABELs of MACHINE', 79*9c5db199SXin Li type='string', 80*9c5db199SXin Li metavar='MACHINE') 81*9c5db199SXin Li 82*9c5db199SXin Li 83*9c5db199SXin Li def parse(self): 84*9c5db199SXin Li host_info = topic_common.item_parse_info(attribute_name='hosts', 85*9c5db199SXin Li inline_option='machine') 86*9c5db199SXin Li (options, leftover) = super(label_list, self).parse([host_info]) 87*9c5db199SXin Li 88*9c5db199SXin Li exclusives = [options.all, options.platform_only] 89*9c5db199SXin Li if exclusives.count(True) > 1: 90*9c5db199SXin Li self.invalid_syntax('Only specify one of --all,' 91*9c5db199SXin Li '--platform') 92*9c5db199SXin Li 93*9c5db199SXin Li if len(self.hosts) > 1: 94*9c5db199SXin Li self.invalid_syntax(('Only one machine name allowed. ' 95*9c5db199SXin Li '''Use '%s host list %s' ''' 96*9c5db199SXin Li 'instead.') % 97*9c5db199SXin Li (sys.argv[0], ','.join(self.hosts))) 98*9c5db199SXin Li self.all = options.all 99*9c5db199SXin Li self.platform_only = options.platform_only 100*9c5db199SXin Li self.valid_only = options.valid_only 101*9c5db199SXin Li return (options, leftover) 102*9c5db199SXin Li 103*9c5db199SXin Li 104*9c5db199SXin Li def execute(self): 105*9c5db199SXin Li filters = {} 106*9c5db199SXin Li check_results = {} 107*9c5db199SXin Li if self.hosts: 108*9c5db199SXin Li filters['host__hostname__in'] = self.hosts 109*9c5db199SXin Li check_results['host__hostname__in'] = None 110*9c5db199SXin Li 111*9c5db199SXin Li if self.labels: 112*9c5db199SXin Li filters['name__in'] = self.labels 113*9c5db199SXin Li check_results['name__in'] = 'name' 114*9c5db199SXin Li 115*9c5db199SXin Li return super(label_list, self).execute(op='get_labels', 116*9c5db199SXin Li filters=filters, 117*9c5db199SXin Li check_results=check_results) 118*9c5db199SXin Li 119*9c5db199SXin Li 120*9c5db199SXin Li def output(self, results): 121*9c5db199SXin Li if self.valid_only: 122*9c5db199SXin Li results = [label for label in results 123*9c5db199SXin Li if not label['invalid']] 124*9c5db199SXin Li 125*9c5db199SXin Li if self.platform_only: 126*9c5db199SXin Li results = [label for label in results 127*9c5db199SXin Li if label['platform']] 128*9c5db199SXin Li keys = ['name', 'invalid'] 129*9c5db199SXin Li elif not self.all: 130*9c5db199SXin Li results = [label for label in results 131*9c5db199SXin Li if not label['platform']] 132*9c5db199SXin Li keys = ['name', 'only_if_needed', 'invalid'] 133*9c5db199SXin Li else: 134*9c5db199SXin Li keys = ['name', 'platform', 'only_if_needed', 'invalid'] 135*9c5db199SXin Li 136*9c5db199SXin Li super(label_list, self).output(results, keys) 137*9c5db199SXin Li 138*9c5db199SXin Li 139*9c5db199SXin Liclass label_create(action_common.atest_create, label): 140*9c5db199SXin Li """atest label create <labels>|--blist <file> --platform""" 141*9c5db199SXin Li def __init__(self): 142*9c5db199SXin Li super(label_create, self).__init__() 143*9c5db199SXin Li self.parser.add_option('-t', '--platform', 144*9c5db199SXin Li help='To create this label as a platform', 145*9c5db199SXin Li default=False, 146*9c5db199SXin Li action='store_true') 147*9c5db199SXin Li self.parser.add_option('-o', '--only_if_needed', 148*9c5db199SXin Li help='To mark the label as "only use if needed', 149*9c5db199SXin Li default=False, 150*9c5db199SXin Li action='store_true') 151*9c5db199SXin Li 152*9c5db199SXin Li 153*9c5db199SXin Li def parse(self): 154*9c5db199SXin Li (options, leftover) = super(label_create, 155*9c5db199SXin Li self).parse(req_items='labels') 156*9c5db199SXin Li self.data_item_key = 'name' 157*9c5db199SXin Li self.data['platform'] = options.platform 158*9c5db199SXin Li self.data['only_if_needed'] = options.only_if_needed 159*9c5db199SXin Li return (options, leftover) 160*9c5db199SXin Li 161*9c5db199SXin Li 162*9c5db199SXin Liclass label_delete(action_common.atest_delete, label): 163*9c5db199SXin Li """atest label delete <labels>|--blist <file>""" 164*9c5db199SXin Li pass 165*9c5db199SXin Li 166*9c5db199SXin Li 167*9c5db199SXin Li 168*9c5db199SXin Liclass label_add_or_remove(label): 169*9c5db199SXin Li """Parent for `atest label` add and `label remove`""" 170*9c5db199SXin Li def __init__(self): 171*9c5db199SXin Li super(label_add_or_remove, self).__init__() 172*9c5db199SXin Li lower_words = tuple(word.lower() for word in self.usage_words) 173*9c5db199SXin Li self.parser.add_option('-m', '--machine', 174*9c5db199SXin Li help=('%s MACHINE(s) %s the LABEL' % 175*9c5db199SXin Li self.usage_words), 176*9c5db199SXin Li type='string', 177*9c5db199SXin Li metavar='MACHINE') 178*9c5db199SXin Li self.parser.add_option('-M', '--mlist', 179*9c5db199SXin Li help='File containing machines to %s %s ' 180*9c5db199SXin Li 'the LABEL' % lower_words, 181*9c5db199SXin Li type='string', 182*9c5db199SXin Li metavar='MACHINE_FLIST') 183*9c5db199SXin Li 184*9c5db199SXin Li 185*9c5db199SXin Li def parse(self): 186*9c5db199SXin Li host_info = topic_common.item_parse_info(attribute_name='hosts', 187*9c5db199SXin Li inline_option='machine', 188*9c5db199SXin Li filename_option='mlist') 189*9c5db199SXin Li (options, leftover) = super(label_add_or_remove, 190*9c5db199SXin Li self).parse([host_info], 191*9c5db199SXin Li req_items='labels') 192*9c5db199SXin Li 193*9c5db199SXin Li if not getattr(self, 'hosts', None): 194*9c5db199SXin Li self.invalid_syntax('%s %s requires at least one host' % 195*9c5db199SXin Li (self.msg_topic, 196*9c5db199SXin Li self.usage_action)) 197*9c5db199SXin Li return (options, leftover) 198*9c5db199SXin Li 199*9c5db199SXin Li 200*9c5db199SXin Liclass label_add(action_common.atest_add, label_add_or_remove): 201*9c5db199SXin Li """atest label add <labels>|--blist <file> 202*9c5db199SXin Li --platform [--machine <machine>] [--mlist <file>]""" 203*9c5db199SXin Li pass 204*9c5db199SXin Li 205*9c5db199SXin Li 206*9c5db199SXin Liclass label_remove(action_common.atest_remove, label_add_or_remove): 207*9c5db199SXin Li """atest label remove <labels>|--blist <file> 208*9c5db199SXin Li [--machine <machine>] [--mlist <file>]""" 209*9c5db199SXin Li pass 210