blob: ea4eccddd15d50edef6f22c5bd5ad66ac608e7c3 [file] [log] [blame]
Devin Lim61643762017-12-07 15:55:38 -08001#!groovy
2import groovy.time.*
Devin Lim81ab48b2018-02-09 14:24:57 -08003generalFuncs = evaluate readTrusted( 'TestON/JenkinsFile/GeneralFuncs.groovy' )
Jeremy Ronquillo14ecc172018-03-05 09:57:17 -08004
Devin Lim61643762017-12-07 15:55:38 -08005def initializeTrend( machine ){
6 table_name = "executed_test_tests"
7 result_name = "executed_test_results"
8 testMachine = "TestStation-" + machine + "s";
9 this.machine = machine
10 isSCPF = false
Devin Lim981f80b2018-04-09 11:25:59 -070011 isTrend = true
Devin Lim61643762017-12-07 15:55:38 -080012 generalFuncs.initBasicVars();
13}
14def initialize( type, SCPFfuncs ){
15 init( type )
16 SCPFfunc = SCPFfuncs
17 isSCPF = true
18 machine = machineType[ type ]
19}
20def initialize( type ){
21 init( type )
22 SCPFfunc = null
23 table_name = "executed_test_tests"
24 result_name = "executed_test_results"
25 trend_generator_file = generalFuncs.rScriptLocation + "testCategoryTrend.R"
26 build_stats_generator_file = generalFuncs.rScriptLocation + "testCategoryBuildStats.R"
27 isSCPF = false
28}
29def init( type ){
30 machineType = [ "FUNC" : "VM",
31 "HA" : "VM",
Devin Lim431408d2018-03-23 17:51:31 -070032 "SR" : "Fabric",
Devin Lim61643762017-12-07 15:55:38 -080033 "SCPF" : "BM",
34 "USECASE" : "BM" ]
35 testType = type;
36 testMachine = "TestStation-" + machineType[ type ] + "s";
Devin Lim981f80b2018-04-09 11:25:59 -070037 isTrend = false
Devin Lim61643762017-12-07 15:55:38 -080038 generalFuncs.initBasicVars();
39}
Devin Lim86e40532018-04-06 12:44:06 -070040def additionalInitForSR( branch ){
Devin Limc38e6932018-04-06 18:04:33 -070041 testMachine = ( ( new StringBuilder( testMachine ) ).insert( testMachine.size()-1, fabricOn( branch ) ) ).toString()
Devin Lim6cccad52018-04-09 11:32:19 -070042 if( isTrend )
43 machine += fabricOn( branch )
44 else
45 machineType[ testType ] += fabricOn( branch )
Devin Lim86e40532018-04-06 12:44:06 -070046 print testMachine
47}
48def fabricOn( branch ){
Devin Limc4054d52018-04-13 18:58:33 -070049 return branch.reverse().take(4).reverse() == "1.13" ? '2' : '3'
50// Temp Fix return branch.reverse().take(6).reverse() == "master" ? '2' : '3'
Devin Lim86e40532018-04-06 12:44:06 -070051}
Devin Lim61643762017-12-07 15:55:38 -080052def printType(){
53 echo testType;
54 echo testMachine;
55}
56def getProperties(){
57 node( testMachine ){
58 return readProperties( file:'/var/jenkins/TestONOS.property' );
59 }
60}
61def getTestsToRun( testList ){
62 testList.tokenize("\n;, ")
63}
64def getCurrentTime(){
Devin Limd1fb8e92018-02-28 16:29:33 -080065 TimeZone.setDefault( TimeZone.getTimeZone('PST') )
Devin Lim61643762017-12-07 15:55:38 -080066 return new Date();
67}
68def getTotalTime( start, end ){
69 return TimeCategory.minus( end, start );
70}
71def printTestToRun( testList ){
72 for ( String test : testList ) {
73 println test;
74 }
75}
76def sendResultToSlack( start, isManualRun, branch ){
77 try{
78 if( isManualRun == "false" ){
79 end = getCurrentTime();
80 TimeDuration duration = TimeCategory.minus( end , start );
81 slackSend( color:"#5816EE",
82 message: testType + "-" + branch + " tests ended at: " + end.toString() + "\nTime took : " + duration )
83 }
84 }
85 catch( all ){}
86}
87def initAndRunTest( testName, testCategory ){
Devin Limf5bf9b52018-02-28 18:16:21 -080088 // after ifconfig : ''' + borrowCell( testName ) + '''
Devin Lim61643762017-12-07 15:55:38 -080089 return '''#!/bin/bash -l
90 set -i # interactive
91 set +e
92 shopt -s expand_aliases # expand alias in non-interactive mode
93 export PYTHONUNBUFFERED=1
94 ifconfig
Devin Lim61643762017-12-07 15:55:38 -080095 echo "ONOS Branch is: $ONOSBranch"
96 echo "TestON Branch is: $TestONBranch"
97 echo "Test date: "
98 date
99 cd ~
100 export PATH=$PATH:onos/tools/test/bin
101 timeout 240 stc shutdown | head -100
102 timeout 240 stc teardown | head -100
103 timeout 240 stc shutdown | head -100
104 cd ~/OnosSystemTest/TestON/bin
105 git log |head
106 ./cleanup.sh -f
Devin Lima7b97a42018-04-09 14:26:38 -0700107 ''' + "./cli.py run " + ( !isSCPF ? testName : testCategory[ testName ][ 'test' ] ) + " --params GRAPH/nodeCluster=" + machineType[ testType ] + '''
Devin Lim61643762017-12-07 15:55:38 -0800108 ./cleanup.sh -f
109 # cleanup config changes
110 cd ~/onos/tools/package/config
111 git clean -df'''
112}
113def copyLogs( testName ){
114 result = ""
115 if( testType == "SR" ){
116 result = '''
117 sudo rm /var/jenkins/workspace/SR-log-${WikiPrefix}/*
118 sudo cp *karaf.log.* /var/jenkins/workspace/SR-log-${WikiPrefix}/
119 sudo cp *Flows* /var/jenkins/workspace/SR-log-${WikiPrefix}/
120 sudo cp *Groups* /var/jenkins/workspace/SR-log-${WikiPrefix}/
Devin Lima7b97a42018-04-09 14:26:38 -0700121 sudo cp *.tar.gz /var/jenkins/workspace/SR-log-${WikiPrefix}/
Devin Lim6faa3f92018-05-01 13:16:25 -0700122 sudo cp t3-* /var/jenkins/workspace/SR-log-${WikiPrefix}/
Devin Lim61643762017-12-07 15:55:38 -0800123 '''
124 }
125 return result
126}
127def cleanAndCopyFiles( testName ){
128 return '''#!/bin/bash -i
129 set +e
130 echo "ONOS Branch is: ${ONOSBranch}"
131 echo "TestON Branch is: ${TestONBranch}"
132 echo "Job name is: "''' + testName + '''
133 echo "Workspace is: ${WORKSPACE}/"
134 echo "Wiki page to post is: ${WikiPrefix}-"
135 # remove any leftover files from previous tests
136 sudo rm ${WORKSPACE}/*Wiki.txt
137 sudo rm ${WORKSPACE}/*Summary.txt
138 sudo rm ${WORKSPACE}/*Result.txt
139 sudo rm ${WORKSPACE}/*.csv
140 #copy files to workspace
141 cd `ls -t ~/OnosSystemTest/TestON/logs/*/ | head -1 | sed 's/://'`
142 ''' + copyLogs( testName ) + '''
143 sudo cp *.txt ${WORKSPACE}/
144 sudo cp *.csv ${WORKSPACE}/
145 cd ${WORKSPACE}/
146 for i in *.csv
147 do mv "$i" "$WikiPrefix"-"$i"
148 done
149 ls -al
150 cd '''
151}
152def fetchLogs( testName ){
153 return '''#!/bin/bash
154 set +e
155 cd ~/OnosSystemTest/TestON/logs
156 echo "Job Name is: " + ''' + testName + '''
157 TestONlogDir=$(ls -t | grep ${TEST_NAME}_ |head -1)
158 echo "########################################################################################"
159 echo "##### copying ONOS logs from all nodes to TestON/logs directory: ${TestONlogDir}"
160 echo "########################################################################################"
161 cd $TestONlogDir
162 if [ $? -eq 1 ]
163 then
164 echo "Job name does not match any test suite name to move log!"
165 else
166 pwd
167 for i in $OC{1..7}; do onos-fetch-logs $i || echo log does not exist; done
168 fi
169 cd'''
170}
171def isPostingResult( manual, postresult ){
172 return manual == "false" || postresult == "true"
173}
174def postResult( prop, graphOnly ){
175 if( graphOnly || isPostingResult( prop[ "manualRun" ], prop[ "postResult" ] ) ){
176 def post = build job: "postjob-" + ( graphOnly ? machine : machineType[ testType ] ), propagate: false
177 }
178}
179def postLogs( testName, prefix ){
180 resultURL = ""
181 if( testType == "SR" ){
182 def post = build job: "SR-log-" + prefix, propagate: false
183 resultURL = post.getAbsoluteUrl()
184 }
185 return resultURL
186}
187def getSlackChannel(){
188 return "#" + ( testType == "SR" ? "sr-failures" : "jenkins-related" )
189}
190def analyzeResult( prop, workSpace, testName, otherTestName, resultURL, wikiLink, isSCPF ){
191 node( testMachine ){
192 resultContents = readFile workSpace + "/" + testName + "Result.txt"
193 resultContents = resultContents.split("\n")
194 if( resultContents[ 0 ] == "1" ){
195 print "All passed"
196 }else{
197 print "Failed"
198 if( prop[ "manualRun" ] == "false" ){
199 slackSend( channel:getSlackChannel(), color:"FF0000", message: "[" + prop[ "ONOSBranch" ] + "]"
200 + otherTestName + " : Failed!\n" + resultContents[ 1 ] + "\n"
201 + "[TestON log] : \n"
Devin Limd1fb8e92018-02-28 16:29:33 -0800202 + "https://jenkins.onosproject.org/blue/organizations/jenkins/${env.JOB_NAME}/detail/${env.JOB_NAME}/${env.BUILD_NUMBER}/pipeline"
Devin Lim61643762017-12-07 15:55:38 -0800203 + ( isSCPF ? "" : ( "\n[Result on Wiki] : \n" + "https://wiki.onosproject.org/display/ONOS/" + wikiLink.replaceAll( "\\s","+" ) ) )
204 + ( resultURL != "" ? ( "\n[Karaf log] : \n" + resultURL + "artifact/" ) : "" ),
205 teamDomain: 'onosproject' )
206 }
207 Failed
208 }
209 }
210}
Devin Lime89761a2018-03-16 17:52:57 -0700211def publishToConfluence( isManualRun, isPostResult, wikiLink, file ){
212 if( isPostingResult( isManualRun, isPostResult ) ){
Devin Lim61643762017-12-07 15:55:38 -0800213 publishConfluence siteName: 'wiki.onosproject.org', pageName: wikiLink, spaceName: 'ONOS',
Devin Lim1253ae82018-02-26 11:13:36 -0800214 attachArchivedArtifacts: true, buildIfUnstable: true,
Devin Lim61643762017-12-07 15:55:38 -0800215 editorList: [
216 confluenceWritePage( confluenceFile( file ) )
217 ]
218 }
219
220}
221def runTest( testName, toBeRun, prop, pureTestName, graphOnly, testCategory, graph_generator_file, graph_saved_directory ) {
222 return {
223 catchError{
224 stage( testName ) {
225 if ( toBeRun ){
226 workSpace = "/var/jenkins/workspace/" + testName
227 def fileContents = ""
228 node( testMachine ){
229 withEnv( [ 'ONOSBranch=' + prop[ "ONOSBranch" ],
230 'ONOSJVMHeap=' + prop[ "ONOSJVMHeap" ],
231 'TestONBranch=' + prop[ "TestONBranch" ],
232 'ONOSTag=' + prop[ "ONOSTag" ],
233 'WikiPrefix=' + prop[ "WikiPrefix" ],
234 'WORKSPACE=' + workSpace ] ){
235 if( ! graphOnly ){
236 sh initAndRunTest( testName, testCategory )
237 // For the Wiki page
238 sh cleanAndCopyFiles( pureTestName )
239 }
240 databaseAndGraph( prop, testName, graphOnly, graph_generator_file, graph_saved_directory )
241 if( ! graphOnly ){
242 sh fetchLogs( pureTestName )
243 if( !isSCPF )
Devin Lime89761a2018-03-16 17:52:57 -0700244 publishToConfluence( prop[ "manualRun" ], prop[ "postResult" ],
245 testCategory[ testName ][ 'wiki_link' ],
246 workSpace + "/" + testCategory[ testName ][ 'wiki_file' ] )
Devin Lim61643762017-12-07 15:55:38 -0800247 }
248 }
249
250
251 }
252 postResult( prop, graphOnly )
253 if( ! graphOnly ){
254 resultURL = postLogs( testName, prop[ "WikiPrefix" ] )
255 analyzeResult( prop, workSpace, pureTestName, testName, resultURL, isSCPF ? "" : testCategory[ testName ][ 'wiki_link' ], isSCPF )
256 }
257 }
258 }
259 }
260 }
261}
262def borrowCell( testName ){
263 result = ""
264 if( testType == "SR" ){
265 result = '''
266 cd
267 source ~/borrow.cell
268 '''
269 }
270 return result
271}
272def databaseAndGraph( prop, testName, graphOnly, graph_generator_file, graph_saved_directory ){
273 if( graphOnly || isPostingResult( prop[ "manualRun" ], prop[ "postResult" ] ) ){
274 // Post Results
275 withCredentials( [
276 string( credentialsId: 'db_pass', variable: 'pass' ),
277 string( credentialsId: 'db_user', variable: 'user' ),
278 string( credentialsId: 'db_host', variable: 'host' ),
279 string( credentialsId: 'db_port', variable: 'port' ) ] ) {
280 def database_command = generalFuncs.database_command_create( pass, host, port, user ) + ( !isSCPF ? sqlCommand( testName ) : SCPFfunc.sqlCommand( testName ) )
281 sh '''#!/bin/bash
282 export DATE=\$(date +%F_%T)
283 cd ~
284 pwd ''' + ( graphOnly ? "" : ( !isSCPF ? databasePart( prop[ "WikiPrefix" ], testName, database_command ) :
285 SCPFfunc.databasePart( testName, database_command ) ) ) + '''
286 ''' + ( !isSCPF ? graphGenerating( host, port, user, pass, testName, prop, graph_saved_directory, graph_generator_file ) : SCPFfunc.getGraphGeneratingCommand( host, port, user, pass, testName, prop ) )
287 }
288 }
289}
Devin Lim86e40532018-04-06 12:44:06 -0700290def generateCategoryStatsGraph( testMachineOn, manualRun, postresult, stat_file, pie_file, type, branch, testListPart, save_path, pieTestListPart ){
Devin Lim61643762017-12-07 15:55:38 -0800291
292 if( isPostingResult( manualRun, postresult ) ){
Devin Lim86e40532018-04-06 12:44:06 -0700293 node( testMachineOn ){
Devin Lim61643762017-12-07 15:55:38 -0800294
295 withCredentials( [
296 string( credentialsId: 'db_pass', variable: 'pass' ),
297 string( credentialsId: 'db_user', variable: 'user' ),
298 string( credentialsId: 'db_host', variable: 'host' ),
299 string( credentialsId: 'db_port', variable: 'port' ) ] ) {
300 sh '''#!/bin/bash
301 ''' + generalFuncs.basicGraphPart( generalFuncs.rScriptLocation + stat_file, host, port, user, pass, type, branch ) + " \"" + testListPart + "\" latest " + save_path + '''
302 ''' + getOverallPieGraph( generalFuncs.rScriptLocation + pie_file, host, port, user, pass, branch, type, pieTestListPart, 'y', save_path ) + '''
303 ''' + getOverallPieGraph( generalFuncs.rScriptLocation + pie_file, host, port, user, pass, branch, type, pieTestListPart, 'n', save_path )
304 }
305 }
306 postResult( [], true )
307 }
308}
309def makeTestList( list, commaNeeded ){
310 return generalFuncs.getTestList( list ) + ( commaNeeded ? "," : "" )
311}
312def createStatsList( testCategory, list, semiNeeded ){
313 return testCategory + "-" + generalFuncs.getTestList( list ) + ( semiNeeded ? ";" : "" )
314}
315def generateOverallGraph( prop, testCategory, graph_saved_directory ){
316
317 if( isPostingResult( prop[ "manualRun" ], prop[ "postResult" ] ) ){
318 node( testMachine ){
319
320 withCredentials( [
321 string( credentialsId: 'db_pass', variable: 'pass' ),
322 string( credentialsId: 'db_user', variable: 'user' ),
323 string( credentialsId: 'db_host', variable: 'host' ),
324 string( credentialsId: 'db_port', variable: 'port' ) ] ) {
325 testList = generalFuncs.getTestList( testCategory )
326 sh '''#!/bin/bash
327 ''' + generalFuncs.basicGraphPart( trend_generator_file, host, port, user, pass, testType, prop[ "ONOSBranch" ] ) + " " + testList + " 20 " + graph_saved_directory
328 }
329 }
330 postResult( prop, false )
331 }
332}
333def getOverallPieGraph( file, host, port, user, pass, branch, type, testList, yOrN, path ){
334 return generalFuncs.basicGraphPart( file, host, port, user, pass, type, branch ) + " \"" + testList + "\" latest " + yOrN + " " + path
335}
336def sqlCommand( testName ){
337 return "\"INSERT INTO " + table_name + " VALUES('\$DATE','" + result_name + "','" + testName + "',\$BUILD_NUMBER, '\$ONOSBranch', \$line);\" "
338}
339def graphGenerating( host, port, user, pass, testName, prop, graph_saved_directory, graph_generator_file ){
340 return generalFuncs.basicGraphPart( graph_generator_file, host, port, user, pass, testName, prop[ "ONOSBranch" ] ) + " 20 " + graph_saved_directory
341}
342def databasePart( wikiPrefix, testName, database_command ){
343 return '''
344 sed 1d ''' + workSpace + "/" + wikiPrefix + "-" + testName + '''.csv | while read line
345 do
346 echo \$line
347 echo ''' + database_command + '''
348 done '''
349}
Devin Lim86e40532018-04-06 12:44:06 -0700350def generateStatGraph( testMachineOn, onos_branch, AllTheTests, stat_graph_generator_file, pie_graph_generator_file, graph_saved_directory ){
Jeremy Ronquillo14ecc172018-03-05 09:57:17 -0800351 testListPart = createStatsList( "FUNC", AllTheTests[ "FUNC" ], true ) +
352 createStatsList( "HA", AllTheTests[ "HA" ], true ) +
353 createStatsList( "USECASE", AllTheTests[ "USECASE" ], false )
354 pieTestList = makeTestList( AllTheTests[ "FUNC" ], true ) +
355 makeTestList( AllTheTests[ "HA" ], true ) +
356 makeTestList( AllTheTests[ "USECASE" ], false )
Devin Lim86e40532018-04-06 12:44:06 -0700357 generateCategoryStatsGraph( testMachineOn, "false", "true", stat_graph_generator_file, pie_graph_generator_file, "ALL", onos_branch, testListPart, graph_saved_directory, pieTestList )
Jeremy Ronquillo14ecc172018-03-05 09:57:17 -0800358}
Jeremy Ronquillof78a6ca2018-03-12 09:20:57 -0700359def branchWithPrefix( branch ){
360 return ( ( branch != "master" ) ? "onos-" : "" ) + branch
361}
Devin Lim1253ae82018-02-26 11:13:36 -0800362return this;