blob: 395d747b7183e1118eae0c1f07ce3bfe8ac9ef49 [file] [log] [blame]
Flavio Castro0a05b8d2016-06-16 17:26:51 -07001import os
2import imp
3import time
Flavio Castro49c218d2016-06-21 16:55:57 -07004import json
Flavio Castro0a05b8d2016-06-16 17:26:51 -07005
6from core import utilities
7
8
9class Testcaselib:
10 @staticmethod
11 def initTest( main ):
12 """
13 - Construct tests variables
14 - GIT ( optional )
15 - Checkout ONOS master branch
16 - Pull latest ONOS code
17 - Building ONOS ( optional )
18 - Install ONOS package
19 - Build ONOS package
20 """
Flavio Castro0a05b8d2016-06-16 17:26:51 -070021 main.step( "Constructing test variables" )
22 # Test variables
23 main.cellName = main.params[ 'ENV' ][ 'cellName' ]
24 main.apps = main.params[ 'ENV' ][ 'cellApps' ]
25 main.diff = main.params[ 'ENV' ][ 'diffApps' ]
26 gitBranch = main.params[ 'GIT' ][ 'branch' ]
27 main.path = os.path.dirname( main.testFile )
Flavio Castro5608a392016-06-22 17:02:35 -070028 main.dependencyPath = main.path + "/../dependencies/"
Flavio Castro0a05b8d2016-06-16 17:26:51 -070029 main.topology = main.params[ 'DEPENDENCY' ][ 'topology' ]
30 wrapperFile1 = main.params[ 'DEPENDENCY' ][ 'wrapper1' ]
Flavio Castro5608a392016-06-22 17:02:35 -070031 main.scale = (main.params[ 'SCALE' ][ 'size' ]).split( "," )
Flavio Castro0a05b8d2016-06-16 17:26:51 -070032 main.maxNodes = int( main.params[ 'SCALE' ][ 'max' ] )
Flavio Castro5608a392016-06-22 17:02:35 -070033 # main.ONOSport = main.params[ 'CTRL' ][ 'port' ]
Flavio Castro0a05b8d2016-06-16 17:26:51 -070034 main.startUpSleep = int( main.params[ 'SLEEP' ][ 'startup' ] )
Flavio Castro5608a392016-06-22 17:02:35 -070035 main.cellData = { } # for creating cell file
36 main.CLIs = [ ]
37 main.ONOSip = [ ]
38 main.RESTs = [ ]
Flavio Castro0a05b8d2016-06-16 17:26:51 -070039
40 # Assigning ONOS cli handles to a list
Flavio Castro5608a392016-06-22 17:02:35 -070041 for i in range( 1, main.maxNodes + 1 ):
Flavio Castro0a05b8d2016-06-16 17:26:51 -070042 main.CLIs.append( getattr( main, 'ONOScli' + str( i ) ) )
Flavio Castro49c218d2016-06-21 16:55:57 -070043 main.RESTs.append( getattr( main, 'ONOSrest' + str( i ) ) )
Flavio Castro5608a392016-06-22 17:02:35 -070044 main.ONOSip.append( main.CLIs[ i - 1 ].ip_address )
Flavio Castro0a05b8d2016-06-16 17:26:51 -070045 # -- INIT SECTION, ONLY RUNS ONCE -- #
46 main.startUp = imp.load_source( wrapperFile1,
47 main.dependencyPath +
48 wrapperFile1 +
49 ".py" )
50
51 copyResult1 = main.ONOSbench.scp( main.Mininet1,
52 main.dependencyPath +
53 main.topology,
54 main.Mininet1.home,
55 direction="to" )
56 if main.CLIs:
57 stepResult = main.TRUE
58 else:
59 main.log.error( "Did not properly created list of ONOS CLI handle" )
60 stepResult = main.FALSE
61
62 utilities.assert_equals( expect=main.TRUE,
63 actual=stepResult,
64 onpass="Successfully construct " +
65 "test variables ",
66 onfail="Failed to construct test variables" )
67
68 @staticmethod
69 def installOnos( main ):
70 """
71 - Set up cell
72 - Create cell file
73 - Set cell file
74 - Verify cell file
75 - Kill ONOS process
76 - Uninstall ONOS cluster
77 - Verify ONOS start up
78 - Install ONOS cluster
79 - Connect to cli
80 """
81 # main.scale[ 0 ] determines the current number of ONOS controller
Flavio Castro5608a392016-06-22 17:02:35 -070082 apps = main.apps
Flavio Castro0a05b8d2016-06-16 17:26:51 -070083 if main.diff:
84 apps = main.apps + "," + main.diff
Flavio Castro5608a392016-06-22 17:02:35 -070085 else:
86 main.log.error( "App list is empty" )
87 main.case( "Package and start ONOS using apps:" + apps )
Flavio Castro0a05b8d2016-06-16 17:26:51 -070088 print "NODE COUNT = ", main.numCtrls
89 print main.ONOSip
Flavio Castro5608a392016-06-22 17:02:35 -070090 tempOnosIp = [ ]
Flavio Castro0a05b8d2016-06-16 17:26:51 -070091 for i in range( main.numCtrls ):
Flavio Castro5608a392016-06-22 17:02:35 -070092 tempOnosIp.append( main.ONOSip[ i ] )
Flavio Castro0a05b8d2016-06-16 17:26:51 -070093 onosUser = main.params[ 'ENV' ][ 'cellUser' ]
Flavio Castro5608a392016-06-22 17:02:35 -070094 main.step( "Create and Apply cell file" )
Flavio Castro0a05b8d2016-06-16 17:26:51 -070095 main.ONOSbench.createCellFile( main.ONOSbench.ip_address,
96 "temp",
97 main.Mininet1.ip_address,
98 apps,
99 tempOnosIp,
100 onosUser )
101 cellResult = main.ONOSbench.setCell( "temp" )
Flavio Castro5608a392016-06-22 17:02:35 -0700102 verifyResult = main.ONOSbench.verifyCell( )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700103 stepResult = cellResult and verifyResult
104 utilities.assert_equals( expect=main.TRUE,
105 actual=stepResult,
106 onpass="Successfully applied cell to " + \
107 "environment",
108 onfail="Failed to apply cell to environment " )
Flavio Castro5608a392016-06-22 17:02:35 -0700109 # kill off all onos processes
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700110 main.log.info( "Safety check, killing all ONOS processes" +
111 " before initiating environment setup" )
112 for i in range( main.maxNodes ):
113 main.ONOSbench.onosDie( main.ONOSip[ i ] )
114 main.step( "Create and Install ONOS package" )
Flavio Castro5608a392016-06-22 17:02:35 -0700115 packageResult = main.ONOSbench.onosPackage( )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700116
117 onosInstallResult = main.TRUE
118 for i in range( main.numCtrls ):
119 onosInstallResult = onosInstallResult and \
Flavio Castro5608a392016-06-22 17:02:35 -0700120 main.ONOSbench.onosInstall(
121 node=main.ONOSip[ i ] )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700122 stepResult = onosInstallResult
123 utilities.assert_equals( expect=main.TRUE,
124 actual=stepResult,
125 onpass="Successfully installed ONOS package",
126 onfail="Failed to install ONOS package" )
127 main.step( "Starting ONOS service" )
Flavio Castro5608a392016-06-22 17:02:35 -0700128 stopResult, startResult, onosIsUp = main.TRUE, main.TRUE, main.TRUE,
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700129 for i in range( main.numCtrls ):
130 onosIsUp = onosIsUp and main.ONOSbench.isup( main.ONOSip[ i ] )
131 if onosIsUp == main.TRUE:
132 main.log.report( "ONOS instance is up and ready" )
133 else:
134 main.log.report( "ONOS instance may not be up, stop and " +
135 "start ONOS again " )
136 for i in range( main.numCtrls ):
137 stopResult = stopResult and \
138 main.ONOSbench.onosStop( main.ONOSip[ i ] )
139 for i in range( main.numCtrls ):
140 startResult = startResult and \
141 main.ONOSbench.onosStart( main.ONOSip[ i ] )
142 stepResult = onosIsUp and stopResult and startResult
143
144 utilities.assert_equals( expect=main.TRUE,
145 actual=stepResult,
146 onpass="ONOS service is ready",
147 onfail="ONOS service did not start properly" )
148 main.step( "Checking if ONOS CLI is ready" )
149 for i in range( main.numCtrls ):
Flavio Castro5608a392016-06-22 17:02:35 -0700150 main.CLIs[ i ].startCellCli( )
151 cliResult = main.CLIs[ i ].startOnosCli( main.ONOSip[ i ],
152 commandlineTimeout=60,
153 onosStartTimeout=100 )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700154 utilities.assert_equals( expect=main.TRUE,
155 actual=cliResult,
156 onpass="ONOS CLI is ready",
157 onfail="ONOS CLI is not ready" )
Flavio Castro5608a392016-06-22 17:02:35 -0700158 main.active = 0
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700159 for i in range( 10 ):
160 ready = True
Flavio Castro5608a392016-06-22 17:02:35 -0700161 output = main.CLIs[ main.active ].summary( )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700162 if not output:
163 ready = False
164 if ready:
165 break
166 time.sleep( 10 )
167 utilities.assert_equals( expect=True, actual=ready,
168 onpass="ONOS summary command succeded",
169 onfail="ONOS summary command failed" )
170
Flavio Castro49c218d2016-06-21 16:55:57 -0700171 with open( main.dependencyPath + "/" + main.cfgName + ".json" ) as cfg:
Flavio Castro5608a392016-06-22 17:02:35 -0700172 main.RESTs[ main.active ].setNetCfg( json.load( cfg ) )
Flavio Castro49c218d2016-06-21 16:55:57 -0700173
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700174 if not ready:
175 main.log.error( "ONOS startup failed!" )
Flavio Castro5608a392016-06-22 17:02:35 -0700176 main.cleanup( )
177 main.exit( )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700178
179 for i in range( main.numCtrls ):
Flavio Castro5608a392016-06-22 17:02:35 -0700180 main.CLIs[ i ].logSet( "DEBUG", "org.onosproject.segmentrouting" )
181 main.CLIs[ i ].logSet( "DEBUG", "org.onosproject.driver.pipeline" )
182 main.CLIs[ i ].logSet( "DEBUG", "org.onosproject.store.group.impl" )
183 main.CLIs[ i ].logSet( "DEBUG",
184 "org.onosproject.net.flowobjective.impl" )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700185
186 @staticmethod
187 def startMininet( main, topology, args="" ):
188 main.step( "Starting Mininet Topology" )
189 arg = "--onos %d %s" % (main.numCtrls, args)
Flavio Castro5608a392016-06-22 17:02:35 -0700190 main.topology = topology
191 topoResult = main.Mininet1.startNet(
192 topoFile=main.dependencyPath + main.topology, args=arg )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700193 stepResult = topoResult
194 utilities.assert_equals( expect=main.TRUE,
195 actual=stepResult,
196 onpass="Successfully loaded topology",
197 onfail="Failed to load topology" )
198 # Exit if topology did not load properly
199 if not topoResult:
Flavio Castro5608a392016-06-22 17:02:35 -0700200 main.cleanup( )
201 main.exit( )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700202
203 @staticmethod
Flavio Castro5608a392016-06-22 17:02:35 -0700204 def checkFlows( main, minFlowCount ):
205 main.step(
206 " Check whether the flow count is bigger than %s" % minFlowCount )
207 count = utilities.retry( main.CLIs[ main.active ].checkFlowCount,
Flavio Castro02b43632016-06-20 17:07:27 -0700208 main.FALSE,
Flavio Castro5608a392016-06-22 17:02:35 -0700209 kwargs={ 'min': minFlowCount },
Flavio Castro02b43632016-06-20 17:07:27 -0700210 attempts=10,
Flavio Castro5608a392016-06-22 17:02:35 -0700211 sleep=10 )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700212 utilities.assertEquals( \
213 expect=True,
Flavio Castro5608a392016-06-22 17:02:35 -0700214 actual=(count > 0),
215 onpass="Flow count looks correct: " + str( count ),
216 onfail="Flow count looks wrong: " + str( count ) )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700217
218 main.step( "Check whether all flow status are ADDED" )
Flavio Castro5608a392016-06-22 17:02:35 -0700219 flowCheck = utilities.retry( main.CLIs[ main.active ].checkFlowsState,
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700220 main.FALSE,
Flavio Castro5608a392016-06-22 17:02:35 -0700221 kwargs={ 'isPENDING': False },
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700222 attempts=10,
Flavio Castro5608a392016-06-22 17:02:35 -0700223 sleep=10 )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700224 utilities.assertEquals( \
225 expect=main.TRUE,
226 actual=flowCheck,
227 onpass="Flow status is correct!",
228 onfail="Flow status is wrong!" )
Flavio Castro5608a392016-06-22 17:02:35 -0700229 main.ONOSbench.dumpFlows( main.ONOSip[ main.active ],
230 main.logdir, "flowsBefore" + main.cfgName )
231 main.ONOSbench.dumpGroups( main.ONOSip[ 0 ],
232 main.logdir, "groupsBefore" + main.cfgName )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700233
234 @staticmethod
Flavio Castro5608a392016-06-22 17:02:35 -0700235 def pingAll( main, tag="" ):
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700236 main.log.report( "Check full connectivity" )
Flavio Castro5608a392016-06-22 17:02:35 -0700237 main.step( "Check full connectivity %s" % tag )
238 pa = main.Mininet1.pingall( )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700239 utilities.assert_equals( expect=main.TRUE, actual=pa,
240 onpass="Full connectivity successfully tested",
241 onfail="Full connectivity failed" )
Flavio Castro5608a392016-06-22 17:02:35 -0700242 main.ONOSbench.dumpFlows( main.ONOSip[ main.active ],
243 main.logdir, "flowsOn" + tag )
244 main.ONOSbench.dumpGroups( main.ONOSip[ main.active ],
245 main.logdir, "groupsOn" + tag )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700246
247 @staticmethod
248 def killLink( main, end1, end2, switches, links ):
249 """
250 end1,end2: identify the switches, ex.: 'leaf1', 'spine1'
251 switches, links: number of expected switches and links after linkDown, ex.: '4', '6'
252 Kill a link and verify ONOS can see the proper link change
253 """
254 main.linkSleep = float( main.params[ 'timers' ][ 'LinkDiscovery' ] )
Flavio Castro5608a392016-06-22 17:02:35 -0700255 main.step( "Kill link between %s and %s" % (end1, end2) )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700256 LinkDown = main.Mininet1.link( END1=end1, END2=end2, OPTION="down" )
Flavio Castro5608a392016-06-22 17:02:35 -0700257 main.log.info(
258 "Waiting %s seconds for link down to be discovered" % main.linkSleep )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700259 time.sleep( main.linkSleep )
Flavio Castro5608a392016-06-22 17:02:35 -0700260 topology = utilities.retry( main.CLIs[ main.active ].checkStatus,
261 main.FALSE,
262 kwargs={ 'numoswitch': switches,
263 'numolink': links },
264 attempts=10,
265 sleep=main.linkSleep )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700266 result = topology & LinkDown
267 utilities.assert_equals( expect=main.TRUE, actual=result,
268 onpass="Link down successful",
269 onfail="Failed to turn off link?" )
270
271 @staticmethod
Flavio Castro5608a392016-06-22 17:02:35 -0700272 def restoreLink( main, end1, end2, dpid1, dpid2, port1, port2, switches,
273 links ):
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700274 """
275 Params:
276 end1,end2: identify the end switches, ex.: 'leaf1', 'spine1'
277 dpid1, dpid2: dpid of the end switches respectively, ex.: 'of:0000000000000002'
Flavio Castro02b43632016-06-20 17:07:27 -0700278 port1, port2: respective port of the end switches that connects to the link, ex.:'1'
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700279 switches, links: number of expected switches and links after linkDown, ex.: '4', '6'
280 Kill a link and verify ONOS can see the proper link change
281 """
Flavio Castro5608a392016-06-22 17:02:35 -0700282 main.step( "Restore link between %s and %s" % (end1, end2) )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700283 result = False
Flavio Castro5608a392016-06-22 17:02:35 -0700284 count = 0
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700285 while True:
Flavio Castro5608a392016-06-22 17:02:35 -0700286 count += 0
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700287 main.Mininet1.link( END1=end1, END2=end2, OPTION="up" )
288 main.Mininet1.link( END2=end1, END1=end2, OPTION="up" )
Flavio Castro5608a392016-06-22 17:02:35 -0700289 main.log.info(
290 "Waiting %s seconds for link up to be discovered" % main.linkSleep )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700291 time.sleep( main.linkSleep )
Flavio Castro5608a392016-06-22 17:02:35 -0700292 main.CLIs[ main.active ].portstate( dpid=dpid1, port=port1 )
293 main.CLIs[ main.active ].portstate( dpid=dpid2, port=port2 )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700294 time.sleep( main.linkSleep )
295
Flavio Castro5608a392016-06-22 17:02:35 -0700296 result = main.CLIs[ main.active ].checkStatus( numoswitch=switches,
297 numolink=links )
298 if count > 5 or result:
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700299 break
300 utilities.assert_equals( expect=main.TRUE, actual=result,
301 onpass="Link up successful",
302 onfail="Failed to bring link up" )
303
304 @staticmethod
305 def killSwitch( main, switch, switches, links ):
306 """
307 Params: switches, links: number of expected switches and links after SwitchDown, ex.: '4', '6'
Flavio Castro02b43632016-06-20 17:07:27 -0700308 Completely kill a switch and verify ONOS can see the proper change
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700309 """
310 main.switchSleep = float( main.params[ 'timers' ][ 'SwitchDiscovery' ] )
311 main.step( "Kill " + switch )
312 main.log.info( "Stopping" + switch )
313 main.Mininet1.switch( SW=switch, OPTION="stop" )
Flavio Castro5608a392016-06-22 17:02:35 -0700314 # todo make this repeatable
315 main.log.info( "Waiting %s seconds for switch down to be discovered" % (
316 main.switchSleep) )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700317 time.sleep( main.switchSleep )
Flavio Castro5608a392016-06-22 17:02:35 -0700318 topology = utilities.retry( main.CLIs[ main.active ].checkStatus,
319 main.FALSE,
320 kwargs={ 'numoswitch': switches,
321 'numolink': links },
322 attempts=10,
323 sleep=main.switchSleep )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700324 utilities.assert_equals( expect=main.TRUE, actual=topology,
325 onpass="Kill switch successful",
326 onfail="Failed to kill switch?" )
327
328 @staticmethod
329 def recoverSwitch( main, switch, switches, links ):
330 """
331 Params: switches, links: number of expected switches and links after SwitchUp, ex.: '4', '6'
332 Recover a switch and verify ONOS can see the proper change
333 """
Flavio Castro5608a392016-06-22 17:02:35 -0700334 # todo make this repeatable
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700335 main.step( "Recovering " + switch )
336 main.log.info( "Starting" + switch )
Flavio Castro5608a392016-06-22 17:02:35 -0700337 main.Mininet1.switch( SW=switch, OPTION="start" )
338 main.log.info( "Waiting %s seconds for switch up to be discovered" % (
339 main.switchSleep) )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700340 time.sleep( main.switchSleep )
Flavio Castro5608a392016-06-22 17:02:35 -0700341 topology = utilities.retry( main.CLIs[ main.active ].checkStatus,
342 main.FALSE,
343 kwargs={ 'numoswitch': switches,
344 'numolink': links },
345 attempts=10,
346 sleep=main.switchSleep )
Flavio Castro0a05b8d2016-06-16 17:26:51 -0700347 utilities.assert_equals( expect=main.TRUE, actual=topology,
348 onpass="Switch recovery successful",
349 onfail="Failed to recover switch?" )
350
351 @staticmethod
352 def cleanup( main ):
353 """
354 Stop Onos-cluster.
355 Stops Mininet
356 Copies ONOS log
357 """
Flavio Castro5608a392016-06-22 17:02:35 -0700358 main.Mininet1.stopNet( )
Flavio Castro49c218d2016-06-21 16:55:57 -0700359 main.ONOSbench.scp( main.ONOScli1, "/opt/onos/log/karaf.log",
Flavio Castro5608a392016-06-22 17:02:35 -0700360 "/tmp/karaf.log", direction="from" )
Flavio Castro49c218d2016-06-21 16:55:57 -0700361 main.ONOSbench.cpLogsToDir( "/tmp/karaf.log", main.logdir,
Flavio Castro5608a392016-06-22 17:02:35 -0700362 copyFileName="karaf.log." + main.cfgName )
Flavio Castro49c218d2016-06-21 16:55:57 -0700363 for i in range( main.numCtrls ):
Flavio Castro5608a392016-06-22 17:02:35 -0700364 main.ONOSbench.onosStop( main.ONOSip[ i ] )