blob: 832fe298cf0138851089cbda43ea4caa1674edae [file] [log] [blame]
andrewonlab95ce8322014-10-13 14:12:04 -04001#!/usr/bin/env python
2
kelvin8ec71442015-01-15 16:57:00 -08003"""
andrewonlab95ce8322014-10-13 14:12:04 -04004This driver enters the onos> prompt to issue commands.
5
kelvin8ec71442015-01-15 16:57:00 -08006Please follow the coding style demonstrated by existing
andrewonlab95ce8322014-10-13 14:12:04 -04007functions and document properly.
8
9If you are a contributor to the driver, please
10list your email here for future contact:
11
12jhall@onlab.us
13andrew@onlab.us
Jon Halle8217482014-10-17 13:49:14 -040014shreya@onlab.us
andrewonlab95ce8322014-10-13 14:12:04 -040015
16OCT 13 2014
17
kelvin8ec71442015-01-15 16:57:00 -080018"""
andrewonlab95ce8322014-10-13 14:12:04 -040019import pexpect
20import re
Jon Hall30b82fa2015-03-04 17:15:43 -080021import json
22import types
Jon Hallbd16b922015-03-26 17:53:15 -070023import time
kelvin-onlaba4074292015-07-09 15:19:49 -070024import os
andrewonlab95ce8322014-10-13 14:12:04 -040025from drivers.common.clidriver import CLI
26
andrewonlab95ce8322014-10-13 14:12:04 -040027
kelvin8ec71442015-01-15 16:57:00 -080028class OnosCliDriver( CLI ):
andrewonlab95ce8322014-10-13 14:12:04 -040029
kelvin8ec71442015-01-15 16:57:00 -080030 def __init__( self ):
31 """
32 Initialize client
33 """
Jon Hallefbd9792015-03-05 16:11:36 -080034 self.name = None
35 self.home = None
36 self.handle = None
kelvin8ec71442015-01-15 16:57:00 -080037 super( CLI, self ).__init__()
38
39 def connect( self, **connectargs ):
40 """
andrewonlab95ce8322014-10-13 14:12:04 -040041 Creates ssh handle for ONOS cli.
kelvin8ec71442015-01-15 16:57:00 -080042 """
andrewonlab95ce8322014-10-13 14:12:04 -040043 try:
44 for key in connectargs:
kelvin8ec71442015-01-15 16:57:00 -080045 vars( self )[ key ] = connectargs[ key ]
andrew@onlab.us658ec012015-03-11 15:13:09 -070046 self.home = "~/onos"
andrewonlab95ce8322014-10-13 14:12:04 -040047 for key in self.options:
48 if key == "home":
kelvin8ec71442015-01-15 16:57:00 -080049 self.home = self.options[ 'home' ]
andrewonlab95ce8322014-10-13 14:12:04 -040050 break
kelvin-onlabfb521662015-02-27 09:52:40 -080051 if self.home is None or self.home == "":
Jon Halle94919c2015-03-23 11:42:57 -070052 self.home = "~/onos"
andrewonlab95ce8322014-10-13 14:12:04 -040053
kelvin-onlaba4074292015-07-09 15:19:49 -070054 for key in self.options:
55 if key == 'onosIp':
56 self.onosIp = self.options[ 'onosIp' ]
57 break
58
kelvin8ec71442015-01-15 16:57:00 -080059 self.name = self.options[ 'name' ]
kelvin-onlaba4074292015-07-09 15:19:49 -070060
61 try:
Jon Hallc6793552016-01-19 14:18:37 -080062 if os.getenv( str( self.ip_address ) ) is not None:
kelvin-onlaba4074292015-07-09 15:19:49 -070063 self.ip_address = os.getenv( str( self.ip_address ) )
64 else:
65 main.log.info( self.name +
66 ": Trying to connect to " +
67 self.ip_address )
68
69 except KeyError:
70 main.log.info( "Invalid host name," +
71 " connecting to local host instead" )
72 self.ip_address = 'localhost'
73 except Exception as inst:
74 main.log.error( "Uncaught exception: " + str( inst ) )
75
kelvin8ec71442015-01-15 16:57:00 -080076 self.handle = super( OnosCliDriver, self ).connect(
kelvin-onlab08679eb2015-01-21 16:11:48 -080077 user_name=self.user_name,
78 ip_address=self.ip_address,
kelvin-onlab898a6c62015-01-16 14:13:53 -080079 port=self.port,
80 pwd=self.pwd,
81 home=self.home )
andrewonlab95ce8322014-10-13 14:12:04 -040082
kelvin8ec71442015-01-15 16:57:00 -080083 self.handle.sendline( "cd " + self.home )
84 self.handle.expect( "\$" )
andrewonlab95ce8322014-10-13 14:12:04 -040085 if self.handle:
86 return self.handle
kelvin8ec71442015-01-15 16:57:00 -080087 else:
88 main.log.info( "NO ONOS HANDLE" )
andrewonlab95ce8322014-10-13 14:12:04 -040089 return main.FALSE
Jon Halld4d4b372015-01-28 16:02:41 -080090 except TypeError:
91 main.log.exception( self.name + ": Object not as expected" )
92 return None
andrewonlab95ce8322014-10-13 14:12:04 -040093 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -080094 main.log.error( self.name + ": EOF exception found" )
95 main.log.error( self.name + ": " + self.handle.before )
andrewonlab95ce8322014-10-13 14:12:04 -040096 main.cleanup()
97 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -080098 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -080099 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab95ce8322014-10-13 14:12:04 -0400100 main.cleanup()
101 main.exit()
102
kelvin8ec71442015-01-15 16:57:00 -0800103 def disconnect( self ):
104 """
andrewonlab95ce8322014-10-13 14:12:04 -0400105 Called when Test is complete to disconnect the ONOS handle.
kelvin8ec71442015-01-15 16:57:00 -0800106 """
Jon Halld61331b2015-02-17 16:35:47 -0800107 response = main.TRUE
andrewonlab95ce8322014-10-13 14:12:04 -0400108 try:
Jon Hall61282e32015-03-19 11:34:11 -0700109 if self.handle:
110 i = self.logout()
111 if i == main.TRUE:
112 self.handle.sendline( "" )
113 self.handle.expect( "\$" )
114 self.handle.sendline( "exit" )
115 self.handle.expect( "closed" )
Jon Halld4d4b372015-01-28 16:02:41 -0800116 except TypeError:
117 main.log.exception( self.name + ": Object not as expected" )
Jon Halld61331b2015-02-17 16:35:47 -0800118 response = main.FALSE
andrewonlab95ce8322014-10-13 14:12:04 -0400119 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800120 main.log.error( self.name + ": EOF exception found" )
121 main.log.error( self.name + ": " + self.handle.before )
Jon Hall61282e32015-03-19 11:34:11 -0700122 except ValueError:
Jon Hall1a77a1e2015-04-06 10:41:13 -0700123 main.log.exception( "Exception in disconnect of " + self.name )
Jon Hall61282e32015-03-19 11:34:11 -0700124 response = main.TRUE
Jon Hallfebb1c72015-03-05 13:30:09 -0800125 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800126 main.log.exception( self.name + ": Connection failed to the host" )
andrewonlab95ce8322014-10-13 14:12:04 -0400127 response = main.FALSE
128 return response
129
kelvin8ec71442015-01-15 16:57:00 -0800130 def logout( self ):
131 """
andrewonlab38d2b4a2014-11-13 16:28:47 -0500132 Sends 'logout' command to ONOS cli
Jon Hall61282e32015-03-19 11:34:11 -0700133 Returns main.TRUE if exited CLI and
134 main.FALSE on timeout (not guranteed you are disconnected)
135 None on TypeError
136 Exits test on unknown error or pexpect exits unexpectedly
kelvin8ec71442015-01-15 16:57:00 -0800137 """
andrewonlab38d2b4a2014-11-13 16:28:47 -0500138 try:
Jon Hall61282e32015-03-19 11:34:11 -0700139 if self.handle:
140 self.handle.sendline( "" )
141 i = self.handle.expect( [ "onos>", "\$", pexpect.TIMEOUT ],
142 timeout=10 )
143 if i == 0: # In ONOS CLI
144 self.handle.sendline( "logout" )
Jon Hallbfe00002016-04-05 10:23:54 -0700145 j = self.handle.expect( [ "\$",
146 "Command not found:",
147 pexpect.TIMEOUT ] )
148 if j == 0: # Successfully logged out
149 return main.TRUE
150 elif j == 1 or j == 2:
151 # ONOS didn't fully load, and logout command isn't working
152 # or the command timed out
153 self.handle.send( "\x04" ) # send ctrl-d
Jon Hall64ab3bd2016-05-13 11:29:44 -0700154 try:
155 self.handle.expect( "\$" )
156 except pexpect.TIMEOUT:
157 main.log.error( "ONOS did not respond to 'logout' or CTRL-d" )
Jon Hallbfe00002016-04-05 10:23:54 -0700158 return main.TRUE
159 else: # some other output
160 main.log.warn( "Unknown repsonse to logout command: '{}'",
161 repr( self.handle.before ) )
162 return main.FALSE
Jon Hall61282e32015-03-19 11:34:11 -0700163 elif i == 1: # not in CLI
164 return main.TRUE
165 elif i == 3: # Timeout
166 return main.FALSE
167 else:
andrewonlab9627f432014-11-14 12:45:10 -0500168 return main.TRUE
Jon Halld4d4b372015-01-28 16:02:41 -0800169 except TypeError:
170 main.log.exception( self.name + ": Object not as expected" )
171 return None
andrewonlab38d2b4a2014-11-13 16:28:47 -0500172 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800173 main.log.error( self.name + ": eof exception found" )
Jon Hall61282e32015-03-19 11:34:11 -0700174 main.log.error( self.name + ": " + self.handle.before )
andrewonlab38d2b4a2014-11-13 16:28:47 -0500175 main.cleanup()
176 main.exit()
Jon Hall61282e32015-03-19 11:34:11 -0700177 except ValueError:
Jon Hall5aa168b2015-03-23 14:23:09 -0700178 main.log.error( self.name +
179 "ValueError exception in logout method" )
Jon Hallfebb1c72015-03-05 13:30:09 -0800180 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800181 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab38d2b4a2014-11-13 16:28:47 -0500182 main.cleanup()
183 main.exit()
184
kelvin-onlabd3b64892015-01-20 13:26:24 -0800185 def setCell( self, cellname ):
kelvin8ec71442015-01-15 16:57:00 -0800186 """
andrewonlab95ce8322014-10-13 14:12:04 -0400187 Calls 'cell <name>' to set the environment variables on ONOSbench
kelvin8ec71442015-01-15 16:57:00 -0800188
andrewonlab95ce8322014-10-13 14:12:04 -0400189 Before issuing any cli commands, set the environment variable first.
kelvin8ec71442015-01-15 16:57:00 -0800190 """
andrewonlab95ce8322014-10-13 14:12:04 -0400191 try:
192 if not cellname:
kelvin8ec71442015-01-15 16:57:00 -0800193 main.log.error( "Must define cellname" )
andrewonlab95ce8322014-10-13 14:12:04 -0400194 main.cleanup()
195 main.exit()
196 else:
kelvin8ec71442015-01-15 16:57:00 -0800197 self.handle.sendline( "cell " + str( cellname ) )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800198 # Expect the cellname in the ONOSCELL variable.
kelvin8ec71442015-01-15 16:57:00 -0800199 # Note that this variable name is subject to change
andrewonlab95ce8322014-10-13 14:12:04 -0400200 # and that this driver will have to change accordingly
Cameron Franke9c94fb02015-01-21 10:20:20 -0800201 self.handle.expect(str(cellname))
andrew@onlab.usc400b112015-01-21 15:33:19 -0800202 handleBefore = self.handle.before
203 handleAfter = self.handle.after
kelvin8ec71442015-01-15 16:57:00 -0800204 # Get the rest of the handle
Cameron Franke9c94fb02015-01-21 10:20:20 -0800205 self.handle.sendline("")
206 self.handle.expect("\$")
andrew@onlab.usc400b112015-01-21 15:33:19 -0800207 handleMore = self.handle.before
andrewonlab95ce8322014-10-13 14:12:04 -0400208
kelvin-onlabd3b64892015-01-20 13:26:24 -0800209 main.log.info( "Cell call returned: " + handleBefore +
210 handleAfter + handleMore )
andrewonlab95ce8322014-10-13 14:12:04 -0400211
212 return main.TRUE
213
Jon Halld4d4b372015-01-28 16:02:41 -0800214 except TypeError:
215 main.log.exception( self.name + ": Object not as expected" )
216 return None
andrewonlab95ce8322014-10-13 14:12:04 -0400217 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800218 main.log.error( self.name + ": eof exception found" )
219 main.log.error( self.name + ": " + self.handle.before )
andrewonlab95ce8322014-10-13 14:12:04 -0400220 main.cleanup()
221 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800222 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800223 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab95ce8322014-10-13 14:12:04 -0400224 main.cleanup()
225 main.exit()
kelvin8ec71442015-01-15 16:57:00 -0800226
pingping-lin57a56ce2015-05-20 16:43:48 -0700227 def startOnosCli( self, ONOSIp, karafTimeout="",
Jon Hallc6793552016-01-19 14:18:37 -0800228 commandlineTimeout=10, onosStartTimeout=60 ):
kelvin8ec71442015-01-15 16:57:00 -0800229 """
Jon Hallefbd9792015-03-05 16:11:36 -0800230 karafTimeout is an optional argument. karafTimeout value passed
kelvin-onlabd3b64892015-01-20 13:26:24 -0800231 by user would be used to set the current karaf shell idle timeout.
232 Note that when ever this property is modified the shell will exit and
Hari Krishnad7b9c202015-01-05 10:38:14 -0800233 the subsequent login would reflect new idle timeout.
kelvin-onlabd3b64892015-01-20 13:26:24 -0800234 Below is an example to start a session with 60 seconds idle timeout
235 ( input value is in milliseconds ):
kelvin8ec71442015-01-15 16:57:00 -0800236
Hari Krishna25d42f72015-01-05 15:08:28 -0800237 tValue = "60000"
kelvin-onlabd3b64892015-01-20 13:26:24 -0800238 main.ONOScli1.startOnosCli( ONOSIp, karafTimeout=tValue )
kelvin8ec71442015-01-15 16:57:00 -0800239
kelvin-onlabd3b64892015-01-20 13:26:24 -0800240 Note: karafTimeout is left as str so that this could be read
241 and passed to startOnosCli from PARAMS file as str.
kelvin8ec71442015-01-15 16:57:00 -0800242 """
You Wangf69ab392016-01-26 16:34:38 -0800243 self.onosIp = ONOSIp
andrewonlab95ce8322014-10-13 14:12:04 -0400244 try:
kelvin8ec71442015-01-15 16:57:00 -0800245 self.handle.sendline( "" )
246 x = self.handle.expect( [
pingping-lin57a56ce2015-05-20 16:43:48 -0700247 "\$", "onos>" ], commandlineTimeout)
andrewonlab48829f62014-11-17 13:49:01 -0500248
249 if x == 1:
kelvin8ec71442015-01-15 16:57:00 -0800250 main.log.info( "ONOS cli is already running" )
andrewonlab48829f62014-11-17 13:49:01 -0500251 return main.TRUE
andrewonlab95ce8322014-10-13 14:12:04 -0400252
kelvin8ec71442015-01-15 16:57:00 -0800253 # Wait for onos start ( -w ) and enter onos cli
kelvin-onlabd3b64892015-01-20 13:26:24 -0800254 self.handle.sendline( "onos -w " + str( ONOSIp ) )
kelvin8ec71442015-01-15 16:57:00 -0800255 i = self.handle.expect( [
256 "onos>",
pingping-lin57a56ce2015-05-20 16:43:48 -0700257 pexpect.TIMEOUT ], onosStartTimeout )
andrewonlab2a7ea9b2014-10-24 12:21:05 -0400258
259 if i == 0:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800260 main.log.info( str( ONOSIp ) + " CLI Started successfully" )
Hari Krishnae36ef212015-01-04 14:09:13 -0800261 if karafTimeout:
kelvin8ec71442015-01-15 16:57:00 -0800262 self.handle.sendline(
Hari Krishnaac4e1782015-01-26 12:09:12 -0800263 "config:property-set -p org.apache.karaf.shell\
264 sshIdleTimeout " +
kelvin8ec71442015-01-15 16:57:00 -0800265 karafTimeout )
266 self.handle.expect( "\$" )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800267 self.handle.sendline( "onos -w " + str( ONOSIp ) )
kelvin8ec71442015-01-15 16:57:00 -0800268 self.handle.expect( "onos>" )
andrewonlab2a7ea9b2014-10-24 12:21:05 -0400269 return main.TRUE
270 else:
kelvin8ec71442015-01-15 16:57:00 -0800271 # If failed, send ctrl+c to process and try again
272 main.log.info( "Starting CLI failed. Retrying..." )
273 self.handle.send( "\x03" )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800274 self.handle.sendline( "onos -w " + str( ONOSIp ) )
kelvin8ec71442015-01-15 16:57:00 -0800275 i = self.handle.expect( [ "onos>", pexpect.TIMEOUT ],
276 timeout=30 )
andrewonlab3a7c3c72014-10-24 17:21:03 -0400277 if i == 0:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800278 main.log.info( str( ONOSIp ) + " CLI Started " +
kelvin8ec71442015-01-15 16:57:00 -0800279 "successfully after retry attempt" )
Hari Krishnae36ef212015-01-04 14:09:13 -0800280 if karafTimeout:
kelvin8ec71442015-01-15 16:57:00 -0800281 self.handle.sendline(
kelvin-onlabd3b64892015-01-20 13:26:24 -0800282 "config:property-set -p org.apache.karaf.shell\
283 sshIdleTimeout " +
kelvin8ec71442015-01-15 16:57:00 -0800284 karafTimeout )
285 self.handle.expect( "\$" )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800286 self.handle.sendline( "onos -w " + str( ONOSIp ) )
kelvin8ec71442015-01-15 16:57:00 -0800287 self.handle.expect( "onos>" )
andrewonlab3a7c3c72014-10-24 17:21:03 -0400288 return main.TRUE
289 else:
kelvin8ec71442015-01-15 16:57:00 -0800290 main.log.error( "Connection to CLI " +
kelvin-onlabd3b64892015-01-20 13:26:24 -0800291 str( ONOSIp ) + " timeout" )
andrewonlab3a7c3c72014-10-24 17:21:03 -0400292 return main.FALSE
andrewonlab95ce8322014-10-13 14:12:04 -0400293
Jon Halld4d4b372015-01-28 16:02:41 -0800294 except TypeError:
295 main.log.exception( self.name + ": Object not as expected" )
296 return None
andrewonlab95ce8322014-10-13 14:12:04 -0400297 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800298 main.log.error( self.name + ": EOF exception found" )
299 main.log.error( self.name + ": " + self.handle.before )
andrewonlab95ce8322014-10-13 14:12:04 -0400300 main.cleanup()
301 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800302 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800303 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab95ce8322014-10-13 14:12:04 -0400304 main.cleanup()
305 main.exit()
306
suibin zhang116647a2016-05-06 16:30:09 -0700307 def startCellCli( self, karafTimeout="",
308 commandlineTimeout=10, onosStartTimeout=60 ):
309 """
310 Start CLI on onos ecll handle.
311
312 karafTimeout is an optional argument. karafTimeout value passed
313 by user would be used to set the current karaf shell idle timeout.
314 Note that when ever this property is modified the shell will exit and
315 the subsequent login would reflect new idle timeout.
316 Below is an example to start a session with 60 seconds idle timeout
317 ( input value is in milliseconds ):
318
319 tValue = "60000"
320
321 Note: karafTimeout is left as str so that this could be read
322 and passed to startOnosCli from PARAMS file as str.
323 """
324
325 try:
326 self.handle.sendline( "" )
327 x = self.handle.expect( [
328 "\$", "onos>" ], commandlineTimeout)
329
330 if x == 1:
331 main.log.info( "ONOS cli is already running" )
332 return main.TRUE
333
334 # Wait for onos start ( -w ) and enter onos cli
335 self.handle.sendline( "/opt/onos/bin/onos" )
336 i = self.handle.expect( [
337 "onos>",
338 pexpect.TIMEOUT ], onosStartTimeout )
339
340 if i == 0:
341 main.log.info( self.name + " CLI Started successfully" )
342 if karafTimeout:
343 self.handle.sendline(
344 "config:property-set -p org.apache.karaf.shell\
345 sshIdleTimeout " +
346 karafTimeout )
347 self.handle.expect( "\$" )
348 self.handle.sendline( "/opt/onos/bin/onos" )
349 self.handle.expect( "onos>" )
350 return main.TRUE
351 else:
352 # If failed, send ctrl+c to process and try again
353 main.log.info( "Starting CLI failed. Retrying..." )
354 self.handle.send( "\x03" )
355 self.handle.sendline( "/opt/onos/bin/onos" )
356 i = self.handle.expect( [ "onos>", pexpect.TIMEOUT ],
357 timeout=30 )
358 if i == 0:
359 main.log.info( self.name + " CLI Started " +
360 "successfully after retry attempt" )
361 if karafTimeout:
362 self.handle.sendline(
363 "config:property-set -p org.apache.karaf.shell\
364 sshIdleTimeout " +
365 karafTimeout )
366 self.handle.expect( "\$" )
367 self.handle.sendline( "/opt/onos/bin/onos" )
368 self.handle.expect( "onos>" )
369 return main.TRUE
370 else:
371 main.log.error( "Connection to CLI " +
372 self.name + " timeout" )
373 return main.FALSE
374
375 except TypeError:
376 main.log.exception( self.name + ": Object not as expected" )
377 return None
378 except pexpect.EOF:
379 main.log.error( self.name + ": EOF exception found" )
380 main.log.error( self.name + ": " + self.handle.before )
381 main.cleanup()
382 main.exit()
383 except Exception:
384 main.log.exception( self.name + ": Uncaught exception!" )
385 main.cleanup()
386 main.exit()
387
YPZhangebf9eb52016-05-12 15:20:24 -0700388 def log( self, cmdStr, level="",noExit=False):
kelvin-onlab9f541032015-02-04 16:19:53 -0800389 """
390 log the commands in the onos CLI.
kelvin-onlab338f5512015-02-06 10:53:16 -0800391 returns main.TRUE on success
Jon Hallefbd9792015-03-05 16:11:36 -0800392 returns main.FALSE if Error occurred
YPZhangebf9eb52016-05-12 15:20:24 -0700393 if noExit is True, TestON will not exit, but clean up
kelvin-onlab338f5512015-02-06 10:53:16 -0800394 Available level: DEBUG, TRACE, INFO, WARN, ERROR
395 Level defaults to INFO
kelvin-onlab9f541032015-02-04 16:19:53 -0800396 """
397 try:
kelvin-onlab338f5512015-02-06 10:53:16 -0800398 lvlStr = ""
399 if level:
400 lvlStr = "--level=" + level
401
kelvin-onlab338f5512015-02-06 10:53:16 -0800402 self.handle.sendline( "log:log " + lvlStr + " " + cmdStr )
Jon Hall390696c2015-05-05 17:13:41 -0700403 self.handle.expect( "log:log" )
kelvin-onlab9f541032015-02-04 16:19:53 -0800404 self.handle.expect( "onos>" )
kelvin-onlabfb521662015-02-27 09:52:40 -0800405
kelvin-onlab9f541032015-02-04 16:19:53 -0800406 response = self.handle.before
407 if re.search( "Error", response ):
408 return main.FALSE
409 return main.TRUE
Jon Hall80daded2015-05-27 16:07:00 -0700410 except pexpect.TIMEOUT:
411 main.log.exception( self.name + ": TIMEOUT exception found" )
YPZhangebf9eb52016-05-12 15:20:24 -0700412 if noExit:
413 main.cleanup()
414 return None
415 else:
416 main.cleanup()
417 main.exit()
kelvin-onlab9f541032015-02-04 16:19:53 -0800418 except pexpect.EOF:
419 main.log.error( self.name + ": EOF exception found" )
420 main.log.error( self.name + ": " + self.handle.before )
YPZhangebf9eb52016-05-12 15:20:24 -0700421 if noExit:
422 main.cleanup()
423 return None
424 else:
425 main.cleanup()
426 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800427 except Exception:
kelvin-onlabfb521662015-02-27 09:52:40 -0800428 main.log.exception( self.name + ": Uncaught exception!" )
YPZhangebf9eb52016-05-12 15:20:24 -0700429 if noExit:
430 main.cleanup()
431 return None
432 else:
433 main.cleanup()
434 main.exit()
andrewonlab95ce8322014-10-13 14:12:04 -0400435
YPZhangebf9eb52016-05-12 15:20:24 -0700436 def sendline( self, cmdStr, showResponse=False, debug=False, timeout=10, noExit=False ):
kelvin8ec71442015-01-15 16:57:00 -0800437 """
Jon Halle3f39ff2015-01-13 11:50:53 -0800438 Send a completely user specified string to
439 the onos> prompt. Use this function if you have
andrewonlaba18f6bf2014-10-13 19:31:54 -0400440 a very specific command to send.
Jon Halle3f39ff2015-01-13 11:50:53 -0800441
YPZhangebf9eb52016-05-12 15:20:24 -0700442 if noExit is True, TestON will not exit, but clean up
443
andrewonlaba18f6bf2014-10-13 19:31:54 -0400444 Warning: There are no sanity checking to commands
445 sent using this method.
GlennRCed771242016-01-13 17:02:47 -0800446
kelvin8ec71442015-01-15 16:57:00 -0800447 """
andrewonlaba18f6bf2014-10-13 19:31:54 -0400448 try:
Jon Halla495f562016-05-16 18:03:26 -0700449 # Try to reconnect if disconnected from cli
450 self.handle.sendline( "" )
451 i = self.handle.expect( [ "onos>", "\$", pexpect.TIMEOUT ] )
452 if i == 1:
453 main.log.error( self.name + ": onos cli session closed. ")
454 if self.onosIp:
455 main.log.warn( "Trying to reconnect " + self.onosIp )
456 reconnectResult = self.startOnosCli( self.onosIp )
457 if reconnectResult:
458 main.log.info( self.name + ": onos cli session reconnected." )
459 else:
460 main.log.error( self.name + ": reconnection failed." )
461 main.cleanup()
462 main.exit()
463 else:
464 main.cleanup()
465 main.exit()
466 if i == 2:
467 self.handle.sendline( "" )
468 self.handle.expect( "onos>" )
469
Jon Hall14a03b52016-05-11 12:07:30 -0700470 if debug:
471 # NOTE: This adds and average of .4 seconds per call
472 logStr = "\"Sending CLI command: '" + cmdStr + "'\""
YPZhangebf9eb52016-05-12 15:20:24 -0700473 self.log( logStr,noExit=noExit )
kelvin-onlabd3b64892015-01-20 13:26:24 -0800474 self.handle.sendline( cmdStr )
GlennRCed771242016-01-13 17:02:47 -0800475 i = self.handle.expect( ["onos>", "\$"], timeout )
Jon Hall63604932015-02-26 17:09:50 -0800476 response = self.handle.before
Jon Hall63604932015-02-26 17:09:50 -0800477 # TODO: do something with i
Jon Hallc6793552016-01-19 14:18:37 -0800478 main.log.info( "Command '" + str( cmdStr ) + "' sent to "
479 + self.name + "." )
Jon Hallc6358dd2015-04-10 12:44:28 -0700480 if debug:
Jon Hall390696c2015-05-05 17:13:41 -0700481 main.log.debug( self.name + ": Raw output" )
482 main.log.debug( self.name + ": " + repr( response ) )
Jon Hallc6358dd2015-04-10 12:44:28 -0700483
484 # Remove ANSI color control strings from output
kelvin-onlabd3b64892015-01-20 13:26:24 -0800485 ansiEscape = re.compile( r'\x1b[^m]*m' )
Jon Hall63604932015-02-26 17:09:50 -0800486 response = ansiEscape.sub( '', response )
Jon Hallc6358dd2015-04-10 12:44:28 -0700487 if debug:
Jon Hall390696c2015-05-05 17:13:41 -0700488 main.log.debug( self.name + ": ansiEscape output" )
489 main.log.debug( self.name + ": " + repr( response ) )
Jon Hallc6358dd2015-04-10 12:44:28 -0700490
kelvin-onlabfb521662015-02-27 09:52:40 -0800491 # Remove extra return chars that get added
Jon Hall63604932015-02-26 17:09:50 -0800492 response = re.sub( r"\s\r", "", response )
Jon Hallc6358dd2015-04-10 12:44:28 -0700493 if debug:
Jon Hall390696c2015-05-05 17:13:41 -0700494 main.log.debug( self.name + ": Removed extra returns " +
495 "from output" )
496 main.log.debug( self.name + ": " + repr( response ) )
Jon Hallc6358dd2015-04-10 12:44:28 -0700497
498 # Strip excess whitespace
Jon Hall63604932015-02-26 17:09:50 -0800499 response = response.strip()
Jon Hallc6358dd2015-04-10 12:44:28 -0700500 if debug:
Jon Hall390696c2015-05-05 17:13:41 -0700501 main.log.debug( self.name + ": parsed and stripped output" )
502 main.log.debug( self.name + ": " + repr( response ) )
Jon Hallc6358dd2015-04-10 12:44:28 -0700503
Jon Hall63604932015-02-26 17:09:50 -0800504 # parse for just the output, remove the cmd from response
Jon Hallc6358dd2015-04-10 12:44:28 -0700505 output = response.split( cmdStr.strip(), 1 )
506 if debug:
Jon Hall390696c2015-05-05 17:13:41 -0700507 main.log.debug( self.name + ": split output" )
Jon Hallc6358dd2015-04-10 12:44:28 -0700508 for r in output:
Jon Hall390696c2015-05-05 17:13:41 -0700509 main.log.debug( self.name + ": " + repr( r ) )
GlennRC85870432015-11-23 11:45:51 -0800510 output = output[1].strip()
511 if showResponse:
GlennRCed771242016-01-13 17:02:47 -0800512 main.log.info( "Response from ONOS: {}".format( output ) )
GlennRC85870432015-11-23 11:45:51 -0800513 return output
GlennRCed771242016-01-13 17:02:47 -0800514 except pexpect.TIMEOUT:
515 main.log.error( self.name + ":ONOS timeout" )
516 if debug:
517 main.log.debug( self.handle.before )
518 return None
Jon Hallc6358dd2015-04-10 12:44:28 -0700519 except IndexError:
520 main.log.exception( self.name + ": Object not as expected" )
Jon Halla495f562016-05-16 18:03:26 -0700521 main.log.debug( "response: {}".format( repr( response ) ) )
Jon Hallc6358dd2015-04-10 12:44:28 -0700522 return None
Jon Halld4d4b372015-01-28 16:02:41 -0800523 except TypeError:
524 main.log.exception( self.name + ": Object not as expected" )
525 return None
andrewonlaba18f6bf2014-10-13 19:31:54 -0400526 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800527 main.log.error( self.name + ": EOF exception found" )
528 main.log.error( self.name + ": " + self.handle.before )
YPZhangebf9eb52016-05-12 15:20:24 -0700529 if noExit:
530 main.cleanup()
531 return None
532 else:
533 main.cleanup()
534 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800535 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800536 main.log.exception( self.name + ": Uncaught exception!" )
YPZhangebf9eb52016-05-12 15:20:24 -0700537 if noExit:
538 main.cleanup()
539 return None
540 else:
541 main.cleanup()
542 main.exit()
andrewonlaba18f6bf2014-10-13 19:31:54 -0400543
kelvin8ec71442015-01-15 16:57:00 -0800544 # IMPORTANT NOTE:
545 # For all cli commands, naming convention should match
kelvin-onlabd3b64892015-01-20 13:26:24 -0800546 # the cli command changing 'a:b' with 'aB'.
547 # Ex ) onos:topology > onosTopology
548 # onos:links > onosLinks
549 # feature:list > featureList
Jon Halle3f39ff2015-01-13 11:50:53 -0800550
kelvin-onlabd3b64892015-01-20 13:26:24 -0800551 def addNode( self, nodeId, ONOSIp, tcpPort="" ):
kelvin8ec71442015-01-15 16:57:00 -0800552 """
andrewonlabc2d05aa2014-10-13 16:51:10 -0400553 Adds a new cluster node by ID and address information.
554 Required:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800555 * nodeId
556 * ONOSIp
andrewonlabc2d05aa2014-10-13 16:51:10 -0400557 Optional:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800558 * tcpPort
kelvin8ec71442015-01-15 16:57:00 -0800559 """
andrewonlabc2d05aa2014-10-13 16:51:10 -0400560 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800561 cmdStr = "add-node " + str( nodeId ) + " " +\
562 str( ONOSIp ) + " " + str( tcpPort )
563 handle = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -0700564 assert handle is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -0800565 assert "Command not found:" not in handle, handle
kelvin-onlab898a6c62015-01-16 14:13:53 -0800566 if re.search( "Error", handle ):
kelvin8ec71442015-01-15 16:57:00 -0800567 main.log.error( "Error in adding node" )
568 main.log.error( handle )
Jon Halle3f39ff2015-01-13 11:50:53 -0800569 return main.FALSE
andrewonlabc2d05aa2014-10-13 16:51:10 -0400570 else:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800571 main.log.info( "Node " + str( ONOSIp ) + " added" )
andrewonlabc2d05aa2014-10-13 16:51:10 -0400572 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -0800573 except AssertionError:
574 main.log.exception( "" )
575 return None
Jon Halld4d4b372015-01-28 16:02:41 -0800576 except TypeError:
577 main.log.exception( self.name + ": Object not as expected" )
578 return None
andrewonlabc2d05aa2014-10-13 16:51:10 -0400579 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800580 main.log.error( self.name + ": EOF exception found" )
581 main.log.error( self.name + ": " + self.handle.before )
andrewonlabc2d05aa2014-10-13 16:51:10 -0400582 main.cleanup()
583 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800584 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800585 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlabc2d05aa2014-10-13 16:51:10 -0400586 main.cleanup()
587 main.exit()
588
kelvin-onlabd3b64892015-01-20 13:26:24 -0800589 def removeNode( self, nodeId ):
kelvin8ec71442015-01-15 16:57:00 -0800590 """
andrewonlab86dc3082014-10-13 18:18:38 -0400591 Removes a cluster by ID
592 Issues command: 'remove-node [<node-id>]'
593 Required:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800594 * nodeId
kelvin8ec71442015-01-15 16:57:00 -0800595 """
andrewonlab86dc3082014-10-13 18:18:38 -0400596 try:
andrewonlab86dc3082014-10-13 18:18:38 -0400597
kelvin-onlabd3b64892015-01-20 13:26:24 -0800598 cmdStr = "remove-node " + str( nodeId )
Jon Hall08f61bc2015-04-13 16:00:30 -0700599 handle = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -0700600 assert handle is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -0800601 assert "Command not found:" not in handle, handle
Jon Hallc6358dd2015-04-10 12:44:28 -0700602 if re.search( "Error", handle ):
603 main.log.error( "Error in removing node" )
604 main.log.error( handle )
605 return main.FALSE
606 else:
607 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -0800608 except AssertionError:
609 main.log.exception( "" )
610 return None
Jon Halld4d4b372015-01-28 16:02:41 -0800611 except TypeError:
612 main.log.exception( self.name + ": Object not as expected" )
613 return None
andrewonlab86dc3082014-10-13 18:18:38 -0400614 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800615 main.log.error( self.name + ": EOF exception found" )
616 main.log.error( self.name + ": " + self.handle.before )
andrewonlab86dc3082014-10-13 18:18:38 -0400617 main.cleanup()
618 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800619 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800620 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab86dc3082014-10-13 18:18:38 -0400621 main.cleanup()
622 main.exit()
andrewonlabc2d05aa2014-10-13 16:51:10 -0400623
Jon Hall61282e32015-03-19 11:34:11 -0700624 def nodes( self, jsonFormat=True):
kelvin8ec71442015-01-15 16:57:00 -0800625 """
andrewonlab7c211572014-10-15 16:45:20 -0400626 List the nodes currently visible
627 Issues command: 'nodes'
Jon Hall61282e32015-03-19 11:34:11 -0700628 Optional argument:
629 * jsonFormat - boolean indicating if you want output in json
kelvin8ec71442015-01-15 16:57:00 -0800630 """
andrewonlab7c211572014-10-15 16:45:20 -0400631 try:
Jon Hallc6358dd2015-04-10 12:44:28 -0700632 cmdStr = "nodes"
Jon Hall61282e32015-03-19 11:34:11 -0700633 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -0700634 cmdStr += " -j"
635 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -0700636 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -0800637 assert "Command not found:" not in output, output
Jon Hallc6358dd2015-04-10 12:44:28 -0700638 return output
Jon Hallc6793552016-01-19 14:18:37 -0800639 except AssertionError:
640 main.log.exception( "" )
641 return None
Jon Halld4d4b372015-01-28 16:02:41 -0800642 except TypeError:
643 main.log.exception( self.name + ": Object not as expected" )
644 return None
andrewonlab7c211572014-10-15 16:45:20 -0400645 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800646 main.log.error( self.name + ": EOF exception found" )
647 main.log.error( self.name + ": " + self.handle.before )
andrewonlab7c211572014-10-15 16:45:20 -0400648 main.cleanup()
649 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800650 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800651 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab7c211572014-10-15 16:45:20 -0400652 main.cleanup()
653 main.exit()
654
kelvin8ec71442015-01-15 16:57:00 -0800655 def topology( self ):
656 """
Hari Krishnaef1bd4e2015-03-12 16:55:30 -0700657 Definition:
Jon Hall390696c2015-05-05 17:13:41 -0700658 Returns the output of topology command.
Hari Krishnaef1bd4e2015-03-12 16:55:30 -0700659 Return:
660 topology = current ONOS topology
kelvin8ec71442015-01-15 16:57:00 -0800661 """
andrewonlab95ce8322014-10-13 14:12:04 -0400662 try:
Hari Krishnaef1bd4e2015-03-12 16:55:30 -0700663 cmdStr = "topology -j"
kelvin-onlabd3b64892015-01-20 13:26:24 -0800664 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -0800665 assert "Command not found:" not in handle, handle
Jon Hallc6358dd2015-04-10 12:44:28 -0700666 main.log.info( cmdStr + " returned: " + str( handle ) )
andrewonlab95ce8322014-10-13 14:12:04 -0400667 return handle
Jon Hallc6793552016-01-19 14:18:37 -0800668 except AssertionError:
669 main.log.exception( "" )
Jon Halld4d4b372015-01-28 16:02:41 -0800670 return None
Jon Halld4d4b372015-01-28 16:02:41 -0800671 except TypeError:
672 main.log.exception( self.name + ": Object not as expected" )
673 return None
andrewonlabc2d05aa2014-10-13 16:51:10 -0400674 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800675 main.log.error( self.name + ": EOF exception found" )
676 main.log.error( self.name + ": " + self.handle.before )
andrewonlabc2d05aa2014-10-13 16:51:10 -0400677 main.cleanup()
678 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800679 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800680 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlabc2d05aa2014-10-13 16:51:10 -0400681 main.cleanup()
682 main.exit()
Jon Hallffb386d2014-11-21 13:43:38 -0800683
jenkins7ead5a82015-03-13 10:28:21 -0700684 def deviceRemove( self, deviceId ):
685 """
686 Removes particular device from storage
687
688 TODO: refactor this function
689 """
690 try:
Jon Hallc6358dd2015-04-10 12:44:28 -0700691 cmdStr = "device-remove " + str( deviceId )
692 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -0800693 assert "Command not found:" not in handle, handle
Jon Hallc6358dd2015-04-10 12:44:28 -0700694 if re.search( "Error", handle ):
695 main.log.error( "Error in removing device" )
696 main.log.error( handle )
697 return main.FALSE
698 else:
699 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -0800700 except AssertionError:
701 main.log.exception( "" )
702 return None
jenkins7ead5a82015-03-13 10:28:21 -0700703 except TypeError:
704 main.log.exception( self.name + ": Object not as expected" )
705 return None
706 except pexpect.EOF:
707 main.log.error( self.name + ": EOF exception found" )
708 main.log.error( self.name + ": " + self.handle.before )
709 main.cleanup()
710 main.exit()
711 except Exception:
712 main.log.exception( self.name + ": Uncaught exception!" )
713 main.cleanup()
714 main.exit()
jenkins7ead5a82015-03-13 10:28:21 -0700715
kelvin-onlabd3b64892015-01-20 13:26:24 -0800716 def devices( self, jsonFormat=True ):
kelvin8ec71442015-01-15 16:57:00 -0800717 """
Jon Hall7b02d952014-10-17 20:14:54 -0400718 Lists all infrastructure devices or switches
andrewonlab86dc3082014-10-13 18:18:38 -0400719 Optional argument:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800720 * jsonFormat - boolean indicating if you want output in json
kelvin8ec71442015-01-15 16:57:00 -0800721 """
andrewonlab86dc3082014-10-13 18:18:38 -0400722 try:
Jon Hallc6358dd2015-04-10 12:44:28 -0700723 cmdStr = "devices"
kelvin-onlabd3b64892015-01-20 13:26:24 -0800724 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -0700725 cmdStr += " -j"
726 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -0800727 assert "Command not found:" not in handle, handle
Jon Hallc6358dd2015-04-10 12:44:28 -0700728 return handle
Jon Hallc6793552016-01-19 14:18:37 -0800729 except AssertionError:
730 main.log.exception( "" )
731 return None
Jon Halld4d4b372015-01-28 16:02:41 -0800732 except TypeError:
733 main.log.exception( self.name + ": Object not as expected" )
734 return None
andrewonlab7c211572014-10-15 16:45:20 -0400735 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800736 main.log.error( self.name + ": EOF exception found" )
737 main.log.error( self.name + ": " + self.handle.before )
andrewonlab7c211572014-10-15 16:45:20 -0400738 main.cleanup()
739 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800740 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800741 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab7c211572014-10-15 16:45:20 -0400742 main.cleanup()
743 main.exit()
744
kelvin-onlabd3b64892015-01-20 13:26:24 -0800745 def balanceMasters( self ):
kelvin8ec71442015-01-15 16:57:00 -0800746 """
Hari Krishnaa43d4e92014-12-19 13:22:40 -0800747 This balances the devices across all controllers
748 by issuing command: 'onos> onos:balance-masters'
749 If required this could be extended to return devices balanced output.
kelvin8ec71442015-01-15 16:57:00 -0800750 """
Hari Krishnaa43d4e92014-12-19 13:22:40 -0800751 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800752 cmdStr = "onos:balance-masters"
Jon Hallc6358dd2015-04-10 12:44:28 -0700753 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -0800754 assert "Command not found:" not in handle, handle
Jon Hallc6358dd2015-04-10 12:44:28 -0700755 if re.search( "Error", handle ):
756 main.log.error( "Error in balancing masters" )
757 main.log.error( handle )
758 return main.FALSE
759 else:
760 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -0800761 except AssertionError:
762 main.log.exception( "" )
763 return None
Jon Halld4d4b372015-01-28 16:02:41 -0800764 except TypeError:
765 main.log.exception( self.name + ": Object not as expected" )
766 return None
Hari Krishnaa43d4e92014-12-19 13:22:40 -0800767 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800768 main.log.error( self.name + ": EOF exception found" )
769 main.log.error( self.name + ": " + self.handle.before )
Hari Krishnaa43d4e92014-12-19 13:22:40 -0800770 main.cleanup()
771 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800772 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800773 main.log.exception( self.name + ": Uncaught exception!" )
Hari Krishnaa43d4e92014-12-19 13:22:40 -0800774 main.cleanup()
775 main.exit()
776
Jon Hallc6793552016-01-19 14:18:37 -0800777 def checkMasters( self, jsonFormat=True ):
acsmars24950022015-07-30 18:00:43 -0700778 """
779 Returns the output of the masters command.
780 Optional argument:
781 * jsonFormat - boolean indicating if you want output in json
782 """
783 try:
784 cmdStr = "onos:masters"
785 if jsonFormat:
786 cmdStr += " -j"
787 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -0700788 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -0800789 assert "Command not found:" not in output, output
acsmars24950022015-07-30 18:00:43 -0700790 return output
Jon Hallc6793552016-01-19 14:18:37 -0800791 except AssertionError:
792 main.log.exception( "" )
793 return None
acsmars24950022015-07-30 18:00:43 -0700794 except TypeError:
795 main.log.exception( self.name + ": Object not as expected" )
796 return None
797 except pexpect.EOF:
798 main.log.error( self.name + ": EOF exception found" )
799 main.log.error( self.name + ": " + self.handle.before )
800 main.cleanup()
801 main.exit()
802 except Exception:
803 main.log.exception( self.name + ": Uncaught exception!" )
804 main.cleanup()
805 main.exit()
806
Jon Hallc6793552016-01-19 14:18:37 -0800807 def checkBalanceMasters( self, jsonFormat=True ):
acsmars24950022015-07-30 18:00:43 -0700808 """
809 Uses the master command to check that the devices' leadership
810 is evenly divided
811
812 Dependencies: checkMasters() and summary()
813
814 Returns main.True if the devices are balanced
815 Returns main.False if the devices are unbalanced
816 Exits on Exception
817 Returns None on TypeError
818 """
819 try:
Jon Hallc6793552016-01-19 14:18:37 -0800820 summaryOutput = self.summary()
821 totalDevices = json.loads( summaryOutput )[ "devices" ]
822 except ( TypeError, ValueError ):
823 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, summaryOutput ) )
824 return None
825 try:
acsmars24950022015-07-30 18:00:43 -0700826 totalOwnedDevices = 0
Jon Hallc6793552016-01-19 14:18:37 -0800827 mastersOutput = self.checkMasters()
828 masters = json.loads( mastersOutput )
acsmars24950022015-07-30 18:00:43 -0700829 first = masters[ 0 ][ "size" ]
830 for master in masters:
831 totalOwnedDevices += master[ "size" ]
832 if master[ "size" ] > first + 1 or master[ "size" ] < first - 1:
833 main.log.error( "Mastership not balanced" )
834 main.log.info( "\n" + self.checkMasters( False ) )
835 return main.FALSE
836 main.log.info( "Mastership balanced between " \
837 + str( len(masters) ) + " masters" )
838 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -0800839 except ( TypeError, ValueError ):
840 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, mastersOutput ) )
acsmars24950022015-07-30 18:00:43 -0700841 return None
842 except pexpect.EOF:
843 main.log.error( self.name + ": EOF exception found" )
844 main.log.error( self.name + ": " + self.handle.before )
845 main.cleanup()
846 main.exit()
847 except Exception:
848 main.log.exception( self.name + ": Uncaught exception!" )
849 main.cleanup()
850 main.exit()
851
kelvin-onlabd3b64892015-01-20 13:26:24 -0800852 def links( self, jsonFormat=True ):
kelvin8ec71442015-01-15 16:57:00 -0800853 """
Jon Halle8217482014-10-17 13:49:14 -0400854 Lists all core links
855 Optional argument:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800856 * jsonFormat - boolean indicating if you want output in json
kelvin8ec71442015-01-15 16:57:00 -0800857 """
Jon Halle8217482014-10-17 13:49:14 -0400858 try:
Jon Hallc6358dd2015-04-10 12:44:28 -0700859 cmdStr = "links"
kelvin-onlabd3b64892015-01-20 13:26:24 -0800860 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -0700861 cmdStr += " -j"
862 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -0800863 assert "Command not found:" not in handle, handle
Jon Hallc6358dd2015-04-10 12:44:28 -0700864 return handle
Jon Hallc6793552016-01-19 14:18:37 -0800865 except AssertionError:
866 main.log.exception( "" )
867 return None
Jon Halld4d4b372015-01-28 16:02:41 -0800868 except TypeError:
869 main.log.exception( self.name + ": Object not as expected" )
870 return None
Jon Halle8217482014-10-17 13:49:14 -0400871 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800872 main.log.error( self.name + ": EOF exception found" )
873 main.log.error( self.name + ": " + self.handle.before )
Jon Halle8217482014-10-17 13:49:14 -0400874 main.cleanup()
875 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800876 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800877 main.log.exception( self.name + ": Uncaught exception!" )
Jon Halle8217482014-10-17 13:49:14 -0400878 main.cleanup()
879 main.exit()
880
kelvin-onlabd3b64892015-01-20 13:26:24 -0800881 def ports( self, jsonFormat=True ):
kelvin8ec71442015-01-15 16:57:00 -0800882 """
Jon Halle8217482014-10-17 13:49:14 -0400883 Lists all ports
884 Optional argument:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800885 * jsonFormat - boolean indicating if you want output in json
kelvin8ec71442015-01-15 16:57:00 -0800886 """
Jon Halle8217482014-10-17 13:49:14 -0400887 try:
Jon Hallc6358dd2015-04-10 12:44:28 -0700888 cmdStr = "ports"
kelvin-onlabd3b64892015-01-20 13:26:24 -0800889 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -0700890 cmdStr += " -j"
891 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -0800892 assert "Command not found:" not in handle, handle
Jon Hallc6358dd2015-04-10 12:44:28 -0700893 return handle
Jon Hallc6793552016-01-19 14:18:37 -0800894 except AssertionError:
895 main.log.exception( "" )
896 return None
Jon Halld4d4b372015-01-28 16:02:41 -0800897 except TypeError:
898 main.log.exception( self.name + ": Object not as expected" )
899 return None
Jon Halle8217482014-10-17 13:49:14 -0400900 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800901 main.log.error( self.name + ": EOF exception found" )
902 main.log.error( self.name + ": " + self.handle.before )
Jon Halle8217482014-10-17 13:49:14 -0400903 main.cleanup()
904 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800905 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800906 main.log.exception( self.name + ": Uncaught exception!" )
Jon Halle8217482014-10-17 13:49:14 -0400907 main.cleanup()
908 main.exit()
909
kelvin-onlabd3b64892015-01-20 13:26:24 -0800910 def roles( self, jsonFormat=True ):
kelvin8ec71442015-01-15 16:57:00 -0800911 """
Jon Hall983a1702014-10-28 18:44:22 -0400912 Lists all devices and the controllers with roles assigned to them
913 Optional argument:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800914 * jsonFormat - boolean indicating if you want output in json
kelvin8ec71442015-01-15 16:57:00 -0800915 """
andrewonlab7c211572014-10-15 16:45:20 -0400916 try:
Jon Hallc6358dd2015-04-10 12:44:28 -0700917 cmdStr = "roles"
kelvin-onlabd3b64892015-01-20 13:26:24 -0800918 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -0700919 cmdStr += " -j"
920 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -0800921 assert "Command not found:" not in handle, handle
Jon Hallc6358dd2015-04-10 12:44:28 -0700922 return handle
Jon Hallc6793552016-01-19 14:18:37 -0800923 except AssertionError:
924 main.log.exception( "" )
925 return None
Jon Halld4d4b372015-01-28 16:02:41 -0800926 except TypeError:
927 main.log.exception( self.name + ": Object not as expected" )
928 return None
Jon Hall983a1702014-10-28 18:44:22 -0400929 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800930 main.log.error( self.name + ": EOF exception found" )
931 main.log.error( self.name + ": " + self.handle.before )
Jon Hall983a1702014-10-28 18:44:22 -0400932 main.cleanup()
933 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800934 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800935 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall983a1702014-10-28 18:44:22 -0400936 main.cleanup()
937 main.exit()
938
kelvin-onlabd3b64892015-01-20 13:26:24 -0800939 def getRole( self, deviceId ):
kelvin-onlab898a6c62015-01-16 14:13:53 -0800940 """
Jon Halle3f39ff2015-01-13 11:50:53 -0800941 Given the a string containing the json representation of the "roles"
942 cli command and a partial or whole device id, returns a json object
943 containing the roles output for the first device whose id contains
944 "device_id"
Jon Hall983a1702014-10-28 18:44:22 -0400945
946 Returns:
Jon Halle3f39ff2015-01-13 11:50:53 -0800947 A dict of the role assignments for the given device or
948 None if no match
kelvin8ec71442015-01-15 16:57:00 -0800949 """
Jon Hall983a1702014-10-28 18:44:22 -0400950 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800951 if deviceId is None:
Jon Hall983a1702014-10-28 18:44:22 -0400952 return None
953 else:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800954 rawRoles = self.roles()
955 rolesJson = json.loads( rawRoles )
kelvin8ec71442015-01-15 16:57:00 -0800956 # search json for the device with id then return the device
kelvin-onlabd3b64892015-01-20 13:26:24 -0800957 for device in rolesJson:
kelvin8ec71442015-01-15 16:57:00 -0800958 # print device
kelvin-onlabd3b64892015-01-20 13:26:24 -0800959 if str( deviceId ) in device[ 'id' ]:
Jon Hall983a1702014-10-28 18:44:22 -0400960 return device
961 return None
Jon Hallc6793552016-01-19 14:18:37 -0800962 except ( TypeError, ValueError ):
963 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, rawRoles ) )
Jon Halld4d4b372015-01-28 16:02:41 -0800964 return None
andrewonlab86dc3082014-10-13 18:18:38 -0400965 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800966 main.log.error( self.name + ": EOF exception found" )
967 main.log.error( self.name + ": " + self.handle.before )
andrewonlab86dc3082014-10-13 18:18:38 -0400968 main.cleanup()
969 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800970 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -0800971 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab86dc3082014-10-13 18:18:38 -0400972 main.cleanup()
973 main.exit()
Jon Hall94fd0472014-12-08 11:52:42 -0800974
kelvin-onlabd3b64892015-01-20 13:26:24 -0800975 def rolesNotNull( self ):
kelvin8ec71442015-01-15 16:57:00 -0800976 """
Jon Hall94fd0472014-12-08 11:52:42 -0800977 Iterates through each device and checks if there is a master assigned
978 Returns: main.TRUE if each device has a master
979 main.FALSE any device has no master
kelvin8ec71442015-01-15 16:57:00 -0800980 """
Jon Hall94fd0472014-12-08 11:52:42 -0800981 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -0800982 rawRoles = self.roles()
983 rolesJson = json.loads( rawRoles )
kelvin8ec71442015-01-15 16:57:00 -0800984 # search json for the device with id then return the device
kelvin-onlabd3b64892015-01-20 13:26:24 -0800985 for device in rolesJson:
kelvin8ec71442015-01-15 16:57:00 -0800986 # print device
987 if device[ 'master' ] == "none":
988 main.log.warn( "Device has no master: " + str( device ) )
Jon Hall94fd0472014-12-08 11:52:42 -0800989 return main.FALSE
990 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -0800991 except ( TypeError, ValueError ):
992 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, rawRoles ) )
Jon Halld4d4b372015-01-28 16:02:41 -0800993 return None
Jon Hall94fd0472014-12-08 11:52:42 -0800994 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -0800995 main.log.error( self.name + ": EOF exception found" )
996 main.log.error( self.name + ": " + self.handle.before )
Jon Hall94fd0472014-12-08 11:52:42 -0800997 main.cleanup()
998 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -0800999 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001000 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall94fd0472014-12-08 11:52:42 -08001001 main.cleanup()
1002 main.exit()
1003
kelvin-onlabd3b64892015-01-20 13:26:24 -08001004 def paths( self, srcId, dstId ):
kelvin8ec71442015-01-15 16:57:00 -08001005 """
andrewonlab3e15ead2014-10-15 14:21:34 -04001006 Returns string of paths, and the cost.
1007 Issues command: onos:paths <src> <dst>
kelvin8ec71442015-01-15 16:57:00 -08001008 """
andrewonlab3e15ead2014-10-15 14:21:34 -04001009 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001010 cmdStr = "onos:paths " + str( srcId ) + " " + str( dstId )
1011 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08001012 assert "Command not found:" not in handle, handle
Jon Halle3f39ff2015-01-13 11:50:53 -08001013 if re.search( "Error", handle ):
kelvin8ec71442015-01-15 16:57:00 -08001014 main.log.error( "Error in getting paths" )
1015 return ( handle, "Error" )
andrewonlab3e15ead2014-10-15 14:21:34 -04001016 else:
kelvin8ec71442015-01-15 16:57:00 -08001017 path = handle.split( ";" )[ 0 ]
1018 cost = handle.split( ";" )[ 1 ]
1019 return ( path, cost )
Jon Hallc6793552016-01-19 14:18:37 -08001020 except AssertionError:
1021 main.log.exception( "" )
1022 return ( handle, "Error" )
Jon Halld4d4b372015-01-28 16:02:41 -08001023 except TypeError:
1024 main.log.exception( self.name + ": Object not as expected" )
1025 return ( handle, "Error" )
andrewonlab3e15ead2014-10-15 14:21:34 -04001026 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001027 main.log.error( self.name + ": EOF exception found" )
1028 main.log.error( self.name + ": " + self.handle.before )
andrewonlab3e15ead2014-10-15 14:21:34 -04001029 main.cleanup()
1030 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001031 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001032 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab3e15ead2014-10-15 14:21:34 -04001033 main.cleanup()
1034 main.exit()
Jon Hallffb386d2014-11-21 13:43:38 -08001035
kelvin-onlabd3b64892015-01-20 13:26:24 -08001036 def hosts( self, jsonFormat=True ):
kelvin8ec71442015-01-15 16:57:00 -08001037 """
Jon Hallffb386d2014-11-21 13:43:38 -08001038 Lists all discovered hosts
Jon Hall42db6dc2014-10-24 19:03:48 -04001039 Optional argument:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001040 * jsonFormat - boolean indicating if you want output in json
kelvin8ec71442015-01-15 16:57:00 -08001041 """
Jon Hall42db6dc2014-10-24 19:03:48 -04001042 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07001043 cmdStr = "hosts"
kelvin-onlabd3b64892015-01-20 13:26:24 -08001044 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -07001045 cmdStr += " -j"
1046 handle = self.sendline( cmdStr )
Jeremyd9e4eb12016-04-13 12:09:06 -07001047 if handle:
1048 assert "Command not found:" not in handle, handle
Jon Hallbaf53162015-12-17 17:04:34 -08001049 # TODO: Maybe make this less hardcoded
1050 # ConsistentMap Exceptions
1051 assert "org.onosproject.store.service" not in handle
1052 # Node not leader
1053 assert "java.lang.IllegalStateException" not in handle
Jon Hallc6358dd2015-04-10 12:44:28 -07001054 return handle
Jon Hallc6793552016-01-19 14:18:37 -08001055 except AssertionError:
Jeremyd9e4eb12016-04-13 12:09:06 -07001056 main.log.exception( "Error in processing '" + cmdStr + "' " +
Jeremy Songster6949cea2016-04-19 18:13:18 -07001057 "command: " + str( handle ) )
Jon Hallc6793552016-01-19 14:18:37 -08001058 return None
Jon Halld4d4b372015-01-28 16:02:41 -08001059 except TypeError:
1060 main.log.exception( self.name + ": Object not as expected" )
1061 return None
Jon Hall42db6dc2014-10-24 19:03:48 -04001062 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001063 main.log.error( self.name + ": EOF exception found" )
1064 main.log.error( self.name + ": " + self.handle.before )
Jon Hall42db6dc2014-10-24 19:03:48 -04001065 main.cleanup()
1066 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001067 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001068 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall42db6dc2014-10-24 19:03:48 -04001069 main.cleanup()
1070 main.exit()
1071
kelvin-onlabd3b64892015-01-20 13:26:24 -08001072 def getHost( self, mac ):
kelvin8ec71442015-01-15 16:57:00 -08001073 """
Jon Hall42db6dc2014-10-24 19:03:48 -04001074 Return the first host from the hosts api whose 'id' contains 'mac'
Jon Halle3f39ff2015-01-13 11:50:53 -08001075
Jon Hallefbd9792015-03-05 16:11:36 -08001076 Note: mac must be a colon separated mac address, but could be a
Jon Halle3f39ff2015-01-13 11:50:53 -08001077 partial mac address
1078
Jon Hall42db6dc2014-10-24 19:03:48 -04001079 Return None if there is no match
kelvin8ec71442015-01-15 16:57:00 -08001080 """
Jon Hall42db6dc2014-10-24 19:03:48 -04001081 try:
kelvin8ec71442015-01-15 16:57:00 -08001082 if mac is None:
Jon Hall42db6dc2014-10-24 19:03:48 -04001083 return None
1084 else:
1085 mac = mac
kelvin-onlabd3b64892015-01-20 13:26:24 -08001086 rawHosts = self.hosts()
1087 hostsJson = json.loads( rawHosts )
kelvin8ec71442015-01-15 16:57:00 -08001088 # search json for the host with mac then return the device
kelvin-onlabd3b64892015-01-20 13:26:24 -08001089 for host in hostsJson:
kelvin8ec71442015-01-15 16:57:00 -08001090 # print "%s in %s?" % ( mac, host[ 'id' ] )
Jon Halld4d4b372015-01-28 16:02:41 -08001091 if not host:
1092 pass
1093 elif mac in host[ 'id' ]:
Jon Hall42db6dc2014-10-24 19:03:48 -04001094 return host
1095 return None
Jon Hallc6793552016-01-19 14:18:37 -08001096 except ( TypeError, ValueError ):
1097 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, rawHosts ) )
Jon Halld4d4b372015-01-28 16:02:41 -08001098 return None
Jon Hall42db6dc2014-10-24 19:03:48 -04001099 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001100 main.log.error( self.name + ": EOF exception found" )
1101 main.log.error( self.name + ": " + self.handle.before )
Jon Hall42db6dc2014-10-24 19:03:48 -04001102 main.cleanup()
1103 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001104 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001105 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall42db6dc2014-10-24 19:03:48 -04001106 main.cleanup()
1107 main.exit()
1108
kelvin-onlabd3b64892015-01-20 13:26:24 -08001109 def getHostsId( self, hostList ):
kelvin8ec71442015-01-15 16:57:00 -08001110 """
1111 Obtain list of hosts
andrewonlab3f0a4af2014-10-17 12:25:14 -04001112 Issues command: 'onos> hosts'
kelvin8ec71442015-01-15 16:57:00 -08001113
andrewonlab3f0a4af2014-10-17 12:25:14 -04001114 Required:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001115 * hostList: List of hosts obtained by Mininet
andrewonlab3f0a4af2014-10-17 12:25:14 -04001116 IMPORTANT:
1117 This function assumes that you started your
kelvin8ec71442015-01-15 16:57:00 -08001118 topology with the option '--mac'.
andrewonlab3f0a4af2014-10-17 12:25:14 -04001119 Furthermore, it assumes that value of VLAN is '-1'
1120 Description:
kelvin8ec71442015-01-15 16:57:00 -08001121 Converts mininet hosts ( h1, h2, h3... ) into
1122 ONOS format ( 00:00:00:00:00:01/-1 , ... )
1123 """
andrewonlab3f0a4af2014-10-17 12:25:14 -04001124 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001125 onosHostList = []
andrewonlab3f0a4af2014-10-17 12:25:14 -04001126
kelvin-onlabd3b64892015-01-20 13:26:24 -08001127 for host in hostList:
kelvin8ec71442015-01-15 16:57:00 -08001128 host = host.replace( "h", "" )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001129 hostHex = hex( int( host ) ).zfill( 12 )
1130 hostHex = str( hostHex ).replace( 'x', '0' )
1131 i = iter( str( hostHex ) )
1132 hostHex = ":".join( a + b for a, b in zip( i, i ) )
1133 hostHex = hostHex + "/-1"
1134 onosHostList.append( hostHex )
andrewonlab3f0a4af2014-10-17 12:25:14 -04001135
kelvin-onlabd3b64892015-01-20 13:26:24 -08001136 return onosHostList
andrewonlab3f0a4af2014-10-17 12:25:14 -04001137
Jon Halld4d4b372015-01-28 16:02:41 -08001138 except TypeError:
1139 main.log.exception( self.name + ": Object not as expected" )
1140 return None
andrewonlab3f0a4af2014-10-17 12:25:14 -04001141 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001142 main.log.error( self.name + ": EOF exception found" )
1143 main.log.error( self.name + ": " + self.handle.before )
andrewonlab3f0a4af2014-10-17 12:25:14 -04001144 main.cleanup()
1145 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001146 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001147 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab3f0a4af2014-10-17 12:25:14 -04001148 main.cleanup()
1149 main.exit()
andrewonlab3e15ead2014-10-15 14:21:34 -04001150
Jeremy Songsterff553672016-05-12 17:06:23 -07001151 def addHostIntent( self, hostIdOne, hostIdTwo, vlanId="", setVlan="" ):
kelvin8ec71442015-01-15 16:57:00 -08001152 """
andrewonlabe6745342014-10-17 14:29:13 -04001153 Required:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001154 * hostIdOne: ONOS host id for host1
1155 * hostIdTwo: ONOS host id for host2
Jeremy Songster832f9e92016-05-05 14:30:49 -07001156 Optional:
1157 * vlanId: specify a VLAN id for the intent
Jeremy Songsterff553672016-05-12 17:06:23 -07001158 * setVlan: specify a VLAN id treatment
andrewonlabe6745342014-10-17 14:29:13 -04001159 Description:
Jon Hallefbd9792015-03-05 16:11:36 -08001160 Adds a host-to-host intent ( bidirectional ) by
Jon Hallb1290e82014-11-18 16:17:48 -05001161 specifying the two hosts.
kelvin-onlabfb521662015-02-27 09:52:40 -08001162 Returns:
1163 A string of the intent id or None on Error
kelvin8ec71442015-01-15 16:57:00 -08001164 """
andrewonlabe6745342014-10-17 14:29:13 -04001165 try:
Jeremy Songster832f9e92016-05-05 14:30:49 -07001166 cmdStr = "add-host-intent "
1167 if vlanId:
1168 cmdStr += "-v " + str( vlanId ) + " "
Jeremy Songsterff553672016-05-12 17:06:23 -07001169 if setVlan:
1170 cmdStr += "--setVlan " + str( vlanId ) + " "
Jeremy Songster832f9e92016-05-05 14:30:49 -07001171 cmdStr += str( hostIdOne ) + " " + str( hostIdTwo )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001172 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08001173 assert "Command not found:" not in handle, handle
Hari Krishnaac4e1782015-01-26 12:09:12 -08001174 if re.search( "Error", handle ):
1175 main.log.error( "Error in adding Host intent" )
Jon Hall61282e32015-03-19 11:34:11 -07001176 main.log.debug( "Response from ONOS was: " + repr( handle ) )
kelvin-onlabfb521662015-02-27 09:52:40 -08001177 return None
Hari Krishnaac4e1782015-01-26 12:09:12 -08001178 else:
1179 main.log.info( "Host intent installed between " +
kelvin-onlabfb521662015-02-27 09:52:40 -08001180 str( hostIdOne ) + " and " + str( hostIdTwo ) )
1181 match = re.search('id=0x([\da-f]+),', handle)
1182 if match:
1183 return match.group()[3:-1]
1184 else:
1185 main.log.error( "Error, intent ID not found" )
Jon Hall61282e32015-03-19 11:34:11 -07001186 main.log.debug( "Response from ONOS was: " +
1187 repr( handle ) )
kelvin-onlabfb521662015-02-27 09:52:40 -08001188 return None
Jon Hallc6793552016-01-19 14:18:37 -08001189 except AssertionError:
1190 main.log.exception( "" )
1191 return None
Jon Halld4d4b372015-01-28 16:02:41 -08001192 except TypeError:
1193 main.log.exception( self.name + ": Object not as expected" )
1194 return None
andrewonlabe6745342014-10-17 14:29:13 -04001195 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001196 main.log.error( self.name + ": EOF exception found" )
1197 main.log.error( self.name + ": " + self.handle.before )
andrewonlabe6745342014-10-17 14:29:13 -04001198 main.cleanup()
1199 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001200 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001201 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlabe6745342014-10-17 14:29:13 -04001202 main.cleanup()
1203 main.exit()
1204
kelvin-onlabd3b64892015-01-20 13:26:24 -08001205 def addOpticalIntent( self, ingressDevice, egressDevice ):
kelvin8ec71442015-01-15 16:57:00 -08001206 """
andrewonlab7b31d232014-10-24 13:31:47 -04001207 Required:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001208 * ingressDevice: device id of ingress device
1209 * egressDevice: device id of egress device
andrewonlab7b31d232014-10-24 13:31:47 -04001210 Optional:
1211 TODO: Still needs to be implemented via dev side
kelvin-onlabfb521662015-02-27 09:52:40 -08001212 Description:
1213 Adds an optical intent by specifying an ingress and egress device
1214 Returns:
1215 A string of the intent id or None on error
kelvin-onlab898a6c62015-01-16 14:13:53 -08001216 """
andrewonlab7b31d232014-10-24 13:31:47 -04001217 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001218 cmdStr = "add-optical-intent " + str( ingressDevice ) +\
1219 " " + str( egressDevice )
1220 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08001221 assert "Command not found:" not in handle, handle
kelvin-onlab898a6c62015-01-16 14:13:53 -08001222 # If error, return error message
Jon Halle3f39ff2015-01-13 11:50:53 -08001223 if re.search( "Error", handle ):
kelvin-onlabfb521662015-02-27 09:52:40 -08001224 main.log.error( "Error in adding Optical intent" )
1225 return None
andrewonlab7b31d232014-10-24 13:31:47 -04001226 else:
kelvin-onlabfb521662015-02-27 09:52:40 -08001227 main.log.info( "Optical intent installed between " +
1228 str( ingressDevice ) + " and " +
1229 str( egressDevice ) )
1230 match = re.search('id=0x([\da-f]+),', handle)
1231 if match:
1232 return match.group()[3:-1]
1233 else:
1234 main.log.error( "Error, intent ID not found" )
1235 return None
Jon Hallc6793552016-01-19 14:18:37 -08001236 except AssertionError:
1237 main.log.exception( "" )
1238 return None
Jon Halld4d4b372015-01-28 16:02:41 -08001239 except TypeError:
1240 main.log.exception( self.name + ": Object not as expected" )
1241 return None
andrewonlab7b31d232014-10-24 13:31:47 -04001242 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001243 main.log.error( self.name + ": EOF exception found" )
1244 main.log.error( self.name + ": " + self.handle.before )
andrewonlab7b31d232014-10-24 13:31:47 -04001245 main.cleanup()
1246 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001247 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001248 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab7b31d232014-10-24 13:31:47 -04001249 main.cleanup()
1250 main.exit()
1251
kelvin-onlabd3b64892015-01-20 13:26:24 -08001252 def addPointIntent(
kelvin-onlab898a6c62015-01-16 14:13:53 -08001253 self,
kelvin-onlabd3b64892015-01-20 13:26:24 -08001254 ingressDevice,
1255 egressDevice,
1256 portIngress="",
1257 portEgress="",
kelvin-onlab898a6c62015-01-16 14:13:53 -08001258 ethType="",
1259 ethSrc="",
1260 ethDst="",
1261 bandwidth="",
kelvin-onlabd3b64892015-01-20 13:26:24 -08001262 lambdaAlloc=False,
kelvin-onlab898a6c62015-01-16 14:13:53 -08001263 ipProto="",
1264 ipSrc="",
1265 ipDst="",
1266 tcpSrc="",
Jeremy Songster832f9e92016-05-05 14:30:49 -07001267 tcpDst="",
Jeremy Songsterff553672016-05-12 17:06:23 -07001268 vlanId="",
1269 setVlan="" ):
kelvin8ec71442015-01-15 16:57:00 -08001270 """
andrewonlab4dbb4d82014-10-17 18:22:31 -04001271 Required:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001272 * ingressDevice: device id of ingress device
1273 * egressDevice: device id of egress device
andrewonlab289e4b72014-10-21 21:24:18 -04001274 Optional:
1275 * ethType: specify ethType
kelvin8ec71442015-01-15 16:57:00 -08001276 * ethSrc: specify ethSrc ( i.e. src mac addr )
1277 * ethDst: specify ethDst ( i.e. dst mac addr )
andrewonlab0dbb6ec2014-11-06 13:46:55 -05001278 * bandwidth: specify bandwidth capacity of link
kelvin-onlabd3b64892015-01-20 13:26:24 -08001279 * lambdaAlloc: if True, intent will allocate lambda
andrewonlab40ccd8b2014-11-06 16:23:34 -05001280 for the specified intent
Jon Halle3f39ff2015-01-13 11:50:53 -08001281 * ipProto: specify ip protocol
andrewonlabf77e0cb2014-11-11 17:17:59 -05001282 * ipSrc: specify ip source address
1283 * ipDst: specify ip destination address
1284 * tcpSrc: specify tcp source port
1285 * tcpDst: specify tcp destination port
Jeremy Songster832f9e92016-05-05 14:30:49 -07001286 * vlanId: specify vlan ID
Jeremy Songsterff553672016-05-12 17:06:23 -07001287 * setVlan: specify a VLAN id treatment
andrewonlab4dbb4d82014-10-17 18:22:31 -04001288 Description:
kelvin8ec71442015-01-15 16:57:00 -08001289 Adds a point-to-point intent ( uni-directional ) by
andrewonlab289e4b72014-10-21 21:24:18 -04001290 specifying device id's and optional fields
kelvin-onlabfb521662015-02-27 09:52:40 -08001291 Returns:
1292 A string of the intent id or None on error
andrewonlab289e4b72014-10-21 21:24:18 -04001293
Jon Halle3f39ff2015-01-13 11:50:53 -08001294 NOTE: This function may change depending on the
andrewonlab4dbb4d82014-10-17 18:22:31 -04001295 options developers provide for point-to-point
1296 intent via cli
kelvin8ec71442015-01-15 16:57:00 -08001297 """
andrewonlab4dbb4d82014-10-17 18:22:31 -04001298 try:
Jeremy Songsterff553672016-05-12 17:06:23 -07001299 cmd = "add-point-intent"
andrewonlab36af3822014-11-18 17:48:18 -05001300
Jeremy Songsterff553672016-05-12 17:06:23 -07001301 if ethType:
1302 cmd += " --ethType " + str( ethType )
1303 if ethSrc:
1304 cmd += " --ethSrc " + str( ethSrc )
1305 if ethDst:
1306 cmd += " --ethDst " + str( ethDst )
1307 if bandwidth:
1308 cmd += " --bandwidth " + str( bandwidth )
1309 if lambdaAlloc:
1310 cmd += " --lambda "
1311 if ipProto:
1312 cmd += " --ipProto " + str( ipProto )
1313 if ipSrc:
1314 cmd += " --ipSrc " + str( ipSrc )
1315 if ipDst:
1316 cmd += " --ipDst " + str( ipDst )
1317 if tcpSrc:
1318 cmd += " --tcpSrc " + str( tcpSrc )
1319 if tcpDst:
1320 cmd += " --tcpDst " + str( tcpDst )
1321 if vlanId:
1322 cmd += " -v " + str( vlanId )
1323 if setVlan:
1324 cmd += " --setVlan " + str( setVlan )
andrewonlab289e4b72014-10-21 21:24:18 -04001325
kelvin8ec71442015-01-15 16:57:00 -08001326 # Check whether the user appended the port
1327 # or provided it as an input
kelvin-onlabd3b64892015-01-20 13:26:24 -08001328 if "/" in ingressDevice:
1329 cmd += " " + str( ingressDevice )
andrewonlab36af3822014-11-18 17:48:18 -05001330 else:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001331 if not portIngress:
kelvin-onlabfb521662015-02-27 09:52:40 -08001332 main.log.error( "You must specify the ingress port" )
kelvin8ec71442015-01-15 16:57:00 -08001333 # TODO: perhaps more meaningful return
kelvin-onlabfb521662015-02-27 09:52:40 -08001334 # Would it make sense to throw an exception and exit
1335 # the test?
1336 return None
andrewonlab36af3822014-11-18 17:48:18 -05001337
kelvin8ec71442015-01-15 16:57:00 -08001338 cmd += " " + \
kelvin-onlabd3b64892015-01-20 13:26:24 -08001339 str( ingressDevice ) + "/" +\
1340 str( portIngress ) + " "
andrewonlab36af3822014-11-18 17:48:18 -05001341
kelvin-onlabd3b64892015-01-20 13:26:24 -08001342 if "/" in egressDevice:
1343 cmd += " " + str( egressDevice )
andrewonlab36af3822014-11-18 17:48:18 -05001344 else:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001345 if not portEgress:
kelvin-onlabfb521662015-02-27 09:52:40 -08001346 main.log.error( "You must specify the egress port" )
1347 return None
Jon Halle3f39ff2015-01-13 11:50:53 -08001348
kelvin8ec71442015-01-15 16:57:00 -08001349 cmd += " " +\
kelvin-onlabd3b64892015-01-20 13:26:24 -08001350 str( egressDevice ) + "/" +\
1351 str( portEgress )
kelvin8ec71442015-01-15 16:57:00 -08001352
kelvin-onlab898a6c62015-01-16 14:13:53 -08001353 handle = self.sendline( cmd )
Jon Hallc6793552016-01-19 14:18:37 -08001354 assert "Command not found:" not in handle, handle
kelvin-onlabfb521662015-02-27 09:52:40 -08001355 # If error, return error message
kelvin-onlab898a6c62015-01-16 14:13:53 -08001356 if re.search( "Error", handle ):
kelvin8ec71442015-01-15 16:57:00 -08001357 main.log.error( "Error in adding point-to-point intent" )
kelvin-onlabfb521662015-02-27 09:52:40 -08001358 return None
andrewonlab4dbb4d82014-10-17 18:22:31 -04001359 else:
kelvin-onlabfb521662015-02-27 09:52:40 -08001360 # TODO: print out all the options in this message?
1361 main.log.info( "Point-to-point intent installed between " +
1362 str( ingressDevice ) + " and " +
1363 str( egressDevice ) )
1364 match = re.search('id=0x([\da-f]+),', handle)
1365 if match:
1366 return match.group()[3:-1]
1367 else:
1368 main.log.error( "Error, intent ID not found" )
1369 return None
Jon Hallc6793552016-01-19 14:18:37 -08001370 except AssertionError:
1371 main.log.exception( "" )
1372 return None
Jon Halld4d4b372015-01-28 16:02:41 -08001373 except TypeError:
1374 main.log.exception( self.name + ": Object not as expected" )
1375 return None
andrewonlab4dbb4d82014-10-17 18:22:31 -04001376 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001377 main.log.error( self.name + ": EOF exception found" )
1378 main.log.error( self.name + ": " + self.handle.before )
andrewonlab4dbb4d82014-10-17 18:22:31 -04001379 main.cleanup()
1380 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001381 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001382 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab4dbb4d82014-10-17 18:22:31 -04001383 main.cleanup()
1384 main.exit()
1385
kelvin-onlabd3b64892015-01-20 13:26:24 -08001386 def addMultipointToSinglepointIntent(
kelvin-onlab898a6c62015-01-16 14:13:53 -08001387 self,
shahshreyac2f97072015-03-19 17:04:29 -07001388 ingressDeviceList,
kelvin-onlabd3b64892015-01-20 13:26:24 -08001389 egressDevice,
shahshreyac2f97072015-03-19 17:04:29 -07001390 portIngressList=None,
kelvin-onlabd3b64892015-01-20 13:26:24 -08001391 portEgress="",
kelvin-onlab898a6c62015-01-16 14:13:53 -08001392 ethType="",
1393 ethSrc="",
1394 ethDst="",
1395 bandwidth="",
kelvin-onlabd3b64892015-01-20 13:26:24 -08001396 lambdaAlloc=False,
kelvin-onlab898a6c62015-01-16 14:13:53 -08001397 ipProto="",
1398 ipSrc="",
1399 ipDst="",
1400 tcpSrc="",
1401 tcpDst="",
1402 setEthSrc="",
Jeremy Songster832f9e92016-05-05 14:30:49 -07001403 setEthDst="",
Jeremy Songsterff553672016-05-12 17:06:23 -07001404 vlanId="",
1405 setVlan="" ):
kelvin8ec71442015-01-15 16:57:00 -08001406 """
shahshreyad0c80432014-12-04 16:56:05 -08001407 Note:
shahshreya70622b12015-03-19 17:19:00 -07001408 This function assumes the format of all ingress devices
Jon Hallbe379602015-03-24 13:39:32 -07001409 is same. That is, all ingress devices include port numbers
1410 with a "/" or all ingress devices could specify device
1411 ids and port numbers seperately.
shahshreyad0c80432014-12-04 16:56:05 -08001412 Required:
Jon Hallbe379602015-03-24 13:39:32 -07001413 * ingressDeviceList: List of device ids of ingress device
shahshreyac2f97072015-03-19 17:04:29 -07001414 ( Atleast 2 ingress devices required in the list )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001415 * egressDevice: device id of egress device
shahshreyad0c80432014-12-04 16:56:05 -08001416 Optional:
1417 * ethType: specify ethType
kelvin8ec71442015-01-15 16:57:00 -08001418 * ethSrc: specify ethSrc ( i.e. src mac addr )
1419 * ethDst: specify ethDst ( i.e. dst mac addr )
shahshreyad0c80432014-12-04 16:56:05 -08001420 * bandwidth: specify bandwidth capacity of link
kelvin-onlabd3b64892015-01-20 13:26:24 -08001421 * lambdaAlloc: if True, intent will allocate lambda
shahshreyad0c80432014-12-04 16:56:05 -08001422 for the specified intent
Jon Halle3f39ff2015-01-13 11:50:53 -08001423 * ipProto: specify ip protocol
shahshreyad0c80432014-12-04 16:56:05 -08001424 * ipSrc: specify ip source address
1425 * ipDst: specify ip destination address
1426 * tcpSrc: specify tcp source port
1427 * tcpDst: specify tcp destination port
1428 * setEthSrc: action to Rewrite Source MAC Address
1429 * setEthDst: action to Rewrite Destination MAC Address
Jeremy Songster832f9e92016-05-05 14:30:49 -07001430 * vlanId: specify vlan Id
Jeremy Songsterff553672016-05-12 17:06:23 -07001431 * setVlan: specify VLAN Id treatment
shahshreyad0c80432014-12-04 16:56:05 -08001432 Description:
kelvin8ec71442015-01-15 16:57:00 -08001433 Adds a multipoint-to-singlepoint intent ( uni-directional ) by
shahshreyad0c80432014-12-04 16:56:05 -08001434 specifying device id's and optional fields
kelvin-onlabfb521662015-02-27 09:52:40 -08001435 Returns:
1436 A string of the intent id or None on error
shahshreyad0c80432014-12-04 16:56:05 -08001437
Jon Halle3f39ff2015-01-13 11:50:53 -08001438 NOTE: This function may change depending on the
Jon Hallefbd9792015-03-05 16:11:36 -08001439 options developers provide for multipoint-to-singlepoint
shahshreyad0c80432014-12-04 16:56:05 -08001440 intent via cli
kelvin8ec71442015-01-15 16:57:00 -08001441 """
shahshreyad0c80432014-12-04 16:56:05 -08001442 try:
Jeremy Songsterff553672016-05-12 17:06:23 -07001443 cmd = "add-multi-to-single-intent"
shahshreyad0c80432014-12-04 16:56:05 -08001444
Jeremy Songsterff553672016-05-12 17:06:23 -07001445 if ethType:
1446 cmd += " --ethType " + str( ethType )
1447 if ethSrc:
1448 cmd += " --ethSrc " + str( ethSrc )
1449 if ethDst:
1450 cmd += " --ethDst " + str( ethDst )
1451 if bandwidth:
1452 cmd += " --bandwidth " + str( bandwidth )
1453 if lambdaAlloc:
1454 cmd += " --lambda "
1455 if ipProto:
1456 cmd += " --ipProto " + str( ipProto )
1457 if ipSrc:
1458 cmd += " --ipSrc " + str( ipSrc )
1459 if ipDst:
1460 cmd += " --ipDst " + str( ipDst )
1461 if tcpSrc:
1462 cmd += " --tcpSrc " + str( tcpSrc )
1463 if tcpDst:
1464 cmd += " --tcpDst " + str( tcpDst )
1465 if setEthSrc:
1466 cmd += " --setEthSrc " + str( setEthSrc )
1467 if setEthDst:
1468 cmd += " --setEthDst " + str( setEthDst )
1469 if vlanId:
1470 cmd += " -v " + str( vlanId )
1471 if setVlan:
1472 cmd += " --setVlan " + str( setVlan )
shahshreyad0c80432014-12-04 16:56:05 -08001473
kelvin8ec71442015-01-15 16:57:00 -08001474 # Check whether the user appended the port
1475 # or provided it as an input
shahshreyac2f97072015-03-19 17:04:29 -07001476
1477 if portIngressList is None:
1478 for ingressDevice in ingressDeviceList:
1479 if "/" in ingressDevice:
1480 cmd += " " + str( ingressDevice )
1481 else:
1482 main.log.error( "You must specify " +
Jon Hallbe379602015-03-24 13:39:32 -07001483 "the ingress port" )
shahshreyac2f97072015-03-19 17:04:29 -07001484 # TODO: perhaps more meaningful return
1485 return main.FALSE
shahshreyad0c80432014-12-04 16:56:05 -08001486 else:
Jon Hall71ce4e72015-03-23 14:05:58 -07001487 if len( ingressDeviceList ) == len( portIngressList ):
Jon Hall08f61bc2015-04-13 16:00:30 -07001488 for ingressDevice, portIngress in zip( ingressDeviceList,
1489 portIngressList ):
shahshreya70622b12015-03-19 17:19:00 -07001490 cmd += " " + \
1491 str( ingressDevice ) + "/" +\
1492 str( portIngress ) + " "
kelvin-onlab38143812015-04-01 15:03:01 -07001493 else:
Jon Hall08f61bc2015-04-13 16:00:30 -07001494 main.log.error( "Device list and port list does not " +
1495 "have the same length" )
kelvin-onlab38143812015-04-01 15:03:01 -07001496 return main.FALSE
kelvin-onlabd3b64892015-01-20 13:26:24 -08001497 if "/" in egressDevice:
1498 cmd += " " + str( egressDevice )
shahshreyad0c80432014-12-04 16:56:05 -08001499 else:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001500 if not portEgress:
kelvin8ec71442015-01-15 16:57:00 -08001501 main.log.error( "You must specify " +
1502 "the egress port" )
shahshreyad0c80432014-12-04 16:56:05 -08001503 return main.FALSE
Jon Halle3f39ff2015-01-13 11:50:53 -08001504
kelvin8ec71442015-01-15 16:57:00 -08001505 cmd += " " +\
kelvin-onlabd3b64892015-01-20 13:26:24 -08001506 str( egressDevice ) + "/" +\
1507 str( portEgress )
kelvin-onlab898a6c62015-01-16 14:13:53 -08001508 handle = self.sendline( cmd )
Jon Hallc6793552016-01-19 14:18:37 -08001509 assert "Command not found:" not in handle, handle
kelvin-onlabfb521662015-02-27 09:52:40 -08001510 # If error, return error message
kelvin-onlab898a6c62015-01-16 14:13:53 -08001511 if re.search( "Error", handle ):
kelvin-onlabfb521662015-02-27 09:52:40 -08001512 main.log.error( "Error in adding multipoint-to-singlepoint " +
1513 "intent" )
1514 return None
shahshreyad0c80432014-12-04 16:56:05 -08001515 else:
kelvin-onlabb9408212015-04-01 13:34:04 -07001516 match = re.search('id=0x([\da-f]+),', handle)
1517 if match:
1518 return match.group()[3:-1]
1519 else:
1520 main.log.error( "Error, intent ID not found" )
1521 return None
Jon Hallc6793552016-01-19 14:18:37 -08001522 except AssertionError:
1523 main.log.exception( "" )
1524 return None
kelvin-onlabb9408212015-04-01 13:34:04 -07001525 except TypeError:
1526 main.log.exception( self.name + ": Object not as expected" )
1527 return None
1528 except pexpect.EOF:
1529 main.log.error( self.name + ": EOF exception found" )
1530 main.log.error( self.name + ": " + self.handle.before )
1531 main.cleanup()
1532 main.exit()
1533 except Exception:
1534 main.log.exception( self.name + ": Uncaught exception!" )
1535 main.cleanup()
1536 main.exit()
1537
1538 def addSinglepointToMultipointIntent(
1539 self,
1540 ingressDevice,
1541 egressDeviceList,
1542 portIngress="",
1543 portEgressList=None,
1544 ethType="",
1545 ethSrc="",
1546 ethDst="",
1547 bandwidth="",
1548 lambdaAlloc=False,
1549 ipProto="",
1550 ipSrc="",
1551 ipDst="",
1552 tcpSrc="",
1553 tcpDst="",
1554 setEthSrc="",
Jeremy Songster832f9e92016-05-05 14:30:49 -07001555 setEthDst="",
Jeremy Songsterff553672016-05-12 17:06:23 -07001556 vlanId="",
1557 setVlan="" ):
kelvin-onlabb9408212015-04-01 13:34:04 -07001558 """
1559 Note:
1560 This function assumes the format of all egress devices
1561 is same. That is, all egress devices include port numbers
1562 with a "/" or all egress devices could specify device
1563 ids and port numbers seperately.
1564 Required:
1565 * EgressDeviceList: List of device ids of egress device
1566 ( Atleast 2 eress devices required in the list )
1567 * ingressDevice: device id of ingress device
1568 Optional:
1569 * ethType: specify ethType
1570 * ethSrc: specify ethSrc ( i.e. src mac addr )
1571 * ethDst: specify ethDst ( i.e. dst mac addr )
1572 * bandwidth: specify bandwidth capacity of link
1573 * lambdaAlloc: if True, intent will allocate lambda
1574 for the specified intent
1575 * ipProto: specify ip protocol
1576 * ipSrc: specify ip source address
1577 * ipDst: specify ip destination address
1578 * tcpSrc: specify tcp source port
1579 * tcpDst: specify tcp destination port
1580 * setEthSrc: action to Rewrite Source MAC Address
1581 * setEthDst: action to Rewrite Destination MAC Address
Jeremy Songster832f9e92016-05-05 14:30:49 -07001582 * vlanId: specify vlan Id
Jeremy Songsterff553672016-05-12 17:06:23 -07001583 * setVlan: specify VLAN ID treatment
kelvin-onlabb9408212015-04-01 13:34:04 -07001584 Description:
1585 Adds a singlepoint-to-multipoint intent ( uni-directional ) by
1586 specifying device id's and optional fields
1587 Returns:
1588 A string of the intent id or None on error
1589
1590 NOTE: This function may change depending on the
1591 options developers provide for singlepoint-to-multipoint
1592 intent via cli
1593 """
1594 try:
Jeremy Songsterff553672016-05-12 17:06:23 -07001595 cmd = "add-single-to-multi-intent"
kelvin-onlabb9408212015-04-01 13:34:04 -07001596
Jeremy Songsterff553672016-05-12 17:06:23 -07001597 if ethType:
1598 cmd += " --ethType " + str( ethType )
1599 if ethSrc:
1600 cmd += " --ethSrc " + str( ethSrc )
1601 if ethDst:
1602 cmd += " --ethDst " + str( ethDst )
1603 if bandwidth:
1604 cmd += " --bandwidth " + str( bandwidth )
1605 if lambdaAlloc:
1606 cmd += " --lambda "
1607 if ipProto:
1608 cmd += " --ipProto " + str( ipProto )
1609 if ipSrc:
1610 cmd += " --ipSrc " + str( ipSrc )
1611 if ipDst:
1612 cmd += " --ipDst " + str( ipDst )
1613 if tcpSrc:
1614 cmd += " --tcpSrc " + str( tcpSrc )
1615 if tcpDst:
1616 cmd += " --tcpDst " + str( tcpDst )
1617 if setEthSrc:
1618 cmd += " --setEthSrc " + str( setEthSrc )
1619 if setEthDst:
1620 cmd += " --setEthDst " + str( setEthDst )
1621 if vlanId:
1622 cmd += " -v " + str( vlanId )
1623 if setVlan:
1624 cmd += " --setVlan " + str( setVlan )
kelvin-onlabb9408212015-04-01 13:34:04 -07001625
1626 # Check whether the user appended the port
1627 # or provided it as an input
Jon Hall08f61bc2015-04-13 16:00:30 -07001628
kelvin-onlabb9408212015-04-01 13:34:04 -07001629 if "/" in ingressDevice:
1630 cmd += " " + str( ingressDevice )
1631 else:
1632 if not portIngress:
1633 main.log.error( "You must specify " +
1634 "the Ingress port" )
1635 return main.FALSE
1636
1637 cmd += " " +\
1638 str( ingressDevice ) + "/" +\
1639 str( portIngress )
1640
1641 if portEgressList is None:
1642 for egressDevice in egressDeviceList:
1643 if "/" in egressDevice:
1644 cmd += " " + str( egressDevice )
1645 else:
1646 main.log.error( "You must specify " +
1647 "the egress port" )
1648 # TODO: perhaps more meaningful return
1649 return main.FALSE
1650 else:
1651 if len( egressDeviceList ) == len( portEgressList ):
Jon Hall08f61bc2015-04-13 16:00:30 -07001652 for egressDevice, portEgress in zip( egressDeviceList,
1653 portEgressList ):
kelvin-onlabb9408212015-04-01 13:34:04 -07001654 cmd += " " + \
1655 str( egressDevice ) + "/" +\
1656 str( portEgress )
kelvin-onlab38143812015-04-01 15:03:01 -07001657 else:
Jon Hall08f61bc2015-04-13 16:00:30 -07001658 main.log.error( "Device list and port list does not " +
1659 "have the same length" )
kelvin-onlab38143812015-04-01 15:03:01 -07001660 return main.FALSE
kelvin-onlabb9408212015-04-01 13:34:04 -07001661 handle = self.sendline( cmd )
Jon Hallc6793552016-01-19 14:18:37 -08001662 assert "Command not found:" not in handle, handle
kelvin-onlabb9408212015-04-01 13:34:04 -07001663 # If error, return error message
1664 if re.search( "Error", handle ):
1665 main.log.error( "Error in adding singlepoint-to-multipoint " +
1666 "intent" )
shahshreyac2f97072015-03-19 17:04:29 -07001667 return None
kelvin-onlabb9408212015-04-01 13:34:04 -07001668 else:
1669 match = re.search('id=0x([\da-f]+),', handle)
1670 if match:
1671 return match.group()[3:-1]
1672 else:
1673 main.log.error( "Error, intent ID not found" )
1674 return None
Jon Hallc6793552016-01-19 14:18:37 -08001675 except AssertionError:
1676 main.log.exception( "" )
1677 return None
Jon Halld4d4b372015-01-28 16:02:41 -08001678 except TypeError:
1679 main.log.exception( self.name + ": Object not as expected" )
1680 return None
shahshreyad0c80432014-12-04 16:56:05 -08001681 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001682 main.log.error( self.name + ": EOF exception found" )
1683 main.log.error( self.name + ": " + self.handle.before )
shahshreyad0c80432014-12-04 16:56:05 -08001684 main.cleanup()
1685 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001686 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001687 main.log.exception( self.name + ": Uncaught exception!" )
shahshreyad0c80432014-12-04 16:56:05 -08001688 main.cleanup()
1689 main.exit()
1690
Hari Krishna9e232602015-04-13 17:29:08 -07001691 def addMplsIntent(
1692 self,
1693 ingressDevice,
1694 egressDevice,
Hari Krishna87a17f12015-04-13 17:42:23 -07001695 ingressPort="",
1696 egressPort="",
Hari Krishna9e232602015-04-13 17:29:08 -07001697 ethType="",
1698 ethSrc="",
1699 ethDst="",
1700 bandwidth="",
1701 lambdaAlloc=False,
1702 ipProto="",
1703 ipSrc="",
1704 ipDst="",
1705 tcpSrc="",
1706 tcpDst="",
Hari Krishna87a17f12015-04-13 17:42:23 -07001707 ingressLabel="",
Hari Krishnadfff6672015-04-13 17:53:27 -07001708 egressLabel="",
Hari Krishna9e232602015-04-13 17:29:08 -07001709 priority=""):
1710 """
1711 Required:
1712 * ingressDevice: device id of ingress device
1713 * egressDevice: device id of egress device
1714 Optional:
1715 * ethType: specify ethType
1716 * ethSrc: specify ethSrc ( i.e. src mac addr )
1717 * ethDst: specify ethDst ( i.e. dst mac addr )
1718 * bandwidth: specify bandwidth capacity of link
1719 * lambdaAlloc: if True, intent will allocate lambda
1720 for the specified intent
1721 * ipProto: specify ip protocol
1722 * ipSrc: specify ip source address
1723 * ipDst: specify ip destination address
1724 * tcpSrc: specify tcp source port
1725 * tcpDst: specify tcp destination port
1726 * ingressLabel: Ingress MPLS label
1727 * egressLabel: Egress MPLS label
1728 Description:
1729 Adds MPLS intent by
1730 specifying device id's and optional fields
1731 Returns:
1732 A string of the intent id or None on error
1733
1734 NOTE: This function may change depending on the
1735 options developers provide for MPLS
1736 intent via cli
1737 """
1738 try:
Jeremy Songsterff553672016-05-12 17:06:23 -07001739 cmd = "add-mpls-intent"
Hari Krishna9e232602015-04-13 17:29:08 -07001740
Jeremy Songsterff553672016-05-12 17:06:23 -07001741 if ethType:
1742 cmd += " --ethType " + str( ethType )
1743 if ethSrc:
1744 cmd += " --ethSrc " + str( ethSrc )
1745 if ethDst:
1746 cmd += " --ethDst " + str( ethDst )
1747 if bandwidth:
1748 cmd += " --bandwidth " + str( bandwidth )
1749 if lambdaAlloc:
1750 cmd += " --lambda "
1751 if ipProto:
1752 cmd += " --ipProto " + str( ipProto )
1753 if ipSrc:
1754 cmd += " --ipSrc " + str( ipSrc )
1755 if ipDst:
1756 cmd += " --ipDst " + str( ipDst )
1757 if tcpSrc:
1758 cmd += " --tcpSrc " + str( tcpSrc )
1759 if tcpDst:
1760 cmd += " --tcpDst " + str( tcpDst )
1761 if ingressLabel:
1762 cmd += " --ingressLabel " + str( ingressLabel )
1763 if egressLabel:
1764 cmd += " --egressLabel " + str( egressLabel )
1765 if priority:
1766 cmd += " --priority " + str( priority )
Hari Krishna9e232602015-04-13 17:29:08 -07001767
1768 # Check whether the user appended the port
1769 # or provided it as an input
1770 if "/" in ingressDevice:
1771 cmd += " " + str( ingressDevice )
1772 else:
Hari Krishna87a17f12015-04-13 17:42:23 -07001773 if not ingressPort:
Hari Krishna9e232602015-04-13 17:29:08 -07001774 main.log.error( "You must specify the ingress port" )
1775 return None
1776
1777 cmd += " " + \
1778 str( ingressDevice ) + "/" +\
Hari Krishna87a17f12015-04-13 17:42:23 -07001779 str( ingressPort ) + " "
Hari Krishna9e232602015-04-13 17:29:08 -07001780
1781 if "/" in egressDevice:
1782 cmd += " " + str( egressDevice )
1783 else:
Hari Krishna87a17f12015-04-13 17:42:23 -07001784 if not egressPort:
Hari Krishna9e232602015-04-13 17:29:08 -07001785 main.log.error( "You must specify the egress port" )
1786 return None
1787
1788 cmd += " " +\
1789 str( egressDevice ) + "/" +\
Hari Krishna87a17f12015-04-13 17:42:23 -07001790 str( egressPort )
Hari Krishna9e232602015-04-13 17:29:08 -07001791
1792 handle = self.sendline( cmd )
Jon Hallc6793552016-01-19 14:18:37 -08001793 assert "Command not found:" not in handle, handle
Hari Krishna9e232602015-04-13 17:29:08 -07001794 # If error, return error message
1795 if re.search( "Error", handle ):
1796 main.log.error( "Error in adding mpls intent" )
1797 return None
1798 else:
1799 # TODO: print out all the options in this message?
1800 main.log.info( "MPLS intent installed between " +
1801 str( ingressDevice ) + " and " +
1802 str( egressDevice ) )
1803 match = re.search('id=0x([\da-f]+),', handle)
1804 if match:
1805 return match.group()[3:-1]
1806 else:
1807 main.log.error( "Error, intent ID not found" )
1808 return None
Jon Hallc6793552016-01-19 14:18:37 -08001809 except AssertionError:
1810 main.log.exception( "" )
1811 return None
Hari Krishna9e232602015-04-13 17:29:08 -07001812 except TypeError:
1813 main.log.exception( self.name + ": Object not as expected" )
1814 return None
1815 except pexpect.EOF:
1816 main.log.error( self.name + ": EOF exception found" )
1817 main.log.error( self.name + ": " + self.handle.before )
1818 main.cleanup()
1819 main.exit()
1820 except Exception:
1821 main.log.exception( self.name + ": Uncaught exception!" )
1822 main.cleanup()
1823 main.exit()
1824
Jon Hallefbd9792015-03-05 16:11:36 -08001825 def removeIntent( self, intentId, app='org.onosproject.cli',
1826 purge=False, sync=False ):
kelvin-onlab898a6c62015-01-16 14:13:53 -08001827 """
shahshreya1c818fc2015-02-26 13:44:08 -08001828 Remove intent for specified application id and intent id
Jon Hall61282e32015-03-19 11:34:11 -07001829 Optional args:-
shahshreya1c818fc2015-02-26 13:44:08 -08001830 -s or --sync: Waits for the removal before returning
Jon Hall61282e32015-03-19 11:34:11 -07001831 -p or --purge: Purge the intent from the store after removal
1832
Jon Halle3f39ff2015-01-13 11:50:53 -08001833 Returns:
1834 main.False on error and
1835 cli output otherwise
kelvin-onlab898a6c62015-01-16 14:13:53 -08001836 """
andrewonlab9a50dfe2014-10-17 17:22:31 -04001837 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07001838 cmdStr = "remove-intent"
shahshreya1c818fc2015-02-26 13:44:08 -08001839 if purge:
1840 cmdStr += " -p"
1841 if sync:
1842 cmdStr += " -s"
1843
1844 cmdStr += " " + app + " " + str( intentId )
kelvin-onlabd3b64892015-01-20 13:26:24 -08001845 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08001846 assert "Command not found:" not in handle, handle
Jon Halle3f39ff2015-01-13 11:50:53 -08001847 if re.search( "Error", handle ):
kelvin-onlab898a6c62015-01-16 14:13:53 -08001848 main.log.error( "Error in removing intent" )
Jon Halle3f39ff2015-01-13 11:50:53 -08001849 return main.FALSE
andrewonlab9a50dfe2014-10-17 17:22:31 -04001850 else:
Jon Halle3f39ff2015-01-13 11:50:53 -08001851 # TODO: Should this be main.TRUE
1852 return handle
Jon Hallc6793552016-01-19 14:18:37 -08001853 except AssertionError:
1854 main.log.exception( "" )
1855 return None
Jon Halld4d4b372015-01-28 16:02:41 -08001856 except TypeError:
1857 main.log.exception( self.name + ": Object not as expected" )
1858 return None
andrewonlab9a50dfe2014-10-17 17:22:31 -04001859 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001860 main.log.error( self.name + ": EOF exception found" )
1861 main.log.error( self.name + ": " + self.handle.before )
andrewonlab9a50dfe2014-10-17 17:22:31 -04001862 main.cleanup()
1863 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001864 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001865 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab9a50dfe2014-10-17 17:22:31 -04001866 main.cleanup()
1867 main.exit()
1868
Jeremy42df2e72016-02-23 16:37:46 -08001869 def removeAllIntents( self, purge=False, sync=False, app='org.onosproject.cli' ):
1870 """
1871 Description:
1872 Remove all the intents
1873 Optional args:-
1874 -s or --sync: Waits for the removal before returning
1875 -p or --purge: Purge the intent from the store after removal
1876 Returns:
1877 Returns main.TRUE if all intents are removed, otherwise returns
1878 main.FALSE; Returns None for exception
1879 """
1880 try:
1881 cmdStr = "remove-intent"
1882 if purge:
1883 cmdStr += " -p"
1884 if sync:
1885 cmdStr += " -s"
1886
1887 cmdStr += " " + app
1888 handle = self.sendline( cmdStr )
1889 assert "Command not found:" not in handle, handle
1890 if re.search( "Error", handle ):
1891 main.log.error( "Error in removing intent" )
1892 return main.FALSE
1893 else:
1894 return main.TRUE
1895 except AssertionError:
1896 main.log.exception( "" )
1897 return None
1898 except TypeError:
1899 main.log.exception( self.name + ": Object not as expected" )
1900 return None
1901 except pexpect.EOF:
1902 main.log.error( self.name + ": EOF exception found" )
1903 main.log.error( self.name + ": " + self.handle.before )
1904 main.cleanup()
1905 main.exit()
1906 except Exception:
1907 main.log.exception( self.name + ": Uncaught exception!" )
1908 main.cleanup()
1909 main.exit()
1910
Hari Krishnaacabd5a2015-07-01 17:10:19 -07001911 def purgeWithdrawnIntents( self ):
Hari Krishna0ce0e152015-06-23 09:55:29 -07001912 """
1913 Purges all WITHDRAWN Intents
1914 """
1915 try:
1916 cmdStr = "purge-intents"
1917 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08001918 assert "Command not found:" not in handle, handle
Hari Krishna0ce0e152015-06-23 09:55:29 -07001919 if re.search( "Error", handle ):
1920 main.log.error( "Error in purging intents" )
1921 return main.FALSE
1922 else:
1923 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -08001924 except AssertionError:
1925 main.log.exception( "" )
1926 return None
Hari Krishna0ce0e152015-06-23 09:55:29 -07001927 except TypeError:
1928 main.log.exception( self.name + ": Object not as expected" )
1929 return None
1930 except pexpect.EOF:
1931 main.log.error( self.name + ": EOF exception found" )
1932 main.log.error( self.name + ": " + self.handle.before )
1933 main.cleanup()
1934 main.exit()
1935 except Exception:
1936 main.log.exception( self.name + ": Uncaught exception!" )
1937 main.cleanup()
1938 main.exit()
1939
kelvin-onlabd3b64892015-01-20 13:26:24 -08001940 def routes( self, jsonFormat=False ):
kelvin8ec71442015-01-15 16:57:00 -08001941 """
kelvin-onlab898a6c62015-01-16 14:13:53 -08001942 NOTE: This method should be used after installing application:
1943 onos-app-sdnip
pingping-lin8b306ac2014-11-17 18:13:51 -08001944 Optional:
kelvin-onlabd3b64892015-01-20 13:26:24 -08001945 * jsonFormat: enable output formatting in json
pingping-lin8b306ac2014-11-17 18:13:51 -08001946 Description:
1947 Obtain all routes in the system
kelvin8ec71442015-01-15 16:57:00 -08001948 """
pingping-lin8b306ac2014-11-17 18:13:51 -08001949 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07001950 cmdStr = "routes"
kelvin-onlabd3b64892015-01-20 13:26:24 -08001951 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -07001952 cmdStr += " -j"
1953 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08001954 assert "Command not found:" not in handle, handle
pingping-lin8b306ac2014-11-17 18:13:51 -08001955 return handle
Jon Hallc6793552016-01-19 14:18:37 -08001956 except AssertionError:
1957 main.log.exception( "" )
1958 return None
Jon Halld4d4b372015-01-28 16:02:41 -08001959 except TypeError:
1960 main.log.exception( self.name + ": Object not as expected" )
1961 return None
pingping-lin8b306ac2014-11-17 18:13:51 -08001962 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08001963 main.log.error( self.name + ": EOF exception found" )
1964 main.log.error( self.name + ": " + self.handle.before )
pingping-lin8b306ac2014-11-17 18:13:51 -08001965 main.cleanup()
1966 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08001967 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08001968 main.log.exception( self.name + ": Uncaught exception!" )
pingping-lin8b306ac2014-11-17 18:13:51 -08001969 main.cleanup()
1970 main.exit()
1971
pingping-lin54b03372015-08-13 14:43:10 -07001972 def ipv4RouteNumber( self ):
1973 """
1974 NOTE: This method should be used after installing application:
1975 onos-app-sdnip
1976 Description:
1977 Obtain the total IPv4 routes number in the system
1978 """
1979 try:
1980 cmdStr = "routes -s -j"
1981 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08001982 assert "Command not found:" not in handle, handle
pingping-lin54b03372015-08-13 14:43:10 -07001983 jsonResult = json.loads( handle )
1984 return jsonResult['totalRoutes4']
Jon Hallc6793552016-01-19 14:18:37 -08001985 except AssertionError:
1986 main.log.exception( "" )
1987 return None
1988 except ( TypeError, ValueError ):
1989 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, handle ) )
pingping-lin54b03372015-08-13 14:43:10 -07001990 return None
1991 except pexpect.EOF:
1992 main.log.error( self.name + ": EOF exception found" )
1993 main.log.error( self.name + ": " + self.handle.before )
1994 main.cleanup()
1995 main.exit()
1996 except Exception:
1997 main.log.exception( self.name + ": Uncaught exception!" )
1998 main.cleanup()
1999 main.exit()
2000
pingping-lin8244a3b2015-09-16 13:36:56 -07002001 def intents( self, jsonFormat = True, summary = False, **intentargs):
kelvin8ec71442015-01-15 16:57:00 -08002002 """
andrewonlabe6745342014-10-17 14:29:13 -04002003 Description:
Jon Hallff566d52016-01-15 14:45:36 -08002004 Obtain intents from the ONOS cli.
2005 Optional:
2006 * jsonFormat: Enable output formatting in json, default to True
2007 * summary: Whether only output the intent summary, defaults to False
2008 * type: Only output a certain type of intent. This options is valid
2009 only when jsonFormat is True and summary is True.
kelvin-onlab898a6c62015-01-16 14:13:53 -08002010 """
andrewonlabe6745342014-10-17 14:29:13 -04002011 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07002012 cmdStr = "intents"
pingping-lin8244a3b2015-09-16 13:36:56 -07002013 if summary:
2014 cmdStr += " -s"
kelvin-onlabd3b64892015-01-20 13:26:24 -08002015 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -07002016 cmdStr += " -j"
2017 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08002018 assert "Command not found:" not in handle, handle
pingping-lin8244a3b2015-09-16 13:36:56 -07002019 args = utilities.parse_args( [ "TYPE" ], **intentargs )
acsmars5b5fbaf2015-09-18 10:38:20 -07002020 if "TYPE" in args.keys():
Jon Hallff566d52016-01-15 14:45:36 -08002021 intentType = args[ "TYPE" ]
acsmars5b5fbaf2015-09-18 10:38:20 -07002022 else:
Jon Hallff566d52016-01-15 14:45:36 -08002023 intentType = ""
2024 # IF we want the summary of a specific intent type
2025 if jsonFormat and summary and ( intentType != "" ):
pingping-lin8244a3b2015-09-16 13:36:56 -07002026 jsonResult = json.loads( handle )
Jon Hallff566d52016-01-15 14:45:36 -08002027 if intentType in jsonResult.keys():
2028 return jsonResult[ intentType ]
pingping-lin8244a3b2015-09-16 13:36:56 -07002029 else:
Jon Hallff566d52016-01-15 14:45:36 -08002030 main.log.error( "unknown TYPE, returning all types of intents" )
pingping-lin8244a3b2015-09-16 13:36:56 -07002031 return handle
2032 else:
2033 return handle
Jon Hallc6793552016-01-19 14:18:37 -08002034 except AssertionError:
2035 main.log.exception( "" )
2036 return None
2037 except ( TypeError, ValueError ):
2038 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, handle ) )
pingping-lin54b03372015-08-13 14:43:10 -07002039 return None
2040 except pexpect.EOF:
2041 main.log.error( self.name + ": EOF exception found" )
2042 main.log.error( self.name + ": " + self.handle.before )
2043 main.cleanup()
2044 main.exit()
2045 except Exception:
2046 main.log.exception( self.name + ": Uncaught exception!" )
2047 main.cleanup()
2048 main.exit()
2049
kelvin-onlab54400a92015-02-26 18:05:51 -08002050 def getIntentState(self, intentsId, intentsJson=None):
2051 """
You Wangfdcbfc42016-05-16 12:16:53 -07002052 Description:
2053 Gets intent state. Accepts a single intent ID (string type) or a
2054 list of intent IDs.
2055 Parameters:
2056 intentsId: intent ID, both string type and list type are acceptable
kelvin-onlab54400a92015-02-26 18:05:51 -08002057 intentsJson: parsed json object from the onos:intents api
You Wangfdcbfc42016-05-16 12:16:53 -07002058 Returns:
2059 Returns the state (string type) of the ID if a single intent ID is
2060 accepted.
2061 Returns a list of dictionaries if a list of intent IDs is accepted,
2062 and each dictionary maps 'id' to the Intent ID and 'state' to
2063 corresponding intent state.
kelvin-onlab54400a92015-02-26 18:05:51 -08002064 """
kelvin-onlab54400a92015-02-26 18:05:51 -08002065 try:
2066 state = "State is Undefined"
2067 if not intentsJson:
Jon Hallc6793552016-01-19 14:18:37 -08002068 rawJson = self.intents()
kelvin-onlab54400a92015-02-26 18:05:51 -08002069 else:
Jon Hallc6793552016-01-19 14:18:37 -08002070 rawJson = intentsJson
2071 parsedIntentsJson = json.loads( rawJson )
Jon Hallefbd9792015-03-05 16:11:36 -08002072 if isinstance( intentsId, types.StringType ):
Jon Hallc6793552016-01-19 14:18:37 -08002073 for intent in parsedIntentsJson:
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002074 if intentsId == intent[ 'id' ]:
2075 state = intent[ 'state' ]
kelvin-onlab54400a92015-02-26 18:05:51 -08002076 return state
Jon Hallefbd9792015-03-05 16:11:36 -08002077 main.log.info( "Cannot find intent ID" + str( intentsId ) +
2078 " on the list" )
kelvin-onlab54400a92015-02-26 18:05:51 -08002079 return state
Jon Hallefbd9792015-03-05 16:11:36 -08002080 elif isinstance( intentsId, types.ListType ):
kelvin-onlab07dbd012015-03-04 16:29:39 -08002081 dictList = []
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002082 for i in xrange( len( intentsId ) ):
kelvin-onlab07dbd012015-03-04 16:29:39 -08002083 stateDict = {}
Jon Hallc6793552016-01-19 14:18:37 -08002084 for intents in parsedIntentsJson:
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002085 if intentsId[ i ] == intents[ 'id' ]:
2086 stateDict[ 'state' ] = intents[ 'state' ]
2087 stateDict[ 'id' ] = intentsId[ i ]
Jon Hallefbd9792015-03-05 16:11:36 -08002088 dictList.append( stateDict )
kelvin-onlab54400a92015-02-26 18:05:51 -08002089 break
Jon Hallefbd9792015-03-05 16:11:36 -08002090 if len( intentsId ) != len( dictList ):
2091 main.log.info( "Cannot find some of the intent ID state" )
kelvin-onlab07dbd012015-03-04 16:29:39 -08002092 return dictList
kelvin-onlab54400a92015-02-26 18:05:51 -08002093 else:
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002094 main.log.info( "Invalid intents ID entry" )
kelvin-onlab54400a92015-02-26 18:05:51 -08002095 return None
Jon Hallc6793552016-01-19 14:18:37 -08002096 except ( TypeError, ValueError ):
2097 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, rawJson ) )
kelvin-onlab54400a92015-02-26 18:05:51 -08002098 return None
2099 except pexpect.EOF:
2100 main.log.error( self.name + ": EOF exception found" )
2101 main.log.error( self.name + ": " + self.handle.before )
2102 main.cleanup()
2103 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002104 except Exception:
kelvin-onlab54400a92015-02-26 18:05:51 -08002105 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlabe6745342014-10-17 14:29:13 -04002106 main.cleanup()
2107 main.exit()
Jon Hall390696c2015-05-05 17:13:41 -07002108
kelvin-onlabf512e942015-06-08 19:42:59 -07002109 def checkIntentState( self, intentsId, expectedState='INSTALLED' ):
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002110 """
2111 Description:
2112 Check intents state
2113 Required:
2114 intentsId - List of intents ID to be checked
2115 Optional:
kelvin-onlabf512e942015-06-08 19:42:59 -07002116 expectedState - Check the expected state(s) of each intents
2117 state in the list.
2118 *NOTE: You can pass in a list of expected state,
2119 Eg: expectedState = [ 'INSTALLED' , 'INSTALLING' ]
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002120 Return:
kelvin-onlabf512e942015-06-08 19:42:59 -07002121 Returns main.TRUE only if all intent are the same as expected states
2122 , otherwise, returns main.FALSE.
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002123 """
2124 try:
2125 # Generating a dictionary: intent id as a key and state as value
kelvin-onlabf512e942015-06-08 19:42:59 -07002126 returnValue = main.TRUE
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002127 intentsDict = self.getIntentState( intentsId )
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002128 if len( intentsId ) != len( intentsDict ):
Jon Hallae04e622016-01-27 10:38:05 -08002129 main.log.info( self.name + ": There is something wrong " +
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002130 "getting intents state" )
2131 return main.FALSE
kelvin-onlabf512e942015-06-08 19:42:59 -07002132
2133 if isinstance( expectedState, types.StringType ):
2134 for intents in intentsDict:
2135 if intents.get( 'state' ) != expectedState:
kelvin-onlaba297c4d2015-06-01 13:53:55 -07002136 main.log.debug( self.name + " : Intent ID - " +
2137 intents.get( 'id' ) +
kelvin-onlabf512e942015-06-08 19:42:59 -07002138 " actual state = " +
2139 intents.get( 'state' )
2140 + " does not equal expected state = "
2141 + expectedState )
kelvin-onlaba297c4d2015-06-01 13:53:55 -07002142 returnValue = main.FALSE
kelvin-onlabf512e942015-06-08 19:42:59 -07002143
2144 elif isinstance( expectedState, types.ListType ):
2145 for intents in intentsDict:
2146 if not any( state == intents.get( 'state' ) for state in
2147 expectedState ):
2148 main.log.debug( self.name + " : Intent ID - " +
2149 intents.get( 'id' ) +
2150 " actual state = " +
2151 intents.get( 'state' ) +
2152 " does not equal expected states = "
2153 + str( expectedState ) )
2154 returnValue = main.FALSE
2155
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002156 if returnValue == main.TRUE:
2157 main.log.info( self.name + ": All " +
2158 str( len( intentsDict ) ) +
kelvin-onlabf512e942015-06-08 19:42:59 -07002159 " intents are in " + str( expectedState ) +
2160 " state" )
kelvin-onlabc2dcd3f2015-04-09 16:40:02 -07002161 return returnValue
2162 except TypeError:
2163 main.log.exception( self.name + ": Object not as expected" )
2164 return None
2165 except pexpect.EOF:
2166 main.log.error( self.name + ": EOF exception found" )
2167 main.log.error( self.name + ": " + self.handle.before )
2168 main.cleanup()
2169 main.exit()
2170 except Exception:
2171 main.log.exception( self.name + ": Uncaught exception!" )
2172 main.cleanup()
2173 main.exit()
andrewonlabe6745342014-10-17 14:29:13 -04002174
You Wang66518af2016-05-16 15:32:59 -07002175 def compareIntent( self, intentDict ):
2176 """
2177 Description:
2178 Compare the intent ids and states provided in the argument with all intents in ONOS
2179 Return:
2180 Returns main.TRUE if the two sets of intents match exactly, otherwise main.FALSE
2181 Arguments:
2182 intentDict: a dictionary which maps intent ids to intent states
2183 """
2184 try:
2185 intentsRaw = self.intents()
2186 intentsJson = json.loads( intentsRaw )
2187 intentDictONOS = {}
2188 for intent in intentsJson:
2189 intentDictONOS[ intent[ 'id' ] ] = intent[ 'state' ]
2190 if len( intentDict ) != len( intentDictONOS ):
2191 main.log.info( self.name + ": expected intent count does not match that in ONOS, " +
2192 str( len( intentDict ) ) + " expected and " +
2193 str( len( intentDictONOS ) ) + " actual" )
2194 return main.FALSE
2195 returnValue = main.TRUE
2196 for intentID in intentDict.keys():
2197 if not intentID in intentDictONOS.keys():
2198 main.log.debug( self.name + ": intent ID - " + intentID + " is not in ONOS" )
2199 returnValue = main.FALSE
2200 elif intentDict[ intentID ] != intentDictONOS[ intentID ]:
2201 main.log.debug( self.name + ": intent ID - " + intentID +
2202 " expected state is " + intentDict[ intentID ] +
2203 " but actual state is " + intentDictONOS[ intentID ] )
2204 returnValue = main.FALSE
2205 if returnValue == main.TRUE:
2206 main.log.info( self.name + ": all intent IDs and states match that in ONOS" )
2207 return returnValue
You Wang1be9a512016-05-26 16:54:17 -07002208 except KeyError:
2209 main.log.exception( self.name + ": KeyError exception found" )
2210 return main.ERROR
You Wang66518af2016-05-16 15:32:59 -07002211 except ( TypeError, ValueError ):
2212 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, intentsRaw ) )
You Wang85560372016-05-18 10:44:33 -07002213 return main.ERROR
You Wang66518af2016-05-16 15:32:59 -07002214 except pexpect.EOF:
2215 main.log.error( self.name + ": EOF exception found" )
2216 main.log.error( self.name + ": " + self.handle.before )
2217 main.cleanup()
2218 main.exit()
2219 except Exception:
2220 main.log.exception( self.name + ": Uncaught exception!" )
2221 main.cleanup()
2222 main.exit()
2223
GlennRCed771242016-01-13 17:02:47 -08002224 def checkIntentSummary( self, timeout=60 ):
2225 """
2226 Description:
2227 Check the number of installed intents.
2228 Optional:
2229 timeout - the timeout for pexcept
2230 Return:
2231 Returns main.TRUE only if the number of all installed intents are the same as total intents number
2232 , otherwise, returns main.FALSE.
2233 """
2234
2235 try:
2236 cmd = "intents -s -j"
2237
2238 # Check response if something wrong
2239 response = self.sendline( cmd, timeout=timeout )
2240 if response == None:
2241 return main.False
2242 response = json.loads( response )
2243
2244 # get total and installed number, see if they are match
2245 allState = response.get( 'all' )
2246 if allState.get('total') == allState.get('installed'):
YPZhangb5d3f832016-01-23 22:54:26 -08002247 main.log.info( 'Total Intents: {} Installed Intents: {}'.format( allState.get('total'), allState.get('installed') ) )
GlennRCed771242016-01-13 17:02:47 -08002248 return main.TRUE
YPZhangb5d3f832016-01-23 22:54:26 -08002249 main.log.info( 'Verified Intents failed Excepte intetnes: {} installed intents: {}'.format( allState.get('total'), allState.get('installed') ) )
GlennRCed771242016-01-13 17:02:47 -08002250 return main.FALSE
2251
Jon Hallc6793552016-01-19 14:18:37 -08002252 except ( TypeError, ValueError ):
2253 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, response ) )
GlennRCed771242016-01-13 17:02:47 -08002254 return None
2255 except pexpect.EOF:
2256 main.log.error( self.name + ": EOF exception found" )
2257 main.log.error( self.name + ": " + self.handle.before )
2258 main.cleanup()
2259 main.exit()
2260 except Exception:
2261 main.log.exception( self.name + ": Uncaught exception!" )
2262 main.cleanup()
2263 main.exit()
YPZhangebf9eb52016-05-12 15:20:24 -07002264 except pexpect.TIMEOUT:
2265 main.log.error( self.name + ": ONOS timeout" )
2266 return None
GlennRCed771242016-01-13 17:02:47 -08002267
YPZhangebf9eb52016-05-12 15:20:24 -07002268 def flows( self, state="", jsonFormat=True, timeout=60, noExit=False ):
kelvin8ec71442015-01-15 16:57:00 -08002269 """
Shreya Shah0f01c812014-10-26 20:15:28 -04002270 Optional:
kelvin-onlabd3b64892015-01-20 13:26:24 -08002271 * jsonFormat: enable output formatting in json
Shreya Shah0f01c812014-10-26 20:15:28 -04002272 Description:
Jon Halle3f39ff2015-01-13 11:50:53 -08002273 Obtain flows currently installed
kelvin-onlab898a6c62015-01-16 14:13:53 -08002274 """
Shreya Shah0f01c812014-10-26 20:15:28 -04002275 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07002276 cmdStr = "flows"
kelvin-onlabd3b64892015-01-20 13:26:24 -08002277 if jsonFormat:
GlennRCed771242016-01-13 17:02:47 -08002278 cmdStr += " -j "
2279 cmdStr += state
YPZhangebf9eb52016-05-12 15:20:24 -07002280 handle = self.sendline( cmdStr, timeout=timeout, noExit=noExit )
Jon Hallc6793552016-01-19 14:18:37 -08002281 assert "Command not found:" not in handle, handle
2282 if re.search( "Error:", handle ):
2283 main.log.error( self.name + ": flows() response: " +
2284 str( handle ) )
2285 return handle
2286 except AssertionError:
2287 main.log.exception( "" )
GlennRCed771242016-01-13 17:02:47 -08002288 return None
Jon Halld4d4b372015-01-28 16:02:41 -08002289 except TypeError:
2290 main.log.exception( self.name + ": Object not as expected" )
2291 return None
Jon Hallc6793552016-01-19 14:18:37 -08002292 except pexpect.TIMEOUT:
2293 main.log.error( self.name + ": ONOS timeout" )
2294 return None
Shreya Shah0f01c812014-10-26 20:15:28 -04002295 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002296 main.log.error( self.name + ": EOF exception found" )
2297 main.log.error( self.name + ": " + self.handle.before )
Shreya Shah0f01c812014-10-26 20:15:28 -04002298 main.cleanup()
2299 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002300 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002301 main.log.exception( self.name + ": Uncaught exception!" )
Shreya Shah0f01c812014-10-26 20:15:28 -04002302 main.cleanup()
2303 main.exit()
2304
Flavio Castrod2ffffa2016-04-26 15:56:56 -07002305 def checkFlowCount(self, min=0, timeout=60 ):
2306 count = int(self.getTotalFlowsNum( timeout=timeout ))
2307 return count if (count > min) else False
GlennRCed771242016-01-13 17:02:47 -08002308
YPZhangebf9eb52016-05-12 15:20:24 -07002309 def checkFlowsState( self, isPENDING=True, timeout=60,noExit=False ):
kelvin-onlab4df89f22015-04-13 18:10:23 -07002310 """
2311 Description:
GlennRCed771242016-01-13 17:02:47 -08002312 Check the if all the current flows are in ADDED state
Jon Hallc6793552016-01-19 14:18:37 -08002313 We check PENDING_ADD, PENDING_REMOVE, REMOVED, and FAILED flows,
2314 if the count of those states is 0, which means all current flows
2315 are in ADDED state, and return main.TRUE otherwise return main.FALSE
pingping-linbab7f8a2015-09-21 17:33:36 -07002316 Optional:
GlennRCed771242016-01-13 17:02:47 -08002317 * isPENDING: whether the PENDING_ADD is also a correct status
kelvin-onlab4df89f22015-04-13 18:10:23 -07002318 Return:
2319 returnValue - Returns main.TRUE only if all flows are in
Jon Hallc6793552016-01-19 14:18:37 -08002320 ADDED state or PENDING_ADD if the isPENDING
pingping-linbab7f8a2015-09-21 17:33:36 -07002321 parameter is set true, return main.FALSE otherwise.
kelvin-onlab4df89f22015-04-13 18:10:23 -07002322 """
2323 try:
GlennRCed771242016-01-13 17:02:47 -08002324 states = ["PENDING_ADD", "PENDING_REMOVE", "REMOVED", "FAILED"]
2325 checkedStates = []
2326 statesCount = [0, 0, 0, 0]
2327 for s in states:
Jon Hallc6793552016-01-19 14:18:37 -08002328 rawFlows = self.flows( state=s, timeout = timeout )
YPZhang240842b2016-05-17 12:00:50 -07002329 if rawFlows:
2330 # if we didn't get flows or flows function return None, we should return
2331 # main.Flase
2332 checkedStates.append( json.loads( rawFlows ) )
2333 else:
2334 return main.FALSE
Jon Hallc6793552016-01-19 14:18:37 -08002335 for i in range( len( states ) ):
GlennRCed771242016-01-13 17:02:47 -08002336 for c in checkedStates[i]:
Jon Hallc6793552016-01-19 14:18:37 -08002337 try:
2338 statesCount[i] += int( c.get( "flowCount" ) )
2339 except TypeError:
2340 main.log.exception( "Json object not as expected" )
2341 main.log.info( states[i] + " flows: " + str( statesCount[i] ) )
kelvin-onlabf2ec6e02015-05-27 14:15:28 -07002342
GlennRCed771242016-01-13 17:02:47 -08002343 # We want to count PENDING_ADD if isPENDING is true
2344 if isPENDING:
2345 if statesCount[1] + statesCount[2] + statesCount[3] > 0:
2346 return main.FALSE
pingping-linbab7f8a2015-09-21 17:33:36 -07002347 else:
GlennRCed771242016-01-13 17:02:47 -08002348 if statesCount[0] + statesCount[1] + statesCount[2] + statesCount[3] > 0:
2349 return main.FALSE
GlennRCed771242016-01-13 17:02:47 -08002350 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -08002351 except ( TypeError, ValueError ):
2352 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, rawFlows ) )
kelvin-onlab4df89f22015-04-13 18:10:23 -07002353 return None
YPZhang240842b2016-05-17 12:00:50 -07002354
2355 except AssertionError:
2356 main.log.exception( "" )
2357 return None
kelvin-onlab4df89f22015-04-13 18:10:23 -07002358 except pexpect.EOF:
2359 main.log.error( self.name + ": EOF exception found" )
2360 main.log.error( self.name + ": " + self.handle.before )
2361 main.cleanup()
2362 main.exit()
2363 except Exception:
2364 main.log.exception( self.name + ": Uncaught exception!" )
2365 main.cleanup()
2366 main.exit()
YPZhangebf9eb52016-05-12 15:20:24 -07002367 except pexpect.TIMEOUT:
2368 main.log.error( self.name + ": ONOS timeout" )
2369 return None
2370
kelvin-onlab4df89f22015-04-13 18:10:23 -07002371
GlennRCed771242016-01-13 17:02:47 -08002372 def pushTestIntents( self, ingress, egress, batchSize, offset="",
YPZhangebf9eb52016-05-12 15:20:24 -07002373 options="", timeout=10, background = False, noExit=False ):
kelvin8ec71442015-01-15 16:57:00 -08002374 """
andrewonlab87852b02014-11-19 18:44:19 -05002375 Description:
Jon Halle3f39ff2015-01-13 11:50:53 -08002376 Push a number of intents in a batch format to
andrewonlab87852b02014-11-19 18:44:19 -05002377 a specific point-to-point intent definition
2378 Required:
GlennRCed771242016-01-13 17:02:47 -08002379 * ingress: specify source dpid
2380 * egress: specify destination dpid
2381 * batchSize: specify number of intents to push
andrewonlab87852b02014-11-19 18:44:19 -05002382 Optional:
GlennRCed771242016-01-13 17:02:47 -08002383 * offset: the keyOffset is where the next batch of intents
2384 will be installed
2385 Returns: If failed to push test intents, it will returen None,
2386 if successful, return true.
2387 Timeout expection will return None,
2388 TypeError will return false
2389 other expections will exit()
kelvin8ec71442015-01-15 16:57:00 -08002390 """
andrewonlab87852b02014-11-19 18:44:19 -05002391 try:
GlennRCed771242016-01-13 17:02:47 -08002392 if background:
2393 back = "&"
andrewonlab87852b02014-11-19 18:44:19 -05002394 else:
GlennRCed771242016-01-13 17:02:47 -08002395 back = ""
2396 cmd = "push-test-intents {} {} {} {} {} {}".format( options,
Jon Hallc6793552016-01-19 14:18:37 -08002397 ingress,
2398 egress,
2399 batchSize,
2400 offset,
2401 back )
YPZhangebf9eb52016-05-12 15:20:24 -07002402 response = self.sendline( cmd, timeout=timeout, noExit=noExit )
Jon Hallc6793552016-01-19 14:18:37 -08002403 assert "Command not found:" not in response, response
GlennRCed771242016-01-13 17:02:47 -08002404 main.log.info( response )
2405 if response == None:
2406 return None
2407
2408 # TODO: We should handle if there is failure in installation
2409 return main.TRUE
2410
Jon Hallc6793552016-01-19 14:18:37 -08002411 except AssertionError:
2412 main.log.exception( "" )
2413 return None
GlennRCed771242016-01-13 17:02:47 -08002414 except pexpect.TIMEOUT:
2415 main.log.error( self.name + ": ONOS timeout" )
Jon Halld4d4b372015-01-28 16:02:41 -08002416 return None
andrewonlab87852b02014-11-19 18:44:19 -05002417 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002418 main.log.error( self.name + ": EOF exception found" )
2419 main.log.error( self.name + ": " + self.handle.before )
andrewonlab87852b02014-11-19 18:44:19 -05002420 main.cleanup()
2421 main.exit()
GlennRCed771242016-01-13 17:02:47 -08002422 except TypeError:
2423 main.log.exception( self.name + ": Object not as expected" )
Jon Hallc6793552016-01-19 14:18:37 -08002424 return None
Jon Hallfebb1c72015-03-05 13:30:09 -08002425 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002426 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab87852b02014-11-19 18:44:19 -05002427 main.cleanup()
2428 main.exit()
2429
YPZhangebf9eb52016-05-12 15:20:24 -07002430 def getTotalFlowsNum( self, timeout=60, noExit=False ):
YPZhangb5d3f832016-01-23 22:54:26 -08002431 """
2432 Description:
YPZhangf6f14a02016-01-28 15:17:31 -08002433 Get the number of ADDED flows.
YPZhangb5d3f832016-01-23 22:54:26 -08002434 Return:
YPZhangf6f14a02016-01-28 15:17:31 -08002435 The number of ADDED flows
YPZhangb5d3f832016-01-23 22:54:26 -08002436 """
YPZhange3109a72016-02-02 11:25:37 -08002437
YPZhangb5d3f832016-01-23 22:54:26 -08002438 try:
YPZhange3109a72016-02-02 11:25:37 -08002439 # get total added flows number
YPZhangf6f14a02016-01-28 15:17:31 -08002440 cmd = "flows -s|grep ADDED|wc -l"
YPZhangebf9eb52016-05-12 15:20:24 -07002441 totalFlows = self.sendline( cmd, timeout=timeout, noExit=noExit )
YPZhange3109a72016-02-02 11:25:37 -08002442
2443 if totalFlows == None:
2444 # if timeout, we will get total number of all flows, and subtract other states
2445 states = ["PENDING_ADD", "PENDING_REMOVE", "REMOVED", "FAILED"]
2446 checkedStates = []
2447 totalFlows = 0
2448 statesCount = [0, 0, 0, 0]
2449
2450 # get total flows from summary
YPZhangebf9eb52016-05-12 15:20:24 -07002451 response = json.loads( self.sendline( "summary -j", timeout=timeout, noExit=noExit ) )
YPZhange3109a72016-02-02 11:25:37 -08002452 totalFlows = int( response.get("flows") )
2453
2454 for s in states:
2455 rawFlows = self.flows( state=s, timeout = timeout )
2456 if rawFlows == None:
2457 # if timeout, return the total flows number from summary command
2458 return totalFlows
2459 checkedStates.append( json.loads( rawFlows ) )
2460
2461 # Calculate ADDED flows number, equal total subtracts others
2462 for i in range( len( states ) ):
2463 for c in checkedStates[i]:
2464 try:
2465 statesCount[i] += int( c.get( "flowCount" ) )
2466 except TypeError:
2467 main.log.exception( "Json object not as expected" )
2468 totalFlows = totalFlows - int( statesCount[i] )
2469 main.log.info( states[i] + " flows: " + str( statesCount[i] ) )
2470
2471 return totalFlows
2472
Flavio Castrod2ffffa2016-04-26 15:56:56 -07002473 return int(totalFlows)
YPZhange3109a72016-02-02 11:25:37 -08002474
You Wangd3cb2ce2016-05-16 14:01:24 -07002475 except ( TypeError, ValueError ):
2476 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, rawFlows ) )
YPZhangb5d3f832016-01-23 22:54:26 -08002477 return None
2478 except pexpect.EOF:
2479 main.log.error( self.name + ": EOF exception found" )
2480 main.log.error( self.name + ": " + self.handle.before )
2481 main.cleanup()
2482 main.exit()
2483 except Exception:
2484 main.log.exception( self.name + ": Uncaught exception!" )
2485 main.cleanup()
2486 main.exit()
YPZhangebf9eb52016-05-12 15:20:24 -07002487 except pexpect.TIMEOUT:
2488 main.log.error( self.name + ": ONOS timeout" )
2489 return None
YPZhangb5d3f832016-01-23 22:54:26 -08002490
YPZhangebf9eb52016-05-12 15:20:24 -07002491 def getTotalIntentsNum( self, timeout=60 ):
YPZhangb5d3f832016-01-23 22:54:26 -08002492 """
2493 Description:
2494 Get the total number of intents, include every states.
2495 Return:
2496 The number of intents
2497 """
2498 try:
2499 cmd = "summary -j"
YPZhangebf9eb52016-05-12 15:20:24 -07002500 response = self.sendline( cmd, timeout=timeout )
YPZhangb5d3f832016-01-23 22:54:26 -08002501 if response == None:
2502 return -1
2503 response = json.loads( response )
2504 return int( response.get("intents") )
You Wangd3cb2ce2016-05-16 14:01:24 -07002505 except ( TypeError, ValueError ):
2506 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, response ) )
YPZhangb5d3f832016-01-23 22:54:26 -08002507 return None
2508 except pexpect.EOF:
2509 main.log.error( self.name + ": EOF exception found" )
2510 main.log.error( self.name + ": " + self.handle.before )
2511 main.cleanup()
2512 main.exit()
2513 except Exception:
2514 main.log.exception( self.name + ": Uncaught exception!" )
2515 main.cleanup()
2516 main.exit()
2517
kelvin-onlabd3b64892015-01-20 13:26:24 -08002518 def intentsEventsMetrics( self, jsonFormat=True ):
kelvin8ec71442015-01-15 16:57:00 -08002519 """
Jon Halle3f39ff2015-01-13 11:50:53 -08002520 Description:Returns topology metrics
andrewonlab0dbb6ec2014-11-06 13:46:55 -05002521 Optional:
kelvin-onlabd3b64892015-01-20 13:26:24 -08002522 * jsonFormat: enable json formatting of output
kelvin8ec71442015-01-15 16:57:00 -08002523 """
andrewonlab0dbb6ec2014-11-06 13:46:55 -05002524 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07002525 cmdStr = "intents-events-metrics"
kelvin-onlabd3b64892015-01-20 13:26:24 -08002526 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -07002527 cmdStr += " -j"
2528 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08002529 assert "Command not found:" not in handle, handle
andrewonlab0dbb6ec2014-11-06 13:46:55 -05002530 return handle
Jon Hallc6793552016-01-19 14:18:37 -08002531 except AssertionError:
2532 main.log.exception( "" )
2533 return None
Jon Halld4d4b372015-01-28 16:02:41 -08002534 except TypeError:
2535 main.log.exception( self.name + ": Object not as expected" )
2536 return None
andrewonlab0dbb6ec2014-11-06 13:46:55 -05002537 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002538 main.log.error( self.name + ": EOF exception found" )
2539 main.log.error( self.name + ": " + self.handle.before )
andrewonlab0dbb6ec2014-11-06 13:46:55 -05002540 main.cleanup()
2541 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002542 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002543 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab0dbb6ec2014-11-06 13:46:55 -05002544 main.cleanup()
2545 main.exit()
Shreya Shah0f01c812014-10-26 20:15:28 -04002546
kelvin-onlabd3b64892015-01-20 13:26:24 -08002547 def topologyEventsMetrics( self, jsonFormat=True ):
kelvin8ec71442015-01-15 16:57:00 -08002548 """
2549 Description:Returns topology metrics
andrewonlab867212a2014-10-22 20:13:38 -04002550 Optional:
kelvin-onlabd3b64892015-01-20 13:26:24 -08002551 * jsonFormat: enable json formatting of output
kelvin8ec71442015-01-15 16:57:00 -08002552 """
andrewonlab867212a2014-10-22 20:13:38 -04002553 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07002554 cmdStr = "topology-events-metrics"
kelvin-onlabd3b64892015-01-20 13:26:24 -08002555 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -07002556 cmdStr += " -j"
2557 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08002558 assert "Command not found:" not in handle, handle
jenkins7ead5a82015-03-13 10:28:21 -07002559 if handle:
2560 return handle
Jon Hallc6358dd2015-04-10 12:44:28 -07002561 elif jsonFormat:
Jon Hallbe379602015-03-24 13:39:32 -07002562 # Return empty json
jenkins7ead5a82015-03-13 10:28:21 -07002563 return '{}'
Jon Hallc6358dd2015-04-10 12:44:28 -07002564 else:
2565 return handle
Jon Hallc6793552016-01-19 14:18:37 -08002566 except AssertionError:
2567 main.log.exception( "" )
2568 return None
Jon Halld4d4b372015-01-28 16:02:41 -08002569 except TypeError:
2570 main.log.exception( self.name + ": Object not as expected" )
2571 return None
andrewonlab867212a2014-10-22 20:13:38 -04002572 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002573 main.log.error( self.name + ": EOF exception found" )
2574 main.log.error( self.name + ": " + self.handle.before )
andrewonlab867212a2014-10-22 20:13:38 -04002575 main.cleanup()
2576 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002577 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002578 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab867212a2014-10-22 20:13:38 -04002579 main.cleanup()
2580 main.exit()
2581
kelvin8ec71442015-01-15 16:57:00 -08002582 # Wrapper functions ****************
2583 # Wrapper functions use existing driver
2584 # functions and extends their use case.
2585 # For example, we may use the output of
2586 # a normal driver function, and parse it
2587 # using a wrapper function
andrewonlabc2d05aa2014-10-13 16:51:10 -04002588
kelvin-onlabd3b64892015-01-20 13:26:24 -08002589 def getAllIntentsId( self ):
kelvin8ec71442015-01-15 16:57:00 -08002590 """
andrewonlab9a50dfe2014-10-17 17:22:31 -04002591 Description:
2592 Obtain all intent id's in a list
kelvin8ec71442015-01-15 16:57:00 -08002593 """
andrewonlab9a50dfe2014-10-17 17:22:31 -04002594 try:
kelvin8ec71442015-01-15 16:57:00 -08002595 # Obtain output of intents function
kelvin-onlabfb521662015-02-27 09:52:40 -08002596 intentsStr = self.intents(jsonFormat=False)
kelvin-onlabd3b64892015-01-20 13:26:24 -08002597 intentIdList = []
andrewonlab9a50dfe2014-10-17 17:22:31 -04002598
kelvin8ec71442015-01-15 16:57:00 -08002599 # Parse the intents output for ID's
kelvin-onlabd3b64892015-01-20 13:26:24 -08002600 intentsList = [ s.strip() for s in intentsStr.splitlines() ]
2601 for intents in intentsList:
kelvin-onlabfb521662015-02-27 09:52:40 -08002602 match = re.search('id=0x([\da-f]+),', intents)
2603 if match:
2604 tmpId = match.group()[3:-1]
2605 intentIdList.append( tmpId )
kelvin-onlabd3b64892015-01-20 13:26:24 -08002606 return intentIdList
andrewonlab9a50dfe2014-10-17 17:22:31 -04002607
Jon Halld4d4b372015-01-28 16:02:41 -08002608 except TypeError:
2609 main.log.exception( self.name + ": Object not as expected" )
2610 return None
andrewonlab9a50dfe2014-10-17 17:22:31 -04002611 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002612 main.log.error( self.name + ": EOF exception found" )
2613 main.log.error( self.name + ": " + self.handle.before )
andrewonlab9a50dfe2014-10-17 17:22:31 -04002614 main.cleanup()
2615 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002616 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002617 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab9a50dfe2014-10-17 17:22:31 -04002618 main.cleanup()
2619 main.exit()
2620
Jon Hall30b82fa2015-03-04 17:15:43 -08002621 def FlowAddedCount( self, deviceId ):
2622 """
2623 Determine the number of flow rules for the given device id that are
2624 in the added state
2625 """
2626 try:
2627 cmdStr = "flows any " + str( deviceId ) + " | " +\
2628 "grep 'state=ADDED' | wc -l"
2629 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08002630 assert "Command not found:" not in handle, handle
Jon Hall30b82fa2015-03-04 17:15:43 -08002631 return handle
Jon Hallc6793552016-01-19 14:18:37 -08002632 except AssertionError:
2633 main.log.exception( "" )
2634 return None
Jon Hall30b82fa2015-03-04 17:15:43 -08002635 except pexpect.EOF:
2636 main.log.error( self.name + ": EOF exception found" )
2637 main.log.error( self.name + ": " + self.handle.before )
2638 main.cleanup()
2639 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002640 except Exception:
Jon Hall30b82fa2015-03-04 17:15:43 -08002641 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab95ce8322014-10-13 14:12:04 -04002642 main.cleanup()
2643 main.exit()
2644
kelvin-onlabd3b64892015-01-20 13:26:24 -08002645 def getAllDevicesId( self ):
kelvin8ec71442015-01-15 16:57:00 -08002646 """
andrewonlab7e4d2d32014-10-15 13:23:21 -04002647 Use 'devices' function to obtain list of all devices
2648 and parse the result to obtain a list of all device
2649 id's. Returns this list. Returns empty list if no
2650 devices exist
kelvin8ec71442015-01-15 16:57:00 -08002651 List is ordered sequentially
2652
andrewonlab3e15ead2014-10-15 14:21:34 -04002653 This function may be useful if you are not sure of the
kelvin8ec71442015-01-15 16:57:00 -08002654 device id, and wish to execute other commands using
andrewonlab3e15ead2014-10-15 14:21:34 -04002655 the ids. By obtaining the list of device ids on the fly,
2656 you can iterate through the list to get mastership, etc.
kelvin8ec71442015-01-15 16:57:00 -08002657 """
andrewonlab7e4d2d32014-10-15 13:23:21 -04002658 try:
kelvin8ec71442015-01-15 16:57:00 -08002659 # Call devices and store result string
kelvin-onlabd3b64892015-01-20 13:26:24 -08002660 devicesStr = self.devices( jsonFormat=False )
2661 idList = []
kelvin8ec71442015-01-15 16:57:00 -08002662
kelvin-onlabd3b64892015-01-20 13:26:24 -08002663 if not devicesStr:
kelvin8ec71442015-01-15 16:57:00 -08002664 main.log.info( "There are no devices to get id from" )
kelvin-onlabd3b64892015-01-20 13:26:24 -08002665 return idList
kelvin8ec71442015-01-15 16:57:00 -08002666
2667 # Split the string into list by comma
kelvin-onlabd3b64892015-01-20 13:26:24 -08002668 deviceList = devicesStr.split( "," )
kelvin8ec71442015-01-15 16:57:00 -08002669 # Get temporary list of all arguments with string 'id='
kelvin-onlabd3b64892015-01-20 13:26:24 -08002670 tempList = [ dev for dev in deviceList if "id=" in dev ]
kelvin8ec71442015-01-15 16:57:00 -08002671 # Split list further into arguments before and after string
2672 # 'id='. Get the latter portion ( the actual device id ) and
kelvin-onlabd3b64892015-01-20 13:26:24 -08002673 # append to idList
2674 for arg in tempList:
2675 idList.append( arg.split( "id=" )[ 1 ] )
2676 return idList
andrewonlab7e4d2d32014-10-15 13:23:21 -04002677
Jon Halld4d4b372015-01-28 16:02:41 -08002678 except TypeError:
2679 main.log.exception( self.name + ": Object not as expected" )
2680 return None
andrewonlab7e4d2d32014-10-15 13:23:21 -04002681 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002682 main.log.error( self.name + ": EOF exception found" )
2683 main.log.error( self.name + ": " + self.handle.before )
andrewonlab7e4d2d32014-10-15 13:23:21 -04002684 main.cleanup()
2685 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002686 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002687 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab7e4d2d32014-10-15 13:23:21 -04002688 main.cleanup()
2689 main.exit()
2690
kelvin-onlabd3b64892015-01-20 13:26:24 -08002691 def getAllNodesId( self ):
kelvin8ec71442015-01-15 16:57:00 -08002692 """
andrewonlab7c211572014-10-15 16:45:20 -04002693 Uses 'nodes' function to obtain list of all nodes
2694 and parse the result of nodes to obtain just the
kelvin8ec71442015-01-15 16:57:00 -08002695 node id's.
andrewonlab7c211572014-10-15 16:45:20 -04002696 Returns:
2697 list of node id's
kelvin8ec71442015-01-15 16:57:00 -08002698 """
andrewonlab7c211572014-10-15 16:45:20 -04002699 try:
Jon Hall5aa168b2015-03-23 14:23:09 -07002700 nodesStr = self.nodes( jsonFormat=True )
kelvin-onlabd3b64892015-01-20 13:26:24 -08002701 idList = []
Jon Hall5aa168b2015-03-23 14:23:09 -07002702 # Sample nodesStr output
Jon Hallbd182782016-03-28 16:42:22 -07002703 # id=local, address=127.0.0.1:9876, state=READY *
kelvin-onlabd3b64892015-01-20 13:26:24 -08002704 if not nodesStr:
kelvin8ec71442015-01-15 16:57:00 -08002705 main.log.info( "There are no nodes to get id from" )
kelvin-onlabd3b64892015-01-20 13:26:24 -08002706 return idList
Jon Hall5aa168b2015-03-23 14:23:09 -07002707 nodesJson = json.loads( nodesStr )
2708 idList = [ node.get('id') for node in nodesJson ]
kelvin-onlabd3b64892015-01-20 13:26:24 -08002709 return idList
Jon Hallc6793552016-01-19 14:18:37 -08002710 except ( TypeError, ValueError ):
2711 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, nodesStr ) )
Jon Halld4d4b372015-01-28 16:02:41 -08002712 return None
andrewonlab7c211572014-10-15 16:45:20 -04002713 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002714 main.log.error( self.name + ": EOF exception found" )
2715 main.log.error( self.name + ": " + self.handle.before )
andrewonlab7c211572014-10-15 16:45:20 -04002716 main.cleanup()
2717 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002718 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002719 main.log.exception( self.name + ": Uncaught exception!" )
andrewonlab7c211572014-10-15 16:45:20 -04002720 main.cleanup()
2721 main.exit()
andrewonlab7e4d2d32014-10-15 13:23:21 -04002722
kelvin-onlabd3b64892015-01-20 13:26:24 -08002723 def getDevice( self, dpid=None ):
kelvin8ec71442015-01-15 16:57:00 -08002724 """
Jon Halla91c4dc2014-10-22 12:57:04 -04002725 Return the first device from the devices api whose 'id' contains 'dpid'
2726 Return None if there is no match
kelvin8ec71442015-01-15 16:57:00 -08002727 """
Jon Halla91c4dc2014-10-22 12:57:04 -04002728 try:
kelvin8ec71442015-01-15 16:57:00 -08002729 if dpid is None:
Jon Halla91c4dc2014-10-22 12:57:04 -04002730 return None
2731 else:
kelvin8ec71442015-01-15 16:57:00 -08002732 dpid = dpid.replace( ':', '' )
kelvin-onlabd3b64892015-01-20 13:26:24 -08002733 rawDevices = self.devices()
2734 devicesJson = json.loads( rawDevices )
kelvin8ec71442015-01-15 16:57:00 -08002735 # search json for the device with dpid then return the device
kelvin-onlabd3b64892015-01-20 13:26:24 -08002736 for device in devicesJson:
kelvin8ec71442015-01-15 16:57:00 -08002737 # print "%s in %s?" % ( dpid, device[ 'id' ] )
2738 if dpid in device[ 'id' ]:
Jon Halla91c4dc2014-10-22 12:57:04 -04002739 return device
2740 return None
Jon Hallc6793552016-01-19 14:18:37 -08002741 except ( TypeError, ValueError ):
2742 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, rawDevices ) )
Jon Halld4d4b372015-01-28 16:02:41 -08002743 return None
Jon Halla91c4dc2014-10-22 12:57:04 -04002744 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002745 main.log.error( self.name + ": EOF exception found" )
2746 main.log.error( self.name + ": " + self.handle.before )
Jon Halla91c4dc2014-10-22 12:57:04 -04002747 main.cleanup()
2748 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002749 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002750 main.log.exception( self.name + ": Uncaught exception!" )
Jon Halla91c4dc2014-10-22 12:57:04 -04002751 main.cleanup()
2752 main.exit()
2753
You Wang24139872016-05-03 11:48:47 -07002754 def getTopology( self, topologyOutput ):
2755 """
2756 Definition:
2757 Loads a json topology output
2758 Return:
2759 topology = current ONOS topology
2760 """
2761 import json
2762 try:
2763 # either onos:topology or 'topology' will work in CLI
2764 topology = json.loads(topologyOutput)
Jeremy Songsterbc2d8ac2016-05-04 11:25:42 -07002765 main.log.debug( topology )
You Wang24139872016-05-03 11:48:47 -07002766 return topology
You Wangd3cb2ce2016-05-16 14:01:24 -07002767 except ( TypeError, ValueError ):
2768 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, topologyOutput ) )
2769 return None
You Wang24139872016-05-03 11:48:47 -07002770 except pexpect.EOF:
2771 main.log.error( self.name + ": EOF exception found" )
2772 main.log.error( self.name + ": " + self.handle.before )
2773 main.cleanup()
2774 main.exit()
2775 except Exception:
2776 main.log.exception( self.name + ": Uncaught exception!" )
2777 main.cleanup()
2778 main.exit()
2779
2780 def checkStatus(
2781 self,
2782 topologyResult,
2783 numoswitch,
2784 numolink,
2785 logLevel="info" ):
kelvin8ec71442015-01-15 16:57:00 -08002786 """
Jon Hallefbd9792015-03-05 16:11:36 -08002787 Checks the number of switches & links that ONOS sees against the
kelvin8ec71442015-01-15 16:57:00 -08002788 supplied values. By default this will report to main.log, but the
You Wang24139872016-05-03 11:48:47 -07002789 log level can be specific.
kelvin8ec71442015-01-15 16:57:00 -08002790
You Wang24139872016-05-03 11:48:47 -07002791 Params: topologyResult = the output of topology command
Jon Hall42db6dc2014-10-24 19:03:48 -04002792 numoswitch = expected number of switches
Jon Hallefbd9792015-03-05 16:11:36 -08002793 numolink = expected number of links
You Wang24139872016-05-03 11:48:47 -07002794 logLevel = level to log to.
2795 Currently accepts 'info', 'warn' and 'report'
Jon Hall42db6dc2014-10-24 19:03:48 -04002796
Jon Hallefbd9792015-03-05 16:11:36 -08002797 Returns: main.TRUE if the number of switches and links are correct,
2798 main.FALSE if the number of switches and links is incorrect,
Jon Hall42db6dc2014-10-24 19:03:48 -04002799 and main.ERROR otherwise
kelvin8ec71442015-01-15 16:57:00 -08002800 """
Jon Hall42db6dc2014-10-24 19:03:48 -04002801 try:
You Wang24139872016-05-03 11:48:47 -07002802 topology = self.getTopology( topologyResult )
You Wang85560372016-05-18 10:44:33 -07002803 if topology == {} or topology == None:
Jon Hall42db6dc2014-10-24 19:03:48 -04002804 return main.ERROR
2805 output = ""
kelvin8ec71442015-01-15 16:57:00 -08002806 # Is the number of switches is what we expected
2807 devices = topology.get( 'devices', False )
2808 links = topology.get( 'links', False )
kelvin-onlabfb521662015-02-27 09:52:40 -08002809 if devices is False or links is False:
Jon Hall42db6dc2014-10-24 19:03:48 -04002810 return main.ERROR
kelvin-onlabd3b64892015-01-20 13:26:24 -08002811 switchCheck = ( int( devices ) == int( numoswitch ) )
kelvin8ec71442015-01-15 16:57:00 -08002812 # Is the number of links is what we expected
kelvin-onlabd3b64892015-01-20 13:26:24 -08002813 linkCheck = ( int( links ) == int( numolink ) )
You Wang24139872016-05-03 11:48:47 -07002814 if switchCheck and linkCheck:
kelvin8ec71442015-01-15 16:57:00 -08002815 # We expected the correct numbers
You Wang24139872016-05-03 11:48:47 -07002816 output = output + "The number of links and switches match "\
2817 + "what was expected"
Jon Hall42db6dc2014-10-24 19:03:48 -04002818 result = main.TRUE
2819 else:
You Wang24139872016-05-03 11:48:47 -07002820 output = output + \
2821 "The number of links and switches does not match " + \
2822 "what was expected"
Jon Hall42db6dc2014-10-24 19:03:48 -04002823 result = main.FALSE
You Wang24139872016-05-03 11:48:47 -07002824 output = output + "\n ONOS sees %i devices" % int( devices )
2825 output = output + " (%i expected) " % int( numoswitch )
2826 output = output + "and %i links " % int( links )
2827 output = output + "(%i expected)" % int( numolink )
kelvin-onlabd3b64892015-01-20 13:26:24 -08002828 if logLevel == "report":
kelvin8ec71442015-01-15 16:57:00 -08002829 main.log.report( output )
kelvin-onlabd3b64892015-01-20 13:26:24 -08002830 elif logLevel == "warn":
kelvin8ec71442015-01-15 16:57:00 -08002831 main.log.warn( output )
Jon Hall42db6dc2014-10-24 19:03:48 -04002832 else:
You Wang24139872016-05-03 11:48:47 -07002833 main.log.info( output )
kelvin8ec71442015-01-15 16:57:00 -08002834 return result
Jon Hall42db6dc2014-10-24 19:03:48 -04002835 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002836 main.log.error( self.name + ": EOF exception found" )
2837 main.log.error( self.name + ": " + self.handle.before )
Jon Hall42db6dc2014-10-24 19:03:48 -04002838 main.cleanup()
2839 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002840 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002841 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall42db6dc2014-10-24 19:03:48 -04002842 main.cleanup()
2843 main.exit()
Jon Hall1c9e8732014-10-27 19:29:27 -04002844
kelvin-onlabd3b64892015-01-20 13:26:24 -08002845 def deviceRole( self, deviceId, onosNode, role="master" ):
kelvin8ec71442015-01-15 16:57:00 -08002846 """
Jon Hall1c9e8732014-10-27 19:29:27 -04002847 Calls the device-role cli command.
kelvin-onlabd3b64892015-01-20 13:26:24 -08002848 deviceId must be the id of a device as seen in the onos devices command
2849 onosNode is the ip of one of the onos nodes in the cluster
Jon Hall1c9e8732014-10-27 19:29:27 -04002850 role must be either master, standby, or none
2851
Jon Halle3f39ff2015-01-13 11:50:53 -08002852 Returns:
2853 main.TRUE or main.FALSE based on argument verification and
2854 main.ERROR if command returns and error
kelvin-onlab898a6c62015-01-16 14:13:53 -08002855 """
Jon Hall1c9e8732014-10-27 19:29:27 -04002856 try:
Jon Halle3f39ff2015-01-13 11:50:53 -08002857 if role.lower() == "master" or role.lower() == "standby" or\
Jon Hall1c9e8732014-10-27 19:29:27 -04002858 role.lower() == "none":
kelvin-onlabd3b64892015-01-20 13:26:24 -08002859 cmdStr = "device-role " +\
2860 str( deviceId ) + " " +\
2861 str( onosNode ) + " " +\
kelvin-onlab898a6c62015-01-16 14:13:53 -08002862 str( role )
kelvin-onlabd3b64892015-01-20 13:26:24 -08002863 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08002864 assert "Command not found:" not in handle, handle
kelvin-onlab898a6c62015-01-16 14:13:53 -08002865 if re.search( "Error", handle ):
2866 # end color output to escape any colours
2867 # from the cli
kelvin8ec71442015-01-15 16:57:00 -08002868 main.log.error( self.name + ": " +
kelvin-onlab898a6c62015-01-16 14:13:53 -08002869 handle + '\033[0m' )
kelvin8ec71442015-01-15 16:57:00 -08002870 return main.ERROR
kelvin8ec71442015-01-15 16:57:00 -08002871 return main.TRUE
Jon Hall1c9e8732014-10-27 19:29:27 -04002872 else:
kelvin-onlab898a6c62015-01-16 14:13:53 -08002873 main.log.error( "Invalid 'role' given to device_role(). " +
2874 "Value was '" + str(role) + "'." )
Jon Hall1c9e8732014-10-27 19:29:27 -04002875 return main.FALSE
Jon Hallc6793552016-01-19 14:18:37 -08002876 except AssertionError:
2877 main.log.exception( "" )
2878 return None
Jon Halld4d4b372015-01-28 16:02:41 -08002879 except TypeError:
2880 main.log.exception( self.name + ": Object not as expected" )
2881 return None
Jon Hall1c9e8732014-10-27 19:29:27 -04002882 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002883 main.log.error( self.name + ": EOF exception found" )
2884 main.log.error( self.name + ": " + self.handle.before )
Jon Hall1c9e8732014-10-27 19:29:27 -04002885 main.cleanup()
2886 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002887 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002888 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall1c9e8732014-10-27 19:29:27 -04002889 main.cleanup()
2890 main.exit()
2891
kelvin-onlabd3b64892015-01-20 13:26:24 -08002892 def clusters( self, jsonFormat=True ):
kelvin8ec71442015-01-15 16:57:00 -08002893 """
Jon Hall73cf9cc2014-11-20 22:28:38 -08002894 Lists all clusters
Jon Hallffb386d2014-11-21 13:43:38 -08002895 Optional argument:
kelvin-onlabd3b64892015-01-20 13:26:24 -08002896 * jsonFormat - boolean indicating if you want output in json
kelvin8ec71442015-01-15 16:57:00 -08002897 """
Jon Hall73cf9cc2014-11-20 22:28:38 -08002898 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07002899 cmdStr = "clusters"
kelvin-onlabd3b64892015-01-20 13:26:24 -08002900 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -07002901 cmdStr += " -j"
2902 handle = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08002903 assert "Command not found:" not in handle, handle
Jon Hallc6358dd2015-04-10 12:44:28 -07002904 return handle
Jon Hallc6793552016-01-19 14:18:37 -08002905 except AssertionError:
2906 main.log.exception( "" )
2907 return None
Jon Halld4d4b372015-01-28 16:02:41 -08002908 except TypeError:
2909 main.log.exception( self.name + ": Object not as expected" )
2910 return None
Jon Hall73cf9cc2014-11-20 22:28:38 -08002911 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002912 main.log.error( self.name + ": EOF exception found" )
2913 main.log.error( self.name + ": " + self.handle.before )
Jon Hall73cf9cc2014-11-20 22:28:38 -08002914 main.cleanup()
2915 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002916 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002917 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall73cf9cc2014-11-20 22:28:38 -08002918 main.cleanup()
2919 main.exit()
2920
kelvin-onlabd3b64892015-01-20 13:26:24 -08002921 def electionTestLeader( self ):
kelvin-onlab898a6c62015-01-16 14:13:53 -08002922 """
Jon Halle3f39ff2015-01-13 11:50:53 -08002923 CLI command to get the current leader for the Election test application
2924 NOTE: Requires installation of the onos-app-election feature
2925 Returns: Node IP of the leader if one exists
2926 None if none exists
2927 Main.FALSE on error
kelvin-onlab898a6c62015-01-16 14:13:53 -08002928 """
Jon Hall94fd0472014-12-08 11:52:42 -08002929 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -08002930 cmdStr = "election-test-leader"
2931 response = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08002932 assert "Command not found:" not in response, response
Jon Halle3f39ff2015-01-13 11:50:53 -08002933 # Leader
2934 leaderPattern = "The\scurrent\sleader\sfor\sthe\sElection\s" +\
kelvin-onlab898a6c62015-01-16 14:13:53 -08002935 "app\sis\s(?P<node>.+)\."
kelvin-onlabd3b64892015-01-20 13:26:24 -08002936 nodeSearch = re.search( leaderPattern, response )
2937 if nodeSearch:
2938 node = nodeSearch.group( 'node' )
Jon Halle3f39ff2015-01-13 11:50:53 -08002939 main.log.info( "Election-test-leader on " + str( self.name ) +
kelvin-onlab898a6c62015-01-16 14:13:53 -08002940 " found " + node + " as the leader" )
Jon Hall94fd0472014-12-08 11:52:42 -08002941 return node
Jon Halle3f39ff2015-01-13 11:50:53 -08002942 # no leader
2943 nullPattern = "There\sis\scurrently\sno\sleader\selected\sfor\s" +\
kelvin-onlab898a6c62015-01-16 14:13:53 -08002944 "the\sElection\sapp"
kelvin-onlabd3b64892015-01-20 13:26:24 -08002945 nullSearch = re.search( nullPattern, response )
2946 if nullSearch:
Jon Halle3f39ff2015-01-13 11:50:53 -08002947 main.log.info( "Election-test-leader found no leader on " +
kelvin-onlab898a6c62015-01-16 14:13:53 -08002948 self.name )
Jon Hall94fd0472014-12-08 11:52:42 -08002949 return None
kelvin-onlab898a6c62015-01-16 14:13:53 -08002950 # error
Jon Halle3f39ff2015-01-13 11:50:53 -08002951 errorPattern = "Command\snot\sfound"
kelvin-onlab898a6c62015-01-16 14:13:53 -08002952 if re.search( errorPattern, response ):
2953 main.log.error( "Election app is not loaded on " + self.name )
Jon Halle3f39ff2015-01-13 11:50:53 -08002954 # TODO: Should this be main.ERROR?
Jon Hall669173b2014-12-17 11:36:30 -08002955 return main.FALSE
2956 else:
Jon Hall390696c2015-05-05 17:13:41 -07002957 main.log.error( "Error in electionTestLeader on " + self.name +
2958 ": " + "unexpected response" )
kelvin8ec71442015-01-15 16:57:00 -08002959 main.log.error( repr( response ) )
Jon Hall669173b2014-12-17 11:36:30 -08002960 return main.FALSE
Jon Hallc6793552016-01-19 14:18:37 -08002961 except AssertionError:
2962 main.log.exception( "" )
2963 return None
Jon Halld4d4b372015-01-28 16:02:41 -08002964 except TypeError:
2965 main.log.exception( self.name + ": Object not as expected" )
2966 return main.FALSE
Jon Hall94fd0472014-12-08 11:52:42 -08002967 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08002968 main.log.error( self.name + ": EOF exception found" )
2969 main.log.error( self.name + ": " + self.handle.before )
Jon Hall94fd0472014-12-08 11:52:42 -08002970 main.cleanup()
2971 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08002972 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08002973 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall94fd0472014-12-08 11:52:42 -08002974 main.cleanup()
2975 main.exit()
2976
kelvin-onlabd3b64892015-01-20 13:26:24 -08002977 def electionTestRun( self ):
kelvin-onlab898a6c62015-01-16 14:13:53 -08002978 """
Jon Halle3f39ff2015-01-13 11:50:53 -08002979 CLI command to run for leadership of the Election test application.
2980 NOTE: Requires installation of the onos-app-election feature
2981 Returns: Main.TRUE on success
2982 Main.FALSE on error
kelvin-onlab898a6c62015-01-16 14:13:53 -08002983 """
Jon Hall94fd0472014-12-08 11:52:42 -08002984 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -08002985 cmdStr = "election-test-run"
2986 response = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08002987 assert "Command not found:" not in response, response
kelvin-onlab898a6c62015-01-16 14:13:53 -08002988 # success
Jon Halle3f39ff2015-01-13 11:50:53 -08002989 successPattern = "Entering\sleadership\selections\sfor\sthe\s" +\
kelvin-onlab898a6c62015-01-16 14:13:53 -08002990 "Election\sapp."
Jon Halle3f39ff2015-01-13 11:50:53 -08002991 search = re.search( successPattern, response )
Jon Hall94fd0472014-12-08 11:52:42 -08002992 if search:
Jon Halle3f39ff2015-01-13 11:50:53 -08002993 main.log.info( self.name + " entering leadership elections " +
kelvin-onlab898a6c62015-01-16 14:13:53 -08002994 "for the Election app." )
Jon Hall94fd0472014-12-08 11:52:42 -08002995 return main.TRUE
kelvin-onlab898a6c62015-01-16 14:13:53 -08002996 # error
Jon Halle3f39ff2015-01-13 11:50:53 -08002997 errorPattern = "Command\snot\sfound"
2998 if re.search( errorPattern, response ):
2999 main.log.error( "Election app is not loaded on " + self.name )
Jon Hall669173b2014-12-17 11:36:30 -08003000 return main.FALSE
3001 else:
Jon Hall390696c2015-05-05 17:13:41 -07003002 main.log.error( "Error in electionTestRun on " + self.name +
3003 ": " + "unexpected response" )
Jon Halle3f39ff2015-01-13 11:50:53 -08003004 main.log.error( repr( response ) )
Jon Hall669173b2014-12-17 11:36:30 -08003005 return main.FALSE
Jon Hallc6793552016-01-19 14:18:37 -08003006 except AssertionError:
3007 main.log.exception( "" )
3008 return None
Jon Halld4d4b372015-01-28 16:02:41 -08003009 except TypeError:
3010 main.log.exception( self.name + ": Object not as expected" )
3011 return main.FALSE
Jon Hall94fd0472014-12-08 11:52:42 -08003012 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08003013 main.log.error( self.name + ": EOF exception found" )
3014 main.log.error( self.name + ": " + self.handle.before )
Jon Hall94fd0472014-12-08 11:52:42 -08003015 main.cleanup()
3016 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08003017 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08003018 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall94fd0472014-12-08 11:52:42 -08003019 main.cleanup()
3020 main.exit()
3021
kelvin-onlabd3b64892015-01-20 13:26:24 -08003022 def electionTestWithdraw( self ):
kelvin8ec71442015-01-15 16:57:00 -08003023 """
Jon Hall94fd0472014-12-08 11:52:42 -08003024 * CLI command to withdraw the local node from leadership election for
3025 * the Election test application.
3026 #NOTE: Requires installation of the onos-app-election feature
3027 Returns: Main.TRUE on success
3028 Main.FALSE on error
kelvin8ec71442015-01-15 16:57:00 -08003029 """
Jon Hall94fd0472014-12-08 11:52:42 -08003030 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -08003031 cmdStr = "election-test-withdraw"
3032 response = self.sendline( cmdStr )
Jon Hallc6793552016-01-19 14:18:37 -08003033 assert "Command not found:" not in response, response
kelvin-onlab898a6c62015-01-16 14:13:53 -08003034 # success
Jon Halle3f39ff2015-01-13 11:50:53 -08003035 successPattern = "Withdrawing\sfrom\sleadership\selections\sfor" +\
kelvin-onlab898a6c62015-01-16 14:13:53 -08003036 "\sthe\sElection\sapp."
Jon Halle3f39ff2015-01-13 11:50:53 -08003037 if re.search( successPattern, response ):
3038 main.log.info( self.name + " withdrawing from leadership " +
kelvin-onlab898a6c62015-01-16 14:13:53 -08003039 "elections for the Election app." )
Jon Hall94fd0472014-12-08 11:52:42 -08003040 return main.TRUE
kelvin-onlab898a6c62015-01-16 14:13:53 -08003041 # error
Jon Halle3f39ff2015-01-13 11:50:53 -08003042 errorPattern = "Command\snot\sfound"
3043 if re.search( errorPattern, response ):
3044 main.log.error( "Election app is not loaded on " + self.name )
Jon Hall669173b2014-12-17 11:36:30 -08003045 return main.FALSE
3046 else:
Jon Hall390696c2015-05-05 17:13:41 -07003047 main.log.error( "Error in electionTestWithdraw on " +
3048 self.name + ": " + "unexpected response" )
Jon Halle3f39ff2015-01-13 11:50:53 -08003049 main.log.error( repr( response ) )
Jon Hall669173b2014-12-17 11:36:30 -08003050 return main.FALSE
Jon Hallc6793552016-01-19 14:18:37 -08003051 except AssertionError:
3052 main.log.exception( "" )
3053 return None
Jon Halld4d4b372015-01-28 16:02:41 -08003054 except TypeError:
3055 main.log.exception( self.name + ": Object not as expected" )
3056 return main.FALSE
Jon Hall94fd0472014-12-08 11:52:42 -08003057 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08003058 main.log.error( self.name + ": EOF exception found" )
3059 main.log.error( self.name + ": " + self.handle.before )
Jon Hall94fd0472014-12-08 11:52:42 -08003060 main.cleanup()
3061 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08003062 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08003063 main.log.exception( self.name + ": Uncaught exception!" )
Jon Hall94fd0472014-12-08 11:52:42 -08003064 main.cleanup()
3065 main.exit()
Jon Hall1c9e8732014-10-27 19:29:27 -04003066
kelvin8ec71442015-01-15 16:57:00 -08003067 def getDevicePortsEnabledCount( self, dpid ):
3068 """
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003069 Get the count of all enabled ports on a particular device/switch
kelvin8ec71442015-01-15 16:57:00 -08003070 """
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003071 try:
Jon Halle3f39ff2015-01-13 11:50:53 -08003072 dpid = str( dpid )
kelvin-onlabd3b64892015-01-20 13:26:24 -08003073 cmdStr = "onos:ports -e " + dpid + " | wc -l"
3074 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003075 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003076 assert "Command not found:" not in output, output
Jon Halle3f39ff2015-01-13 11:50:53 -08003077 if re.search( "No such device", output ):
3078 main.log.error( "Error in getting ports" )
3079 return ( output, "Error" )
Jon Halla495f562016-05-16 18:03:26 -07003080 return output
Jon Hallc6793552016-01-19 14:18:37 -08003081 except AssertionError:
3082 main.log.exception( "" )
3083 return None
Jon Halld4d4b372015-01-28 16:02:41 -08003084 except TypeError:
3085 main.log.exception( self.name + ": Object not as expected" )
3086 return ( output, "Error" )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003087 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08003088 main.log.error( self.name + ": EOF exception found" )
3089 main.log.error( self.name + ": " + self.handle.before )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003090 main.cleanup()
3091 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08003092 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08003093 main.log.exception( self.name + ": Uncaught exception!" )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003094 main.cleanup()
3095 main.exit()
3096
kelvin8ec71442015-01-15 16:57:00 -08003097 def getDeviceLinksActiveCount( self, dpid ):
3098 """
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003099 Get the count of all enabled ports on a particular device/switch
kelvin8ec71442015-01-15 16:57:00 -08003100 """
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003101 try:
kelvin-onlab898a6c62015-01-16 14:13:53 -08003102 dpid = str( dpid )
kelvin-onlabd3b64892015-01-20 13:26:24 -08003103 cmdStr = "onos:links " + dpid + " | grep ACTIVE | wc -l"
3104 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003105 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003106 assert "Command not found:" not in output, output
Jon Halle3f39ff2015-01-13 11:50:53 -08003107 if re.search( "No such device", output ):
kelvin-onlab898a6c62015-01-16 14:13:53 -08003108 main.log.error( "Error in getting ports " )
3109 return ( output, "Error " )
Jon Halla495f562016-05-16 18:03:26 -07003110 return output
Jon Hallc6793552016-01-19 14:18:37 -08003111 except AssertionError:
3112 main.log.exception( "" )
3113 return None
Jon Halld4d4b372015-01-28 16:02:41 -08003114 except TypeError:
3115 main.log.exception( self.name + ": Object not as expected" )
3116 return ( output, "Error " )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003117 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08003118 main.log.error( self.name + ": EOF exception found" )
3119 main.log.error( self.name + ": " + self.handle.before )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003120 main.cleanup()
3121 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08003122 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08003123 main.log.exception( self.name + ": Uncaught exception!" )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003124 main.cleanup()
3125 main.exit()
3126
kelvin8ec71442015-01-15 16:57:00 -08003127 def getAllIntentIds( self ):
3128 """
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003129 Return a list of all Intent IDs
kelvin8ec71442015-01-15 16:57:00 -08003130 """
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003131 try:
kelvin-onlabd3b64892015-01-20 13:26:24 -08003132 cmdStr = "onos:intents | grep id="
3133 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003134 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003135 assert "Command not found:" not in output, output
Jon Halle3f39ff2015-01-13 11:50:53 -08003136 if re.search( "Error", output ):
3137 main.log.error( "Error in getting ports" )
3138 return ( output, "Error" )
Jon Halla495f562016-05-16 18:03:26 -07003139 return output
Jon Hallc6793552016-01-19 14:18:37 -08003140 except AssertionError:
3141 main.log.exception( "" )
3142 return None
Jon Halld4d4b372015-01-28 16:02:41 -08003143 except TypeError:
3144 main.log.exception( self.name + ": Object not as expected" )
3145 return ( output, "Error" )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003146 except pexpect.EOF:
kelvin8ec71442015-01-15 16:57:00 -08003147 main.log.error( self.name + ": EOF exception found" )
3148 main.log.error( self.name + ": " + self.handle.before )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003149 main.cleanup()
3150 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08003151 except Exception:
Jon Halld4d4b372015-01-28 16:02:41 -08003152 main.log.exception( self.name + ": Uncaught exception!" )
3153 main.cleanup()
3154 main.exit()
3155
Jon Hall73509952015-02-24 16:42:56 -08003156 def intentSummary( self ):
3157 """
Jon Hallefbd9792015-03-05 16:11:36 -08003158 Returns a dictionary containing the current intent states and the count
Jon Hall73509952015-02-24 16:42:56 -08003159 """
3160 try:
3161 intents = self.intents( )
Jon Hall08f61bc2015-04-13 16:00:30 -07003162 states = []
Jon Hall5aa168b2015-03-23 14:23:09 -07003163 for intent in json.loads( intents ):
Jon Hall08f61bc2015-04-13 16:00:30 -07003164 states.append( intent.get( 'state', None ) )
3165 out = [ ( i, states.count( i ) ) for i in set( states ) ]
Jon Hall63604932015-02-26 17:09:50 -08003166 main.log.info( dict( out ) )
Jon Hall73509952015-02-24 16:42:56 -08003167 return dict( out )
Jon Hallc6793552016-01-19 14:18:37 -08003168 except ( TypeError, ValueError ):
3169 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, intents ) )
Jon Hall73509952015-02-24 16:42:56 -08003170 return None
3171 except pexpect.EOF:
3172 main.log.error( self.name + ": EOF exception found" )
3173 main.log.error( self.name + ": " + self.handle.before )
3174 main.cleanup()
3175 main.exit()
Jon Hallfebb1c72015-03-05 13:30:09 -08003176 except Exception:
Jon Hall73509952015-02-24 16:42:56 -08003177 main.log.exception( self.name + ": Uncaught exception!" )
3178 main.cleanup()
3179 main.exit()
Jon Hall63604932015-02-26 17:09:50 -08003180
Jon Hall61282e32015-03-19 11:34:11 -07003181 def leaders( self, jsonFormat=True ):
Jon Hall63604932015-02-26 17:09:50 -08003182 """
3183 Returns the output of the leaders command.
Jon Hall61282e32015-03-19 11:34:11 -07003184 Optional argument:
3185 * jsonFormat - boolean indicating if you want output in json
Jon Hall63604932015-02-26 17:09:50 -08003186 """
Jon Hall63604932015-02-26 17:09:50 -08003187 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07003188 cmdStr = "onos:leaders"
Jon Hall61282e32015-03-19 11:34:11 -07003189 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -07003190 cmdStr += " -j"
3191 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003192 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003193 assert "Command not found:" not in output, output
Jon Hallc6358dd2015-04-10 12:44:28 -07003194 return output
Jon Hallc6793552016-01-19 14:18:37 -08003195 except AssertionError:
3196 main.log.exception( "" )
3197 return None
Jon Hall63604932015-02-26 17:09:50 -08003198 except TypeError:
3199 main.log.exception( self.name + ": Object not as expected" )
3200 return None
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003201 except pexpect.EOF:
3202 main.log.error( self.name + ": EOF exception found" )
3203 main.log.error( self.name + ": " + self.handle.before )
3204 main.cleanup()
3205 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003206 except Exception:
Jon Hall63604932015-02-26 17:09:50 -08003207 main.log.exception( self.name + ": Uncaught exception!" )
Hari Krishnaa43d4e92014-12-19 13:22:40 -08003208 main.cleanup()
3209 main.exit()
Jon Hall63604932015-02-26 17:09:50 -08003210
acsmarsa4a4d1e2015-07-10 16:01:24 -07003211 def leaderCandidates( self, jsonFormat=True ):
3212 """
3213 Returns the output of the leaders -c command.
3214 Optional argument:
3215 * jsonFormat - boolean indicating if you want output in json
3216 """
3217 try:
3218 cmdStr = "onos:leaders -c"
3219 if jsonFormat:
3220 cmdStr += " -j"
3221 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003222 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003223 assert "Command not found:" not in output, output
acsmarsa4a4d1e2015-07-10 16:01:24 -07003224 return output
Jon Hallc6793552016-01-19 14:18:37 -08003225 except AssertionError:
3226 main.log.exception( "" )
3227 return None
acsmarsa4a4d1e2015-07-10 16:01:24 -07003228 except TypeError:
3229 main.log.exception( self.name + ": Object not as expected" )
3230 return None
3231 except pexpect.EOF:
3232 main.log.error( self.name + ": EOF exception found" )
3233 main.log.error( self.name + ": " + self.handle.before )
3234 main.cleanup()
3235 main.exit()
3236 except Exception:
3237 main.log.exception( self.name + ": Uncaught exception!" )
3238 main.cleanup()
3239 main.exit()
3240
Jon Hallc6793552016-01-19 14:18:37 -08003241 def specificLeaderCandidate( self, topic ):
acsmarsa4a4d1e2015-07-10 16:01:24 -07003242 """
3243 Returns a list in format [leader,candidate1,candidate2,...] for a given
3244 topic parameter and an empty list if the topic doesn't exist
3245 If no leader is elected leader in the returned list will be "none"
3246 Returns None if there is a type error processing the json object
3247 """
3248 try:
Jon Hall6e709752016-02-01 13:38:46 -08003249 cmdStr = "onos:leaders -j"
Jon Hallc6793552016-01-19 14:18:37 -08003250 rawOutput = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003251 assert rawOutput is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003252 assert "Command not found:" not in rawOutput, rawOutput
3253 output = json.loads( rawOutput )
acsmarsa4a4d1e2015-07-10 16:01:24 -07003254 results = []
3255 for dict in output:
3256 if dict["topic"] == topic:
3257 leader = dict["leader"]
Jon Hallc6793552016-01-19 14:18:37 -08003258 candidates = re.split( ", ", dict["candidates"][1:-1] )
3259 results.append( leader )
3260 results.extend( candidates )
acsmarsa4a4d1e2015-07-10 16:01:24 -07003261 return results
Jon Hallc6793552016-01-19 14:18:37 -08003262 except AssertionError:
3263 main.log.exception( "" )
3264 return None
3265 except ( TypeError, ValueError ):
3266 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, rawOutput ) )
acsmarsa4a4d1e2015-07-10 16:01:24 -07003267 return None
3268 except pexpect.EOF:
3269 main.log.error( self.name + ": EOF exception found" )
3270 main.log.error( self.name + ": " + self.handle.before )
3271 main.cleanup()
3272 main.exit()
3273 except Exception:
3274 main.log.exception( self.name + ": Uncaught exception!" )
3275 main.cleanup()
3276 main.exit()
3277
Jon Hall61282e32015-03-19 11:34:11 -07003278 def pendingMap( self, jsonFormat=True ):
Jon Hall63604932015-02-26 17:09:50 -08003279 """
3280 Returns the output of the intent Pending map.
3281 """
Jon Hall63604932015-02-26 17:09:50 -08003282 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07003283 cmdStr = "onos:intents -p"
Jon Hall61282e32015-03-19 11:34:11 -07003284 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -07003285 cmdStr += " -j"
3286 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003287 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003288 assert "Command not found:" not in output, output
Jon Hallc6358dd2015-04-10 12:44:28 -07003289 return output
Jon Hallc6793552016-01-19 14:18:37 -08003290 except AssertionError:
3291 main.log.exception( "" )
3292 return None
Jon Hall63604932015-02-26 17:09:50 -08003293 except TypeError:
3294 main.log.exception( self.name + ": Object not as expected" )
3295 return None
3296 except pexpect.EOF:
3297 main.log.error( self.name + ": EOF exception found" )
3298 main.log.error( self.name + ": " + self.handle.before )
3299 main.cleanup()
3300 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003301 except Exception:
Jon Hall63604932015-02-26 17:09:50 -08003302 main.log.exception( self.name + ": Uncaught exception!" )
3303 main.cleanup()
3304 main.exit()
3305
Jon Hall61282e32015-03-19 11:34:11 -07003306 def partitions( self, jsonFormat=True ):
Jon Hall63604932015-02-26 17:09:50 -08003307 """
3308 Returns the output of the raft partitions command for ONOS.
3309 """
Jon Hall61282e32015-03-19 11:34:11 -07003310 # Sample JSON
3311 # {
3312 # "leader": "tcp://10.128.30.11:7238",
3313 # "members": [
3314 # "tcp://10.128.30.11:7238",
3315 # "tcp://10.128.30.17:7238",
3316 # "tcp://10.128.30.13:7238",
3317 # ],
3318 # "name": "p1",
3319 # "term": 3
3320 # },
Jon Hall63604932015-02-26 17:09:50 -08003321 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07003322 cmdStr = "onos:partitions"
Jon Hall61282e32015-03-19 11:34:11 -07003323 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -07003324 cmdStr += " -j"
3325 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003326 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003327 assert "Command not found:" not in output, output
Jon Hallc6358dd2015-04-10 12:44:28 -07003328 return output
Jon Hallc6793552016-01-19 14:18:37 -08003329 except AssertionError:
3330 main.log.exception( "" )
3331 return None
Jon Hall63604932015-02-26 17:09:50 -08003332 except TypeError:
3333 main.log.exception( self.name + ": Object not as expected" )
3334 return None
3335 except pexpect.EOF:
3336 main.log.error( self.name + ": EOF exception found" )
3337 main.log.error( self.name + ": " + self.handle.before )
3338 main.cleanup()
3339 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003340 except Exception:
Jon Hall63604932015-02-26 17:09:50 -08003341 main.log.exception( self.name + ": Uncaught exception!" )
3342 main.cleanup()
3343 main.exit()
3344
Jon Hallbe379602015-03-24 13:39:32 -07003345 def apps( self, jsonFormat=True ):
3346 """
3347 Returns the output of the apps command for ONOS. This command lists
3348 information about installed ONOS applications
3349 """
3350 # Sample JSON object
3351 # [{"name":"org.onosproject.openflow","id":0,"version":"1.2.0",
3352 # "description":"ONOS OpenFlow protocol southbound providers",
3353 # "origin":"ON.Lab","permissions":"[]","featuresRepo":"",
3354 # "features":"[onos-openflow]","state":"ACTIVE"}]
3355 try:
Jon Hallc6358dd2015-04-10 12:44:28 -07003356 cmdStr = "onos:apps"
Jon Hallbe379602015-03-24 13:39:32 -07003357 if jsonFormat:
Jon Hallc6358dd2015-04-10 12:44:28 -07003358 cmdStr += " -j"
3359 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003360 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003361 assert "Command not found:" not in output, output
3362 assert "Error executing command" not in output, output
Jon Hallc6358dd2015-04-10 12:44:28 -07003363 return output
Jon Hallbe379602015-03-24 13:39:32 -07003364 # FIXME: look at specific exceptions/Errors
3365 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08003366 main.log.exception( "Error in processing onos:app command." )
Jon Hallbe379602015-03-24 13:39:32 -07003367 return None
3368 except TypeError:
3369 main.log.exception( self.name + ": Object not as expected" )
3370 return None
3371 except pexpect.EOF:
3372 main.log.error( self.name + ": EOF exception found" )
3373 main.log.error( self.name + ": " + self.handle.before )
3374 main.cleanup()
3375 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003376 except Exception:
Jon Hallbe379602015-03-24 13:39:32 -07003377 main.log.exception( self.name + ": Uncaught exception!" )
3378 main.cleanup()
3379 main.exit()
3380
Jon Hall146f1522015-03-24 15:33:24 -07003381 def appStatus( self, appName ):
3382 """
3383 Uses the onos:apps cli command to return the status of an application.
3384 Returns:
3385 "ACTIVE" - If app is installed and activated
3386 "INSTALLED" - If app is installed and deactivated
3387 "UNINSTALLED" - If app is not installed
3388 None - on error
3389 """
Jon Hall146f1522015-03-24 15:33:24 -07003390 try:
3391 if not isinstance( appName, types.StringType ):
3392 main.log.error( self.name + ".appStatus(): appName must be" +
3393 " a string" )
3394 return None
3395 output = self.apps( jsonFormat=True )
3396 appsJson = json.loads( output )
3397 state = None
3398 for app in appsJson:
3399 if appName == app.get('name'):
3400 state = app.get('state')
3401 break
3402 if state == "ACTIVE" or state == "INSTALLED":
3403 return state
3404 elif state is None:
3405 return "UNINSTALLED"
3406 elif state:
3407 main.log.error( "Unexpected state from 'onos:apps': " +
3408 str( state ) )
3409 return state
Jon Hallc6793552016-01-19 14:18:37 -08003410 except ( TypeError, ValueError ):
3411 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, output ) )
Jon Hall146f1522015-03-24 15:33:24 -07003412 return None
3413 except pexpect.EOF:
3414 main.log.error( self.name + ": EOF exception found" )
3415 main.log.error( self.name + ": " + self.handle.before )
3416 main.cleanup()
3417 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003418 except Exception:
Jon Hall146f1522015-03-24 15:33:24 -07003419 main.log.exception( self.name + ": Uncaught exception!" )
3420 main.cleanup()
3421 main.exit()
3422
Jon Hallbe379602015-03-24 13:39:32 -07003423 def app( self, appName, option ):
3424 """
3425 Interacts with the app command for ONOS. This command manages
3426 application inventory.
3427 """
Jon Hallbe379602015-03-24 13:39:32 -07003428 try:
Jon Hallbd16b922015-03-26 17:53:15 -07003429 # Validate argument types
3430 valid = True
3431 if not isinstance( appName, types.StringType ):
3432 main.log.error( self.name + ".app(): appName must be a " +
3433 "string" )
3434 valid = False
3435 if not isinstance( option, types.StringType ):
3436 main.log.error( self.name + ".app(): option must be a string" )
3437 valid = False
3438 if not valid:
3439 return main.FALSE
3440 # Validate Option
3441 option = option.lower()
3442 # NOTE: Install may become a valid option
3443 if option == "activate":
3444 pass
3445 elif option == "deactivate":
3446 pass
3447 elif option == "uninstall":
3448 pass
3449 else:
3450 # Invalid option
3451 main.log.error( "The ONOS app command argument only takes " +
3452 "the values: (activate|deactivate|uninstall)" +
3453 "; was given '" + option + "'")
3454 return main.FALSE
Jon Hall146f1522015-03-24 15:33:24 -07003455 cmdStr = "onos:app " + option + " " + appName
Jon Hallbe379602015-03-24 13:39:32 -07003456 output = self.sendline( cmdStr )
Jon Hallbe379602015-03-24 13:39:32 -07003457 if "Error executing command" in output:
3458 main.log.error( "Error in processing onos:app command: " +
3459 str( output ) )
Jon Hall146f1522015-03-24 15:33:24 -07003460 return main.FALSE
Jon Hallbe379602015-03-24 13:39:32 -07003461 elif "No such application" in output:
3462 main.log.error( "The application '" + appName +
3463 "' is not installed in ONOS" )
Jon Hall146f1522015-03-24 15:33:24 -07003464 return main.FALSE
3465 elif "Command not found:" in output:
3466 main.log.error( "Error in processing onos:app command: " +
3467 str( output ) )
3468 return main.FALSE
Jon Hallbd16b922015-03-26 17:53:15 -07003469 elif "Unsupported command:" in output:
3470 main.log.error( "Incorrect command given to 'app': " +
3471 str( output ) )
Jon Hallbe379602015-03-24 13:39:32 -07003472 # NOTE: we may need to add more checks here
Jon Hallbd16b922015-03-26 17:53:15 -07003473 # else: Command was successful
Jon Hall08f61bc2015-04-13 16:00:30 -07003474 # main.log.debug( "app response: " + repr( output ) )
Jon Hallbe379602015-03-24 13:39:32 -07003475 return main.TRUE
3476 except TypeError:
3477 main.log.exception( self.name + ": Object not as expected" )
3478 return main.ERROR
3479 except pexpect.EOF:
3480 main.log.error( self.name + ": EOF exception found" )
3481 main.log.error( self.name + ": " + self.handle.before )
3482 main.cleanup()
3483 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003484 except Exception:
Jon Hallbe379602015-03-24 13:39:32 -07003485 main.log.exception( self.name + ": Uncaught exception!" )
3486 main.cleanup()
3487 main.exit()
Jon Hall146f1522015-03-24 15:33:24 -07003488
Jon Hallbd16b922015-03-26 17:53:15 -07003489 def activateApp( self, appName, check=True ):
Jon Hall146f1522015-03-24 15:33:24 -07003490 """
3491 Activate an app that is already installed in ONOS
Jon Hallbd16b922015-03-26 17:53:15 -07003492 appName is the hierarchical app name, not the feature name
3493 If check is True, method will check the status of the app after the
3494 command is issued
Jon Hall146f1522015-03-24 15:33:24 -07003495 Returns main.TRUE if the command was successfully sent
3496 main.FALSE if the cli responded with an error or given
3497 incorrect input
3498 """
3499 try:
3500 if not isinstance( appName, types.StringType ):
3501 main.log.error( self.name + ".activateApp(): appName must be" +
3502 " a string" )
3503 return main.FALSE
3504 status = self.appStatus( appName )
3505 if status == "INSTALLED":
3506 response = self.app( appName, "activate" )
Jon Hallbd16b922015-03-26 17:53:15 -07003507 if check and response == main.TRUE:
3508 for i in range(10): # try 10 times then give up
Jon Hallbd16b922015-03-26 17:53:15 -07003509 status = self.appStatus( appName )
3510 if status == "ACTIVE":
3511 return main.TRUE
3512 else:
Jon Hall050e1bd2015-03-30 13:33:02 -07003513 main.log.debug( "The state of application " +
3514 appName + " is " + status )
Jon Hallbd16b922015-03-26 17:53:15 -07003515 time.sleep( 1 )
3516 return main.FALSE
3517 else: # not 'check' or command didn't succeed
3518 return response
Jon Hall146f1522015-03-24 15:33:24 -07003519 elif status == "ACTIVE":
3520 return main.TRUE
3521 elif status == "UNINSTALLED":
3522 main.log.error( self.name + ": Tried to activate the " +
3523 "application '" + appName + "' which is not " +
3524 "installed." )
3525 else:
3526 main.log.error( "Unexpected return value from appStatus: " +
3527 str( status ) )
3528 return main.ERROR
3529 except TypeError:
3530 main.log.exception( self.name + ": Object not as expected" )
3531 return main.ERROR
3532 except pexpect.EOF:
3533 main.log.error( self.name + ": EOF exception found" )
3534 main.log.error( self.name + ": " + self.handle.before )
3535 main.cleanup()
3536 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003537 except Exception:
Jon Hall146f1522015-03-24 15:33:24 -07003538 main.log.exception( self.name + ": Uncaught exception!" )
3539 main.cleanup()
3540 main.exit()
3541
Jon Hallbd16b922015-03-26 17:53:15 -07003542 def deactivateApp( self, appName, check=True ):
Jon Hall146f1522015-03-24 15:33:24 -07003543 """
3544 Deactivate an app that is already activated in ONOS
Jon Hallbd16b922015-03-26 17:53:15 -07003545 appName is the hierarchical app name, not the feature name
3546 If check is True, method will check the status of the app after the
3547 command is issued
Jon Hall146f1522015-03-24 15:33:24 -07003548 Returns main.TRUE if the command was successfully sent
3549 main.FALSE if the cli responded with an error or given
3550 incorrect input
3551 """
3552 try:
3553 if not isinstance( appName, types.StringType ):
3554 main.log.error( self.name + ".deactivateApp(): appName must " +
3555 "be a string" )
3556 return main.FALSE
3557 status = self.appStatus( appName )
3558 if status == "INSTALLED":
3559 return main.TRUE
3560 elif status == "ACTIVE":
3561 response = self.app( appName, "deactivate" )
Jon Hallbd16b922015-03-26 17:53:15 -07003562 if check and response == main.TRUE:
3563 for i in range(10): # try 10 times then give up
3564 status = self.appStatus( appName )
3565 if status == "INSTALLED":
3566 return main.TRUE
3567 else:
3568 time.sleep( 1 )
3569 return main.FALSE
3570 else: # not check or command didn't succeed
3571 return response
Jon Hall146f1522015-03-24 15:33:24 -07003572 elif status == "UNINSTALLED":
3573 main.log.warn( self.name + ": Tried to deactivate the " +
3574 "application '" + appName + "' which is not " +
3575 "installed." )
3576 return main.TRUE
3577 else:
3578 main.log.error( "Unexpected return value from appStatus: " +
3579 str( status ) )
3580 return main.ERROR
3581 except TypeError:
3582 main.log.exception( self.name + ": Object not as expected" )
3583 return main.ERROR
3584 except pexpect.EOF:
3585 main.log.error( self.name + ": EOF exception found" )
3586 main.log.error( self.name + ": " + self.handle.before )
3587 main.cleanup()
3588 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003589 except Exception:
Jon Hall146f1522015-03-24 15:33:24 -07003590 main.log.exception( self.name + ": Uncaught exception!" )
3591 main.cleanup()
3592 main.exit()
3593
Jon Hallbd16b922015-03-26 17:53:15 -07003594 def uninstallApp( self, appName, check=True ):
Jon Hall146f1522015-03-24 15:33:24 -07003595 """
3596 Uninstall an app that is already installed in ONOS
Jon Hallbd16b922015-03-26 17:53:15 -07003597 appName is the hierarchical app name, not the feature name
3598 If check is True, method will check the status of the app after the
3599 command is issued
Jon Hall146f1522015-03-24 15:33:24 -07003600 Returns main.TRUE if the command was successfully sent
3601 main.FALSE if the cli responded with an error or given
3602 incorrect input
3603 """
3604 # TODO: check with Thomas about the state machine for apps
3605 try:
3606 if not isinstance( appName, types.StringType ):
3607 main.log.error( self.name + ".uninstallApp(): appName must " +
3608 "be a string" )
3609 return main.FALSE
3610 status = self.appStatus( appName )
3611 if status == "INSTALLED":
3612 response = self.app( appName, "uninstall" )
Jon Hallbd16b922015-03-26 17:53:15 -07003613 if check and response == main.TRUE:
3614 for i in range(10): # try 10 times then give up
3615 status = self.appStatus( appName )
3616 if status == "UNINSTALLED":
3617 return main.TRUE
3618 else:
3619 time.sleep( 1 )
3620 return main.FALSE
3621 else: # not check or command didn't succeed
3622 return response
Jon Hall146f1522015-03-24 15:33:24 -07003623 elif status == "ACTIVE":
3624 main.log.warn( self.name + ": Tried to uninstall the " +
3625 "application '" + appName + "' which is " +
3626 "currently active." )
3627 response = self.app( appName, "uninstall" )
Jon Hallbd16b922015-03-26 17:53:15 -07003628 if check and response == main.TRUE:
3629 for i in range(10): # try 10 times then give up
3630 status = self.appStatus( appName )
3631 if status == "UNINSTALLED":
3632 return main.TRUE
3633 else:
3634 time.sleep( 1 )
3635 return main.FALSE
3636 else: # not check or command didn't succeed
3637 return response
Jon Hall146f1522015-03-24 15:33:24 -07003638 elif status == "UNINSTALLED":
3639 return main.TRUE
3640 else:
3641 main.log.error( "Unexpected return value from appStatus: " +
3642 str( status ) )
3643 return main.ERROR
3644 except TypeError:
3645 main.log.exception( self.name + ": Object not as expected" )
3646 return main.ERROR
3647 except pexpect.EOF:
3648 main.log.error( self.name + ": EOF exception found" )
3649 main.log.error( self.name + ": " + self.handle.before )
3650 main.cleanup()
3651 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003652 except Exception:
Jon Hall146f1522015-03-24 15:33:24 -07003653 main.log.exception( self.name + ": Uncaught exception!" )
3654 main.cleanup()
3655 main.exit()
Jon Hallbd16b922015-03-26 17:53:15 -07003656
3657 def appIDs( self, jsonFormat=True ):
3658 """
3659 Show the mappings between app id and app names given by the 'app-ids'
3660 cli command
3661 """
3662 try:
3663 cmdStr = "app-ids"
3664 if jsonFormat:
3665 cmdStr += " -j"
Jon Hallc6358dd2015-04-10 12:44:28 -07003666 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003667 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003668 assert "Command not found:" not in output, output
3669 assert "Error executing command" not in output, output
Jon Hallc6358dd2015-04-10 12:44:28 -07003670 return output
Jon Hallbd16b922015-03-26 17:53:15 -07003671 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08003672 main.log.exception( "Error in processing onos:app-ids command." )
Jon Hallbd16b922015-03-26 17:53:15 -07003673 return None
3674 except TypeError:
3675 main.log.exception( self.name + ": Object not as expected" )
3676 return None
3677 except pexpect.EOF:
3678 main.log.error( self.name + ": EOF exception found" )
3679 main.log.error( self.name + ": " + self.handle.before )
3680 main.cleanup()
3681 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003682 except Exception:
Jon Hallbd16b922015-03-26 17:53:15 -07003683 main.log.exception( self.name + ": Uncaught exception!" )
3684 main.cleanup()
3685 main.exit()
3686
3687 def appToIDCheck( self ):
3688 """
3689 This method will check that each application's ID listed in 'apps' is
3690 the same as the ID listed in 'app-ids'. The check will also check that
3691 there are no duplicate IDs issued. Note that an app ID should be
3692 a globaly unique numerical identifier for app/app-like features. Once
3693 an ID is registered, the ID is never freed up so that if an app is
3694 reinstalled it will have the same ID.
3695
3696 Returns: main.TRUE if the check passes and
3697 main.FALSE if the check fails or
3698 main.ERROR if there is some error in processing the test
3699 """
3700 try:
Jon Hall390696c2015-05-05 17:13:41 -07003701 bail = False
Jon Hallc6793552016-01-19 14:18:37 -08003702 rawJson = self.appIDs( jsonFormat=True )
3703 if rawJson:
3704 ids = json.loads( rawJson )
Jon Hall390696c2015-05-05 17:13:41 -07003705 else:
Jon Hallc6793552016-01-19 14:18:37 -08003706 main.log.error( "app-ids returned nothing:" + repr( rawJson ) )
Jon Hall390696c2015-05-05 17:13:41 -07003707 bail = True
Jon Hallc6793552016-01-19 14:18:37 -08003708 rawJson = self.apps( jsonFormat=True )
3709 if rawJson:
3710 apps = json.loads( rawJson )
Jon Hall390696c2015-05-05 17:13:41 -07003711 else:
Jon Hallc6793552016-01-19 14:18:37 -08003712 main.log.error( "apps returned nothing:" + repr( rawJson ) )
Jon Hall390696c2015-05-05 17:13:41 -07003713 bail = True
3714 if bail:
3715 return main.FALSE
Jon Hallbd16b922015-03-26 17:53:15 -07003716 result = main.TRUE
3717 for app in apps:
3718 appID = app.get( 'id' )
3719 if appID is None:
3720 main.log.error( "Error parsing app: " + str( app ) )
3721 result = main.FALSE
3722 appName = app.get( 'name' )
3723 if appName is None:
3724 main.log.error( "Error parsing app: " + str( app ) )
3725 result = main.FALSE
3726 # get the entry in ids that has the same appID
Jon Hall390696c2015-05-05 17:13:41 -07003727 current = filter( lambda item: item[ 'id' ] == appID, ids )
Jon Hall050e1bd2015-03-30 13:33:02 -07003728 # main.log.debug( "Comparing " + str( app ) + " to " +
3729 # str( current ) )
Jon Hallbd16b922015-03-26 17:53:15 -07003730 if not current: # if ids doesn't have this id
3731 result = main.FALSE
3732 main.log.error( "'app-ids' does not have the ID for " +
3733 str( appName ) + " that apps does." )
3734 elif len( current ) > 1:
3735 # there is more than one app with this ID
3736 result = main.FALSE
3737 # We will log this later in the method
3738 elif not current[0][ 'name' ] == appName:
3739 currentName = current[0][ 'name' ]
3740 result = main.FALSE
3741 main.log.error( "'app-ids' has " + str( currentName ) +
3742 " registered under id:" + str( appID ) +
3743 " but 'apps' has " + str( appName ) )
3744 else:
3745 pass # id and name match!
3746 # now make sure that app-ids has no duplicates
3747 idsList = []
3748 namesList = []
3749 for item in ids:
3750 idsList.append( item[ 'id' ] )
3751 namesList.append( item[ 'name' ] )
3752 if len( idsList ) != len( set( idsList ) ) or\
3753 len( namesList ) != len( set( namesList ) ):
3754 main.log.error( "'app-ids' has some duplicate entries: \n"
3755 + json.dumps( ids,
3756 sort_keys=True,
3757 indent=4,
3758 separators=( ',', ': ' ) ) )
3759 result = main.FALSE
3760 return result
Jon Hallc6793552016-01-19 14:18:37 -08003761 except ( TypeError, ValueError ):
3762 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, rawJson ) )
Jon Hallbd16b922015-03-26 17:53:15 -07003763 return main.ERROR
3764 except pexpect.EOF:
3765 main.log.error( self.name + ": EOF exception found" )
3766 main.log.error( self.name + ": " + self.handle.before )
3767 main.cleanup()
3768 main.exit()
Jon Hall77ba41c2015-04-06 10:25:40 -07003769 except Exception:
Jon Hallbd16b922015-03-26 17:53:15 -07003770 main.log.exception( self.name + ": Uncaught exception!" )
3771 main.cleanup()
3772 main.exit()
3773
Jon Hallfb760a02015-04-13 15:35:03 -07003774 def getCfg( self, component=None, propName=None, short=False,
3775 jsonFormat=True ):
3776 """
3777 Get configuration settings from onos cli
3778 Optional arguments:
3779 component - Optionally only list configurations for a specific
3780 component. If None, all components with configurations
3781 are displayed. Case Sensitive string.
3782 propName - If component is specified, propName option will show
3783 only this specific configuration from that component.
3784 Case Sensitive string.
3785 jsonFormat - Returns output as json. Note that this will override
3786 the short option
3787 short - Short, less verbose, version of configurations.
3788 This is overridden by the json option
3789 returns:
3790 Output from cli as a string or None on error
3791 """
3792 try:
3793 baseStr = "cfg"
3794 cmdStr = " get"
3795 componentStr = ""
3796 if component:
3797 componentStr += " " + component
3798 if propName:
3799 componentStr += " " + propName
3800 if jsonFormat:
3801 baseStr += " -j"
3802 elif short:
3803 baseStr += " -s"
3804 output = self.sendline( baseStr + cmdStr + componentStr )
Jon Halla495f562016-05-16 18:03:26 -07003805 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003806 assert "Command not found:" not in output, output
3807 assert "Error executing command" not in output, output
Jon Hallfb760a02015-04-13 15:35:03 -07003808 return output
3809 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08003810 main.log.exception( "Error in processing 'cfg get' command." )
Jon Hallfb760a02015-04-13 15:35:03 -07003811 return None
3812 except TypeError:
3813 main.log.exception( self.name + ": Object not as expected" )
3814 return None
3815 except pexpect.EOF:
3816 main.log.error( self.name + ": EOF exception found" )
3817 main.log.error( self.name + ": " + self.handle.before )
3818 main.cleanup()
3819 main.exit()
3820 except Exception:
3821 main.log.exception( self.name + ": Uncaught exception!" )
3822 main.cleanup()
3823 main.exit()
3824
3825 def setCfg( self, component, propName, value=None, check=True ):
3826 """
3827 Set/Unset configuration settings from ONOS cli
Jon Hall390696c2015-05-05 17:13:41 -07003828 Required arguments:
Jon Hallfb760a02015-04-13 15:35:03 -07003829 component - The case sensitive name of the component whose
3830 property is to be set
3831 propName - The case sensitive name of the property to be set/unset
Jon Hall390696c2015-05-05 17:13:41 -07003832 Optional arguments:
Jon Hallfb760a02015-04-13 15:35:03 -07003833 value - The value to set the property to. If None, will unset the
3834 property and revert it to it's default value(if applicable)
3835 check - Boolean, Check whether the option was successfully set this
3836 only applies when a value is given.
3837 returns:
3838 main.TRUE on success or main.FALSE on failure. If check is False,
3839 will return main.TRUE unless there is an error
3840 """
3841 try:
3842 baseStr = "cfg"
3843 cmdStr = " set " + str( component ) + " " + str( propName )
3844 if value is not None:
3845 cmdStr += " " + str( value )
3846 output = self.sendline( baseStr + cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003847 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003848 assert "Command not found:" not in output, output
3849 assert "Error executing command" not in output, output
Jon Hallfb760a02015-04-13 15:35:03 -07003850 if value and check:
3851 results = self.getCfg( component=str( component ),
3852 propName=str( propName ),
3853 jsonFormat=True )
3854 # Check if current value is what we just set
3855 try:
3856 jsonOutput = json.loads( results )
3857 current = jsonOutput[ 'value' ]
Jon Hallc6793552016-01-19 14:18:37 -08003858 except ( TypeError, ValueError ):
Jon Hallfb760a02015-04-13 15:35:03 -07003859 main.log.exception( "Error parsing cfg output" )
3860 main.log.error( "output:" + repr( results ) )
3861 return main.FALSE
3862 if current == str( value ):
3863 return main.TRUE
3864 return main.FALSE
3865 return main.TRUE
3866 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08003867 main.log.exception( "Error in processing 'cfg set' command." )
Jon Hallfb760a02015-04-13 15:35:03 -07003868 return main.FALSE
Jon Hallc6793552016-01-19 14:18:37 -08003869 except ( TypeError, ValueError ):
3870 main.log.exception( "{}: Object not as expected: {!r}".format( self.name, results ) )
Jon Hallfb760a02015-04-13 15:35:03 -07003871 return main.FALSE
3872 except pexpect.EOF:
3873 main.log.error( self.name + ": EOF exception found" )
3874 main.log.error( self.name + ": " + self.handle.before )
3875 main.cleanup()
3876 main.exit()
3877 except Exception:
3878 main.log.exception( self.name + ": Uncaught exception!" )
3879 main.cleanup()
3880 main.exit()
3881
Jon Hall390696c2015-05-05 17:13:41 -07003882 def setTestAdd( self, setName, values ):
3883 """
3884 CLI command to add elements to a distributed set.
3885 Arguments:
3886 setName - The name of the set to add to.
3887 values - The value(s) to add to the set, space seperated.
3888 Example usages:
3889 setTestAdd( "set1", "a b c" )
3890 setTestAdd( "set2", "1" )
3891 returns:
3892 main.TRUE on success OR
3893 main.FALSE if elements were already in the set OR
3894 main.ERROR on error
3895 """
3896 try:
3897 cmdStr = "set-test-add " + str( setName ) + " " + str( values )
3898 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003899 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003900 assert "Command not found:" not in output, output
Jon Hallfeff3082015-05-19 10:23:26 -07003901 try:
3902 # TODO: Maybe make this less hardcoded
3903 # ConsistentMap Exceptions
3904 assert "org.onosproject.store.service" not in output
3905 # Node not leader
3906 assert "java.lang.IllegalStateException" not in output
3907 except AssertionError:
Jon Halle1a3b752015-07-22 13:02:46 -07003908 main.log.error( "Error in processing '" + cmdStr + "' " +
Jon Hallfeff3082015-05-19 10:23:26 -07003909 "command: " + str( output ) )
3910 retryTime = 30 # Conservative time, given by Madan
3911 main.log.info( "Waiting " + str( retryTime ) +
3912 "seconds before retrying." )
3913 time.sleep( retryTime ) # Due to change in mastership
3914 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003915 assert output is not None, "Error in sendline"
Jon Hall390696c2015-05-05 17:13:41 -07003916 assert "Error executing command" not in output
3917 positiveMatch = "\[(.*)\] was added to the set " + str( setName )
3918 negativeMatch = "\[(.*)\] was already in set " + str( setName )
3919 main.log.info( self.name + ": " + output )
3920 if re.search( positiveMatch, output):
3921 return main.TRUE
3922 elif re.search( negativeMatch, output):
3923 return main.FALSE
3924 else:
3925 main.log.error( self.name + ": setTestAdd did not" +
3926 " match expected output" )
Jon Hall390696c2015-05-05 17:13:41 -07003927 main.log.debug( self.name + " actual: " + repr( output ) )
3928 return main.ERROR
3929 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08003930 main.log.exception( "Error in processing '" + cmdStr + "' command. " )
Jon Hall390696c2015-05-05 17:13:41 -07003931 return main.ERROR
3932 except TypeError:
3933 main.log.exception( self.name + ": Object not as expected" )
3934 return main.ERROR
3935 except pexpect.EOF:
3936 main.log.error( self.name + ": EOF exception found" )
3937 main.log.error( self.name + ": " + self.handle.before )
3938 main.cleanup()
3939 main.exit()
3940 except Exception:
3941 main.log.exception( self.name + ": Uncaught exception!" )
3942 main.cleanup()
3943 main.exit()
3944
3945 def setTestRemove( self, setName, values, clear=False, retain=False ):
3946 """
3947 CLI command to remove elements from a distributed set.
3948 Required arguments:
3949 setName - The name of the set to remove from.
3950 values - The value(s) to remove from the set, space seperated.
3951 Optional arguments:
3952 clear - Clear all elements from the set
3953 retain - Retain only the given values. (intersection of the
3954 original set and the given set)
3955 returns:
3956 main.TRUE on success OR
3957 main.FALSE if the set was not changed OR
3958 main.ERROR on error
3959 """
3960 try:
3961 cmdStr = "set-test-remove "
3962 if clear:
3963 cmdStr += "-c " + str( setName )
3964 elif retain:
3965 cmdStr += "-r " + str( setName ) + " " + str( values )
3966 else:
3967 cmdStr += str( setName ) + " " + str( values )
3968 output = self.sendline( cmdStr )
Jon Hallfeff3082015-05-19 10:23:26 -07003969 try:
Jon Halla495f562016-05-16 18:03:26 -07003970 assert output is not None, "Error in sendline"
Jon Hallfeff3082015-05-19 10:23:26 -07003971 # TODO: Maybe make this less hardcoded
3972 # ConsistentMap Exceptions
3973 assert "org.onosproject.store.service" not in output
3974 # Node not leader
3975 assert "java.lang.IllegalStateException" not in output
3976 except AssertionError:
Jon Halle1a3b752015-07-22 13:02:46 -07003977 main.log.error( "Error in processing '" + cmdStr + "' " +
Jon Hallfeff3082015-05-19 10:23:26 -07003978 "command: " + str( output ) )
3979 retryTime = 30 # Conservative time, given by Madan
3980 main.log.info( "Waiting " + str( retryTime ) +
3981 "seconds before retrying." )
3982 time.sleep( retryTime ) # Due to change in mastership
3983 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07003984 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08003985 assert "Command not found:" not in output, output
3986 assert "Error executing command" not in output, output
Jon Hall390696c2015-05-05 17:13:41 -07003987 main.log.info( self.name + ": " + output )
3988 if clear:
3989 pattern = "Set " + str( setName ) + " cleared"
3990 if re.search( pattern, output ):
3991 return main.TRUE
3992 elif retain:
3993 positivePattern = str( setName ) + " was pruned to contain " +\
3994 "only elements of set \[(.*)\]"
3995 negativePattern = str( setName ) + " was not changed by " +\
3996 "retaining only elements of the set " +\
3997 "\[(.*)\]"
3998 if re.search( positivePattern, output ):
3999 return main.TRUE
4000 elif re.search( negativePattern, output ):
4001 return main.FALSE
4002 else:
4003 positivePattern = "\[(.*)\] was removed from the set " +\
4004 str( setName )
4005 if ( len( values.split() ) == 1 ):
4006 negativePattern = "\[(.*)\] was not in set " +\
4007 str( setName )
4008 else:
4009 negativePattern = "No element of \[(.*)\] was in set " +\
4010 str( setName )
4011 if re.search( positivePattern, output ):
4012 return main.TRUE
4013 elif re.search( negativePattern, output ):
4014 return main.FALSE
4015 main.log.error( self.name + ": setTestRemove did not" +
4016 " match expected output" )
4017 main.log.debug( self.name + " expected: " + pattern )
4018 main.log.debug( self.name + " actual: " + repr( output ) )
4019 return main.ERROR
4020 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08004021 main.log.exception( "Error in processing '" + cmdStr + "' commandr. " )
Jon Hall390696c2015-05-05 17:13:41 -07004022 return main.ERROR
4023 except TypeError:
4024 main.log.exception( self.name + ": Object not as expected" )
4025 return main.ERROR
4026 except pexpect.EOF:
4027 main.log.error( self.name + ": EOF exception found" )
4028 main.log.error( self.name + ": " + self.handle.before )
4029 main.cleanup()
4030 main.exit()
4031 except Exception:
4032 main.log.exception( self.name + ": Uncaught exception!" )
4033 main.cleanup()
4034 main.exit()
4035
4036 def setTestGet( self, setName, values="" ):
4037 """
4038 CLI command to get the elements in a distributed set.
4039 Required arguments:
4040 setName - The name of the set to remove from.
4041 Optional arguments:
4042 values - The value(s) to check if in the set, space seperated.
4043 returns:
4044 main.ERROR on error OR
4045 A list of elements in the set if no optional arguments are
4046 supplied OR
4047 A tuple containing the list then:
4048 main.FALSE if the given values are not in the set OR
4049 main.TRUE if the given values are in the set OR
4050 """
4051 try:
4052 values = str( values ).strip()
4053 setName = str( setName ).strip()
4054 length = len( values.split() )
4055 containsCheck = None
4056 # Patterns to match
4057 setPattern = "\[(.*)\]"
4058 pattern = "Items in set " + setName + ":\n" + setPattern
4059 containsTrue = "Set " + setName + " contains the value " + values
4060 containsFalse = "Set " + setName + " did not contain the value " +\
4061 values
4062 containsAllTrue = "Set " + setName + " contains the the subset " +\
4063 setPattern
4064 containsAllFalse = "Set " + setName + " did not contain the the" +\
4065 " subset " + setPattern
4066
4067 cmdStr = "set-test-get "
4068 cmdStr += setName + " " + values
4069 output = self.sendline( cmdStr )
Jon Hallfeff3082015-05-19 10:23:26 -07004070 try:
Jon Halla495f562016-05-16 18:03:26 -07004071 assert output is not None, "Error in sendline"
Jon Hallfeff3082015-05-19 10:23:26 -07004072 # TODO: Maybe make this less hardcoded
4073 # ConsistentMap Exceptions
4074 assert "org.onosproject.store.service" not in output
4075 # Node not leader
4076 assert "java.lang.IllegalStateException" not in output
4077 except AssertionError:
Jon Halle1a3b752015-07-22 13:02:46 -07004078 main.log.error( "Error in processing '" + cmdStr + "' " +
Jon Hallfeff3082015-05-19 10:23:26 -07004079 "command: " + str( output ) )
4080 retryTime = 30 # Conservative time, given by Madan
4081 main.log.info( "Waiting " + str( retryTime ) +
4082 "seconds before retrying." )
4083 time.sleep( retryTime ) # Due to change in mastership
4084 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07004085 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004086 assert "Command not found:" not in output, output
4087 assert "Error executing command" not in output, output
Jon Hall390696c2015-05-05 17:13:41 -07004088 main.log.info( self.name + ": " + output )
4089
4090 if length == 0:
4091 match = re.search( pattern, output )
4092 else: # if given values
4093 if length == 1: # Contains output
4094 patternTrue = pattern + "\n" + containsTrue
4095 patternFalse = pattern + "\n" + containsFalse
4096 else: # ContainsAll output
4097 patternTrue = pattern + "\n" + containsAllTrue
4098 patternFalse = pattern + "\n" + containsAllFalse
4099 matchTrue = re.search( patternTrue, output )
4100 matchFalse = re.search( patternFalse, output )
4101 if matchTrue:
4102 containsCheck = main.TRUE
4103 match = matchTrue
4104 elif matchFalse:
4105 containsCheck = main.FALSE
4106 match = matchFalse
4107 else:
4108 main.log.error( self.name + " setTestGet did not match " +\
4109 "expected output" )
4110 main.log.debug( self.name + " expected: " + pattern )
4111 main.log.debug( self.name + " actual: " + repr( output ) )
4112 match = None
4113 if match:
4114 setMatch = match.group( 1 )
4115 if setMatch == '':
4116 setList = []
4117 else:
4118 setList = setMatch.split( ", " )
4119 if length > 0:
4120 return ( setList, containsCheck )
4121 else:
4122 return setList
4123 else: # no match
4124 main.log.error( self.name + ": setTestGet did not" +
4125 " match expected output" )
4126 main.log.debug( self.name + " expected: " + pattern )
4127 main.log.debug( self.name + " actual: " + repr( output ) )
4128 return main.ERROR
4129 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08004130 main.log.exception( "Error in processing '" + cmdStr + "' command." )
Jon Hall390696c2015-05-05 17:13:41 -07004131 return main.ERROR
4132 except TypeError:
4133 main.log.exception( self.name + ": Object not as expected" )
4134 return main.ERROR
4135 except pexpect.EOF:
4136 main.log.error( self.name + ": EOF exception found" )
4137 main.log.error( self.name + ": " + self.handle.before )
4138 main.cleanup()
4139 main.exit()
4140 except Exception:
4141 main.log.exception( self.name + ": Uncaught exception!" )
4142 main.cleanup()
4143 main.exit()
4144
4145 def setTestSize( self, setName ):
4146 """
4147 CLI command to get the elements in a distributed set.
4148 Required arguments:
4149 setName - The name of the set to remove from.
4150 returns:
Jon Hallfeff3082015-05-19 10:23:26 -07004151 The integer value of the size returned or
Jon Hall390696c2015-05-05 17:13:41 -07004152 None on error
4153 """
4154 try:
4155 # TODO: Should this check against the number of elements returned
4156 # and then return true/false based on that?
4157 setName = str( setName ).strip()
4158 # Patterns to match
4159 setPattern = "\[(.*)\]"
4160 pattern = "There are (\d+) items in set " + setName + ":\n" +\
4161 setPattern
4162 cmdStr = "set-test-get -s "
4163 cmdStr += setName
4164 output = self.sendline( cmdStr )
Jon Hallfeff3082015-05-19 10:23:26 -07004165 try:
Jon Halla495f562016-05-16 18:03:26 -07004166 assert output is not None, "Error in sendline"
Jon Hallfeff3082015-05-19 10:23:26 -07004167 # TODO: Maybe make this less hardcoded
4168 # ConsistentMap Exceptions
4169 assert "org.onosproject.store.service" not in output
4170 # Node not leader
4171 assert "java.lang.IllegalStateException" not in output
4172 except AssertionError:
Jon Halle1a3b752015-07-22 13:02:46 -07004173 main.log.error( "Error in processing '" + cmdStr + "' " +
Jon Hallfeff3082015-05-19 10:23:26 -07004174 "command: " + str( output ) )
4175 retryTime = 30 # Conservative time, given by Madan
4176 main.log.info( "Waiting " + str( retryTime ) +
4177 "seconds before retrying." )
4178 time.sleep( retryTime ) # Due to change in mastership
4179 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07004180 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004181 assert "Command not found:" not in output, output
4182 assert "Error executing command" not in output, output
Jon Hall390696c2015-05-05 17:13:41 -07004183 main.log.info( self.name + ": " + output )
4184 match = re.search( pattern, output )
4185 if match:
4186 setSize = int( match.group( 1 ) )
4187 setMatch = match.group( 2 )
4188 if len( setMatch.split() ) == setSize:
4189 main.log.info( "The size returned by " + self.name +
4190 " matches the number of elements in " +
4191 "the returned set" )
4192 else:
4193 main.log.error( "The size returned by " + self.name +
4194 " does not match the number of " +
4195 "elements in the returned set." )
4196 return setSize
4197 else: # no match
4198 main.log.error( self.name + ": setTestGet did not" +
4199 " match expected output" )
4200 main.log.debug( self.name + " expected: " + pattern )
4201 main.log.debug( self.name + " actual: " + repr( output ) )
4202 return None
4203 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08004204 main.log.exception( "Error in processing '" + cmdStr + "' command." )
acsmarsa4a4d1e2015-07-10 16:01:24 -07004205 return None
Jon Hall390696c2015-05-05 17:13:41 -07004206 except TypeError:
4207 main.log.exception( self.name + ": Object not as expected" )
4208 return None
4209 except pexpect.EOF:
4210 main.log.error( self.name + ": EOF exception found" )
4211 main.log.error( self.name + ": " + self.handle.before )
4212 main.cleanup()
4213 main.exit()
4214 except Exception:
4215 main.log.exception( self.name + ": Uncaught exception!" )
4216 main.cleanup()
4217 main.exit()
4218
Jon Hall80daded2015-05-27 16:07:00 -07004219 def counters( self, jsonFormat=True ):
Jon Hall390696c2015-05-05 17:13:41 -07004220 """
4221 Command to list the various counters in the system.
4222 returns:
Jon Hall80daded2015-05-27 16:07:00 -07004223 if jsonFormat, a string of the json object returned by the cli
4224 command
4225 if not jsonFormat, the normal string output of the cli command
Jon Hall390696c2015-05-05 17:13:41 -07004226 None on error
4227 """
Jon Hall390696c2015-05-05 17:13:41 -07004228 try:
4229 counters = {}
4230 cmdStr = "counters"
Jon Hall80daded2015-05-27 16:07:00 -07004231 if jsonFormat:
4232 cmdStr += " -j"
Jon Hall390696c2015-05-05 17:13:41 -07004233 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07004234 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004235 assert "Command not found:" not in output, output
4236 assert "Error executing command" not in output, output
Jon Hall390696c2015-05-05 17:13:41 -07004237 main.log.info( self.name + ": " + output )
Jon Hall80daded2015-05-27 16:07:00 -07004238 return output
Jon Hall390696c2015-05-05 17:13:41 -07004239 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08004240 main.log.exception( "Error in processing 'counters' command." )
Jon Hall80daded2015-05-27 16:07:00 -07004241 return None
Jon Hall390696c2015-05-05 17:13:41 -07004242 except TypeError:
4243 main.log.exception( self.name + ": Object not as expected" )
Jon Hall80daded2015-05-27 16:07:00 -07004244 return None
Jon Hall390696c2015-05-05 17:13:41 -07004245 except pexpect.EOF:
4246 main.log.error( self.name + ": EOF exception found" )
4247 main.log.error( self.name + ": " + self.handle.before )
4248 main.cleanup()
4249 main.exit()
4250 except Exception:
4251 main.log.exception( self.name + ": Uncaught exception!" )
4252 main.cleanup()
4253 main.exit()
4254
Jon Hall935db192016-04-19 00:22:04 -07004255 def counterTestAddAndGet( self, counter, delta=1 ):
Jon Hall390696c2015-05-05 17:13:41 -07004256 """
Jon Halle1a3b752015-07-22 13:02:46 -07004257 CLI command to add a delta to then get a distributed counter.
Jon Hall390696c2015-05-05 17:13:41 -07004258 Required arguments:
4259 counter - The name of the counter to increment.
4260 Optional arguments:
Jon Halle1a3b752015-07-22 13:02:46 -07004261 delta - The long to add to the counter
Jon Hall390696c2015-05-05 17:13:41 -07004262 returns:
4263 integer value of the counter or
4264 None on Error
4265 """
4266 try:
4267 counter = str( counter )
Jon Halle1a3b752015-07-22 13:02:46 -07004268 delta = int( delta )
Jon Hall390696c2015-05-05 17:13:41 -07004269 cmdStr = "counter-test-increment "
Jon Hall390696c2015-05-05 17:13:41 -07004270 cmdStr += counter
Jon Halle1a3b752015-07-22 13:02:46 -07004271 if delta != 1:
4272 cmdStr += " " + str( delta )
Jon Hall390696c2015-05-05 17:13:41 -07004273 output = self.sendline( cmdStr )
Jon Hallfeff3082015-05-19 10:23:26 -07004274 try:
Jon Halla495f562016-05-16 18:03:26 -07004275 assert output is not None, "Error in sendline"
Jon Hallfeff3082015-05-19 10:23:26 -07004276 # TODO: Maybe make this less hardcoded
4277 # ConsistentMap Exceptions
4278 assert "org.onosproject.store.service" not in output
4279 # Node not leader
4280 assert "java.lang.IllegalStateException" not in output
4281 except AssertionError:
Jon Halle1a3b752015-07-22 13:02:46 -07004282 main.log.error( "Error in processing '" + cmdStr + "' " +
Jon Hallfeff3082015-05-19 10:23:26 -07004283 "command: " + str( output ) )
4284 retryTime = 30 # Conservative time, given by Madan
4285 main.log.info( "Waiting " + str( retryTime ) +
4286 "seconds before retrying." )
4287 time.sleep( retryTime ) # Due to change in mastership
4288 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07004289 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004290 assert "Command not found:" not in output, output
4291 assert "Error executing command" not in output, output
Jon Hall390696c2015-05-05 17:13:41 -07004292 main.log.info( self.name + ": " + output )
Jon Halle1a3b752015-07-22 13:02:46 -07004293 pattern = counter + " was updated to (-?\d+)"
Jon Hall390696c2015-05-05 17:13:41 -07004294 match = re.search( pattern, output )
4295 if match:
4296 return int( match.group( 1 ) )
4297 else:
Jon Halle1a3b752015-07-22 13:02:46 -07004298 main.log.error( self.name + ": counterTestAddAndGet did not" +
Jon Hall390696c2015-05-05 17:13:41 -07004299 " match expected output." )
4300 main.log.debug( self.name + " expected: " + pattern )
4301 main.log.debug( self.name + " actual: " + repr( output ) )
4302 return None
4303 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08004304 main.log.exception( "Error in processing '" + cmdStr + "' command." )
Jon Hall390696c2015-05-05 17:13:41 -07004305 return None
4306 except TypeError:
4307 main.log.exception( self.name + ": Object not as expected" )
4308 return None
4309 except pexpect.EOF:
4310 main.log.error( self.name + ": EOF exception found" )
4311 main.log.error( self.name + ": " + self.handle.before )
4312 main.cleanup()
4313 main.exit()
4314 except Exception:
4315 main.log.exception( self.name + ": Uncaught exception!" )
4316 main.cleanup()
4317 main.exit()
4318
Jon Hall935db192016-04-19 00:22:04 -07004319 def counterTestGetAndAdd( self, counter, delta=1 ):
Jon Halle1a3b752015-07-22 13:02:46 -07004320 """
4321 CLI command to get a distributed counter then add a delta to it.
4322 Required arguments:
4323 counter - The name of the counter to increment.
4324 Optional arguments:
4325 delta - The long to add to the counter
Jon Halle1a3b752015-07-22 13:02:46 -07004326 returns:
4327 integer value of the counter or
4328 None on Error
4329 """
4330 try:
4331 counter = str( counter )
4332 delta = int( delta )
4333 cmdStr = "counter-test-increment -g "
Jon Halle1a3b752015-07-22 13:02:46 -07004334 cmdStr += counter
4335 if delta != 1:
4336 cmdStr += " " + str( delta )
4337 output = self.sendline( cmdStr )
4338 try:
Jon Halla495f562016-05-16 18:03:26 -07004339 assert output is not None, "Error in sendline"
Jon Halle1a3b752015-07-22 13:02:46 -07004340 # TODO: Maybe make this less hardcoded
4341 # ConsistentMap Exceptions
4342 assert "org.onosproject.store.service" not in output
4343 # Node not leader
4344 assert "java.lang.IllegalStateException" not in output
4345 except AssertionError:
4346 main.log.error( "Error in processing '" + cmdStr + "' " +
4347 "command: " + str( output ) )
4348 retryTime = 30 # Conservative time, given by Madan
4349 main.log.info( "Waiting " + str( retryTime ) +
4350 "seconds before retrying." )
4351 time.sleep( retryTime ) # Due to change in mastership
4352 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07004353 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004354 assert "Command not found:" not in output, output
4355 assert "Error executing command" not in output, output
Jon Halle1a3b752015-07-22 13:02:46 -07004356 main.log.info( self.name + ": " + output )
4357 pattern = counter + " was updated to (-?\d+)"
4358 match = re.search( pattern, output )
4359 if match:
4360 return int( match.group( 1 ) )
4361 else:
4362 main.log.error( self.name + ": counterTestGetAndAdd did not" +
4363 " match expected output." )
4364 main.log.debug( self.name + " expected: " + pattern )
4365 main.log.debug( self.name + " actual: " + repr( output ) )
4366 return None
4367 except AssertionError:
Jon Hallc6793552016-01-19 14:18:37 -08004368 main.log.exception( "Error in processing '" + cmdStr + "' command." )
Jon Halle1a3b752015-07-22 13:02:46 -07004369 return None
4370 except TypeError:
4371 main.log.exception( self.name + ": Object not as expected" )
4372 return None
4373 except pexpect.EOF:
4374 main.log.error( self.name + ": EOF exception found" )
4375 main.log.error( self.name + ": " + self.handle.before )
4376 main.cleanup()
4377 main.exit()
4378 except Exception:
4379 main.log.exception( self.name + ": Uncaught exception!" )
4380 main.cleanup()
4381 main.exit()
4382
kelvin-onlaba297c4d2015-06-01 13:53:55 -07004383 def summary( self, jsonFormat=True ):
4384 """
4385 Description: Execute summary command in onos
4386 Returns: json object ( summary -j ), returns main.FALSE if there is
4387 no output
4388
4389 """
4390 try:
4391 cmdStr = "summary"
4392 if jsonFormat:
4393 cmdStr += " -j"
4394 handle = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07004395 assert handle is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004396 assert "Command not found:" not in handle, handle
Jon Hall6e709752016-02-01 13:38:46 -08004397 assert "Error:" not in handle, handle
kelvin-onlaba297c4d2015-06-01 13:53:55 -07004398 if not handle:
4399 main.log.error( self.name + ": There is no output in " +
4400 "summary command" )
4401 return main.FALSE
4402 return handle
Jon Hallc6793552016-01-19 14:18:37 -08004403 except AssertionError:
Jon Hall6e709752016-02-01 13:38:46 -08004404 main.log.exception( "{} Error in summary output:".format( self.name ) )
Jon Hallc6793552016-01-19 14:18:37 -08004405 return None
kelvin-onlaba297c4d2015-06-01 13:53:55 -07004406 except TypeError:
4407 main.log.exception( self.name + ": Object not as expected" )
4408 return None
4409 except pexpect.EOF:
4410 main.log.error( self.name + ": EOF exception found" )
4411 main.log.error( self.name + ": " + self.handle.before )
4412 main.cleanup()
4413 main.exit()
4414 except Exception:
4415 main.log.exception( self.name + ": Uncaught exception!" )
4416 main.cleanup()
4417 main.exit()
Jon Hall2a5002c2015-08-21 16:49:11 -07004418
Jon Hall935db192016-04-19 00:22:04 -07004419 def transactionalMapGet( self, keyName ):
Jon Hall2a5002c2015-08-21 16:49:11 -07004420 """
4421 CLI command to get the value of a key in a consistent map using
4422 transactions. This a test function and can only get keys from the
4423 test map hard coded into the cli command
4424 Required arguments:
4425 keyName - The name of the key to get
Jon Hall2a5002c2015-08-21 16:49:11 -07004426 returns:
4427 The string value of the key or
4428 None on Error
4429 """
4430 try:
4431 keyName = str( keyName )
4432 cmdStr = "transactional-map-test-get "
Jon Hall2a5002c2015-08-21 16:49:11 -07004433 cmdStr += keyName
4434 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07004435 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004436 assert "Command not found:" not in output, output
Jon Hall2a5002c2015-08-21 16:49:11 -07004437 try:
4438 # TODO: Maybe make this less hardcoded
4439 # ConsistentMap Exceptions
4440 assert "org.onosproject.store.service" not in output
4441 # Node not leader
4442 assert "java.lang.IllegalStateException" not in output
4443 except AssertionError:
4444 main.log.error( "Error in processing '" + cmdStr + "' " +
4445 "command: " + str( output ) )
4446 return None
4447 pattern = "Key-value pair \(" + keyName + ", (?P<value>.+)\) found."
4448 if "Key " + keyName + " not found." in output:
Jon Hall9bfadd22016-05-11 14:48:07 -07004449 main.log.warn( output )
Jon Hall2a5002c2015-08-21 16:49:11 -07004450 return None
4451 else:
4452 match = re.search( pattern, output )
4453 if match:
4454 return match.groupdict()[ 'value' ]
4455 else:
4456 main.log.error( self.name + ": transactionlMapGet did not" +
4457 " match expected output." )
4458 main.log.debug( self.name + " expected: " + pattern )
4459 main.log.debug( self.name + " actual: " + repr( output ) )
4460 return None
Jon Hallc6793552016-01-19 14:18:37 -08004461 except AssertionError:
4462 main.log.exception( "" )
4463 return None
Jon Hall2a5002c2015-08-21 16:49:11 -07004464 except TypeError:
4465 main.log.exception( self.name + ": Object not as expected" )
4466 return None
4467 except pexpect.EOF:
4468 main.log.error( self.name + ": EOF exception found" )
4469 main.log.error( self.name + ": " + self.handle.before )
4470 main.cleanup()
4471 main.exit()
4472 except Exception:
4473 main.log.exception( self.name + ": Uncaught exception!" )
4474 main.cleanup()
4475 main.exit()
4476
Jon Hall935db192016-04-19 00:22:04 -07004477 def transactionalMapPut( self, numKeys, value ):
Jon Hall2a5002c2015-08-21 16:49:11 -07004478 """
4479 CLI command to put a value into 'numKeys' number of keys in a
4480 consistent map using transactions. This a test function and can only
4481 put into keys named 'Key#' of the test map hard coded into the cli command
4482 Required arguments:
4483 numKeys - Number of keys to add the value to
4484 value - The string value to put into the keys
Jon Hall2a5002c2015-08-21 16:49:11 -07004485 returns:
4486 A dictionary whose keys are the name of the keys put into the map
4487 and the values of the keys are dictionaries whose key-values are
4488 'value': value put into map and optionaly
4489 'oldValue': Previous value in the key or
4490 None on Error
4491
4492 Example output
4493 { 'Key1': {'oldValue': 'oldTestValue', 'value': 'Testing'},
4494 'Key2': {'value': 'Testing'} }
4495 """
4496 try:
4497 numKeys = str( numKeys )
4498 value = str( value )
4499 cmdStr = "transactional-map-test-put "
Jon Hall2a5002c2015-08-21 16:49:11 -07004500 cmdStr += numKeys + " " + value
4501 output = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07004502 assert output is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004503 assert "Command not found:" not in output, output
Jon Hall2a5002c2015-08-21 16:49:11 -07004504 try:
4505 # TODO: Maybe make this less hardcoded
4506 # ConsistentMap Exceptions
4507 assert "org.onosproject.store.service" not in output
4508 # Node not leader
4509 assert "java.lang.IllegalStateException" not in output
4510 except AssertionError:
4511 main.log.error( "Error in processing '" + cmdStr + "' " +
4512 "command: " + str( output ) )
4513 return None
4514 newPattern = 'Created Key (?P<key>(\w)+) with value (?P<value>(.)+)\.'
4515 updatedPattern = "Put (?P<value>(.)+) into key (?P<key>(\w)+)\. The old value was (?P<oldValue>(.)+)\."
4516 results = {}
4517 for line in output.splitlines():
4518 new = re.search( newPattern, line )
4519 updated = re.search( updatedPattern, line )
4520 if new:
4521 results[ new.groupdict()[ 'key' ] ] = { 'value': new.groupdict()[ 'value' ] }
4522 elif updated:
4523 results[ updated.groupdict()[ 'key' ] ] = { 'value': updated.groupdict()[ 'value' ],
Jon Hallc6793552016-01-19 14:18:37 -08004524 'oldValue': updated.groupdict()[ 'oldValue' ] }
Jon Hall2a5002c2015-08-21 16:49:11 -07004525 else:
4526 main.log.error( self.name + ": transactionlMapGet did not" +
4527 " match expected output." )
Jon Hallc6793552016-01-19 14:18:37 -08004528 main.log.debug( "{} expected: {!r} or {!r}".format( self.name,
4529 newPattern,
4530 updatedPattern ) )
Jon Hall2a5002c2015-08-21 16:49:11 -07004531 main.log.debug( self.name + " actual: " + repr( output ) )
4532 return results
Jon Hallc6793552016-01-19 14:18:37 -08004533 except AssertionError:
4534 main.log.exception( "" )
4535 return None
Jon Hall2a5002c2015-08-21 16:49:11 -07004536 except TypeError:
4537 main.log.exception( self.name + ": Object not as expected" )
4538 return None
4539 except pexpect.EOF:
4540 main.log.error( self.name + ": EOF exception found" )
4541 main.log.error( self.name + ": " + self.handle.before )
4542 main.cleanup()
4543 main.exit()
4544 except Exception:
4545 main.log.exception( self.name + ": Uncaught exception!" )
4546 main.cleanup()
4547 main.exit()
Jon Hallc6793552016-01-19 14:18:37 -08004548
acsmarsdaea66c2015-09-03 11:44:06 -07004549 def maps( self, jsonFormat=True ):
4550 """
4551 Description: Returns result of onos:maps
4552 Optional:
4553 * jsonFormat: enable json formatting of output
4554 """
4555 try:
4556 cmdStr = "maps"
4557 if jsonFormat:
4558 cmdStr += " -j"
4559 handle = self.sendline( cmdStr )
Jon Halla495f562016-05-16 18:03:26 -07004560 assert handle is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004561 assert "Command not found:" not in handle, handle
acsmarsdaea66c2015-09-03 11:44:06 -07004562 return handle
Jon Hallc6793552016-01-19 14:18:37 -08004563 except AssertionError:
4564 main.log.exception( "" )
4565 return None
acsmarsdaea66c2015-09-03 11:44:06 -07004566 except TypeError:
4567 main.log.exception( self.name + ": Object not as expected" )
4568 return None
4569 except pexpect.EOF:
4570 main.log.error( self.name + ": EOF exception found" )
4571 main.log.error( self.name + ": " + self.handle.before )
4572 main.cleanup()
4573 main.exit()
4574 except Exception:
4575 main.log.exception( self.name + ": Uncaught exception!" )
4576 main.cleanup()
4577 main.exit()
GlennRC050596c2015-11-18 17:06:41 -08004578
4579 def getSwController( self, uri, jsonFormat=True ):
4580 """
4581 Descrition: Gets the controller information from the device
4582 """
4583 try:
4584 cmd = "device-controllers "
4585 if jsonFormat:
4586 cmd += "-j "
4587 response = self.sendline( cmd + uri )
Jon Halla495f562016-05-16 18:03:26 -07004588 assert response is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004589 assert "Command not found:" not in response, response
GlennRC050596c2015-11-18 17:06:41 -08004590 return response
Jon Hallc6793552016-01-19 14:18:37 -08004591 except AssertionError:
4592 main.log.exception( "" )
4593 return None
GlennRC050596c2015-11-18 17:06:41 -08004594 except TypeError:
4595 main.log.exception( self.name + ": Object not as expected" )
4596 return None
4597 except pexpect.EOF:
4598 main.log.error( self.name + ": EOF exception found" )
4599 main.log.error( self.name + ": " + self.handle.before )
4600 main.cleanup()
4601 main.exit()
4602 except Exception:
4603 main.log.exception( self.name + ": Uncaught exception!" )
4604 main.cleanup()
4605 main.exit()
4606
4607 def setSwController( self, uri, ip, proto="tcp", port="6653", jsonFormat=True ):
4608 """
4609 Descrition: sets the controller(s) for the specified device
4610
4611 Parameters:
4612 Required: uri - String: The uri of the device(switch).
4613 ip - String or List: The ip address of the controller.
4614 This parameter can be formed in a couple of different ways.
4615 VALID:
4616 10.0.0.1 - just the ip address
4617 tcp:10.0.0.1 - the protocol and the ip address
4618 tcp:10.0.0.1:6653 - the protocol and port can be specified,
4619 so that you can add controllers with different
4620 protocols and ports
4621 INVALID:
4622 10.0.0.1:6653 - this is not supported by ONOS
4623
4624 Optional: proto - The type of connection e.g. tcp, ssl. If a list of ips are given
4625 port - The port number.
4626 jsonFormat - If set ONOS will output in json NOTE: This is currently not supported
4627
4628 Returns: main.TRUE if ONOS returns without any errors, otherwise returns main.FALSE
4629 """
4630 try:
4631 cmd = "device-setcontrollers"
4632
4633 if jsonFormat:
4634 cmd += " -j"
4635 cmd += " " + uri
4636 if isinstance( ip, str ):
4637 ip = [ip]
4638 for item in ip:
4639 if ":" in item:
4640 sitem = item.split( ":" )
4641 if len(sitem) == 3:
4642 cmd += " " + item
4643 elif "." in sitem[1]:
4644 cmd += " {}:{}".format(item, port)
4645 else:
4646 main.log.error( "Malformed entry: " + item )
4647 raise TypeError
4648 else:
4649 cmd += " {}:{}:{}".format( proto, item, port )
GlennRC050596c2015-11-18 17:06:41 -08004650 response = self.sendline( cmd )
Jon Halla495f562016-05-16 18:03:26 -07004651 assert response is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004652 assert "Command not found:" not in response, response
GlennRC050596c2015-11-18 17:06:41 -08004653 if "Error" in response:
4654 main.log.error( response )
4655 return main.FALSE
GlennRC050596c2015-11-18 17:06:41 -08004656 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -08004657 except AssertionError:
4658 main.log.exception( "" )
4659 return None
GlennRC050596c2015-11-18 17:06:41 -08004660 except TypeError:
4661 main.log.exception( self.name + ": Object not as expected" )
4662 return main.FALSE
4663 except pexpect.EOF:
4664 main.log.error( self.name + ": EOF exception found" )
4665 main.log.error( self.name + ": " + self.handle.before )
4666 main.cleanup()
4667 main.exit()
4668 except Exception:
4669 main.log.exception( self.name + ": Uncaught exception!" )
4670 main.cleanup()
4671 main.exit()
GlennRC20fc6522015-12-23 23:26:57 -08004672
4673 def removeDevice( self, device ):
4674 '''
4675 Description:
4676 Remove a device from ONOS by passing the uri of the device(s).
4677 Parameters:
4678 device - (str or list) the id or uri of the device ex. "of:0000000000000001"
4679 Returns:
4680 Returns main.FALSE if an exception is thrown or an error is present
4681 in the response. Otherwise, returns main.TRUE.
4682 NOTE:
4683 If a host cannot be removed, then this function will return main.FALSE
4684 '''
4685 try:
4686 if type( device ) is str:
4687 device = list( device )
4688
4689 for d in device:
4690 time.sleep( 1 )
4691 response = self.sendline( "device-remove {}".format( d ) )
Jon Halla495f562016-05-16 18:03:26 -07004692 assert response is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004693 assert "Command not found:" not in response, response
GlennRC20fc6522015-12-23 23:26:57 -08004694 if "Error" in response:
4695 main.log.warn( "Error for device: {}\nResponse: {}".format( d, response ) )
4696 return main.FALSE
GlennRC20fc6522015-12-23 23:26:57 -08004697 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -08004698 except AssertionError:
4699 main.log.exception( "" )
4700 return main.FALSE
GlennRC20fc6522015-12-23 23:26:57 -08004701 except TypeError:
4702 main.log.exception( self.name + ": Object not as expected" )
4703 return main.FALSE
4704 except pexpect.EOF:
4705 main.log.error( self.name + ": EOF exception found" )
4706 main.log.error( self.name + ": " + self.handle.before )
4707 main.cleanup()
4708 main.exit()
4709 except Exception:
4710 main.log.exception( self.name + ": Uncaught exception!" )
4711 main.cleanup()
4712 main.exit()
4713
4714 def removeHost( self, host ):
4715 '''
4716 Description:
4717 Remove a host from ONOS by passing the id of the host(s)
4718 Parameters:
4719 hostId - (str or list) the id or mac of the host ex. "00:00:00:00:00:01"
4720 Returns:
4721 Returns main.FALSE if an exception is thrown or an error is present
4722 in the response. Otherwise, returns main.TRUE.
4723 NOTE:
4724 If a host cannot be removed, then this function will return main.FALSE
4725 '''
4726 try:
4727 if type( host ) is str:
4728 host = list( host )
4729
4730 for h in host:
4731 time.sleep( 1 )
4732 response = self.sendline( "host-remove {}".format( h ) )
Jon Halla495f562016-05-16 18:03:26 -07004733 assert response is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004734 assert "Command not found:" not in response, response
GlennRC20fc6522015-12-23 23:26:57 -08004735 if "Error" in response:
4736 main.log.warn( "Error for host: {}\nResponse: {}".format( h, response ) )
4737 return main.FALSE
GlennRC20fc6522015-12-23 23:26:57 -08004738 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -08004739 except AssertionError:
4740 main.log.exception( "" )
4741 return None
GlennRC20fc6522015-12-23 23:26:57 -08004742 except TypeError:
4743 main.log.exception( self.name + ": Object not as expected" )
4744 return main.FALSE
4745 except pexpect.EOF:
4746 main.log.error( self.name + ": EOF exception found" )
4747 main.log.error( self.name + ": " + self.handle.before )
4748 main.cleanup()
4749 main.exit()
4750 except Exception:
4751 main.log.exception( self.name + ": Uncaught exception!" )
4752 main.cleanup()
4753 main.exit()
GlennRCed771242016-01-13 17:02:47 -08004754
Jon Hallc6793552016-01-19 14:18:37 -08004755 def link( self, begin, end, state ):
GlennRCed771242016-01-13 17:02:47 -08004756 '''
4757 Description:
4758 Bring link down or up in the null-provider.
4759 params:
4760 begin - (string) One end of a device or switch.
4761 end - (string) the other end of the device or switch
4762 returns:
4763 main.TRUE if no exceptions were thrown and no Errors are
4764 present in the resoponse. Otherwise, returns main.FALSE
4765 '''
4766 try:
Jon Hallc6793552016-01-19 14:18:37 -08004767 cmd = "null-link null:{} null:{} {}".format( begin, end, state )
GlennRCed771242016-01-13 17:02:47 -08004768 response = self.sendline( cmd, showResponse=True )
Jon Halla495f562016-05-16 18:03:26 -07004769 assert response is not None, "Error in sendline"
Jon Hallc6793552016-01-19 14:18:37 -08004770 assert "Command not found:" not in response, response
GlennRCed771242016-01-13 17:02:47 -08004771 if "Error" in response or "Failure" in response:
4772 main.log.error( response )
4773 return main.FALSE
GlennRCed771242016-01-13 17:02:47 -08004774 return main.TRUE
Jon Hallc6793552016-01-19 14:18:37 -08004775 except AssertionError:
4776 main.log.exception( "" )
4777 return None
GlennRCed771242016-01-13 17:02:47 -08004778 except TypeError:
4779 main.log.exception( self.name + ": Object not as expected" )
4780 return main.FALSE
4781 except pexpect.EOF:
4782 main.log.error( self.name + ": EOF exception found" )
4783 main.log.error( self.name + ": " + self.handle.before )
4784 main.cleanup()
4785 main.exit()
4786 except Exception:
4787 main.log.exception( self.name + ": Uncaught exception!" )
4788 main.cleanup()
4789 main.exit()
4790