blob: 59a37e4fbc80975344020621918360fa10700da6 [file] [log] [blame]
Jon Hall6aec96b2015-01-19 14:49:31 -08001"""
Jon Hall73cf9cc2014-11-20 22:28:38 -08002Description: This test is to determine if a single
3 instance ONOS 'cluster' can handle a restart
4
5List of test cases:
6CASE1: Compile ONOS and push it to the test machines
7CASE2: Assign mastership to controllers
8CASE3: Assign intents
9CASE4: Ping across added host intents
10CASE5: Reading state of ONOS
11CASE6: The Failure case. Since this is the Sanity test, we do nothing.
12CASE7: Check state after control plane failure
13CASE8: Compare topo
14CASE9: Link s3-s28 down
15CASE10: Link s3-s28 up
16CASE11: Switch down
17CASE12: Switch up
18CASE13: Clean up
Jon Hall669173b2014-12-17 11:36:30 -080019CASE14: start election app on all onos nodes
20CASE15: Check that Leadership Election is still functional
Jon Hall6aec96b2015-01-19 14:49:31 -080021"""
Jon Hall8f89dda2015-01-22 16:03:33 -080022
23
Jon Hall48cf3ce2015-01-12 15:43:18 -080024class HATestSingleInstanceRestart:
Jon Hall73cf9cc2014-11-20 22:28:38 -080025
Jon Hall6aec96b2015-01-19 14:49:31 -080026 def __init__( self ):
Jon Hall73cf9cc2014-11-20 22:28:38 -080027 self.default = ''
28
Jon Hall6aec96b2015-01-19 14:49:31 -080029 def CASE1( self, main ):
30 """
Jon Hall73cf9cc2014-11-20 22:28:38 -080031 CASE1 is to compile ONOS and push it to the test machines
32
33 Startup sequence:
Jon Hall73cf9cc2014-11-20 22:28:38 -080034 cell <name>
35 onos-verify-cell
36 NOTE: temporary - onos-remove-raft-logs
Jon Hall58c76b72015-02-23 11:09:24 -080037 onos-uninstall
38 start mininet
39 git pull
40 mvn clean install
41 onos-package
Jon Hall73cf9cc2014-11-20 22:28:38 -080042 onos-install -f
43 onos-wait-for-start
Jon Hall58c76b72015-02-23 11:09:24 -080044 start cli sessions
45 start tcpdump
Jon Hall6aec96b2015-01-19 14:49:31 -080046 """
47 main.log.report( "ONOS Single node cluster restart " +
48 "HA test - initialization" )
49 main.case( "Setting up test environment" )
50 # TODO: save all the timers and output them for plotting
Jon Hall73cf9cc2014-11-20 22:28:38 -080051
52 # load some vairables from the params file
Jon Hall8f89dda2015-01-22 16:03:33 -080053 PULLCODE = False
Jon Hall6aec96b2015-01-19 14:49:31 -080054 if main.params[ 'Git' ] == 'True':
Jon Hall8f89dda2015-01-22 16:03:33 -080055 PULLCODE = True
Jon Hall529a37f2015-01-28 10:02:00 -080056 gitBranch = main.params[ 'branch' ]
Jon Hall8f89dda2015-01-22 16:03:33 -080057 cellName = main.params[ 'ENV' ][ 'cellName' ]
Jon Hall6aec96b2015-01-19 14:49:31 -080058
59 # set global variables
Jon Hall8f89dda2015-01-22 16:03:33 -080060 global ONOS1Ip
61 global ONOS1Port
62 global ONOS2Ip
63 global ONOS2Port
64 global ONOS3Ip
65 global ONOS3Port
66 global ONOS4Ip
67 global ONOS4Port
68 global ONOS5Ip
69 global ONOS5Port
70 global ONOS6Ip
71 global ONOS6Port
72 global ONOS7Ip
73 global ONOS7Port
74 global numControllers
Jon Hall73cf9cc2014-11-20 22:28:38 -080075
Jon Hall8f89dda2015-01-22 16:03:33 -080076 ONOS1Ip = main.params[ 'CTRL' ][ 'ip1' ]
77 ONOS1Port = main.params[ 'CTRL' ][ 'port1' ]
78 ONOS2Ip = main.params[ 'CTRL' ][ 'ip2' ]
79 ONOS2Port = main.params[ 'CTRL' ][ 'port2' ]
80 ONOS3Ip = main.params[ 'CTRL' ][ 'ip3' ]
81 ONOS3Port = main.params[ 'CTRL' ][ 'port3' ]
82 ONOS4Ip = main.params[ 'CTRL' ][ 'ip4' ]
83 ONOS4Port = main.params[ 'CTRL' ][ 'port4' ]
84 ONOS5Ip = main.params[ 'CTRL' ][ 'ip5' ]
85 ONOS5Port = main.params[ 'CTRL' ][ 'port5' ]
86 ONOS6Ip = main.params[ 'CTRL' ][ 'ip6' ]
87 ONOS6Port = main.params[ 'CTRL' ][ 'port6' ]
88 ONOS7Ip = main.params[ 'CTRL' ][ 'ip7' ]
89 ONOS7Port = main.params[ 'CTRL' ][ 'port7' ]
90 numControllers = int( main.params[ 'num_controllers' ] )
Jon Hall73cf9cc2014-11-20 22:28:38 -080091
Jon Hall6aec96b2015-01-19 14:49:31 -080092 main.step( "Applying cell variable to environment" )
Jon Hall8f89dda2015-01-22 16:03:33 -080093 cellResult = main.ONOSbench.setCell( cellName )
94 verifyResult = main.ONOSbench.verifyCell()
Jon Hall73cf9cc2014-11-20 22:28:38 -080095
Jon Hall6aec96b2015-01-19 14:49:31 -080096 # FIXME:this is short term fix
97 main.log.report( "Removing raft logs" )
Jon Hall8f89dda2015-01-22 16:03:33 -080098 main.ONOSbench.onosRemoveRaftLogs()
Jon Hall6aec96b2015-01-19 14:49:31 -080099 main.log.report( "Uninstalling ONOS" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800100 main.ONOSbench.onosUninstall( ONOS1Ip )
101 main.ONOSbench.onosUninstall( ONOS2Ip )
102 main.ONOSbench.onosUninstall( ONOS3Ip )
103 main.ONOSbench.onosUninstall( ONOS4Ip )
104 main.ONOSbench.onosUninstall( ONOS5Ip )
105 main.ONOSbench.onosUninstall( ONOS6Ip )
106 main.ONOSbench.onosUninstall( ONOS7Ip )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800107
Jon Hall8f89dda2015-01-22 16:03:33 -0800108 cleanInstallResult = main.TRUE
109 gitPullResult = main.TRUE
Jon Hall73cf9cc2014-11-20 22:28:38 -0800110
Jon Hall97f31752015-02-04 12:01:04 -0800111 main.step( "Starting Mininet" )
112 main.Mininet1.startNet( )
113
Jon Hall6aec96b2015-01-19 14:49:31 -0800114 main.step( "Compiling the latest version of ONOS" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800115 if PULLCODE:
Jon Hall58c76b72015-02-23 11:09:24 -0800116 main.step( "Git checkout and pull " + gitBranch )
Jon Hall529a37f2015-01-28 10:02:00 -0800117 main.ONOSbench.gitCheckout( gitBranch )
Jon Hall8f89dda2015-01-22 16:03:33 -0800118 gitPullResult = main.ONOSbench.gitPull()
Jon Hall73cf9cc2014-11-20 22:28:38 -0800119
Jon Hall6aec96b2015-01-19 14:49:31 -0800120 main.step( "Using mvn clean & install" )
Jon Hall529a37f2015-01-28 10:02:00 -0800121 cleanInstallResult = main.ONOSbench.cleanInstall()
122 else:
123 main.log.warn( "Did not pull new code so skipping mvn " +
124 "clean install" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800125 main.ONOSbench.getVersion( report=True )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800126
Jon Hall8f89dda2015-01-22 16:03:33 -0800127 cellResult = main.ONOSbench.setCell( "SingleHA" )
128 verifyResult = main.ONOSbench.verifyCell()
Jon Hall6aec96b2015-01-19 14:49:31 -0800129 main.step( "Creating ONOS package" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800130 packageResult = main.ONOSbench.onosPackage()
Jon Hall73cf9cc2014-11-20 22:28:38 -0800131
Jon Hall6aec96b2015-01-19 14:49:31 -0800132 main.step( "Installing ONOS package" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800133 onos1InstallResult = main.ONOSbench.onosInstall( options="-f",
134 node=ONOS1Ip )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800135
Jon Hall6aec96b2015-01-19 14:49:31 -0800136 main.step( "Checking if ONOS is up yet" )
Jon Hall6aec96b2015-01-19 14:49:31 -0800137 for i in range( 2 ):
Jon Hall8f89dda2015-01-22 16:03:33 -0800138 onos1Isup = main.ONOSbench.isup( ONOS1Ip )
139 if onos1Isup:
Jon Hall94fd0472014-12-08 11:52:42 -0800140 break
Jon Hall8f89dda2015-01-22 16:03:33 -0800141 if not onos1Isup:
Jon Hall6aec96b2015-01-19 14:49:31 -0800142 main.log.report( "ONOS1 didn't start!" )
Jon Hall94fd0472014-12-08 11:52:42 -0800143
Jon Hall8f89dda2015-01-22 16:03:33 -0800144 cliResult = main.ONOScli1.startOnosCli( ONOS1Ip )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800145
Jon Hall6aec96b2015-01-19 14:49:31 -0800146 main.step( "Start Packet Capture MN" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800147 main.Mininet2.startTcpdump(
Jon Hall6aec96b2015-01-19 14:49:31 -0800148 str( main.params[ 'MNtcpdump' ][ 'folder' ] ) + str( main.TEST )
149 + "-MN.pcap",
150 intf=main.params[ 'MNtcpdump' ][ 'intf' ],
151 port=main.params[ 'MNtcpdump' ][ 'port' ] )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800152
Jon Hall8f89dda2015-01-22 16:03:33 -0800153 case1Result = ( cleanInstallResult and packageResult and
154 cellResult and verifyResult and onos1InstallResult
155 and onos1Isup and cliResult )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800156
Jon Hall8f89dda2015-01-22 16:03:33 -0800157 utilities.assert_equals( expect=main.TRUE, actual=case1Result,
Jon Hall58c76b72015-02-23 11:09:24 -0800158 onpass="Test startup successful",
159 onfail="Test startup NOT successful" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800160
Jon Hall8f89dda2015-01-22 16:03:33 -0800161 if case1Result == main.FALSE:
Jon Hall73cf9cc2014-11-20 22:28:38 -0800162 main.cleanup()
163 main.exit()
164
Jon Hall6aec96b2015-01-19 14:49:31 -0800165 def CASE2( self, main ):
166 """
Jon Hall73cf9cc2014-11-20 22:28:38 -0800167 Assign mastership to controllers
Jon Hall6aec96b2015-01-19 14:49:31 -0800168 """
Jon Hall73cf9cc2014-11-20 22:28:38 -0800169 import re
170
Jon Hall6aec96b2015-01-19 14:49:31 -0800171 main.log.report( "Assigning switches to controllers" )
172 main.case( "Assigning Controllers" )
173 main.step( "Assign switches to controllers" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800174
Jon Hall6aec96b2015-01-19 14:49:31 -0800175 for i in range( 1, 29 ):
Jon Hall8f89dda2015-01-22 16:03:33 -0800176 main.Mininet1.assignSwController(
Jon Hall6aec96b2015-01-19 14:49:31 -0800177 sw=str( i ),
Jon Hall8f89dda2015-01-22 16:03:33 -0800178 ip1=ONOS1Ip, port1=ONOS1Port )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800179
Jon Hall8f89dda2015-01-22 16:03:33 -0800180 mastershipCheck = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -0800181 for i in range( 1, 29 ):
Jon Hall8f89dda2015-01-22 16:03:33 -0800182 response = main.Mininet1.getSwController( "s" + str( i ) )
Jon Hallffb386d2014-11-21 13:43:38 -0800183 try:
Jon Hall6aec96b2015-01-19 14:49:31 -0800184 main.log.info( str( response ) )
Jon Hallffb386d2014-11-21 13:43:38 -0800185 except:
Jon Hall6aec96b2015-01-19 14:49:31 -0800186 main.log.info( repr( response ) )
Jon Hall8f89dda2015-01-22 16:03:33 -0800187 if re.search( "tcp:" + ONOS1Ip, response ):
188 mastershipCheck = mastershipCheck and main.TRUE
Jon Hall73cf9cc2014-11-20 22:28:38 -0800189 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800190 mastershipCheck = main.FALSE
191 if mastershipCheck == main.TRUE:
Jon Hall6aec96b2015-01-19 14:49:31 -0800192 main.log.report( "Switch mastership assigned correctly" )
193 utilities.assert_equals(
194 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -0800195 actual=mastershipCheck,
Jon Hall6aec96b2015-01-19 14:49:31 -0800196 onpass="Switch mastership assigned correctly",
197 onfail="Switches not assigned correctly to controllers" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800198
Jon Hall6aec96b2015-01-19 14:49:31 -0800199 def CASE3( self, main ):
Jon Hall73cf9cc2014-11-20 22:28:38 -0800200 """
201 Assign intents
Jon Hall73cf9cc2014-11-20 22:28:38 -0800202 """
Jon Hall6aec96b2015-01-19 14:49:31 -0800203 # FIXME: we must reinstall intents until we have a persistant
204 # datastore!
Jon Hall73cf9cc2014-11-20 22:28:38 -0800205 import time
Jon Hall58c76b72015-02-23 11:09:24 -0800206 import json
Jon Hall6aec96b2015-01-19 14:49:31 -0800207 main.log.report( "Adding host intents" )
208 main.case( "Adding host Intents" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800209
Jon Hall8f89dda2015-01-22 16:03:33 -0800210 main.step( "Discovering Hosts( Via pingall for now )" )
Jon Hall6aec96b2015-01-19 14:49:31 -0800211 # FIXME: Once we have a host discovery mechanism, use that instead
Jon Hall73cf9cc2014-11-20 22:28:38 -0800212
Jon Hall6aec96b2015-01-19 14:49:31 -0800213 # install onos-app-fwd
214 main.log.info( "Install reactive forwarding app" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800215 main.ONOScli1.featureInstall( "onos-app-fwd" )
Jon Hall94fd0472014-12-08 11:52:42 -0800216
Jon Hall6aec96b2015-01-19 14:49:31 -0800217 # REACTIVE FWD test
Jon Hall8f89dda2015-01-22 16:03:33 -0800218 pingResult = main.FALSE
Jon Hall73cf9cc2014-11-20 22:28:38 -0800219 time1 = time.time()
Jon Hall8f89dda2015-01-22 16:03:33 -0800220 pingResult = main.Mininet1.pingall()
Jon Hall529a37f2015-01-28 10:02:00 -0800221 utilities.assert_equals(
222 expect=main.TRUE,
223 actual=pingResult,
224 onpass="Reactive Pingall test passed",
225 onfail="Reactive Pingall failed, one or more ping pairs failed" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800226 time2 = time.time()
Jon Hall6aec96b2015-01-19 14:49:31 -0800227 main.log.info( "Time for pingall: %2f seconds" % ( time2 - time1 ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800228
Jon Hall6aec96b2015-01-19 14:49:31 -0800229 # uninstall onos-app-fwd
230 main.log.info( "Uninstall reactive forwarding app" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800231 main.ONOScli1.featureUninstall( "onos-app-fwd" )
Jon Hall6aec96b2015-01-19 14:49:31 -0800232 # timeout for fwd flows
233 time.sleep( 10 )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800234
Jon Hall6aec96b2015-01-19 14:49:31 -0800235 main.step( "Add host intents" )
Jon Hall58c76b72015-02-23 11:09:24 -0800236 intentIds = []
Jon Hall6aec96b2015-01-19 14:49:31 -0800237 # TODO: move the host numbers to params
Jon Hall58c76b72015-02-23 11:09:24 -0800238 # Maybe look at all the paths we ping?
Jon Hall8f89dda2015-01-22 16:03:33 -0800239 intentAddResult = True
Jon Hall58c76b72015-02-23 11:09:24 -0800240 hostResult = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -0800241 for i in range( 8, 18 ):
242 main.log.info( "Adding host intent between h" + str( i ) +
243 " and h" + str( i + 10 ) )
244 host1 = "00:00:00:00:00:" + \
245 str( hex( i )[ 2: ] ).zfill( 2 ).upper()
246 host2 = "00:00:00:00:00:" + \
247 str( hex( i + 10 )[ 2: ] ).zfill( 2 ).upper()
Jon Hall1b8f54a2015-02-04 13:24:20 -0800248 # NOTE: getHost can return None
249 host1Dict = main.ONOScli1.getHost( host1 )
250 host2Dict = main.ONOScli1.getHost( host2 )
251 host1Id = None
252 host2Id = None
253 if host1Dict and host2Dict:
254 host1Id = host1Dict.get( 'id', None )
255 host2Id = host2Dict.get( 'id', None )
Jon Hall8f89dda2015-01-22 16:03:33 -0800256 if host1Id and host2Id:
Jon Hall58c76b72015-02-23 11:09:24 -0800257 tmpId = main.ONOScli1.addHostIntent(
Jon Hall8f89dda2015-01-22 16:03:33 -0800258 host1Id,
259 host2Id )
Jon Hall58c76b72015-02-23 11:09:24 -0800260 main.log.info( "Added intent with id: " + tmpId )
261 intentIds.append( tmpId )
Jon Hall669173b2014-12-17 11:36:30 -0800262 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800263 main.log.error( "Error, getHost() failed" )
Jon Hall1b8f54a2015-02-04 13:24:20 -0800264 main.log.warn( json.dumps( json.loads( main.ONOScli1.hosts() ),
265 sort_keys=True,
266 indent=4,
267 separators=( ',', ': ' ) ) )
Jon Hall58c76b72015-02-23 11:09:24 -0800268 hostResult = main.FALSE
269 onosIds = main.ONOScli1.getAllIntentsId()
270 main.log.info( "Submitted intents: " + str( intentIds ) )
271 main.log.info( "Intents in ONOS: " + str( onosIds ) )
272 for intent in intentIds:
273 if intent in onosIds:
274 pass # intent submitted is still in onos
275 else:
276 intentAddResult = False
Jon Hall1b8f54a2015-02-04 13:24:20 -0800277 # Print the intent states
Jon Hall58c76b72015-02-23 11:09:24 -0800278 intents = main.ONOScli1.intents()
Jon Hall1b8f54a2015-02-04 13:24:20 -0800279 intentStates = []
Jon Hall58c76b72015-02-23 11:09:24 -0800280 main.log.info( "%-6s%-15s%-15s" % ( 'Count', 'ID', 'State' ) )
281 count = 0
Jon Hall1b8f54a2015-02-04 13:24:20 -0800282 for intent in json.loads( intents ): # Iter through intents of a node
Jon Hall58c76b72015-02-23 11:09:24 -0800283 state = intent.get( 'state', None )
284 intentId = intent.get( 'id', None )
285 intentStates.append( ( intentId, state ) )
286 # add submitted intents not in the store
287 tmplist = [ i for i, s in intentStates ]
288 missingIntents = False
289 for i in intentIds:
290 if i not in tmplist:
291 intentStates.append( ( i, " - " ) )
292 missingIntents = True
293 intentStates.sort()
294 for i, s in intentStates:
295 count += 1
296 main.log.info( "%-6s%-15s%-15s" %
297 ( str( count ), str( i ), str( s ) ) )
298 intentAddResult = bool( pingResult and hostResult and intentAddResult
299 and not missingIntents)
Jon Hall6aec96b2015-01-19 14:49:31 -0800300 utilities.assert_equals(
301 expect=True,
Jon Hall8f89dda2015-01-22 16:03:33 -0800302 actual=intentAddResult,
Jon Hall529a37f2015-01-28 10:02:00 -0800303 onpass="Pushed host intents to ONOS",
304 onfail="Error in pushing host intents to ONOS" )
Jon Hall58c76b72015-02-23 11:09:24 -0800305
306 if not intentAddResult:
307 import time
308 main.log.info( "Sleeping 60 seconds to see if intents are found" )
309 time.sleep( 60 )
310 onosIds = main.ONOScli1.getAllIntentsId()
311 main.log.info( "Submitted intents: " + str( intentIds ) )
312 main.log.info( "Intents in ONOS: " + str( onosIds ) )
313 # Print the intent states
314 intents = main.ONOScli1.intents()
315 intentStates = []
316 main.log.info( "%-6s%-15s%-15s" % ( 'Count', 'ID', 'State' ) )
317 count = 0
318 for intent in json.loads( intents ):
319 # Iter through intents of a node
320 state = intent.get( 'state', None )
321 intentId = intent.get( 'id', None )
322 intentStates.append( ( intentId, state ) )
323 # add submitted intents not in the store
324 tmplist = [ i for i, s in intentStates ]
325 for i in intentIds:
326 if i not in tmplist:
327 intentStates.append( ( i, " - " ) )
328 intentStates.sort()
329 for i, s in intentStates:
330 count += 1
331 main.log.info( "%-6s%-15s%-15s" %
332 ( str( count ), str( i ), str( s ) ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800333
Jon Hall6aec96b2015-01-19 14:49:31 -0800334 def CASE4( self, main ):
Jon Hall73cf9cc2014-11-20 22:28:38 -0800335 """
336 Ping across added host intents
337 """
Jon Hall58c76b72015-02-23 11:09:24 -0800338 import json
Jon Hall73cf9cc2014-11-20 22:28:38 -0800339 description = " Ping across added host intents"
Jon Hall6aec96b2015-01-19 14:49:31 -0800340 main.log.report( description )
341 main.case( description )
Jon Hall8f89dda2015-01-22 16:03:33 -0800342 PingResult = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -0800343 for i in range( 8, 18 ):
Jon Hall58c76b72015-02-23 11:09:24 -0800344 ping = main.Mininet1.pingHost( src="h" + str( i ),
345 target="h" + str( i + 10 ) )
Jon Hall8f89dda2015-01-22 16:03:33 -0800346 PingResult = PingResult and ping
Jon Hall6aec96b2015-01-19 14:49:31 -0800347 if ping == main.FALSE:
348 main.log.warn( "Ping failed between h" + str( i ) +
349 " and h" + str( i + 10 ) )
350 elif ping == main.TRUE:
351 main.log.info( "Ping test passed!" )
Jon Hall21270ac2015-02-16 17:59:55 -0800352 # Don't set PingResult or you'd override failures
Jon Hall8f89dda2015-01-22 16:03:33 -0800353 if PingResult == main.FALSE:
Jon Hall6aec96b2015-01-19 14:49:31 -0800354 main.log.report(
355 "Intents have not been installed correctly, pings failed." )
Jon Hall58c76b72015-02-23 11:09:24 -0800356 # TODO: pretty print
Jon Hall529a37f2015-01-28 10:02:00 -0800357 main.log.warn( "ONSO1 intents: " )
358 main.log.warn( json.dumps( json.loads( main.ONOScli1.intents() ),
359 sort_keys=True,
360 indent=4,
361 separators=( ',', ': ' ) ) )
Jon Hall8f89dda2015-01-22 16:03:33 -0800362 if PingResult == main.TRUE:
Jon Hall6aec96b2015-01-19 14:49:31 -0800363 main.log.report(
364 "Intents have been installed correctly and verified by pings" )
365 utilities.assert_equals(
366 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -0800367 actual=PingResult,
Jon Hall6aec96b2015-01-19 14:49:31 -0800368 onpass="Intents have been installed correctly and pings work",
369 onfail="Intents have not been installed correctly, pings failed." )
Jon Hall58c76b72015-02-23 11:09:24 -0800370 if PingResult is not main.TRUE:
371 # Print the intent states
372 intents = main.ONOScli1.intents()
373 intentStates = []
374 main.log.info( "%-6s%-15s%-15s" % ( 'Count', 'ID', 'State' ) )
375 count = 0
376 # Iter through intents of a node
377 for intent in json.loads( intents ):
378 state = intent.get( 'state', None )
379 intentId = intent.get( 'id', None )
380 intentStates.append( ( intentId, state ) )
381 intentStates.sort()
382 for i, s in intentStates:
383 count += 1
384 main.log.info( "%-6s%-15s%-15s" %
385 ( str( count ), str( i ), str( s ) ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800386
Jon Hall6aec96b2015-01-19 14:49:31 -0800387 def CASE5( self, main ):
388 """
Jon Hall73cf9cc2014-11-20 22:28:38 -0800389 Reading state of ONOS
Jon Hall6aec96b2015-01-19 14:49:31 -0800390 """
Jon Hall73cf9cc2014-11-20 22:28:38 -0800391 import json
Jon Hall6aec96b2015-01-19 14:49:31 -0800392 # assumes that sts is already in you PYTHONPATH
393 from sts.topology.teston_topology import TestONTopology
Jon Hall73cf9cc2014-11-20 22:28:38 -0800394
Jon Hall6aec96b2015-01-19 14:49:31 -0800395 main.log.report( "Setting up and gathering data for current state" )
396 main.case( "Setting up and gathering data for current state" )
397 # The general idea for this test case is to pull the state of
398 # ( intents,flows, topology,... ) from each ONOS node
399 # We can then compare them with eachother and also with past states
Jon Hall73cf9cc2014-11-20 22:28:38 -0800400
Jon Hall6aec96b2015-01-19 14:49:31 -0800401 main.step( "Get the Mastership of each switch from each controller" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800402 global mastershipState
403 mastershipState = []
Jon Hall94fd0472014-12-08 11:52:42 -0800404
Jon Hall6aec96b2015-01-19 14:49:31 -0800405 # Assert that each device has a master
Jon Hall8f89dda2015-01-22 16:03:33 -0800406 rolesNotNull = main.ONOScli1.rolesNotNull()
Jon Hall6aec96b2015-01-19 14:49:31 -0800407 utilities.assert_equals(
408 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -0800409 actual=rolesNotNull,
Jon Hall6aec96b2015-01-19 14:49:31 -0800410 onpass="Each device has a master",
411 onfail="Some devices don't have a master assigned" )
Jon Hall94fd0472014-12-08 11:52:42 -0800412
Jon Hall8f89dda2015-01-22 16:03:33 -0800413 ONOS1Mastership = main.ONOScli1.roles()
Jon Hall6aec96b2015-01-19 14:49:31 -0800414 # TODO: Make this a meaningful check
Jon Hall8f89dda2015-01-22 16:03:33 -0800415 if "Error" in ONOS1Mastership or not ONOS1Mastership:
Jon Hall6aec96b2015-01-19 14:49:31 -0800416 main.log.report( "Error in getting ONOS roles" )
417 main.log.warn(
418 "ONOS1 mastership response: " +
Jon Hall8f89dda2015-01-22 16:03:33 -0800419 repr( ONOS1Mastership ) )
420 consistentMastership = main.FALSE
Jon Hall73cf9cc2014-11-20 22:28:38 -0800421 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800422 mastershipState = ONOS1Mastership
423 consistentMastership = main.TRUE
Jon Hall73cf9cc2014-11-20 22:28:38 -0800424
Jon Hall6aec96b2015-01-19 14:49:31 -0800425 main.step( "Get the intents from each controller" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800426 global intentState
427 intentState = []
428 ONOS1Intents = main.ONOScli1.intents( jsonFormat=True )
429 intentCheck = main.FALSE
430 if "Error" in ONOS1Intents or not ONOS1Intents:
Jon Hall6aec96b2015-01-19 14:49:31 -0800431 main.log.report( "Error in getting ONOS intents" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800432 main.log.warn( "ONOS1 intents response: " + repr( ONOS1Intents ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800433 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800434 intentCheck = main.TRUE
Jon Hall73cf9cc2014-11-20 22:28:38 -0800435
Jon Hall6aec96b2015-01-19 14:49:31 -0800436 main.step( "Get the flows from each controller" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800437 global flowState
438 flowState = []
Jon Hall8f89dda2015-01-22 16:03:33 -0800439 flowCheck = main.FALSE
Jon Hall58c76b72015-02-23 11:09:24 -0800440 ONOS1Flows = main.ONOScli1.flows( jsonFormat=True )
Jon Hall8f89dda2015-01-22 16:03:33 -0800441 if "Error" in ONOS1Flows or not ONOS1Flows:
Jon Hall58c76b72015-02-23 11:09:24 -0800442 main.log.report( "Error in getting ONOS flows" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800443 main.log.warn( "ONOS1 flows repsponse: " + ONOS1Flows )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800444 else:
Jon Hall6aec96b2015-01-19 14:49:31 -0800445 # TODO: Do a better check, maybe compare flows on switches?
Jon Hall8f89dda2015-01-22 16:03:33 -0800446 flowState = ONOS1Flows
447 flowCheck = main.TRUE
Jon Hall73cf9cc2014-11-20 22:28:38 -0800448
Jon Hall6aec96b2015-01-19 14:49:31 -0800449 main.step( "Get the OF Table entries" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800450 global flows
Jon Hall6aec96b2015-01-19 14:49:31 -0800451 flows = []
452 for i in range( 1, 29 ):
Jon Hall8f89dda2015-01-22 16:03:33 -0800453 flows.append( main.Mininet2.getFlowTable( 1.3, "s" + str( i ) ) )
Jon Hall58c76b72015-02-23 11:09:24 -0800454 if flowCheck == main.FALSE:
455 for table in flows:
456 main.log.warn( table )
Jon Hall6aec96b2015-01-19 14:49:31 -0800457 # TODO: Compare switch flow tables with ONOS flow tables
Jon Hall73cf9cc2014-11-20 22:28:38 -0800458
Jon Hall6aec96b2015-01-19 14:49:31 -0800459 main.step( "Create TestONTopology object" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800460 ctrls = []
461 count = 1
462 temp = ()
Jon Hall6aec96b2015-01-19 14:49:31 -0800463 temp = temp + ( getattr( main, ( 'ONOS' + str( count ) ) ), )
464 temp = temp + ( "ONOS" + str( count ), )
465 temp = temp + ( main.params[ 'CTRL' ][ 'ip' + str( count ) ], )
466 temp = temp + \
467 ( eval( main.params[ 'CTRL' ][ 'port' + str( count ) ] ), )
468 ctrls.append( temp )
469 MNTopo = TestONTopology(
470 main.Mininet1,
471 ctrls ) # can also add Intent API info for intent operations
Jon Hall73cf9cc2014-11-20 22:28:38 -0800472
Jon Hall6aec96b2015-01-19 14:49:31 -0800473 main.step( "Collecting topology information from ONOS" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800474 devices = []
475 devices.append( main.ONOScli1.devices() )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800476 hosts = []
Jon Hall58c76b72015-02-23 11:09:24 -0800477 hosts.append( json.loads( main.ONOScli1.hosts() ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800478 ports = []
479 ports.append( main.ONOScli1.ports() )
480 links = []
481 links.append( main.ONOScli1.links() )
Jon Hall58c76b72015-02-23 11:09:24 -0800482 clusters = []
483 clusters.append( main.ONOScli1.clusters() )
484 ipResult = main.TRUE
485 for controller in range( 0, len( hosts ) ):
486 controllerStr = str( controller + 1 )
487 for host in hosts[ controller ]:
488 if host is None or host.get( 'ips', [] ) == []:
489 main.log.error(
490 "DEBUG:Error with host ips on controller" +
491 controllerStr + ": " + str( host ) )
492 ipResult = main.FALSE
493
494 # there should always only be one cluster
495 numClusters = len( json.loads( clusters[ 0 ] ) )
496 clusterResults = main.FALSE
497 if numClusters == 1:
498 clusterResults = main.TRUE
499 utilities.assert_equals(
500 expect=1,
501 actual=numClusters,
502 onpass="ONOS shows 1 SCC",
503 onfail="ONOS shows " + str( numClusters ) + " SCCs" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800504
Jon Hall6aec96b2015-01-19 14:49:31 -0800505 main.step( "Comparing ONOS topology to MN" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800506 devicesResults = main.TRUE
507 portsResults = main.TRUE
508 linksResults = main.TRUE
Jon Hall58c76b72015-02-23 11:09:24 -0800509 hostsResults = main.TRUE
Jon Hall8f89dda2015-01-22 16:03:33 -0800510 for controller in range( numControllers ):
511 controllerStr = str( controller + 1 )
Jon Hall6aec96b2015-01-19 14:49:31 -0800512 if devices[ controller ] or "Error" not in devices[ controller ]:
Jon Hall8f89dda2015-01-22 16:03:33 -0800513 currentDevicesResult = main.Mininet1.compareSwitches(
Jon Hall6aec96b2015-01-19 14:49:31 -0800514 MNTopo,
Jon Hall58c76b72015-02-23 11:09:24 -0800515 json.loads( devices[ controller ] ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800516 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800517 currentDevicesResult = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -0800518 utilities.assert_equals( expect=main.TRUE,
Jon Hall58c76b72015-02-23 11:09:24 -0800519 actual=currentDevicesResult,
520 onpass="ONOS" + controllerStr +
521 " Switches view is correct",
522 onfail="ONOS" + controllerStr +
523 " Switches view is incorrect" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800524
Jon Hall6aec96b2015-01-19 14:49:31 -0800525 if ports[ controller ] or "Error" not in ports[ controller ]:
Jon Hall8f89dda2015-01-22 16:03:33 -0800526 currentPortsResult = main.Mininet1.comparePorts(
Jon Hall6aec96b2015-01-19 14:49:31 -0800527 MNTopo,
Jon Hall58c76b72015-02-23 11:09:24 -0800528 json.loads( ports[ controller ] ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800529 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800530 currentPortsResult = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -0800531 utilities.assert_equals( expect=main.TRUE,
Jon Hall58c76b72015-02-23 11:09:24 -0800532 actual=currentPortsResult,
533 onpass="ONOS" + controllerStr +
534 " ports view is correct",
535 onfail="ONOS" + controllerStr +
536 " ports view is incorrect" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800537
Jon Hall6aec96b2015-01-19 14:49:31 -0800538 if links[ controller ] or "Error" not in links[ controller ]:
Jon Hall8f89dda2015-01-22 16:03:33 -0800539 currentLinksResult = main.Mininet1.compareLinks(
Jon Hall6aec96b2015-01-19 14:49:31 -0800540 MNTopo,
Jon Hall58c76b72015-02-23 11:09:24 -0800541 json.loads( links[ controller ] ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800542 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800543 currentLinksResult = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -0800544 utilities.assert_equals( expect=main.TRUE,
Jon Hall58c76b72015-02-23 11:09:24 -0800545 actual=currentLinksResult,
546 onpass="ONOS" + controllerStr +
547 " links view is correct",
548 onfail="ONOS" + controllerStr +
549 " links view is incorrect" )
550
551 if hosts[ controller ] or "Error" not in hosts[ controller ]:
552 currentHostsResult = main.Mininet1.compareHosts(
553 MNTopo, hosts[ controller ] )
554 else:
555 currentHostsResult = main.FALSE
556 utilities.assert_equals( expect=main.TRUE,
557 actual=currentHostsResult,
558 onpass="ONOS" + controllerStr +
559 " hosts exist in Mininet",
560 onfail="ONOS" + controllerStr +
561 " hosts don't match Mininet" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800562
Jon Hall8f89dda2015-01-22 16:03:33 -0800563 devicesResults = devicesResults and currentDevicesResult
564 portsResults = portsResults and currentPortsResult
565 linksResults = linksResults and currentLinksResult
Jon Hall58c76b72015-02-23 11:09:24 -0800566 hostsResults = hostsResults and currentHostsResult
Jon Hall73cf9cc2014-11-20 22:28:38 -0800567
Jon Hall58c76b72015-02-23 11:09:24 -0800568 topoResult = devicesResults and portsResults and linksResults\
569 and clusterResults and ipResult and hostsResults
Jon Hall8f89dda2015-01-22 16:03:33 -0800570 utilities.assert_equals( expect=main.TRUE, actual=topoResult,
Jon Hall58c76b72015-02-23 11:09:24 -0800571 onpass="Topology Check Test successful",
572 onfail="Topology Check Test NOT successful" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800573
Jon Hall8f89dda2015-01-22 16:03:33 -0800574 finalAssert = main.TRUE
575 finalAssert = finalAssert and topoResult and flowCheck \
Jon Hall58c76b72015-02-23 11:09:24 -0800576 and intentCheck and consistentMastership and rolesNotNull
Jon Hall8f89dda2015-01-22 16:03:33 -0800577 utilities.assert_equals( expect=main.TRUE, actual=finalAssert,
Jon Hall58c76b72015-02-23 11:09:24 -0800578 onpass="State check successful",
579 onfail="State check NOT successful" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800580
Jon Hall6aec96b2015-01-19 14:49:31 -0800581 def CASE6( self, main ):
582 """
Jon Hallffb386d2014-11-21 13:43:38 -0800583 The Failure case.
Jon Hall6aec96b2015-01-19 14:49:31 -0800584 """
Jon Hallffb386d2014-11-21 13:43:38 -0800585 import time
Jon Hall73cf9cc2014-11-20 22:28:38 -0800586
Jon Hall6aec96b2015-01-19 14:49:31 -0800587 main.log.report( "Restart ONOS node" )
588 main.log.case( "Restart ONOS node" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800589 main.ONOSbench.onosKill( ONOS1Ip )
Jon Hallffb386d2014-11-21 13:43:38 -0800590 start = time.time()
Jon Hall73cf9cc2014-11-20 22:28:38 -0800591
Jon Hall6aec96b2015-01-19 14:49:31 -0800592 main.step( "Checking if ONOS is up yet" )
Jon Hallffb386d2014-11-21 13:43:38 -0800593 count = 0
Jon Hall94fd0472014-12-08 11:52:42 -0800594 while count < 10:
Jon Hall8f89dda2015-01-22 16:03:33 -0800595 onos1Isup = main.ONOSbench.isup( ONOS1Ip )
596 if onos1Isup == main.TRUE:
Jon Hallffb386d2014-11-21 13:43:38 -0800597 elapsed = time.time() - start
598 break
599 else:
600 count = count + 1
Jon Hall73cf9cc2014-11-20 22:28:38 -0800601
Jon Hall8f89dda2015-01-22 16:03:33 -0800602 cliResult = main.ONOScli1.startOnosCli( ONOS1Ip )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800603
Jon Hall8f89dda2015-01-22 16:03:33 -0800604 caseResults = main.TRUE and onos1Isup and cliResult
605 utilities.assert_equals( expect=main.TRUE, actual=caseResults,
Jon Hall58c76b72015-02-23 11:09:24 -0800606 onpass="ONOS restart successful",
607 onfail="ONOS restart NOT successful" )
608 main.log.info( "ESTIMATE: ONOS took %s seconds to restart" %
609 str( elapsed ) )
Jon Hall6aec96b2015-01-19 14:49:31 -0800610 time.sleep( 5 )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800611
Jon Hall6aec96b2015-01-19 14:49:31 -0800612 def CASE7( self, main ):
613 """
Jon Hall73cf9cc2014-11-20 22:28:38 -0800614 Check state after ONOS failure
Jon Hall6aec96b2015-01-19 14:49:31 -0800615 """
Jon Hall73cf9cc2014-11-20 22:28:38 -0800616 import json
Jon Hall6aec96b2015-01-19 14:49:31 -0800617 main.case( "Running ONOS Constant State Tests" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800618
Jon Hall6aec96b2015-01-19 14:49:31 -0800619 # Assert that each device has a master
Jon Hall8f89dda2015-01-22 16:03:33 -0800620 rolesNotNull = main.ONOScli1.rolesNotNull()
Jon Hall6aec96b2015-01-19 14:49:31 -0800621 utilities.assert_equals(
622 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -0800623 actual=rolesNotNull,
Jon Hall6aec96b2015-01-19 14:49:31 -0800624 onpass="Each device has a master",
625 onfail="Some devices don't have a master assigned" )
Jon Hall94fd0472014-12-08 11:52:42 -0800626
Jon Hall6aec96b2015-01-19 14:49:31 -0800627 main.step( "Check if switch roles are consistent across all nodes" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800628 ONOS1Mastership = main.ONOScli1.roles()
Jon Hall6aec96b2015-01-19 14:49:31 -0800629 # FIXME: Refactor this whole case for single instance
Jon Hall8f89dda2015-01-22 16:03:33 -0800630 if "Error" in ONOS1Mastership or not ONOS1Mastership:
Jon Hall6aec96b2015-01-19 14:49:31 -0800631 main.log.report( "Error in getting ONOS mastership" )
Jon Hall58c76b72015-02-23 11:09:24 -0800632 main.log.warn( "ONOS1 mastership response: " +
633 repr( ONOS1Mastership ) )
Jon Hall8f89dda2015-01-22 16:03:33 -0800634 consistentMastership = main.FALSE
Jon Hall73cf9cc2014-11-20 22:28:38 -0800635 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800636 consistentMastership = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -0800637 main.log.report(
638 "Switch roles are consistent across all ONOS nodes" )
639 utilities.assert_equals(
640 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -0800641 actual=consistentMastership,
Jon Hall6aec96b2015-01-19 14:49:31 -0800642 onpass="Switch roles are consistent across all ONOS nodes",
643 onfail="ONOS nodes have different views of switch roles" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800644
645 description2 = "Compare switch roles from before failure"
Jon Hall6aec96b2015-01-19 14:49:31 -0800646 main.step( description2 )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800647
Jon Hall8f89dda2015-01-22 16:03:33 -0800648 currentJson = json.loads( ONOS1Mastership )
649 oldJson = json.loads( mastershipState )
650 mastershipCheck = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -0800651 for i in range( 1, 29 ):
652 switchDPID = str(
Jon Hall58c76b72015-02-23 11:09:24 -0800653 main.Mininet1.getSwitchDPID( switch="s" + str( i ) ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800654
Jon Hall8f89dda2015-01-22 16:03:33 -0800655 current = [ switch[ 'master' ] for switch in currentJson
Jon Hall6aec96b2015-01-19 14:49:31 -0800656 if switchDPID in switch[ 'id' ] ]
Jon Hall8f89dda2015-01-22 16:03:33 -0800657 old = [ switch[ 'master' ] for switch in oldJson
Jon Hall6aec96b2015-01-19 14:49:31 -0800658 if switchDPID in switch[ 'id' ] ]
Jon Hall73cf9cc2014-11-20 22:28:38 -0800659 if current == old:
Jon Hall8f89dda2015-01-22 16:03:33 -0800660 mastershipCheck = mastershipCheck and main.TRUE
Jon Hall73cf9cc2014-11-20 22:28:38 -0800661 else:
Jon Hall6aec96b2015-01-19 14:49:31 -0800662 main.log.warn( "Mastership of switch %s changed" % switchDPID )
Jon Hall8f89dda2015-01-22 16:03:33 -0800663 mastershipCheck = main.FALSE
664 if mastershipCheck == main.TRUE:
Jon Hall6aec96b2015-01-19 14:49:31 -0800665 main.log.report( "Mastership of Switches was not changed" )
666 utilities.assert_equals(
667 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -0800668 actual=mastershipCheck,
Jon Hall6aec96b2015-01-19 14:49:31 -0800669 onpass="Mastership of Switches was not changed",
670 onfail="Mastership of some switches changed" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800671 mastershipCheck = mastershipCheck and consistentMastership
Jon Hall73cf9cc2014-11-20 22:28:38 -0800672
Jon Hall6aec96b2015-01-19 14:49:31 -0800673 main.step( "Get the intents and compare across all nodes" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800674 ONOS1Intents = main.ONOScli1.intents( jsonFormat=True )
675 intentCheck = main.FALSE
676 if "Error" in ONOS1Intents or not ONOS1Intents:
Jon Hall6aec96b2015-01-19 14:49:31 -0800677 main.log.report( "Error in getting ONOS intents" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800678 main.log.warn( "ONOS1 intents response: " + repr( ONOS1Intents ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800679 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800680 intentCheck = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -0800681 main.log.report( "Intents are consistent across all ONOS nodes" )
682 utilities.assert_equals(
683 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -0800684 actual=intentCheck,
Jon Hall6aec96b2015-01-19 14:49:31 -0800685 onpass="Intents are consistent across all ONOS nodes",
686 onfail="ONOS nodes have different views of intents" )
Jon Hall1b8f54a2015-02-04 13:24:20 -0800687 # Print the intent states
688 intents = []
689 intents.append( ONOS1Intents )
690 intentStates = []
691 for node in intents: # Iter through ONOS nodes
692 nodeStates = []
Jon Hall58c76b72015-02-23 11:09:24 -0800693 # Iter through intents of a node
694 for intent in json.loads( node ):
Jon Hall1b8f54a2015-02-04 13:24:20 -0800695 nodeStates.append( intent[ 'state' ] )
696 intentStates.append( nodeStates )
697 out = [ (i, nodeStates.count( i ) ) for i in set( nodeStates ) ]
698 main.log.info( dict( out ) )
699
Jon Hall58c76b72015-02-23 11:09:24 -0800700 # NOTE: Store has no durability, so intents are lost across system
701 # restarts
Jon Hall6aec96b2015-01-19 14:49:31 -0800702 """
703 main.step( "Compare current intents with intents before the failure" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800704 # NOTE: this requires case 5 to pass for intentState to be set.
Jon Hall6aec96b2015-01-19 14:49:31 -0800705 # maybe we should stop the test if that fails?
Jon Hall1b8f54a2015-02-04 13:24:20 -0800706 sameIntents = main.TRUE
707 if intentState and intentState == ONOS1Intents:
Jon Hall8f89dda2015-01-22 16:03:33 -0800708 sameIntents = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -0800709 main.log.report( "Intents are consistent with before failure" )
710 # TODO: possibly the states have changed? we may need to figure out
711 # what the aceptable states are
Jon Hall73cf9cc2014-11-20 22:28:38 -0800712 else:
Jon Hall6aec96b2015-01-19 14:49:31 -0800713 try:
714 main.log.warn( "ONOS1 intents: " )
Jon Hall8f89dda2015-01-22 16:03:33 -0800715 print json.dumps( json.loads( ONOS1Intents ),
Jon Hall6aec96b2015-01-19 14:49:31 -0800716 sort_keys=True, indent=4,
717 separators=( ',', ': ' ) )
718 except:
719 pass
Jon Hall8f89dda2015-01-22 16:03:33 -0800720 sameIntents = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -0800721 utilities.assert_equals(
722 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -0800723 actual=sameIntents,
Jon Hall6aec96b2015-01-19 14:49:31 -0800724 onpass="Intents are consistent with before failure",
725 onfail="The Intents changed during failure" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800726 intentCheck = intentCheck and sameIntents
Jon Hall6aec96b2015-01-19 14:49:31 -0800727 """
728 main.step( "Get the OF Table entries and compare to before " +
729 "component failure" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800730 FlowTables = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -0800731 flows2 = []
732 for i in range( 28 ):
733 main.log.info( "Checking flow table on s" + str( i + 1 ) )
Jon Hall8f89dda2015-01-22 16:03:33 -0800734 tmpFlows = main.Mininet2.getFlowTable( 1.3, "s" + str( i + 1 ) )
735 flows2.append( tmpFlows )
736 tempResult = main.Mininet2.flowComp(
Jon Hall6aec96b2015-01-19 14:49:31 -0800737 flow1=flows[ i ],
Jon Hall8f89dda2015-01-22 16:03:33 -0800738 flow2=tmpFlows )
739 FlowTables = FlowTables and tempResult
740 if FlowTables == main.FALSE:
Jon Hall6aec96b2015-01-19 14:49:31 -0800741 main.log.info( "Differences in flow table for switch: s" +
742 str( i + 1 ) )
Jon Hall8f89dda2015-01-22 16:03:33 -0800743 if FlowTables == main.TRUE:
Jon Hall6aec96b2015-01-19 14:49:31 -0800744 main.log.report( "No changes were found in the flow tables" )
745 utilities.assert_equals(
746 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -0800747 actual=FlowTables,
Jon Hall6aec96b2015-01-19 14:49:31 -0800748 onpass="No changes were found in the flow tables",
749 onfail="Changes were found in the flow tables" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800750
Jon Hall6aec96b2015-01-19 14:49:31 -0800751 # Test of LeadershipElection
Jon Hall669173b2014-12-17 11:36:30 -0800752
Jon Hall8f89dda2015-01-22 16:03:33 -0800753 leader = ONOS1Ip
754 leaderResult = main.TRUE
755 for controller in range( 1, numControllers + 1 ):
Jon Hall6aec96b2015-01-19 14:49:31 -0800756 # loop through ONOScli handlers
757 node = getattr( main, ( 'ONOScli' + str( controller ) ) )
Jon Hall8f89dda2015-01-22 16:03:33 -0800758 leaderN = node.electionTestLeader()
Jon Hall6aec96b2015-01-19 14:49:31 -0800759 # verify leader is ONOS1
760 # NOTE even though we restarted ONOS, it is the only one so onos 1
761 # must be leader
Jon Hall669173b2014-12-17 11:36:30 -0800762 if leaderN == leader:
Jon Hall6aec96b2015-01-19 14:49:31 -0800763 # all is well
Jon Hall669173b2014-12-17 11:36:30 -0800764 pass
765 elif leaderN == main.FALSE:
Jon Hall6aec96b2015-01-19 14:49:31 -0800766 # error in response
767 main.log.report( "Something is wrong with " +
Jon Hall8f89dda2015-01-22 16:03:33 -0800768 "electionTestLeader function, check the" +
Jon Hall6aec96b2015-01-19 14:49:31 -0800769 " error logs" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800770 leaderResult = main.FALSE
Jon Hall669173b2014-12-17 11:36:30 -0800771 elif leader != leaderN:
Jon Hall8f89dda2015-01-22 16:03:33 -0800772 leaderResult = main.FALSE
Jon Hall58c76b72015-02-23 11:09:24 -0800773 main.log.report( "ONOS" + str( controller ) + " sees " +
774 str( leaderN ) +
775 " as the leader of the election app. " +
776 "Leader should be " + str( leader ) )
Jon Hall8f89dda2015-01-22 16:03:33 -0800777 if leaderResult:
778 main.log.report( "Leadership election tests passed( consistent " +
Jon Hall6aec96b2015-01-19 14:49:31 -0800779 "view of leader across listeners and a new " +
Jon Hall8f89dda2015-01-22 16:03:33 -0800780 "leader was re-elected if applicable )" )
Jon Hall6aec96b2015-01-19 14:49:31 -0800781 utilities.assert_equals(
782 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -0800783 actual=leaderResult,
Jon Hall6aec96b2015-01-19 14:49:31 -0800784 onpass="Leadership election passed",
785 onfail="Something went wrong with Leadership election" )
Jon Hall669173b2014-12-17 11:36:30 -0800786
Jon Hall8f89dda2015-01-22 16:03:33 -0800787 result = ( mastershipCheck and intentCheck and FlowTables and
788 rolesNotNull and leaderResult )
Jon Hall6aec96b2015-01-19 14:49:31 -0800789 result = int( result )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800790 if result == main.TRUE:
Jon Hall6aec96b2015-01-19 14:49:31 -0800791 main.log.report( "Constant State Tests Passed" )
792 utilities.assert_equals( expect=main.TRUE, actual=result,
Jon Hall58c76b72015-02-23 11:09:24 -0800793 onpass="Constant State Tests Passed",
794 onfail="Constant state tests failed" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800795
Jon Hall6aec96b2015-01-19 14:49:31 -0800796 def CASE8( self, main ):
797 """
Jon Hall73cf9cc2014-11-20 22:28:38 -0800798 Compare topo
Jon Hall6aec96b2015-01-19 14:49:31 -0800799 """
Jon Hall73cf9cc2014-11-20 22:28:38 -0800800 import sys
Jon Hall6aec96b2015-01-19 14:49:31 -0800801 # FIXME add this path to params
802 sys.path.append( "/home/admin/sts" )
803 # assumes that sts is already in you PYTHONPATH
804 from sts.topology.teston_topology import TestONTopology
Jon Hall73cf9cc2014-11-20 22:28:38 -0800805 import json
806 import time
807
Jon Hall6aec96b2015-01-19 14:49:31 -0800808 description = "Compare ONOS Topology view to Mininet topology"
809 main.case( description )
810 main.log.report( description )
811 main.step( "Create TestONTopology object" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800812 ctrls = []
813 count = 1
814 temp = ()
Jon Hall6aec96b2015-01-19 14:49:31 -0800815 temp = temp + ( getattr( main, ( 'ONOS' + str( count ) ) ), )
816 temp = temp + ( "ONOS" + str( count ), )
817 temp = temp + ( main.params[ 'CTRL' ][ 'ip' + str( count ) ], )
818 temp = temp + \
819 ( eval( main.params[ 'CTRL' ][ 'port' + str( count ) ] ), )
820 ctrls.append( temp )
821 MNTopo = TestONTopology(
822 main.Mininet1,
823 ctrls ) # can also add Intent API info for intent operations
Jon Hall73cf9cc2014-11-20 22:28:38 -0800824
Jon Hall6aec96b2015-01-19 14:49:31 -0800825 main.step( "Comparing ONOS topology to MN" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800826 devicesResults = main.TRUE
827 portsResults = main.TRUE
828 linksResults = main.TRUE
Jon Hall58c76b72015-02-23 11:09:24 -0800829 hostsResults = main.TRUE
Jon Hall8f89dda2015-01-22 16:03:33 -0800830 topoResult = main.FALSE
Jon Hall73cf9cc2014-11-20 22:28:38 -0800831 elapsed = 0
Jon Hallffb386d2014-11-21 13:43:38 -0800832 count = 0
Jon Hall6aec96b2015-01-19 14:49:31 -0800833 main.step( "Collecting topology information from ONOS" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800834 startTime = time.time()
Jon Hall58c76b72015-02-23 11:09:24 -0800835 # Give time for Gossip to work
Jon Hall8f89dda2015-01-22 16:03:33 -0800836 while topoResult == main.FALSE and elapsed < 60:
Jon Hallffb386d2014-11-21 13:43:38 -0800837 count = count + 1
Jon Hall94fd0472014-12-08 11:52:42 -0800838 if count > 1:
Jon Hall58c76b72015-02-23 11:09:24 -0800839 # TODO: Depricate STS usage
840 MNTopo = TestONTopology( main.Mininet1, ctrls )
Jon Hall8f89dda2015-01-22 16:03:33 -0800841 cliStart = time.time()
Jon Hall94fd0472014-12-08 11:52:42 -0800842 devices = []
843 devices.append( main.ONOScli1.devices() )
Jon Hall94fd0472014-12-08 11:52:42 -0800844 hosts = []
Jon Hall58c76b72015-02-23 11:09:24 -0800845 hosts.append( json.loads( main.ONOScli1.hosts() ) )
846 ipResult = main.TRUE
847 for controller in range( 0, len( hosts ) ):
848 controllerStr = str( controller + 1 )
849 for host in hosts[ controller ]:
850 if host is None or host.get( 'ips', [] ) == []:
851 main.log.error(
852 "DEBUG:Error with host ips on controller" +
853 controllerStr + ": " + str( host ) )
854 ipResult = main.FALSE
Jon Hall94fd0472014-12-08 11:52:42 -0800855 ports = []
856 ports.append( main.ONOScli1.ports() )
857 links = []
858 links.append( main.ONOScli1.links() )
Jon Hall58c76b72015-02-23 11:09:24 -0800859 clusters = []
860 clusters.append( main.ONOScli1.clusters() )
861
Jon Hall8f89dda2015-01-22 16:03:33 -0800862 elapsed = time.time() - startTime
863 cliTime = time.time() - cliStart
864 print "CLI time: " + str( cliTime )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800865
Jon Hall8f89dda2015-01-22 16:03:33 -0800866 for controller in range( numControllers ):
867 controllerStr = str( controller + 1 )
Jon Hall6aec96b2015-01-19 14:49:31 -0800868 if devices[ controller ] or "Error" not in devices[
869 controller ]:
Jon Hall8f89dda2015-01-22 16:03:33 -0800870 currentDevicesResult = main.Mininet1.compareSwitches(
Jon Hall6aec96b2015-01-19 14:49:31 -0800871 MNTopo,
Jon Hall58c76b72015-02-23 11:09:24 -0800872 json.loads( devices[ controller ] ) )
Jon Hall94fd0472014-12-08 11:52:42 -0800873 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800874 currentDevicesResult = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -0800875 utilities.assert_equals( expect=main.TRUE,
Jon Hall58c76b72015-02-23 11:09:24 -0800876 actual=currentDevicesResult,
877 onpass="ONOS" + controllerStr +
878 " Switches view is correct",
879 onfail="ONOS" + controllerStr +
880 " Switches view is incorrect" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800881
Jon Hall6aec96b2015-01-19 14:49:31 -0800882 if ports[ controller ] or "Error" not in ports[ controller ]:
Jon Hall8f89dda2015-01-22 16:03:33 -0800883 currentPortsResult = main.Mininet1.comparePorts(
Jon Hall6aec96b2015-01-19 14:49:31 -0800884 MNTopo,
Jon Hall58c76b72015-02-23 11:09:24 -0800885 json.loads( ports[ controller ] ) )
Jon Hall94fd0472014-12-08 11:52:42 -0800886 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800887 currentPortsResult = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -0800888 utilities.assert_equals( expect=main.TRUE,
Jon Hall58c76b72015-02-23 11:09:24 -0800889 actual=currentPortsResult,
890 onpass="ONOS" + controllerStr +
891 " ports view is correct",
892 onfail="ONOS" + controllerStr +
893 " ports view is incorrect" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800894
Jon Hall6aec96b2015-01-19 14:49:31 -0800895 if links[ controller ] or "Error" not in links[ controller ]:
Jon Hall8f89dda2015-01-22 16:03:33 -0800896 currentLinksResult = main.Mininet1.compareLinks(
Jon Hall6aec96b2015-01-19 14:49:31 -0800897 MNTopo,
Jon Hall58c76b72015-02-23 11:09:24 -0800898 json.loads( links[ controller ] ) )
Jon Hall94fd0472014-12-08 11:52:42 -0800899 else:
Jon Hall8f89dda2015-01-22 16:03:33 -0800900 currentLinksResult = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -0800901 utilities.assert_equals( expect=main.TRUE,
Jon Hall58c76b72015-02-23 11:09:24 -0800902 actual=currentLinksResult,
903 onpass="ONOS" + controllerStr +
904 " links view is correct",
905 onfail="ONOS" + controllerStr +
906 " links view is incorrect" )
907
908 if hosts[ controller ] or "Error" not in hosts[ controller ]:
909 currentHostsResult = main.Mininet1.compareHosts(
910 MNTopo, hosts[ controller ] )
911 else:
912 currentHostsResult = main.FALSE
913 utilities.assert_equals( expect=main.TRUE,
914 actual=currentHostsResult,
915 onpass="ONOS" + controllerStr +
916 " hosts exist in Mininet",
917 onfail="ONOS" + controllerStr +
918 " hosts don't match Mininet" )
919
920 devicesResults = devicesResults and currentDevicesResult
921 portsResults = portsResults and currentPortsResult
922 linksResults = linksResults and currentLinksResult
923 hostsResults = hostsResults and currentHostsResult
924
925 # there should always only be one cluster
926 numClusters = len( json.loads( clusters[ 0 ] ) )
927 clusterResults = main.FALSE
928 if numClusters == 1:
929 clusterResults = main.TRUE
930 utilities.assert_equals(
931 expect=1,
932 actual=numClusters,
933 onpass="ONOS shows 1 SCC",
934 onfail="ONOS shows " + str( numClusters ) + " SCCs" )
935
936 topoResult = ( devicesResults and portsResults and linksResults
937 and hostsResults and ipResult and clusterResults )
Jon Hall94fd0472014-12-08 11:52:42 -0800938
Jon Hall8f89dda2015-01-22 16:03:33 -0800939 topoResult = topoResult and int( count <= 2 )
940 note = "note it takes about " + str( int( cliTime ) ) + \
941 " seconds for the test to make all the cli calls to fetch " +\
942 "the topology from each ONOS instance"
Jon Hall1b8f54a2015-02-04 13:24:20 -0800943 main.log.info(
Jon Hall8f89dda2015-01-22 16:03:33 -0800944 "Very crass estimate for topology discovery/convergence( " +
945 str( note ) + " ): " + str( elapsed ) + " seconds, " +
Jon Hall6aec96b2015-01-19 14:49:31 -0800946 str( count ) + " tries" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800947 utilities.assert_equals( expect=main.TRUE, actual=topoResult,
Jon Hall58c76b72015-02-23 11:09:24 -0800948 onpass="Topology Check Test successful",
949 onfail="Topology Check Test NOT successful" )
950 # this is temporary
951 # main.Mininet1.handle.sendline( "py [(s.intfs[i], s.intfs[i].mac) for s in net.switches for i in s.intfs]" )
952 # main.Mininet1.handle.expect( "mininet>" )
953 # main.log.error( main.Mininet1.handle.before )
954 # main.log.error( main.ONOScli1.hosts() )
955
Jon Hall8f89dda2015-01-22 16:03:33 -0800956 if topoResult == main.TRUE:
Jon Hall6aec96b2015-01-19 14:49:31 -0800957 main.log.report( "ONOS topology view matches Mininet topology" )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800958
Jon Hall6aec96b2015-01-19 14:49:31 -0800959 def CASE9( self, main ):
960 """
Jon Hall73cf9cc2014-11-20 22:28:38 -0800961 Link s3-s28 down
Jon Hall6aec96b2015-01-19 14:49:31 -0800962 """
963 import time
964 # NOTE: You should probably run a topology check after this
Jon Hall73cf9cc2014-11-20 22:28:38 -0800965
Jon Hall8f89dda2015-01-22 16:03:33 -0800966 linkSleep = float( main.params[ 'timers' ][ 'LinkDiscovery' ] )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800967
Jon Hall6aec96b2015-01-19 14:49:31 -0800968 description = "Turn off a link to ensure that Link Discovery " +\
Jon Hall58c76b72015-02-23 11:09:24 -0800969 "is working properly"
Jon Hall6aec96b2015-01-19 14:49:31 -0800970 main.log.report( description )
971 main.case( description )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800972
Jon Hall6aec96b2015-01-19 14:49:31 -0800973 main.step( "Kill Link between s3 and s28" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800974 LinkDown = main.Mininet1.link( END1="s3", END2="s28", OPTION="down" )
Jon Hall58c76b72015-02-23 11:09:24 -0800975 main.log.info( "Waiting " + str( linkSleep ) +
976 " seconds for link down to be discovered" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800977 time.sleep( linkSleep )
978 utilities.assert_equals( expect=main.TRUE, actual=LinkDown,
Jon Hall58c76b72015-02-23 11:09:24 -0800979 onpass="Link down succesful",
980 onfail="Failed to bring link down" )
Jon Hall6aec96b2015-01-19 14:49:31 -0800981 # TODO do some sort of check here
Jon Hall73cf9cc2014-11-20 22:28:38 -0800982
Jon Hall6aec96b2015-01-19 14:49:31 -0800983 def CASE10( self, main ):
984 """
Jon Hall73cf9cc2014-11-20 22:28:38 -0800985 Link s3-s28 up
Jon Hall6aec96b2015-01-19 14:49:31 -0800986 """
987 import time
988 # NOTE: You should probably run a topology check after this
Jon Hall73cf9cc2014-11-20 22:28:38 -0800989
Jon Hall8f89dda2015-01-22 16:03:33 -0800990 linkSleep = float( main.params[ 'timers' ][ 'LinkDiscovery' ] )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800991
Jon Hall6aec96b2015-01-19 14:49:31 -0800992 description = "Restore a link to ensure that Link Discovery is " + \
Jon Hall58c76b72015-02-23 11:09:24 -0800993 "working properly"
Jon Hall6aec96b2015-01-19 14:49:31 -0800994 main.log.report( description )
995 main.case( description )
Jon Hall73cf9cc2014-11-20 22:28:38 -0800996
Jon Hall6aec96b2015-01-19 14:49:31 -0800997 main.step( "Bring link between s3 and s28 back up" )
Jon Hall8f89dda2015-01-22 16:03:33 -0800998 LinkUp = main.Mininet1.link( END1="s3", END2="s28", OPTION="up" )
Jon Hall58c76b72015-02-23 11:09:24 -0800999 main.log.info( "Waiting " + str( linkSleep ) +
1000 " seconds for link up to be discovered" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001001 time.sleep( linkSleep )
1002 utilities.assert_equals( expect=main.TRUE, actual=LinkUp,
Jon Hall58c76b72015-02-23 11:09:24 -08001003 onpass="Link up succesful",
1004 onfail="Failed to bring link up" )
Jon Hall6aec96b2015-01-19 14:49:31 -08001005 # TODO do some sort of check here
Jon Hall73cf9cc2014-11-20 22:28:38 -08001006
Jon Hall6aec96b2015-01-19 14:49:31 -08001007 def CASE11( self, main ):
1008 """
Jon Hall73cf9cc2014-11-20 22:28:38 -08001009 Switch Down
Jon Hall6aec96b2015-01-19 14:49:31 -08001010 """
1011 # NOTE: You should probably run a topology check after this
Jon Hall73cf9cc2014-11-20 22:28:38 -08001012 import time
1013
Jon Hall8f89dda2015-01-22 16:03:33 -08001014 switchSleep = float( main.params[ 'timers' ][ 'SwitchDiscovery' ] )
Jon Hall73cf9cc2014-11-20 22:28:38 -08001015
1016 description = "Killing a switch to ensure it is discovered correctly"
Jon Hall6aec96b2015-01-19 14:49:31 -08001017 main.log.report( description )
1018 main.case( description )
1019 switch = main.params[ 'kill' ][ 'switch' ]
1020 switchDPID = main.params[ 'kill' ][ 'dpid' ]
Jon Hall73cf9cc2014-11-20 22:28:38 -08001021
Jon Hall6aec96b2015-01-19 14:49:31 -08001022 # TODO: Make this switch parameterizable
1023 main.step( "Kill " + switch )
1024 main.log.report( "Deleting " + switch )
Jon Hall8f89dda2015-01-22 16:03:33 -08001025 main.Mininet1.delSwitch( switch )
1026 main.log.info( "Waiting " + str( switchSleep ) +
Jon Hall6aec96b2015-01-19 14:49:31 -08001027 " seconds for switch down to be discovered" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001028 time.sleep( switchSleep )
1029 device = main.ONOScli1.getDevice( dpid=switchDPID )
Jon Hall6aec96b2015-01-19 14:49:31 -08001030 # Peek at the deleted switch
1031 main.log.warn( str( device ) )
Jon Hall94fd0472014-12-08 11:52:42 -08001032 result = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -08001033 if device and device[ 'available' ] is False:
Jon Hall94fd0472014-12-08 11:52:42 -08001034 result = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -08001035 utilities.assert_equals( expect=main.TRUE, actual=result,
Jon Hall58c76b72015-02-23 11:09:24 -08001036 onpass="Kill switch succesful",
1037 onfail="Failed to kill switch?" )
Jon Hall73cf9cc2014-11-20 22:28:38 -08001038
Jon Hall6aec96b2015-01-19 14:49:31 -08001039 def CASE12( self, main ):
1040 """
Jon Hall73cf9cc2014-11-20 22:28:38 -08001041 Switch Up
Jon Hall6aec96b2015-01-19 14:49:31 -08001042 """
1043 # NOTE: You should probably run a topology check after this
Jon Hall73cf9cc2014-11-20 22:28:38 -08001044 import time
Jon Hall669173b2014-12-17 11:36:30 -08001045
Jon Hall8f89dda2015-01-22 16:03:33 -08001046 switchSleep = float( main.params[ 'timers' ][ 'SwitchDiscovery' ] )
Jon Hall6aec96b2015-01-19 14:49:31 -08001047 switch = main.params[ 'kill' ][ 'switch' ]
1048 switchDPID = main.params[ 'kill' ][ 'dpid' ]
1049 links = main.params[ 'kill' ][ 'links' ].split()
Jon Hall73cf9cc2014-11-20 22:28:38 -08001050 description = "Adding a switch to ensure it is discovered correctly"
Jon Hall6aec96b2015-01-19 14:49:31 -08001051 main.log.report( description )
1052 main.case( description )
Jon Hall73cf9cc2014-11-20 22:28:38 -08001053
Jon Hall6aec96b2015-01-19 14:49:31 -08001054 main.step( "Add back " + switch )
1055 main.log.report( "Adding back " + switch )
Jon Hall8f89dda2015-01-22 16:03:33 -08001056 main.Mininet1.addSwitch( switch, dpid=switchDPID )
Jon Hall6aec96b2015-01-19 14:49:31 -08001057 # TODO: New dpid or same? Ask Thomas?
1058 for peer in links:
Jon Hall8f89dda2015-01-22 16:03:33 -08001059 main.Mininet1.addLink( switch, peer )
1060 main.Mininet1.assignSwController( sw=switch.split( 's' )[ 1 ],
Jon Hall58c76b72015-02-23 11:09:24 -08001061 ip1=ONOS1Ip,
1062 port1=ONOS1Port )
1063 main.log.info( "Waiting " + str( switchSleep ) +
1064 " seconds for switch up to be discovered" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001065 time.sleep( switchSleep )
1066 device = main.ONOScli1.getDevice( dpid=switchDPID )
Jon Hall6aec96b2015-01-19 14:49:31 -08001067 # Peek at the deleted switch
1068 main.log.warn( str( device ) )
Jon Hall94fd0472014-12-08 11:52:42 -08001069 result = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -08001070 if device and device[ 'available' ]:
Jon Hall94fd0472014-12-08 11:52:42 -08001071 result = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -08001072 utilities.assert_equals( expect=main.TRUE, actual=result,
Jon Hall58c76b72015-02-23 11:09:24 -08001073 onpass="add switch succesful",
1074 onfail="Failed to add switch?" )
Jon Hall73cf9cc2014-11-20 22:28:38 -08001075
Jon Hall6aec96b2015-01-19 14:49:31 -08001076 def CASE13( self, main ):
1077 """
Jon Hall73cf9cc2014-11-20 22:28:38 -08001078 Clean up
Jon Hall6aec96b2015-01-19 14:49:31 -08001079 """
Jon Hall73cf9cc2014-11-20 22:28:38 -08001080 import os
1081 import time
Jon Hall6aec96b2015-01-19 14:49:31 -08001082 # printing colors to terminal
Jon Hall669173b2014-12-17 11:36:30 -08001083 colors = {}
Jon Hall6aec96b2015-01-19 14:49:31 -08001084 colors[ 'cyan' ] = '\033[96m'
1085 colors[ 'purple' ] = '\033[95m'
1086 colors[ 'blue' ] = '\033[94m'
1087 colors[ 'green' ] = '\033[92m'
1088 colors[ 'yellow' ] = '\033[93m'
1089 colors[ 'red' ] = '\033[91m'
1090 colors[ 'end' ] = '\033[0m'
Jon Hall73cf9cc2014-11-20 22:28:38 -08001091 description = "Test Cleanup"
Jon Hall6aec96b2015-01-19 14:49:31 -08001092 main.log.report( description )
1093 main.case( description )
1094 main.step( "Killing tcpdumps" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001095 main.Mininet2.stopTcpdump()
Jon Hall73cf9cc2014-11-20 22:28:38 -08001096
Jon Hall6aec96b2015-01-19 14:49:31 -08001097 main.step( "Checking ONOS Logs for errors" )
1098 print colors[ 'purple' ] + "Checking logs for errors on ONOS1:" + \
Jon Hall8f89dda2015-01-22 16:03:33 -08001099 colors[ 'end' ]
1100 print main.ONOSbench.checkLogs( ONOS1Ip )
Jon Hall6aec96b2015-01-19 14:49:31 -08001101 main.step( "Copying MN pcap and ONOS log files to test station" )
Jon Hall73cf9cc2014-11-20 22:28:38 -08001102 testname = main.TEST
Jon Hall8f89dda2015-01-22 16:03:33 -08001103 teststationUser = main.params[ 'TESTONUSER' ]
1104 teststationIP = main.params[ 'TESTONIP' ]
Jon Hall6aec96b2015-01-19 14:49:31 -08001105 # NOTE: MN Pcap file is being saved to ~/packet_captures
Jon Hall73cf9cc2014-11-20 22:28:38 -08001106 # scp this file as MN and TestON aren't necessarily the same vm
Jon Hall6aec96b2015-01-19 14:49:31 -08001107 # FIXME: scp
1108 # mn files
1109 # TODO: Load these from params
1110 # NOTE: must end in /
Jon Hall8f89dda2015-01-22 16:03:33 -08001111 logFolder = "/opt/onos/log/"
1112 logFiles = [ "karaf.log", "karaf.log.1" ]
Jon Hall6aec96b2015-01-19 14:49:31 -08001113 # NOTE: must end in /
Jon Hall8f89dda2015-01-22 16:03:33 -08001114 dstDir = "~/packet_captures/"
1115 for f in logFiles:
1116 main.ONOSbench.handle.sendline( "scp sdn@" + ONOS1Ip + ":" +
1117 logFolder + f + " " +
1118 teststationUser + "@" +
1119 teststationIP + ":" + dstDir +
Jon Hall6aec96b2015-01-19 14:49:31 -08001120 str( testname ) + "-ONOS1-" + f )
1121 main.ONOSbench.handle.expect( "\$" )
Jon Hall73cf9cc2014-11-20 22:28:38 -08001122
Jon Hall6aec96b2015-01-19 14:49:31 -08001123 # std*.log's
1124 # NOTE: must end in /
Jon Hall8f89dda2015-01-22 16:03:33 -08001125 logFolder = "/opt/onos/var/"
1126 logFiles = [ "stderr.log", "stdout.log" ]
Jon Hall6aec96b2015-01-19 14:49:31 -08001127 # NOTE: must end in /
Jon Hall8f89dda2015-01-22 16:03:33 -08001128 dstDir = "~/packet_captures/"
1129 for f in logFiles:
1130 main.ONOSbench.handle.sendline( "scp sdn@" + ONOS1Ip + ":" +
1131 logFolder + f + " " +
1132 teststationUser + "@" +
1133 teststationIP + ":" + dstDir +
Jon Hall6aec96b2015-01-19 14:49:31 -08001134 str( testname ) + "-ONOS1-" + f )
Jon Hall58c76b72015-02-23 11:09:24 -08001135 main.ONOSbench.handle.expect( "\$" )
Jon Hall6aec96b2015-01-19 14:49:31 -08001136 # sleep so scp can finish
1137 time.sleep( 10 )
Jon Hall58c76b72015-02-23 11:09:24 -08001138 main.Mininet1.stopNet()
Jon Hall6aec96b2015-01-19 14:49:31 -08001139 main.step( "Packing and rotating pcap archives" )
1140 os.system( "~/TestON/dependencies/rotate.sh " + str( testname ) )
Jon Hall73cf9cc2014-11-20 22:28:38 -08001141
Jon Hall6aec96b2015-01-19 14:49:31 -08001142 # TODO: actually check something here
1143 utilities.assert_equals( expect=main.TRUE, actual=main.TRUE,
Jon Hall58c76b72015-02-23 11:09:24 -08001144 onpass="Test cleanup successful",
1145 onfail="Test cleanup NOT successful" )
Jon Hall73cf9cc2014-11-20 22:28:38 -08001146
Jon Hall6aec96b2015-01-19 14:49:31 -08001147 def CASE14( self, main ):
1148 """
Jon Hall669173b2014-12-17 11:36:30 -08001149 start election app on all onos nodes
Jon Hall6aec96b2015-01-19 14:49:31 -08001150 """
Jon Hall8f89dda2015-01-22 16:03:33 -08001151 leaderResult = main.TRUE
Jon Hall6aec96b2015-01-19 14:49:31 -08001152 # install app on onos 1
1153 main.log.info( "Install leadership election app" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001154 main.ONOScli1.featureInstall( "onos-app-election" )
Jon Hall6aec96b2015-01-19 14:49:31 -08001155 # wait for election
1156 # check for leader
Jon Hall8f89dda2015-01-22 16:03:33 -08001157 leader = main.ONOScli1.electionTestLeader()
Jon Hall6aec96b2015-01-19 14:49:31 -08001158 # verify leader is ONOS1
Jon Hall8f89dda2015-01-22 16:03:33 -08001159 if leader == ONOS1Ip:
Jon Hall6aec96b2015-01-19 14:49:31 -08001160 # all is well
Jon Hall669173b2014-12-17 11:36:30 -08001161 pass
Jon Hall6aec96b2015-01-19 14:49:31 -08001162 elif leader is None:
1163 # No leader elected
1164 main.log.report( "No leader was elected" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001165 leaderResult = main.FALSE
Jon Hall669173b2014-12-17 11:36:30 -08001166 elif leader == main.FALSE:
Jon Hall6aec96b2015-01-19 14:49:31 -08001167 # error in response
1168 # TODO: add check for "Command not found:" in the driver, this
1169 # means the app isn't loaded
Jon Hall8f89dda2015-01-22 16:03:33 -08001170 main.log.report( "Something is wrong with electionTestLeader" +
Jon Hall6aec96b2015-01-19 14:49:31 -08001171 " function, check the error logs" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001172 leaderResult = main.FALSE
Jon Hall669173b2014-12-17 11:36:30 -08001173 else:
Jon Hall6aec96b2015-01-19 14:49:31 -08001174 # error in response
1175 main.log.report(
Jon Hall8f89dda2015-01-22 16:03:33 -08001176 "Unexpected response from electionTestLeader function:'" +
1177 str( leader ) +
Jon Hall6aec96b2015-01-19 14:49:31 -08001178 "'" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001179 leaderResult = main.FALSE
Jon Hall669173b2014-12-17 11:36:30 -08001180
Jon Hall6aec96b2015-01-19 14:49:31 -08001181 # install on other nodes and check for leader.
1182 # Should be onos1 and each app should show the same leader
Jon Hall8f89dda2015-01-22 16:03:33 -08001183 for controller in range( 2, numControllers + 1 ):
Jon Hall6aec96b2015-01-19 14:49:31 -08001184 # loop through ONOScli handlers
1185 node = getattr( main, ( 'ONOScli' + str( controller ) ) )
Jon Hall8f89dda2015-01-22 16:03:33 -08001186 node.featureInstall( "onos-app-election" )
1187 leaderN = node.electionTestLeader()
Jon Hall6aec96b2015-01-19 14:49:31 -08001188 # verify leader is ONOS1
Jon Hall8f89dda2015-01-22 16:03:33 -08001189 if leaderN == ONOS1Ip:
Jon Hall6aec96b2015-01-19 14:49:31 -08001190 # all is well
Jon Hall669173b2014-12-17 11:36:30 -08001191 pass
1192 elif leaderN == main.FALSE:
Jon Hall6aec96b2015-01-19 14:49:31 -08001193 # error in response
1194 # TODO: add check for "Command not found:" in the driver, this
1195 # means the app isn't loaded
1196 main.log.report( "Something is wrong with " +
Jon Hall8f89dda2015-01-22 16:03:33 -08001197 "electionTestLeader function, check the" +
Jon Hall6aec96b2015-01-19 14:49:31 -08001198 " error logs" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001199 leaderResult = main.FALSE
Jon Hall669173b2014-12-17 11:36:30 -08001200 elif leader != leaderN:
Jon Hall8f89dda2015-01-22 16:03:33 -08001201 leaderResult = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -08001202 main.log.report( "ONOS" + str( controller ) + " sees " +
1203 str( leaderN ) +
1204 " as the leader of the election app. Leader" +
1205 " should be " +
1206 str( leader ) )
Jon Hall8f89dda2015-01-22 16:03:33 -08001207 if leaderResult:
Jon Hall6aec96b2015-01-19 14:49:31 -08001208 main.log.report( "Leadership election tests passed( consistent " +
1209 "view of leader across listeners and a leader " +
Jon Hall8f89dda2015-01-22 16:03:33 -08001210 "was elected )" )
Jon Hall6aec96b2015-01-19 14:49:31 -08001211 utilities.assert_equals(
1212 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -08001213 actual=leaderResult,
Jon Hall6aec96b2015-01-19 14:49:31 -08001214 onpass="Leadership election passed",
1215 onfail="Something went wrong with Leadership election" )
Jon Hall669173b2014-12-17 11:36:30 -08001216
Jon Hall6aec96b2015-01-19 14:49:31 -08001217 def CASE15( self, main ):
1218 """
Jon Hall669173b2014-12-17 11:36:30 -08001219 Check that Leadership Election is still functional
Jon Hall6aec96b2015-01-19 14:49:31 -08001220 """
Jon Hall8f89dda2015-01-22 16:03:33 -08001221 leaderResult = main.TRUE
Jon Hall669173b2014-12-17 11:36:30 -08001222 description = "Check that Leadership Election is still functional"
Jon Hall6aec96b2015-01-19 14:49:31 -08001223 main.log.report( description )
1224 main.case( description )
1225 main.step( "Find current leader and withdraw" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001226 leader = main.ONOScli1.electionTestLeader()
Jon Hall6aec96b2015-01-19 14:49:31 -08001227 # TODO: do some sanity checking on leader before using it
Jon Hall8f89dda2015-01-22 16:03:33 -08001228 withdrawResult = main.FALSE
1229 if leader == ONOS1Ip:
1230 oldLeader = getattr( main, "ONOScli1" )
Jon Hall6aec96b2015-01-19 14:49:31 -08001231 elif leader is None or leader == main.FALSE:
1232 main.log.report(
1233 "Leader for the election app should be an ONOS node," +
Jon Hall58c76b72015-02-23 11:09:24 -08001234 "instead got '" + str( leader ) + "'" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001235 leaderResult = main.FALSE
1236 withdrawResult = oldLeader.electionTestWithdraw()
Jon Hall6aec96b2015-01-19 14:49:31 -08001237 utilities.assert_equals(
1238 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -08001239 actual=withdrawResult,
Jon Hall6aec96b2015-01-19 14:49:31 -08001240 onpass="App was withdrawn from election",
1241 onfail="App was not withdrawn from election" )
Jon Hall669173b2014-12-17 11:36:30 -08001242
Jon Hall6aec96b2015-01-19 14:49:31 -08001243 main.step( "Make sure new leader is elected" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001244 leaderList = []
1245 leaderN = main.ONOScli1.electionTestLeader()
Jon Hall669173b2014-12-17 11:36:30 -08001246 if leaderN == leader:
Jon Hall6aec96b2015-01-19 14:49:31 -08001247 main.log.report( "ONOS still sees " + str( leaderN ) +
1248 " as leader after they withdrew" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001249 leaderResult = main.FALSE
Jon Hall669173b2014-12-17 11:36:30 -08001250 elif leaderN == main.FALSE:
Jon Hall6aec96b2015-01-19 14:49:31 -08001251 # error in response
1252 # TODO: add check for "Command not found:" in the driver, this
1253 # means the app isn't loaded
Jon Hall8f89dda2015-01-22 16:03:33 -08001254 main.log.report( "Something is wrong with electionTestLeader " +
Jon Hall6aec96b2015-01-19 14:49:31 -08001255 "function, check the error logs" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001256 leaderResult = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -08001257 elif leaderN is None:
1258 main.log.info(
1259 "There is no leader after the app withdrew from election" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001260 if leaderResult:
1261 main.log.report( "Leadership election tests passed( There is no " +
1262 "leader after the old leader resigned )" )
Jon Hall6aec96b2015-01-19 14:49:31 -08001263 utilities.assert_equals(
1264 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -08001265 actual=leaderResult,
Jon Hall6aec96b2015-01-19 14:49:31 -08001266 onpass="Leadership election passed",
1267 onfail="Something went wrong with Leadership election" )
Jon Hall669173b2014-12-17 11:36:30 -08001268
Jon Hall58c76b72015-02-23 11:09:24 -08001269 main.step( "Run for election on old leader( just so everyone " +
1270 "is in the hat )" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001271 runResult = oldLeader.electionTestRun()
Jon Hall6aec96b2015-01-19 14:49:31 -08001272 utilities.assert_equals(
1273 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -08001274 actual=runResult,
Jon Hall6aec96b2015-01-19 14:49:31 -08001275 onpass="App re-ran for election",
1276 onfail="App failed to run for election" )
Jon Hall8f89dda2015-01-22 16:03:33 -08001277 leader = main.ONOScli1.electionTestLeader()
Jon Hall6aec96b2015-01-19 14:49:31 -08001278 # verify leader is ONOS1
Jon Hall8f89dda2015-01-22 16:03:33 -08001279 if leader == ONOS1Ip:
1280 leaderResult = main.TRUE
Jon Hall669173b2014-12-17 11:36:30 -08001281 else:
Jon Hall8f89dda2015-01-22 16:03:33 -08001282 leaderResult = main.FALSE
Jon Hall6aec96b2015-01-19 14:49:31 -08001283 # TODO: assert on run and withdraw results?
Jon Hall669173b2014-12-17 11:36:30 -08001284
Jon Hall6aec96b2015-01-19 14:49:31 -08001285 utilities.assert_equals(
1286 expect=main.TRUE,
Jon Hall8f89dda2015-01-22 16:03:33 -08001287 actual=leaderResult,
Jon Hall6aec96b2015-01-19 14:49:31 -08001288 onpass="Leadership election passed",
1289 onfail="ONOS1's election app was not leader after it re-ran " +
1290 "for election" )