|
| 1 | +//summarize MSVC errors from an appveyor log |
| 2 | +// compile with 'go build summarize-appveyor-log.go' |
| 3 | +package main |
| 4 | + |
| 5 | +import ( |
| 6 | + "fmt" |
| 7 | + "bufio" |
| 8 | + "os" |
| 9 | + "regexp" |
| 10 | + "strings" |
| 11 | +) |
| 12 | + |
| 13 | +//uses stdin and stdout |
| 14 | +func main() { |
| 15 | + log := unwrap() |
| 16 | + warns,errs := countMessages(log) |
| 17 | + printMessages("warning",warns) |
| 18 | + printMessages("error",errs) |
| 19 | +} |
| 20 | + |
| 21 | +/* the regex will match lines like |
| 22 | + [ 00:03:42] c:\projects\stepcode\src\base\sc_benchmark.h(45): war*ning C4251: 'benchmark::descr' : class 'std::basic_string<char,std::char_traits<char>,std::allocator<char>>' needs to have dll-interface to be used by clients of class 'benchmark' [C:\projects\STEPcode\build\src\base\base.vcxproj] |
| 23 | + [00:03:48] C:\projects\STEPcode\src\base\sc_benchmark.cc(61): warning C4244: '=' : conversion from 'SIZE_T' to 'long', possible loss of data [C:\projects\STEPcode\build\src\base\base.vcxproj]* |
| 24 | +*/ |
| 25 | +func countMessages(log string) (warns, errs map[string][]string) { |
| 26 | + warns = make (map[string][]string) |
| 27 | + errs = make (map[string][]string) |
| 28 | + tstamp := `\[\d\d:\d\d:\d\d\] ` |
| 29 | + fname := " *(.*)" |
| 30 | + fline := `\((\d+)\): ` |
| 31 | + msgNr := `([A-Z]\d+): ` |
| 32 | + msgTxt := `([^\[]*) ` |
| 33 | + tail := `\[[^\[\]]*\]` |
| 34 | + warnRe := regexp.MustCompile(tstamp + fname + fline + `warning ` + msgNr + msgTxt + tail) |
| 35 | + errRe := regexp.MustCompile(tstamp + fname + fline + `error ` + msgNr + msgTxt + tail) |
| 36 | + reScanner := bufio.NewScanner(strings.NewReader(log)) |
| 37 | + for reScanner.Scan() { |
| 38 | + line := reScanner.Text() |
| 39 | + if warnRe.MatchString(line) { |
| 40 | + key := warnRe.ReplaceAllString(line, "$3") |
| 41 | + path := strings.ToLower(warnRe.ReplaceAllString(line, "$1:$2")) |
| 42 | + arr := warns[key] |
| 43 | + if arr == nil { |
| 44 | + arr = make([]string,5) |
| 45 | + //detailed text as first string in array |
| 46 | + text := warnRe.ReplaceAllString(line, "$4") |
| 47 | + arr[0] = fmt.Sprintf("%s", text) |
| 48 | + } |
| 49 | + //eliminate duplicates |
| 50 | + match := false |
| 51 | + for _, l := range arr { |
| 52 | + if l == path { |
| 53 | + match = true |
| 54 | + } |
| 55 | + } |
| 56 | + if !match { |
| 57 | + warns[key] = append(arr, path) |
| 58 | + } |
| 59 | + } else if errRe.MatchString(line) { |
| 60 | + key := errRe.ReplaceAllString(line, "$3") |
| 61 | + path := strings.ToLower(errRe.ReplaceAllString(line, "$1:$2")) |
| 62 | + arr := errs[key] |
| 63 | + if arr == nil { |
| 64 | + arr = make([]string,5) |
| 65 | + //detailed text as first string in array |
| 66 | + text := errRe.ReplaceAllString(line, "$4") |
| 67 | + arr[0] = fmt.Sprintf("%s", text) |
| 68 | + } |
| 69 | + //eliminate duplicates |
| 70 | + match := false |
| 71 | + for _, l := range arr { |
| 72 | + if l == path { |
| 73 | + match = true |
| 74 | + } |
| 75 | + } |
| 76 | + if !match { |
| 77 | + errs[key] = append(arr, path) |
| 78 | + } |
| 79 | + } |
| 80 | + } |
| 81 | + return |
| 82 | +} |
| 83 | + |
| 84 | +func printMessages( typ string, m map[string][]string) { |
| 85 | + for k,v := range m { |
| 86 | + for i,l := range v { |
| 87 | + //first string is an example, not a location |
| 88 | + if i == 0 { |
| 89 | + fmt.Printf("%s %s (i.e. \"%s\")\n", typ, k, l) |
| 90 | + } else if len(l) > 1 { //not sure where blank lines are coming from... |
| 91 | + fmt.Printf(" >> %s\n",l) |
| 92 | + } |
| 93 | + } |
| 94 | + } |
| 95 | +} |
| 96 | + |
| 97 | +func unwrap() (log string) { |
| 98 | + //read stdin, write stdout |
| 99 | + newline := true |
| 100 | + unwrapScanner := bufio.NewScanner(os.Stdin) |
| 101 | + for unwrapScanner.Scan() { |
| 102 | + lastNewline := newline |
| 103 | + line := unwrapScanner.Text() |
| 104 | + newline = (len(line) < 240) |
| 105 | + if !lastNewline { |
| 106 | + log += fmt.Sprintf("%s", line[11:]) |
| 107 | + } else { |
| 108 | + log += fmt.Sprintf("%s", line) |
| 109 | + } |
| 110 | + if newline { |
| 111 | + log += fmt.Sprintf("\n") |
| 112 | + } |
| 113 | + } |
| 114 | + if err := unwrapScanner.Err(); err != nil { |
| 115 | + fmt.Fprintln(os.Stderr, "Error reading appveyor log:", err) |
| 116 | + } |
| 117 | + return |
| 118 | +} |
0 commit comments