blob: 4e53ee2c9a15b4fa010b14aa9d149a22ee67581f [file] [log] [blame]
adminbae64d82013-08-01 10:50:15 -07001#!/usr/bin/env python
2'''
3Created on 22-Oct-2012
Jon Hall65844a32015-03-09 19:09:37 -07004
adminbae64d82013-08-01 10:50:15 -07005@author: Anil Kumar (anilkumar.s@paxterrasolutions.com)
6
7
8 TestON is free software: you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation, either version 2 of the License, or
11 (at your option) any later version.
12
13 TestON is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
Jon Hall65844a32015-03-09 19:09:37 -070019 along with TestON. If not, see <http://www.gnu.org/licenses/>.
adminbae64d82013-08-01 10:50:15 -070020
21
22
23teston is the main module.
24
25'''
26
27import sys
28import getpass
29import os
30import re
31import __builtin__
32import new
33import xmldict
Jon Hall30b82fa2015-03-04 17:15:43 -080034import importlib
Jon Hall5b586732015-06-11 11:39:39 -070035import threading
adminbae64d82013-08-01 10:50:15 -070036module = new.module("test")
37import openspeak
Hari Krishnabe4b97b2015-07-15 12:19:43 -070038import subprocess
adminbae64d82013-08-01 10:50:15 -070039global path, drivers_path, core_path, tests_path,logs_path
Jon Hall44506242015-07-29 17:40:26 -070040location = os.path.abspath( os.path.dirname( __file__ ) )
41path = re.sub( "(core|bin)$", "", location )
Jon Hall2a5002c2015-08-21 16:49:11 -070042drivers_path = path+"drivers"
adminbae64d82013-08-01 10:50:15 -070043core_path = path+"core"
44tests_path = path+"tests"
45logs_path = path+"logs/"
46config_path = path + "config/"
Jon Hall44506242015-07-29 17:40:26 -070047sys.path.append( path )
48sys.path.append( drivers_path )
49sys.path.append( core_path )
50sys.path.append( tests_path )
adminbae64d82013-08-01 10:50:15 -070051
52from core.utilities import Utilities
kelvin-onlabfb521662015-02-27 09:52:40 -080053from core.Thread import Thread
adminbae64d82013-08-01 10:50:15 -070054
adminbae64d82013-08-01 10:50:15 -070055
56class TestON:
57 '''
kelvin-onlabf70fd542015-05-07 18:41:40 -070058 TestON will initiate the specified test.
59 The main tasks are :
60 * Initiate the required Component handles for the test.
adminbae64d82013-08-01 10:50:15 -070061 * Create Log file Handles.
adminbae64d82013-08-01 10:50:15 -070062 '''
63 def __init__(self,options):
64 '''
65 Initialise the component handles specified in the topology file of the specified test.
adminbae64d82013-08-01 10:50:15 -070066 '''
67 # Initialization of the variables.
68 __builtin__.main = self
adminbae64d82013-08-01 10:50:15 -070069 __builtin__.path = path
70 __builtin__.utilities = Utilities()
71 self.TRUE = 1
72 self.FALSE = 0
73 self.ERROR = -1
kelvin-onlabf70fd542015-05-07 18:41:40 -070074 self.NORESULT = 2
adminbae64d82013-08-01 10:50:15 -070075 self.FAIL = False
76 self.PASS = True
kelvin-onlabf70fd542015-05-07 18:41:40 -070077 self.CASERESULT = self.ERROR
78 self.STEPRESULT = self.NORESULT
79 self.stepResults = []
adminbae64d82013-08-01 10:50:15 -070080 self.init_result = self.TRUE
81 self.testResult = "Summary"
kelvin-onlabf70fd542015-05-07 18:41:40 -070082 self.stepName = ""
83 self.stepCache = ""
Jon Halld61331b2015-02-17 16:35:47 -080084 self.EXPERIMENTAL_MODE = False
adminbae64d82013-08-01 10:50:15 -070085 self.test_target = None
86 self.lastcommand = None
Jon Halld61331b2015-02-17 16:35:47 -080087 self.testDir = tests_path
88 self.configFile = config_path + "teston.cfg"
adminbae64d82013-08-01 10:50:15 -070089 self.parsingClass = "xmlparser"
90 self.parserPath = core_path + "/xmlparser"
91 self.loggerPath = core_path + "/logger"
92 self.loggerClass = "Logger"
93 self.logs_path = logs_path
94 self.driver = ''
kelvin-onlabfb521662015-02-27 09:52:40 -080095 self.Thread = Thread
Jon Hall5b586732015-06-11 11:39:39 -070096 self.cleanupFlag = False
97 self.cleanupLock = threading.Lock()
Jon Hall0fc0d452015-07-14 09:49:58 -070098 self.initiated = False
Jon Hall65844a32015-03-09 19:09:37 -070099
adminbae64d82013-08-01 10:50:15 -0700100 self.configparser()
101 verifyOptions(options)
102 load_logger()
103 self.componentDictionary = {}
104 self.componentDictionary = self.topology ['COMPONENT']
105 self.driversList=[]
106 if type(self.componentDictionary) == str :
107 self.componentDictionary = dict(self.componentDictionary)
Jon Hall65844a32015-03-09 19:09:37 -0700108
adminbae64d82013-08-01 10:50:15 -0700109 for component in self.componentDictionary :
110 self.driversList.append(self.componentDictionary[component]['type'])
Jon Hall65844a32015-03-09 19:09:37 -0700111
adminbae64d82013-08-01 10:50:15 -0700112 self.driversList = list(set(self.driversList)) # Removing duplicates.
113 # Checking the test_target option set for the component or not
114 if type(self.componentDictionary) == dict:
115 for component in self.componentDictionary.keys():
116 if 'test_target' in self.componentDictionary[component].keys():
117 self.test_target = component
Jon Hall65844a32015-03-09 19:09:37 -0700118
Jon Halld61331b2015-02-17 16:35:47 -0800119 # Checking for the openspeak file and test script
adminbae64d82013-08-01 10:50:15 -0700120 self.logger.initlog(self)
121
122 # Creating Drivers Handles
123 initString = "\n"+"*" * 30+"\n CASE INIT \n"+"*" * 30+"\n"
124 self.log.exact(initString)
125 self.driverObject = {}
126 self.random_order = 111 # Random order id to connect the components
127 components_connect_order = {}
128 #component_list.append()
129 if type(self.componentDictionary) == dict:
130 for component in self.componentDictionary.keys():
131 self.componentDictionary[component]['connect_order'] = self.componentDictionary[component]['connect_order'] if ('connect_order' in self.componentDictionary[component].keys()) else str(self.get_random())
132 components_connect_order[component] = eval(self.componentDictionary[component]['connect_order'])
133 #Ordering components based on the connect order.
134 ordered_component_list =sorted(components_connect_order, key=lambda key: components_connect_order[key])
135 print ordered_component_list
adminbae64d82013-08-01 10:50:15 -0700136 for component in ordered_component_list:
137 self.componentInit(component)
138
139 def configparser(self):
140 '''
141 It will parse the config file (teston.cfg) and return as dictionary
142 '''
143 matchFileName = re.match(r'(.*)\.cfg', self.configFile, re.M | re.I)
144 if matchFileName:
145 xml = open(self.configFile).read()
146 try :
147 self.configDict = xmldict.xml_to_dict(xml)
148 return self.configDict
Jon Hallebe9cea2015-09-04 17:39:44 +0000149 except Exception:
adminbae64d82013-08-01 10:50:15 -0700150 print "There is no such file to parse " + self.configFile
kelvin-onlabf70fd542015-05-07 18:41:40 -0700151
adminbae64d82013-08-01 10:50:15 -0700152 def componentInit(self,component):
153 '''
154 This method will initialize specified component
155 '''
156 global driver_options
Jon Hall0fc0d452015-07-14 09:49:58 -0700157 self.initiated = False
adminbae64d82013-08-01 10:50:15 -0700158 self.log.info("Creating component Handle: "+component)
Jon Halld61331b2015-02-17 16:35:47 -0800159 driver_options = {}
adminbae64d82013-08-01 10:50:15 -0700160 if 'COMPONENTS' in self.componentDictionary[component].keys():
161 driver_options =dict(self.componentDictionary[component]['COMPONENTS'])
162
163 driver_options['name']=component
164 driverName = self.componentDictionary[component]['type']
165 driver_options ['type'] = driverName
kelvin-onlabf70fd542015-05-07 18:41:40 -0700166
adminbae64d82013-08-01 10:50:15 -0700167 classPath = self.getDriverPath(driverName.lower())
Jon Hall30b82fa2015-03-04 17:15:43 -0800168 driverModule = importlib.import_module(classPath)
adminbae64d82013-08-01 10:50:15 -0700169 driverClass = getattr(driverModule, driverName)
170 driverObject = driverClass()
kelvin-onlabf70fd542015-05-07 18:41:40 -0700171
Hari Krishnabe4b97b2015-07-15 12:19:43 -0700172 if ( "OCN" in self.componentDictionary[component]['host'] and main.onoscell ):
173 self.componentDictionary[component]['host'] = main.mnIP
174
adminbae64d82013-08-01 10:50:15 -0700175 connect_result = driverObject.connect(user_name = self.componentDictionary[component]['user'] if ('user' in self.componentDictionary[component].keys()) else getpass.getuser(),
176 ip_address= self.componentDictionary[component]['host'] if ('host' in self.componentDictionary[component].keys()) else 'localhost',
177 pwd = self.componentDictionary[component]['password'] if ('password' in self.componentDictionary[component].keys()) else 'changeme',
178 port = self.componentDictionary[component]['port'] if ('port' in self.componentDictionary[component].keys()) else None,
179 options = driver_options)
cameron@onlab.us5cc6a372015-05-11 17:18:07 -0700180
adminbae64d82013-08-01 10:50:15 -0700181 if not connect_result:
Jon Hall166e4a42015-08-10 12:03:41 -0700182 self.log.error("Exiting from the test execution because the connecting to the "+component+" component failed.")
Jon Halld61331b2015-02-17 16:35:47 -0800183 self.exit()
kelvin-onlabf70fd542015-05-07 18:41:40 -0700184
adminbae64d82013-08-01 10:50:15 -0700185 vars(self)[component] = driverObject
Jon Hall0fc0d452015-07-14 09:49:58 -0700186 self.initiated = True
kelvin-onlabf70fd542015-05-07 18:41:40 -0700187
adminbae64d82013-08-01 10:50:15 -0700188 def run(self):
189 '''
kelvin-onlabf70fd542015-05-07 18:41:40 -0700190 The Execution of the test script's cases listed in the Test params file will be done here.
191 And Update each test case result.
192 This method will return TRUE if it executed all the test cases successfully,
adminbae64d82013-08-01 10:50:15 -0700193 else will retun FALSE
194 '''
adminbae64d82013-08-01 10:50:15 -0700195 self.testCaseResult = {}
Jon Halla1185982014-09-15 14:55:10 -0700196 self.TOTAL_TC = 0
adminbae64d82013-08-01 10:50:15 -0700197 self.TOTAL_TC_RUN = 0
Jon Halld61331b2015-02-17 16:35:47 -0800198 self.TOTAL_TC_PLANNED = 0
adminbae64d82013-08-01 10:50:15 -0700199 self.TOTAL_TC_NORESULT = 0
200 self.TOTAL_TC_FAIL = 0
201 self.TOTAL_TC_PASS = 0
Jon Halla1185982014-09-15 14:55:10 -0700202 self.TEST_ITERATION = 0
adminbae64d82013-08-01 10:50:15 -0700203 self.stepCount = 0
kelvin-onlabf70fd542015-05-07 18:41:40 -0700204 self.CASERESULT = self.NORESULT
205
Jon Halld61331b2015-02-17 16:35:47 -0800206 import testparser
adminbae64d82013-08-01 10:50:15 -0700207 testFile = self.tests_path + "/"+self.TEST + "/"+self.TEST + ".py"
208 test = testparser.TestParser(testFile)
209 self.testscript = test.testscript
210 self.code = test.getStepCode()
Jon Hallfebb1c72015-03-05 13:30:09 -0800211 repeat= int(self.params['repeat']) if ('repeat' in self.params) else 1
212 self.TOTAL_TC_PLANNED = len(self.testcases_list)*repeat
kelvin-onlabf70fd542015-05-07 18:41:40 -0700213
adminbae64d82013-08-01 10:50:15 -0700214 result = self.TRUE
Jon Hallfebb1c72015-03-05 13:30:09 -0800215 while(repeat):
Jon Halla1185982014-09-15 14:55:10 -0700216 for self.CurrentTestCaseNumber in self.testcases_list:
Jon Halld61331b2015-02-17 16:35:47 -0800217 result = self.runCase(self.CurrentTestCaseNumber)
Jon Hallfebb1c72015-03-05 13:30:09 -0800218 repeat-=1
adminbae64d82013-08-01 10:50:15 -0700219 return result
kelvin-onlabf70fd542015-05-07 18:41:40 -0700220
Jon Halle234cc42015-08-31 15:26:47 -0700221 def runCase( self, testCaseNumber ):
adminbae64d82013-08-01 10:50:15 -0700222 self.CurrentTestCaseNumber = testCaseNumber
kelvin-onlabf70fd542015-05-07 18:41:40 -0700223 self.CurrentTestCase = ""
224 self.stepResults = []
225 self.stepName = ""
Jon Hall783bbf92015-07-23 14:33:19 -0700226 self.caseExplanation = ""
adminbae64d82013-08-01 10:50:15 -0700227 result = self.TRUE
228 self.stepCount = 0
229 self.EXPERIMENTAL_MODE = self.FALSE
230 self.addCaseHeader()
Jon Halle234cc42015-08-31 15:26:47 -0700231 self.testCaseNumber = str( testCaseNumber )
232 self.CASERESULT = self.NORESULT
adminbae64d82013-08-01 10:50:15 -0700233 stopped = False
234 try :
235 self.stepList = self.code[self.testCaseNumber].keys()
Jon Halld61331b2015-02-17 16:35:47 -0800236 except KeyError:
Jon Halle234cc42015-08-31 15:26:47 -0700237 self.log.error( "There is no Test-Case " + self.testCaseNumber )
Jon Hallfebb1c72015-03-05 13:30:09 -0800238 return self.FALSE
adminbae64d82013-08-01 10:50:15 -0700239 self.stepCount = 0
240 while self.stepCount < len(self.code[self.testCaseNumber].keys()):
241 result = self.runStep(self.stepList,self.code,self.testCaseNumber)
Jon Hallfebb1c72015-03-05 13:30:09 -0800242 if result == self.FALSE:
adminbae64d82013-08-01 10:50:15 -0700243 break
Jon Hallfebb1c72015-03-05 13:30:09 -0800244 elif result == self.TRUE:
adminbae64d82013-08-01 10:50:15 -0700245 continue
Jon Halle234cc42015-08-31 15:26:47 -0700246 if not stopped:
247 if self.CASERESULT == self.TRUE or self.CASERESULT == self.FALSE:
248 # Result was already explitily set somewhere else like skipCase()
249 pass
250 elif all( self.TRUE == i for i in self.stepResults ):
kelvin-onlabf70fd542015-05-07 18:41:40 -0700251 # ALL PASSED
252 self.CASERESULT = self.TRUE
253 elif self.FALSE in self.stepResults:
254 # AT LEAST ONE FAILED
255 self.CASERESULT = self.FALSE
256 elif self.TRUE in self.stepResults:
257 # AT LEAST ONE PASSED
258 self.CASERESULT = self.TRUE
259 else:
260 self.CASERESULT = self.NORESULT
adminbae64d82013-08-01 10:50:15 -0700261 self.testCaseResult[str(self.CurrentTestCaseNumber)] = self.CASERESULT
262 self.logger.updateCaseResults(self)
Jon Hall783bbf92015-07-23 14:33:19 -0700263 self.log.wiki( "<p>" + self.caseExplanation + "</p>" )
264 self.log.summary( self.caseExplanation )
kelvin-onlabf70fd542015-05-07 18:41:40 -0700265 self.log.wiki( "<ul>" )
266 for line in self.stepCache.splitlines():
267 if re.search( " - PASS$", line ):
268 self.log.wiki( "<li>" + line + " <ac:emoticon ac:name=\"tick\" /></li>\n" )
269 elif re.search( " - FAIL$", line ):
270 self.log.wiki( "<li>" + line + " <ac:emoticon ac:name=\"cross\" /></li>\n" )
271 elif re.search( " - No Result$", line ):
272 self.log.wiki( "<li>" + line + " <ac:emoticon ac:name=\"warning\" /></li>\n" )
Jon Hall90627612015-06-09 14:57:02 -0700273 else: # Should only be on fail message
274 self.log.wiki( "<ul><li>" + line + "</li></ul>\n" )
kelvin-onlabf70fd542015-05-07 18:41:40 -0700275 self.log.wiki( "</ul>" )
276 self.log.summary( self.stepCache )
277 self.stepCache = ""
adminbae64d82013-08-01 10:50:15 -0700278 return result
kelvin-onlabf70fd542015-05-07 18:41:40 -0700279
adminbae64d82013-08-01 10:50:15 -0700280 def runStep(self,stepList,code,testCaseNumber):
281 if not cli.pause:
282 try :
283 step = stepList[self.stepCount]
kelvin-onlabf70fd542015-05-07 18:41:40 -0700284 self.STEPRESULT = self.NORESULT
Jon Halle234cc42015-08-31 15:26:47 -0700285 self.onFailMsg = "No on fail message given"
adminbae64d82013-08-01 10:50:15 -0700286 exec code[testCaseNumber][step] in module.__dict__
287 self.stepCount = self.stepCount + 1
kelvin-onlabf70fd542015-05-07 18:41:40 -0700288 if step > 0:
289 self.stepCache += "\t"+str(testCaseNumber)+"."+str(step)+" "+self.stepName+" - "
290 if self.STEPRESULT == self.TRUE:
291 self.stepCache += "PASS\n"
kelvin-onlabf70fd542015-05-07 18:41:40 -0700292 elif self.STEPRESULT == self.FALSE:
293 self.stepCache += "FAIL\n"
Jon Hall8ce34e82015-06-05 10:41:45 -0700294 # TODO: Print the on-fail statement here
Jon Hall90627612015-06-09 14:57:02 -0700295 self.stepCache += "\t\t" + self.onFailMsg + "\n"
kelvin-onlabf70fd542015-05-07 18:41:40 -0700296 else:
297 self.stepCache += "No Result\n"
kelvin-onlabf70fd542015-05-07 18:41:40 -0700298 self.stepResults.append(self.STEPRESULT)
Jon Halle234cc42015-08-31 15:26:47 -0700299 except StopIteration: # Raised in self.skipCase()
300 self.log.warn( "Skipping the rest of CASE" +
301 str( testCaseNumber ) )
302 self.stepResults.append(self.STEPRESULT)
303 self.stepCache += "\t\t" + self.onFailMsg + "\n"
304 self.stepCount = self.stepCount + 1
305 return self.FALSE
Jon Hall5b586732015-06-11 11:39:39 -0700306 except StandardError:
Jon Hall40d2cbd2015-06-03 16:24:29 -0700307 self.log.exception( "\nException in the following section of" +
Jon Halle234cc42015-08-31 15:26:47 -0700308 " code: " + str( testCaseNumber ) + "." +
309 str( step ) + ": " + self.stepName )
Jon Hall63604932015-02-26 17:09:50 -0800310 #print code[testCaseNumber][step]
adminbae64d82013-08-01 10:50:15 -0700311 self.stepCount = self.stepCount + 1
kelvin-onlabf70fd542015-05-07 18:41:40 -0700312 self.logger.updateCaseResults(self)
313 #WIKI results
314 self.log.wiki( "<ul>" )
315 for line in self.stepCache.splitlines():
316 if re.search( " - PASS$", line ):
317 self.log.wiki( "<li>" + line + " <ac:emoticon ac:name=\"tick\" /></li>\n" )
318 elif re.search( " - FAIL$", line ):
319 self.log.wiki( "<li>" + line + " <ac:emoticon ac:name=\"cross\" /></li>\n" )
320 elif re.search( " - No Result$", line ):
321 self.log.wiki( "<li>" + line + " <ac:emoticon ac:name=\"warning\" /></li>\n" )
Jon Hall90627612015-06-09 14:57:02 -0700322 else: # Should only be on fail message
323 self.log.wiki( "<ul><li>" + line + "</li></ul>\n" )
kelvin-onlabf70fd542015-05-07 18:41:40 -0700324 self.log.wiki( "</ul>" )
325 #summary results
326 self.log.summary( self.stepCache )
327 self.stepCache = ""
shahshreya957feaa2015-03-23 16:08:29 -0700328 self.cleanup()
Jon Hall00539b12015-04-03 13:55:46 -0700329 self.exit()
Jon Halle234cc42015-08-31 15:26:47 -0700330 return self.TRUE
adminbae64d82013-08-01 10:50:15 -0700331 if cli.stop:
332 cli.stop = False
333 stopped = True
334 self.TOTAL_TC_NORESULT = self.TOTAL_TC_NORESULT + 1
335 self.testCaseResult[str(self.CurrentTestCaseNumber)] = "Stopped"
336 self.logger.updateCaseResults(self)
337 result = self.cleanup()
Jon Halle234cc42015-08-31 15:26:47 -0700338 return self.FALSE
339
340 def skipCase( self, result="DEFAULT", msg=None ):
341 """
342 Will skip the rest of the code in a test case. The case results will be
343 determined as normal based on completed assertions unless the result
344 argument is given.
345
346 Optional Arguments:
347 result: Case insensite string. Can be 'PASS' or 'FAIL' and will set
348 the case result accordingly.
349 msg: Message to be printed when the case is skipped in the reports.
350 """
351 result = result.upper().strip()
352 if result == "PASS":
353 self.CASERESULT = self.TRUE
354 elif result == "FAIL":
355 self.CASERESULT = self.FALSE
356 self.onFailMsg = "Skipping the rest of this case. "
357 if msg:
358 self.onFailMsg += str( msg )
359 raise StopIteration
kelvin-onlabf70fd542015-05-07 18:41:40 -0700360
adminbae64d82013-08-01 10:50:15 -0700361 def addCaseHeader(self):
362 caseHeader = "\n"+"*" * 30+"\n Result summary for Testcase"+str(self.CurrentTestCaseNumber)+"\n"+"*" * 30+"\n"
Jon Halld61331b2015-02-17 16:35:47 -0800363 self.log.exact(caseHeader)
364 caseHeader = "\n"+"*" * 40 +"\nStart of Test Case"+str(self.CurrentTestCaseNumber)+" : "
adminbae64d82013-08-01 10:50:15 -0700365 for driver in self.componentDictionary.keys():
366 vars(self)[driver+'log'].info(caseHeader)
kelvin-onlabf70fd542015-05-07 18:41:40 -0700367
adminbae64d82013-08-01 10:50:15 -0700368 def addCaseFooter(self):
369 if self.stepCount-1 > 0 :
370 previousStep = " "+str(self.CurrentTestCaseNumber)+"."+str(self.stepCount-1)+": "+ str(self.stepName) + ""
371 stepHeader = "\n"+"*" * 40+"\nEnd of Step "+previousStep+"\n"+"*" * 40+"\n"
kelvin-onlabf70fd542015-05-07 18:41:40 -0700372
adminbae64d82013-08-01 10:50:15 -0700373 caseFooter = "\n"+"*" * 40+"\nEnd of Test case "+str(self.CurrentTestCaseNumber)+"\n"+"*" * 40+"\n"
kelvin-onlabf70fd542015-05-07 18:41:40 -0700374
adminbae64d82013-08-01 10:50:15 -0700375 for driver in self.driversList:
376 vars(self)[driver].write(stepHeader+"\n"+caseFooter)
377
378 def cleanup(self):
379 '''
Jon Hall5b586732015-06-11 11:39:39 -0700380 Print a summary of the current test's results then attempt to release
381 all the component handles and the close opened file handles.
adminbae64d82013-08-01 10:50:15 -0700382
Jon Hall5b586732015-06-11 11:39:39 -0700383 This function shouldbe threadsafe such that cleanup will only be
384 executed once per test.
385
386 This will return TRUE if all the component handles and log handles
387 closed properly, else return FALSE.
adminbae64d82013-08-01 10:50:15 -0700388 '''
389 result = self.TRUE
Jon Hall5b586732015-06-11 11:39:39 -0700390 lock = self.cleanupLock
391 if lock.acquire( False ):
392 try:
393 if self.cleanupFlag is False: # First thread to run this
394 self.cleanupFlag = True
Jon Hall0fc0d452015-07-14 09:49:58 -0700395 if self.initiated:
396 self.logger.testSummary(self)
Jon Hall5b586732015-06-11 11:39:39 -0700397 for component in self.componentDictionary.keys():
398 try :
399 tempObject = vars(self)[component]
400 print "Disconnecting from " + str(tempObject.name) + ": " + \
401 str(tempObject)
402 tempObject.disconnect()
Jon Hallebe9cea2015-09-04 17:39:44 +0000403 except Exception:
Jon Hall5b586732015-06-11 11:39:39 -0700404 self.log.exception( "Exception while disconnecting from " +
405 str( component ) )
406 result = self.FALSE
407 # Closing all the driver's session files
408 for driver in self.componentDictionary.keys():
409 try:
410 vars(self)[driver].close_log_handles()
Jon Hallebe9cea2015-09-04 17:39:44 +0000411 except Exception:
Jon Hall5b586732015-06-11 11:39:39 -0700412 self.log.exception( "Exception while closing log files for " +
413 str( driver ) )
414 result = self.FALSE
415 else:
416 pass # Someone else already ran through this function
417 finally:
418 lock.release()
419 else: # Someone already has a lock
420 # NOTE: This could cause problems if we don't release the lock
421 # correctly
422 lock.acquire() # Wait for the other thread to finish
423 # NOTE: If we don't wait, exit could be called while the thread
424 # with the lock is still cleaning up
425 lock.release()
adminbae64d82013-08-01 10:50:15 -0700426 return result
Jon Halld61331b2015-02-17 16:35:47 -0800427
adminbae64d82013-08-01 10:50:15 -0700428 def pause(self):
429 '''
430 This function will pause the test's execution, and will continue after user provide 'resume' command.
431 '''
432 __builtin__.testthread.pause()
kelvin-onlabf70fd542015-05-07 18:41:40 -0700433
adminbae64d82013-08-01 10:50:15 -0700434 def onfail(self,*components):
435 '''
kelvin-onlabf70fd542015-05-07 18:41:40 -0700436 When test step failed, calling all the components onfail.
adminbae64d82013-08-01 10:50:15 -0700437 '''
adminbae64d82013-08-01 10:50:15 -0700438 if not components:
439 try :
440 for component in self.componentDictionary.keys():
441 tempObject = vars(self)[component]
442 result = tempObject.onfail()
Jon Hallebe9cea2015-09-04 17:39:44 +0000443 except(Exception),e:
adminbae64d82013-08-01 10:50:15 -0700444 print str(e)
445 result = self.FALSE
adminbae64d82013-08-01 10:50:15 -0700446 else:
447 try :
448 for component in components:
449 tempObject = vars(self)[component]
450 result = tempObject.onfail()
Jon Hallebe9cea2015-09-04 17:39:44 +0000451 except(Exception),e:
adminbae64d82013-08-01 10:50:15 -0700452 print str(e)
453 result = self.FALSE
kelvin-onlabf70fd542015-05-07 18:41:40 -0700454
adminbae64d82013-08-01 10:50:15 -0700455 def getDriverPath(self,driverName):
456 '''
457 Based on the component 'type' specified in the params , this method will find the absolute path ,
458 by recursively searching the name of the component.
459 '''
460 import commands
461
462 cmd = "find "+drivers_path+" -name "+driverName+".py"
463 result = commands.getoutput(cmd)
kelvin-onlabf70fd542015-05-07 18:41:40 -0700464
adminbae64d82013-08-01 10:50:15 -0700465 result_array = str(result).split('\n')
466 result_count = 0
kelvin-onlabf70fd542015-05-07 18:41:40 -0700467
adminbae64d82013-08-01 10:50:15 -0700468 for drivers_list in result_array:
469 result_count = result_count+1
470 if result_count > 1 :
471 print "found "+driverName+" "+ str(result_count) + " times"+str(result_array)
472 self.exit()
kelvin-onlabf70fd542015-05-07 18:41:40 -0700473
adminbae64d82013-08-01 10:50:15 -0700474 result = re.sub("(.*)drivers","",result)
Jon Hall166e4a42015-08-10 12:03:41 -0700475 result = re.sub("\/\/","/",result)
adminbae64d82013-08-01 10:50:15 -0700476 result = re.sub("\.py","",result)
477 result = re.sub("\.pyc","",result)
478 result = re.sub("\/",".",result)
479 result = "drivers"+result
480 return result
adminbae64d82013-08-01 10:50:15 -0700481
482 def step(self,stepDesc):
483 '''
484 The step information of the test-case will append to the logs.
485 '''
486 previousStep = " "+str(self.CurrentTestCaseNumber)+"."+str(self.stepCount-1)+": "+ str(self.stepName) + ""
487 self.stepName = stepDesc
488
489 stepName = " "+str(self.CurrentTestCaseNumber)+"."+str(self.stepCount)+": "+ str(stepDesc) + ""
490 try :
491 if self.stepCount == 0:
492 stepName = " INIT : Initializing the test case :"+self.CurrentTestCase
493 except AttributeError:
494 stepName = " INIT : Initializing the test case :"+str(self.CurrentTestCaseNumber)
kelvin-onlabf70fd542015-05-07 18:41:40 -0700495
adminbae64d82013-08-01 10:50:15 -0700496 self.log.step(stepName)
497 stepHeader = ""
498 if self.stepCount > 1 :
499 stepHeader = "\n"+"-"*45+"\nEnd of Step "+previousStep+"\n"+"-"*45+"\n"
kelvin-onlabf70fd542015-05-07 18:41:40 -0700500
Jon Halld61331b2015-02-17 16:35:47 -0800501 stepHeader += "\n"+"-"*45+"\nStart of Step"+stepName+"\n"+"-"*45+"\n"
adminbae64d82013-08-01 10:50:15 -0700502 for driver in self.componentDictionary.keys():
503 vars(self)[driver+'log'].info(stepHeader)
kelvin-onlabf70fd542015-05-07 18:41:40 -0700504
adminbae64d82013-08-01 10:50:15 -0700505 def case(self,testCaseName):
506 '''
507 Test's each test-case information will append to the logs.
508 '''
Jon Halld61331b2015-02-17 16:35:47 -0800509 self.CurrentTestCase = testCaseName
adminbae64d82013-08-01 10:50:15 -0700510 testCaseName = " " + str(testCaseName) + ""
511 self.log.case(testCaseName)
Jon Halld61331b2015-02-17 16:35:47 -0800512 caseHeader = testCaseName+"\n"+"*" * 40+"\n"
adminbae64d82013-08-01 10:50:15 -0700513 for driver in self.componentDictionary.keys():
514 vars(self)[driver+'log'].info(caseHeader)
kelvin-onlabf70fd542015-05-07 18:41:40 -0700515
adminbae64d82013-08-01 10:50:15 -0700516 def testDesc(self,description):
517 '''
518 Test description will append to the logs.
519 '''
520 description = "Test Description : " + str (description) + ""
521 self.log.info(description)
kelvin-onlabf70fd542015-05-07 18:41:40 -0700522
adminbae64d82013-08-01 10:50:15 -0700523 def _getTest(self):
524 '''
525 This method will parse the test script to find required test information.
526 '''
527 testFile = self.tests_path + "/"+self.TEST + "/"+self.TEST + ".py"
528 testFileHandler = open(testFile, 'r')
529 testFileList = testFileHandler.readlines()
530 testFileHandler.close()
531 #self.TOTAL_TC_PLANNED = 0
532 counter = 0
533 for index in range(len(testFileList)):
534 lineMatch = re.match('\s+def CASE(\d+)(.*):',testFileList[index],0)
535 if lineMatch:
536 counter = counter + 1
Jon Halla1185982014-09-15 14:55:10 -0700537 self.TC_PLANNED = len(self.testcases_list)
kelvin-onlabf70fd542015-05-07 18:41:40 -0700538
adminbae64d82013-08-01 10:50:15 -0700539 def response_parser(self,response, return_format):
540 ''' It will load the default response parser '''
541 response_dict = {}
542 response_dict = self.response_to_dict(response, return_format)
Jon Halld61331b2015-02-17 16:35:47 -0800543 return_format_string = self.dict_to_return_format(response,return_format,response_dict)
adminbae64d82013-08-01 10:50:15 -0700544 return return_format_string
kelvin-onlabf70fd542015-05-07 18:41:40 -0700545
adminbae64d82013-08-01 10:50:15 -0700546 def response_to_dict(self,response,return_format):
adminbae64d82013-08-01 10:50:15 -0700547 response_dict = {}
548 json_match = re.search('^\s*{', response)
549 xml_match = re.search('^\s*\<', response)
550 ini_match = re.search('^\s*\[', response)
551 if json_match :
Jon Hallfebb1c72015-03-05 13:30:09 -0800552 self.log.info(" Response is in 'JSON' format and Converting to '"+return_format+"' format")
Jon Halld61331b2015-02-17 16:35:47 -0800553 # Formatting the json string
adminbae64d82013-08-01 10:50:15 -0700554 response = re.sub(r"{\s*'?(\w)", r'{"\1', response)
555 response = re.sub(r",\s*'?(\w)", r',"\1', response)
556 response = re.sub(r"(\w)'?\s*:", r'\1":', response)
557 response = re.sub(r":\s*'(\w)'\s*([,}])", r':"\1"\2', response)
adminbae64d82013-08-01 10:50:15 -0700558 try :
559 import json
560 response_dict = json.loads(response)
Jon Hallebe9cea2015-09-04 17:39:44 +0000561 except Exception:
Jon Hall2a5002c2015-08-21 16:49:11 -0700562 self.log.exception( "Json Parser is unable to parse the string" )
adminbae64d82013-08-01 10:50:15 -0700563 return response_dict
adminbae64d82013-08-01 10:50:15 -0700564 elif ini_match :
Jon Hallfebb1c72015-03-05 13:30:09 -0800565 self.log.info(" Response is in 'INI' format and Converting to '"+return_format+"' format")
adminbae64d82013-08-01 10:50:15 -0700566 from configobj import ConfigObj
567 response_file = open("respnse_file.temp",'w')
568 response_file.write(response)
Jon Halld61331b2015-02-17 16:35:47 -0800569 response_file.close()
adminbae64d82013-08-01 10:50:15 -0700570 response_dict = ConfigObj("respnse_file.temp")
571 return response_dict
adminbae64d82013-08-01 10:50:15 -0700572 elif xml_match :
Jon Hallfebb1c72015-03-05 13:30:09 -0800573 self.log.info(" Response is in 'XML' format and Converting to '"+return_format+"' format")
adminbae64d82013-08-01 10:50:15 -0700574 try :
adminbae64d82013-08-01 10:50:15 -0700575 response_dict = xmldict.xml_to_dict("<response> "+str(response)+" </response>")
Jon Hallebe9cea2015-09-04 17:39:44 +0000576 except Exception, e:
577 self.log.exception( e )
adminbae64d82013-08-01 10:50:15 -0700578 return response_dict
kelvin-onlabf70fd542015-05-07 18:41:40 -0700579
adminbae64d82013-08-01 10:50:15 -0700580 def dict_to_return_format(self,response,return_format,response_dict):
adminbae64d82013-08-01 10:50:15 -0700581 if return_format =='table' :
582 ''' Will return in table format'''
583 to_do = "Call the table output formatter"
584 global response_table
585 response_table = '\n'
586 response_table = response_table +'\t'.join(response_dict)+"\n"
kelvin-onlabf70fd542015-05-07 18:41:40 -0700587
adminbae64d82013-08-01 10:50:15 -0700588 def get_table(value_to_convert):
589 ''' This will parse the dictionary recusrsively and print as table format'''
590 table_data = ""
591 if type(value_to_convert) == dict :
592 table_data = table_data +'\t'.join(value_to_convert)+"\n"
593 for temp_val in value_to_convert.values() :
594 table_data = table_data + get_table(temp_val)
595 else :
596 table_data = table_data + str(value_to_convert) +"\t"
Jon Halld61331b2015-02-17 16:35:47 -0800597 return table_data
kelvin-onlabf70fd542015-05-07 18:41:40 -0700598
adminbae64d82013-08-01 10:50:15 -0700599 for value in response_dict.values() :
600 response_table = response_table + get_table(value)
Jon Hall88e498c2015-03-06 09:54:35 -0800601 # response_table = response_table + '\t'.join(response_dict.values())
adminbae64d82013-08-01 10:50:15 -0700602 return response_table
kelvin-onlabf70fd542015-05-07 18:41:40 -0700603
adminbae64d82013-08-01 10:50:15 -0700604 elif return_format =='config':
605 ''' Will return in config format'''
606 to_do = 'Call dict to config coverter'
607 response_string = str(response_dict)
608 print response_string
609 response_config = re.sub(",", "\n\t", response_string)
610 response_config = re.sub("u\'", "\'", response_config)
611 response_config = re.sub("{", "", response_config)
612 response_config = re.sub("}", "\n", response_config)
613 response_config = re.sub(":", " =", response_config)
614 return "[response]\n\t "+response_config
adminbae64d82013-08-01 10:50:15 -0700615 elif return_format == 'xml':
616 ''' Will return in xml format'''
adminbae64d82013-08-01 10:50:15 -0700617 response_xml = xmldict.dict_to_xml(response_dict)
618 response_xml = re.sub(">\s*<", ">\n<", response_xml)
619 return "\n"+response_xml
adminbae64d82013-08-01 10:50:15 -0700620 elif return_format == 'json':
621 ''' Will return in json format'''
622 to_do = 'Call dict to xml coverter'
623 import json
624 response_json = json.dumps(response_dict)
625 return response_json
kelvin-onlabf70fd542015-05-07 18:41:40 -0700626
adminbae64d82013-08-01 10:50:15 -0700627 def get_random(self):
628 self.random_order = self.random_order + 1
629 return self.random_order
kelvin-onlabf70fd542015-05-07 18:41:40 -0700630
adminbae64d82013-08-01 10:50:15 -0700631 def exit(self):
632 __builtin__.testthread = None
Jon Hall5b586732015-06-11 11:39:39 -0700633 for thread in threading.enumerate():
634 if thread.isAlive():
635 try:
636 thread._Thread__stop()
637 except:
Jon Hallebe9cea2015-09-04 17:39:44 +0000638 print(str(thread.getName()) + ' could not be terminated' )
adminbae64d82013-08-01 10:50:15 -0700639 sys.exit()
640
641def verifyOptions(options):
642 '''
643 This will verify the command line options and set to default values, if any option not given in command line.
644 '''
645 import pprint
646 pp = pprint.PrettyPrinter(indent=4)
647
Jon Hall88e498c2015-03-06 09:54:35 -0800648 # pp.pprint(options)
adminbae64d82013-08-01 10:50:15 -0700649 verifyTest(options)
650 verifyExample(options)
651 verifyTestScript(options)
652 verifyParams()
653 verifyLogdir(options)
654 verifyMail(options)
655 verifyTestCases(options)
Hari Krishna03f530e2015-07-10 17:28:27 -0700656 verifyOnosCell(options)
adminbae64d82013-08-01 10:50:15 -0700657
658def verifyTest(options):
Jon Hall44506242015-07-29 17:40:26 -0700659 try:
660 if options.testname:
661 main.TEST = options.testname
662 main.classPath = "tests."+main.TEST+"."+main.TEST
663 main.tests_path = tests_path
664 elif options.example:
665 main.TEST = options.example
666 main.tests_path = path+"/examples/"
667 main.classPath = "examples."+main.TEST+"."+main.TEST
668 except AttributeError:
adminbae64d82013-08-01 10:50:15 -0700669 print "Test or Example not specified please specify the --test <test name > or --example <example name>"
Jon Hall5b586732015-06-11 11:39:39 -0700670 main.exit()
adminbae64d82013-08-01 10:50:15 -0700671
672def verifyExample(options):
673 if options.example:
674 main.testDir = path+'/examples/'
675 main.tests_path = path+"/examples/"
676 main.classPath = "examples."+main.TEST+"."+main.TEST
kelvin-onlabf70fd542015-05-07 18:41:40 -0700677
adminbae64d82013-08-01 10:50:15 -0700678def verifyLogdir(options):
Jon Hall88e498c2015-03-06 09:54:35 -0800679 # Verifying Log directory option
adminbae64d82013-08-01 10:50:15 -0700680 if options.logdir:
681 main.logdir = options.logdir
682 else :
Jon Halld61331b2015-02-17 16:35:47 -0800683 main.logdir = main.FALSE
kelvin-onlabf70fd542015-05-07 18:41:40 -0700684
adminbae64d82013-08-01 10:50:15 -0700685def verifyMail(options):
Jon Halld61331b2015-02-17 16:35:47 -0800686 # Checking the mailing list
adminbae64d82013-08-01 10:50:15 -0700687 if options.mail:
688 main.mail = options.mail
689 elif main.params.has_key('mail'):
690 main.mail = main.params['mail']
691 else :
692 main.mail = 'paxweb@paxterrasolutions.com'
693
694def verifyTestCases(options):
Jon Hall88e498c2015-03-06 09:54:35 -0800695 # Getting Test cases list
adminbae64d82013-08-01 10:50:15 -0700696 if options.testcases:
Jon Hallfebb1c72015-03-05 13:30:09 -0800697 testcases_list = options.testcases
Jon Hall88e498c2015-03-06 09:54:35 -0800698 # sys.exit()
adminbae64d82013-08-01 10:50:15 -0700699 testcases_list = re.sub("(\[|\])", "", options.testcases)
700 main.testcases_list = eval(testcases_list+",")
701 else :
702 if 'testcases' in main.params.keys():
Jon Halla1185982014-09-15 14:55:10 -0700703 temp = eval(main.params['testcases']+",")
704 list1=[]
705 if type(temp[0])==list:
Jon Hallfebb1c72015-03-05 13:30:09 -0800706 for test in temp:
707 for testcase in test:
708 if type(testcase)==int:
709 testcase=[testcase]
710 list1.extend(testcase)
711 else :
712 temp=list(temp)
713 for testcase in temp:
714 if type(testcase)==int:
715 testcase=[testcase]
716 list1.extend(testcase)
717 main.testcases_list=list1
adminbae64d82013-08-01 10:50:15 -0700718 else :
719 print "testcases not specifed in params, please provide in params file or 'testcases' commandline argument"
Jon Halld61331b2015-02-17 16:35:47 -0800720 sys.exit()
kelvin-onlabf70fd542015-05-07 18:41:40 -0700721
Hari Krishna03f530e2015-07-10 17:28:27 -0700722def verifyOnosCell(options):
Hari Krishnabe4b97b2015-07-15 12:19:43 -0700723 # Verifying onoscell option
Hari Krishna03f530e2015-07-10 17:28:27 -0700724 if options.onoscell:
725 main.onoscell = options.onoscell
Hari Krishnabe4b97b2015-07-15 12:19:43 -0700726 main.onosIPs = []
727 main.mnIP = ""
728 cellCMD = ". ~/.profile; cell "+main.onoscell
729 output=subprocess.check_output( ["bash", '-c', cellCMD] )
730 splitOutput = output.splitlines()
731 for i in range( len(splitOutput) ):
732 if( re.match( "OCN", splitOutput[i] ) ):
733 mnNode=splitOutput[i].split("=")
734 main.mnIP = mnNode[1]
735 # cell already sorts OC variables in bash, so no need to sort in TestON
736 if( re.match( "OC[1-9]", splitOutput[i] ) ):
737 onosNodes = splitOutput[i].split("=")
738 main.onosIPs.append( onosNodes[1] )
Hari Krishna03f530e2015-07-10 17:28:27 -0700739 else :
740 main.onoscell = main.FALSE
741
adminbae64d82013-08-01 10:50:15 -0700742def verifyTestScript(options):
743 '''
744 Verifyies test script.
745 '''
Jon Halld61331b2015-02-17 16:35:47 -0800746 main.openspeak = openspeak.OpenSpeak()
adminbae64d82013-08-01 10:50:15 -0700747 openspeakfile = main.testDir+"/" + main.TEST + "/" + main.TEST + ".ospk"
748 testfile = main.testDir+"/" + main.TEST + "/" + main.TEST + ".py"
Jon Hall44506242015-07-29 17:40:26 -0700749 if os.path.exists(openspeakfile):
750 # Openspeak file found, compiling to python
adminbae64d82013-08-01 10:50:15 -0700751 main.openspeak.compiler(openspeakfile=openspeakfile,writetofile=1)
752 elif os.path.exists(testfile):
Jon Hall44506242015-07-29 17:40:26 -0700753 # No openspeak found, using python file instead
754 pass
adminbae64d82013-08-01 10:50:15 -0700755 else:
Jon Hall44506242015-07-29 17:40:26 -0700756 print "\nThere is no \""+main.TEST+"\" test script.\nPlease provide a " +\
757 "Python or OpenSpeak test script in the tests folder: " +\
758 main.testDir+"/" + main.TEST + "/"
adminbae64d82013-08-01 10:50:15 -0700759 __builtin__.testthread = None
760 main.exit()
adminbae64d82013-08-01 10:50:15 -0700761 try :
adminbae64d82013-08-01 10:50:15 -0700762 testModule = __import__(main.classPath, globals(), locals(), [main.TEST], -1)
Jon Hallebe9cea2015-09-04 17:39:44 +0000763 except(ImportError):
Jon Hall44506242015-07-29 17:40:26 -0700764 print "There was an import error, it might mean that there is no test named "+main.TEST
Jon Halld61331b2015-02-17 16:35:47 -0800765 main.exit()
adminbae64d82013-08-01 10:50:15 -0700766
767 testClass = getattr(testModule, main.TEST)
768 main.testObject = testClass()
769 load_parser()
Jon Halld61331b2015-02-17 16:35:47 -0800770 main.params = main.parser.parseParams(main.classPath)
771 main.topology = main.parser.parseTopology(main.classPath)
kelvin-onlabf70fd542015-05-07 18:41:40 -0700772
adminbae64d82013-08-01 10:50:15 -0700773def verifyParams():
774 try :
775 main.params = main.params['PARAMS']
Jon Hallebe9cea2015-09-04 17:39:44 +0000776 except(KeyError):
adminbae64d82013-08-01 10:50:15 -0700777 print "Error with the params file: Either the file not specified or the format is not correct"
Jon Halld61331b2015-02-17 16:35:47 -0800778 main.exit()
adminbae64d82013-08-01 10:50:15 -0700779 try :
780 main.topology = main.topology['TOPOLOGY']
Jon Hallebe9cea2015-09-04 17:39:44 +0000781 except(KeyError):
adminbae64d82013-08-01 10:50:15 -0700782 print "Error with the Topology file: Either the file not specified or the format is not correct"
783 main.exit()
kelvin-onlabf70fd542015-05-07 18:41:40 -0700784
adminbae64d82013-08-01 10:50:15 -0700785def load_parser() :
786 '''
787 It facilitates the loading customised parser for topology and params file.
788 It loads parser mentioned in tab named parser of teston.cfg file.
789 It also loads default xmlparser if no parser have specified in teston.cfg file.
790
791 '''
792 confighash = main.configDict
793 if 'file' in confighash['config']['parser'] and 'class' in confighash['config']['parser']:
Jon Hall44506242015-07-29 17:40:26 -0700794 path = confighash['config']['parser']['file']
795 if path != None or confighash['config']['parser']['class']!= None:
796 try:
797 module = re.sub( r".py\s*$", "", path )
adminbae64d82013-08-01 10:50:15 -0700798 moduleList = module.split("/")
799 newModule = ".".join([moduleList[len(moduleList) - 2],moduleList[len(moduleList) - 1]])
Jon Hall44506242015-07-29 17:40:26 -0700800 parsingClass = confighash['config']['parser']['class']
801 parsingModule = __import__(newModule, globals(), locals(), [parsingClass], -1)
802 parsingClass = getattr(parsingModule, parsingClass)
803 main.parser = parsingClass()
804 #hashobj = main.parser.parseParams(main.classPath)
805 if hasattr(main.parser,"parseParams") and hasattr(main.parser,"parseTopology") and hasattr(main.parser,"parse"):
806 pass
807 else:
808 print "Invalid parser format"
adminbae64d82013-08-01 10:50:15 -0700809 main.exit()
Jon Hall44506242015-07-29 17:40:26 -0700810 except ImportError:
811 print "Could not find the file " + path + " using default parser."
Jon Halld61331b2015-02-17 16:35:47 -0800812 load_defaultParser()
Jon Hall44506242015-07-29 17:40:26 -0700813 elif confighash['config']['parser']['file'] == None or confighash['config']['parser']['class'] == None:
Jon Halld61331b2015-02-17 16:35:47 -0800814 load_defaultParser()
adminbae64d82013-08-01 10:50:15 -0700815 else:
816 load_defaultParser()
817
818def load_defaultParser():
819 '''
820 It will load the default parser which is xml parser to parse the params and topology file.
821 '''
822 moduleList = main.parserPath.split("/")
823 newModule = ".".join([moduleList[len(moduleList) - 2],moduleList[len(moduleList) - 1]])
824 try :
Jon Halld61331b2015-02-17 16:35:47 -0800825 parsingClass = main.parsingClass
adminbae64d82013-08-01 10:50:15 -0700826 parsingModule = __import__(newModule, globals(), locals(), [parsingClass], -1)
827 parsingClass = getattr(parsingModule, parsingClass)
828 main.parser = parsingClass()
829 if hasattr(main.parser,"parseParams") and hasattr(main.parser,"parseTopology") and hasattr(main.parser,"parse") :
830 pass
831 else:
832 main.exit()
833
834 except ImportError:
835 print sys.exc_info()[1]
836
adminbae64d82013-08-01 10:50:15 -0700837def load_logger() :
838 '''
839 It facilitates the loading customised parser for topology and params file.
840 It loads parser mentioned in tab named parser of teston.cfg file.
841 It also loads default xmlparser if no parser have specified in teston.cfg file.
842
843 '''
844 confighash = main.configDict
845 if 'file' in confighash['config']['logger'] and 'class' in confighash['config']['logger']:
Jon Hall44506242015-07-29 17:40:26 -0700846 path = confighash['config']['logger']['file']
847 if path != None or confighash['config']['logger']['class']!= None :
848 try:
849 module = re.sub( r".py\s*$", "", path )
adminbae64d82013-08-01 10:50:15 -0700850 moduleList = module.split("/")
851 newModule = ".".join([moduleList[len(moduleList) - 2],moduleList[len(moduleList) - 1]])
Jon Hall44506242015-07-29 17:40:26 -0700852 loggerClass = confighash['config']['logger']['class']
853 loggerModule = __import__(newModule, globals(), locals(), [loggerClass], -1)
854 loggerClass = getattr(loggerModule, loggerClass)
855 main.logger = loggerClass()
856 #hashobj = main.parser.parseParams(main.classPath)
857 except ImportError:
858 print "Could not find the file " + path + " using default logger."
adminbae64d82013-08-01 10:50:15 -0700859 load_defaultlogger()
Jon Halld61331b2015-02-17 16:35:47 -0800860 elif confighash['config']['parser']['file'] == None or confighash['config']['parser']['class'] == None :
861 load_defaultlogger()
adminbae64d82013-08-01 10:50:15 -0700862 else:
863 load_defaultlogger()
864
865def load_defaultlogger():
866 '''
867 It will load the default parser which is xml parser to parse the params and topology file.
868 '''
869 moduleList = main.loggerPath.split("/")
870 newModule = ".".join([moduleList[len(moduleList) - 2],moduleList[len(moduleList) - 1]])
871 try :
Jon Halld61331b2015-02-17 16:35:47 -0800872 loggerClass = main.loggerClass
adminbae64d82013-08-01 10:50:15 -0700873 loggerModule = __import__(newModule, globals(), locals(), [loggerClass], -1)
874 loggerClass = getattr(loggerModule, loggerClass)
875 main.logger = loggerClass()
876
877 except ImportError:
878 print sys.exc_info()[1]
Jon Halld61331b2015-02-17 16:35:47 -0800879 main.exit()
adminbae64d82013-08-01 10:50:15 -0700880
adminbae64d82013-08-01 10:50:15 -0700881def _echo(self):
882 print "THIS IS ECHO"