leo hendrickson
/
S
simple-mbed-cloud-client/mbed-cloud-client/mbed-client-pal/Test/Unity/auto/parseOutput.rb@0:25fa8795676b, 2021-04-18 (annotated)
- Committer:
- leothedragon
- Date:
- Sun Apr 18 15:20:23 2021 +0000
- Revision:
- 0:25fa8795676b
DS
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
leothedragon | 0:25fa8795676b | 1 | #============================================================ |
leothedragon | 0:25fa8795676b | 2 | # Author: John Theofanopoulos |
leothedragon | 0:25fa8795676b | 3 | # A simple parser. Takes the output files generated during the build process and |
leothedragon | 0:25fa8795676b | 4 | # extracts information relating to the tests. |
leothedragon | 0:25fa8795676b | 5 | # |
leothedragon | 0:25fa8795676b | 6 | # Notes: |
leothedragon | 0:25fa8795676b | 7 | # To capture an output file under VS builds use the following: |
leothedragon | 0:25fa8795676b | 8 | # devenv [build instructions] > Output.txt & type Output.txt |
leothedragon | 0:25fa8795676b | 9 | # |
leothedragon | 0:25fa8795676b | 10 | # To capture an output file under GCC/Linux builds use the following: |
leothedragon | 0:25fa8795676b | 11 | # make | tee Output.txt |
leothedragon | 0:25fa8795676b | 12 | # |
leothedragon | 0:25fa8795676b | 13 | # To use this parser use the following command |
leothedragon | 0:25fa8795676b | 14 | # ruby parseOutput.rb [options] [file] |
leothedragon | 0:25fa8795676b | 15 | # options: -xml : produce a JUnit compatible XML file |
leothedragon | 0:25fa8795676b | 16 | # file : file to scan for results |
leothedragon | 0:25fa8795676b | 17 | #============================================================ |
leothedragon | 0:25fa8795676b | 18 | |
leothedragon | 0:25fa8795676b | 19 | |
leothedragon | 0:25fa8795676b | 20 | class ParseOutput |
leothedragon | 0:25fa8795676b | 21 | # The following flag is set to true when a test is found or false otherwise. |
leothedragon | 0:25fa8795676b | 22 | @testFlag |
leothedragon | 0:25fa8795676b | 23 | @xmlOut |
leothedragon | 0:25fa8795676b | 24 | @arrayList |
leothedragon | 0:25fa8795676b | 25 | @totalTests |
leothedragon | 0:25fa8795676b | 26 | @classIndex |
leothedragon | 0:25fa8795676b | 27 | |
leothedragon | 0:25fa8795676b | 28 | # Set the flag to indicate if there will be an XML output file or not |
leothedragon | 0:25fa8795676b | 29 | def setXmlOutput() |
leothedragon | 0:25fa8795676b | 30 | @xmlOut = true |
leothedragon | 0:25fa8795676b | 31 | end |
leothedragon | 0:25fa8795676b | 32 | |
leothedragon | 0:25fa8795676b | 33 | # if write our output to XML |
leothedragon | 0:25fa8795676b | 34 | def writeXmlOuput() |
leothedragon | 0:25fa8795676b | 35 | output = File.open("report.xml", "w") |
leothedragon | 0:25fa8795676b | 36 | output << "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" |
leothedragon | 0:25fa8795676b | 37 | @arrayList.each do |item| |
leothedragon | 0:25fa8795676b | 38 | output << item << "\n" |
leothedragon | 0:25fa8795676b | 39 | end |
leothedragon | 0:25fa8795676b | 40 | output << "</testsuite>\n" |
leothedragon | 0:25fa8795676b | 41 | end |
leothedragon | 0:25fa8795676b | 42 | |
leothedragon | 0:25fa8795676b | 43 | # This function will try and determine when the suite is changed. This is |
leothedragon | 0:25fa8795676b | 44 | # is the name that gets added to the classname parameter. |
leothedragon | 0:25fa8795676b | 45 | def testSuiteVerify(testSuiteName) |
leothedragon | 0:25fa8795676b | 46 | if @testFlag == false |
leothedragon | 0:25fa8795676b | 47 | @testFlag = true; |
leothedragon | 0:25fa8795676b | 48 | # Split the path name |
leothedragon | 0:25fa8795676b | 49 | testName = testSuiteName.split("/") |
leothedragon | 0:25fa8795676b | 50 | # Remove the extension |
leothedragon | 0:25fa8795676b | 51 | baseName = testName[testName.size - 1].split(".") |
leothedragon | 0:25fa8795676b | 52 | @testSuite = "test." + baseName[0] |
leothedragon | 0:25fa8795676b | 53 | printf "New Test: %s\n", @testSuite |
leothedragon | 0:25fa8795676b | 54 | end |
leothedragon | 0:25fa8795676b | 55 | end |
leothedragon | 0:25fa8795676b | 56 | |
leothedragon | 0:25fa8795676b | 57 | |
leothedragon | 0:25fa8795676b | 58 | # Test was flagged as having passed so format the output |
leothedragon | 0:25fa8795676b | 59 | def testPassed(array) |
leothedragon | 0:25fa8795676b | 60 | lastItem = array.length - 1 |
leothedragon | 0:25fa8795676b | 61 | testName = array[lastItem - 1] |
leothedragon | 0:25fa8795676b | 62 | testSuiteVerify(array[@className]) |
leothedragon | 0:25fa8795676b | 63 | printf "%-40s PASS\n", testName |
leothedragon | 0:25fa8795676b | 64 | if @xmlOut == true |
leothedragon | 0:25fa8795676b | 65 | @arrayList.push " <testcase classname=\"" + @testSuite + "\" name=\"" + testName + "\"/>" |
leothedragon | 0:25fa8795676b | 66 | end |
leothedragon | 0:25fa8795676b | 67 | end |
leothedragon | 0:25fa8795676b | 68 | |
leothedragon | 0:25fa8795676b | 69 | # Test was flagged as being ingored so format the output |
leothedragon | 0:25fa8795676b | 70 | def testIgnored(array) |
leothedragon | 0:25fa8795676b | 71 | lastItem = array.length - 1 |
leothedragon | 0:25fa8795676b | 72 | testName = array[lastItem - 2] |
leothedragon | 0:25fa8795676b | 73 | reason = array[lastItem].chomp |
leothedragon | 0:25fa8795676b | 74 | testSuiteVerify(array[@className]) |
leothedragon | 0:25fa8795676b | 75 | printf "%-40s IGNORED\n", testName |
leothedragon | 0:25fa8795676b | 76 | if @xmlOut == true |
leothedragon | 0:25fa8795676b | 77 | @arrayList.push " <testcase classname=\"" + @testSuite + "\" name=\"" + testName + "\">" |
leothedragon | 0:25fa8795676b | 78 | @arrayList.push " <skipped type=\"TEST IGNORED\"> " + reason + " </skipped>" |
leothedragon | 0:25fa8795676b | 79 | @arrayList.push " </testcase>" |
leothedragon | 0:25fa8795676b | 80 | end |
leothedragon | 0:25fa8795676b | 81 | end |
leothedragon | 0:25fa8795676b | 82 | |
leothedragon | 0:25fa8795676b | 83 | # Test was flagged as having failed so format the line |
leothedragon | 0:25fa8795676b | 84 | def testFailed(array) |
leothedragon | 0:25fa8795676b | 85 | lastItem = array.length - 1 |
leothedragon | 0:25fa8795676b | 86 | testName = array[lastItem - 2] |
leothedragon | 0:25fa8795676b | 87 | reason = array[lastItem].chomp + " at line: " + array[lastItem - 3] |
leothedragon | 0:25fa8795676b | 88 | testSuiteVerify(array[@className]) |
leothedragon | 0:25fa8795676b | 89 | printf "%-40s FAILED\n", testName |
leothedragon | 0:25fa8795676b | 90 | if @xmlOut == true |
leothedragon | 0:25fa8795676b | 91 | @arrayList.push " <testcase classname=\"" + @testSuite + "\" name=\"" + testName + "\">" |
leothedragon | 0:25fa8795676b | 92 | @arrayList.push " <failure type=\"ASSERT FAILED\"> " + reason + " </failure>" |
leothedragon | 0:25fa8795676b | 93 | @arrayList.push " </testcase>" |
leothedragon | 0:25fa8795676b | 94 | end |
leothedragon | 0:25fa8795676b | 95 | end |
leothedragon | 0:25fa8795676b | 96 | |
leothedragon | 0:25fa8795676b | 97 | |
leothedragon | 0:25fa8795676b | 98 | # Figure out what OS we are running on. For now we are assuming if it's not Windows it must |
leothedragon | 0:25fa8795676b | 99 | # be Unix based. |
leothedragon | 0:25fa8795676b | 100 | def detectOS() |
leothedragon | 0:25fa8795676b | 101 | myOS = RUBY_PLATFORM.split("-") |
leothedragon | 0:25fa8795676b | 102 | if myOS.size == 2 |
leothedragon | 0:25fa8795676b | 103 | if myOS[1] == "mingw32" |
leothedragon | 0:25fa8795676b | 104 | @className = 1 |
leothedragon | 0:25fa8795676b | 105 | else |
leothedragon | 0:25fa8795676b | 106 | @className = 0 |
leothedragon | 0:25fa8795676b | 107 | end |
leothedragon | 0:25fa8795676b | 108 | else |
leothedragon | 0:25fa8795676b | 109 | @className = 0 |
leothedragon | 0:25fa8795676b | 110 | end |
leothedragon | 0:25fa8795676b | 111 | |
leothedragon | 0:25fa8795676b | 112 | end |
leothedragon | 0:25fa8795676b | 113 | |
leothedragon | 0:25fa8795676b | 114 | # Main function used to parse the file that was captured. |
leothedragon | 0:25fa8795676b | 115 | def process(name) |
leothedragon | 0:25fa8795676b | 116 | @testFlag = false |
leothedragon | 0:25fa8795676b | 117 | @arrayList = Array.new |
leothedragon | 0:25fa8795676b | 118 | |
leothedragon | 0:25fa8795676b | 119 | detectOS() |
leothedragon | 0:25fa8795676b | 120 | |
leothedragon | 0:25fa8795676b | 121 | puts "Parsing file: " + name |
leothedragon | 0:25fa8795676b | 122 | |
leothedragon | 0:25fa8795676b | 123 | |
leothedragon | 0:25fa8795676b | 124 | testPass = 0 |
leothedragon | 0:25fa8795676b | 125 | testFail = 0 |
leothedragon | 0:25fa8795676b | 126 | testIgnore = 0 |
leothedragon | 0:25fa8795676b | 127 | puts "" |
leothedragon | 0:25fa8795676b | 128 | puts "=================== RESULTS =====================" |
leothedragon | 0:25fa8795676b | 129 | puts "" |
leothedragon | 0:25fa8795676b | 130 | File.open(name).each do |line| |
leothedragon | 0:25fa8795676b | 131 | # Typical test lines look like this: |
leothedragon | 0:25fa8795676b | 132 | # <path>/<test_file>.c:36:test_tc1000_opsys:FAIL: Expected 1 Was 0 |
leothedragon | 0:25fa8795676b | 133 | # <path>/<test_file>.c:112:test_tc5004_initCanChannel:IGNORE: Not Yet Implemented |
leothedragon | 0:25fa8795676b | 134 | # <path>/<test_file>.c:115:test_tc5100_initCanVoidPtrs:PASS |
leothedragon | 0:25fa8795676b | 135 | # |
leothedragon | 0:25fa8795676b | 136 | # where path is different on Unix vs Windows devices (Windows leads with a drive letter) |
leothedragon | 0:25fa8795676b | 137 | lineArray = line.split(":") |
leothedragon | 0:25fa8795676b | 138 | lineSize = lineArray.size |
leothedragon | 0:25fa8795676b | 139 | # If we were able to split the line then we can look to see if any of our target words |
leothedragon | 0:25fa8795676b | 140 | # were found. Case is important. |
leothedragon | 0:25fa8795676b | 141 | if lineSize >= 4 |
leothedragon | 0:25fa8795676b | 142 | # Determine if this test passed |
leothedragon | 0:25fa8795676b | 143 | if line.include? ":PASS" |
leothedragon | 0:25fa8795676b | 144 | testPassed(lineArray) |
leothedragon | 0:25fa8795676b | 145 | testPass += 1 |
leothedragon | 0:25fa8795676b | 146 | elsif line.include? ":FAIL:" |
leothedragon | 0:25fa8795676b | 147 | testFailed(lineArray) |
leothedragon | 0:25fa8795676b | 148 | testFail += 1 |
leothedragon | 0:25fa8795676b | 149 | elsif line.include? ":IGNORE:" |
leothedragon | 0:25fa8795676b | 150 | testIgnored(lineArray) |
leothedragon | 0:25fa8795676b | 151 | testIgnore += 1 |
leothedragon | 0:25fa8795676b | 152 | # If none of the keywords are found there are no more tests for this suite so clear |
leothedragon | 0:25fa8795676b | 153 | # the test flag |
leothedragon | 0:25fa8795676b | 154 | else |
leothedragon | 0:25fa8795676b | 155 | @testFlag = false |
leothedragon | 0:25fa8795676b | 156 | end |
leothedragon | 0:25fa8795676b | 157 | else |
leothedragon | 0:25fa8795676b | 158 | @testFlag = false |
leothedragon | 0:25fa8795676b | 159 | end |
leothedragon | 0:25fa8795676b | 160 | end |
leothedragon | 0:25fa8795676b | 161 | puts "" |
leothedragon | 0:25fa8795676b | 162 | puts "=================== SUMMARY =====================" |
leothedragon | 0:25fa8795676b | 163 | puts "" |
leothedragon | 0:25fa8795676b | 164 | puts "Tests Passed : " + testPass.to_s |
leothedragon | 0:25fa8795676b | 165 | puts "Tests Failed : " + testFail.to_s |
leothedragon | 0:25fa8795676b | 166 | puts "Tests Ignored : " + testIgnore.to_s |
leothedragon | 0:25fa8795676b | 167 | @totalTests = testPass + testFail + testIgnore |
leothedragon | 0:25fa8795676b | 168 | if @xmlOut == true |
leothedragon | 0:25fa8795676b | 169 | heading = "<testsuite tests=\"" + @totalTests.to_s + "\" failures=\"" + testFail.to_s + "\"" + " skips=\"" + testIgnore.to_s + "\">" |
leothedragon | 0:25fa8795676b | 170 | @arrayList.insert(0, heading) |
leothedragon | 0:25fa8795676b | 171 | writeXmlOuput() |
leothedragon | 0:25fa8795676b | 172 | end |
leothedragon | 0:25fa8795676b | 173 | |
leothedragon | 0:25fa8795676b | 174 | # return result |
leothedragon | 0:25fa8795676b | 175 | end |
leothedragon | 0:25fa8795676b | 176 | |
leothedragon | 0:25fa8795676b | 177 | end |
leothedragon | 0:25fa8795676b | 178 | |
leothedragon | 0:25fa8795676b | 179 | # If the command line has no values in, used a default value of Output.txt |
leothedragon | 0:25fa8795676b | 180 | parseMyFile = ParseOutput.new |
leothedragon | 0:25fa8795676b | 181 | |
leothedragon | 0:25fa8795676b | 182 | if ARGV.size >= 1 |
leothedragon | 0:25fa8795676b | 183 | ARGV.each do |a| |
leothedragon | 0:25fa8795676b | 184 | if a == "-xml" |
leothedragon | 0:25fa8795676b | 185 | parseMyFile.setXmlOutput(); |
leothedragon | 0:25fa8795676b | 186 | else |
leothedragon | 0:25fa8795676b | 187 | parseMyFile.process(a) |
leothedragon | 0:25fa8795676b | 188 | break |
leothedragon | 0:25fa8795676b | 189 | end |
leothedragon | 0:25fa8795676b | 190 | end |
leothedragon | 0:25fa8795676b | 191 | end |