OLD | NEW |
1 <!-- | 1 <!-- |
2 Copyright 2014 The Chromium Authors. All rights reserved. | 2 Copyright 2014 The Chromium Authors. All rights reserved. |
3 Use of this source code is governed by a BSD-style license that can be | 3 Use of this source code is governed by a BSD-style license that can be |
4 found in the LICENSE file. | 4 found in the LICENSE file. |
5 --> | 5 --> |
6 | 6 |
| 7 <link rel="import" href="../model/ct-failure.html"> |
| 8 |
7 <polymer-element name="ct-failure-analyzer" attributes="failures builderLatestRe
visions"> | 9 <polymer-element name="ct-failure-analyzer" attributes="failures builderLatestRe
visions"> |
8 <script> | 10 <script> |
9 // FIXME: Don't use a polymer component for this. Instead use a Failures mod
el | 11 // FIXME: Don't use a polymer component for this. Instead use a Failures mod
el |
10 // object that knows how to do the XHR and process the data appropriately. | 12 // object that knows how to do the XHR and process the data appropriately. |
11 Polymer({ | 13 Polymer({ |
12 builderLatestRevisions: {}, | 14 builderLatestRevisions: {}, |
13 failures: {}, | 15 failures: {}, |
14 | 16 |
15 update: function() { | 17 update: function() { |
16 net.json('http://auto-sheriff.appspot.com/data').then(function(data) { | 18 net.json('http://auto-sheriff.appspot.com/data').then(function(data) { |
17 // FIXME: Don't special-case the blink master. | 19 // FIXME: Don't special-case the blink master. |
18 this.builderLatestRevisions = data.latest_revisions['chromium.webkit']
; | 20 this.builderLatestRevisions = data.latest_revisions['chromium.webkit']
; |
19 this.failures.builders = {}; | 21 this.failures = []; |
20 this.failures.unexpected = []; | |
21 data.range_groups.forEach(function(group) { | 22 data.range_groups.forEach(function(group) { |
22 this._processFailuresForGroup(group, data.alerts); | 23 this._processFailuresForGroup(group, data.alerts); |
23 }.bind(this)); | 24 }.bind(this)); |
| 25 // FIXME: Sort this.failures by severity of regression, then by oldest
FailingRevision. |
24 }.bind(this)); | 26 }.bind(this)); |
25 }, | 27 }, |
26 | 28 |
| 29 _failureComparator: function(a, b) { |
| 30 if (a.step > b.step) |
| 31 return 1; |
| 32 if (a.step < b.step) |
| 33 return -1 |
| 34 if (a.testName > b.testName) |
| 35 return 1; |
| 36 if (a.testName < b.testName) |
| 37 return -1 |
| 38 return 0; |
| 39 }, |
| 40 |
27 _processFailuresForGroup: function(group, failures) { | 41 _processFailuresForGroup: function(group, failures) { |
28 var failuresByReason = {}; | 42 var failuresByReason = {}; |
29 var failingBuildersWithoutReasons = {}; | |
30 | 43 |
31 group.failure_keys.forEach(function(failure_key) { | 44 group.failure_keys.forEach(function(failure_key) { |
32 var failure = failures.find(function(item) { return item.key == failur
e_key; }); | 45 var failure = failures.find(function(item) { return item.key == failur
e_key; }); |
33 if (failure.ignored_by.length) | 46 if (failure.ignored_by.length) |
34 return; | 47 return; |
35 | 48 |
36 // FIXME: Make sheriff-o-matic work for all waterfalls. | 49 // FIXME: Make sheriff-o-matic work for all waterfalls. |
37 if (!failure.master_url.endsWith('chromium.webkit')) | 50 if (!failure.master_url.endsWith('chromium.webkit')) |
38 return; | 51 return; |
39 | 52 |
40 // FIXME: Have sheriff-o-matic show non-webkit_tests failures by reaso
n. | 53 var reason, failureType; |
41 if (!failure.reason || failure.step_name != 'webkit_tests') { | 54 if (failure.reason) { |
42 var builder = failure.builder_name; | 55 // FIXME: Store the actual failure type in a different field instead
of smashing it into the reason. |
43 if (!failingBuildersWithoutReasons[builder]) | 56 var parts = failure.reason.split(':'); |
44 failingBuildersWithoutReasons[builder] = {}; | 57 reason = parts[0]; |
45 failingBuildersWithoutReasons[builder][failure.step_name] = 1; | 58 failureType = parts[1] || 'FAIL'; |
46 return; | 59 } else { |
| 60 reason = null; |
| 61 failureType = 'UNKNOWN'; |
47 } | 62 } |
48 | 63 |
49 // FIXME: Store the actual failure type in a different field instead o
f smashing it into the reason. | 64 var failureKey = JSON.stringify({ |
50 var parts = failure.reason.split(':'); | 65 step: failure.step_name, |
51 var reason = parts[0]; | 66 reason: reason, |
52 var failureType = parts[1]; | 67 }); |
53 | 68 |
54 if (!failuresByReason[reason]) | 69 // FIXME: Use a model class instead of a dumb object. |
55 failuresByReason[reason] = {} | 70 if (!failuresByReason[failureKey]) |
56 failuresByReason[reason][failure.builder_name] = { | 71 failuresByReason[failureKey] = {}; |
| 72 // FIXME: If we have multiple builders with the same name across maste
rs in |
| 73 // a failure group, then this will incorrectly overwrite one of the va
lues. |
| 74 failuresByReason[failureKey][failure.builder_name] = { |
| 75 // FIXME: Rename to failureType. |
57 actual: failureType, | 76 actual: failureType, |
| 77 lastFailingBuild: failure.last_failing_build, |
| 78 masterUrl: failure.master_url, |
58 }; | 79 }; |
59 }.bind(this)); | 80 }.bind(this)); |
60 | 81 |
61 var groupedFailures = []; | 82 var groupedFailures = []; |
62 var oldestFailingRevision = Number(group.merged_first_failing.blink); | |
63 var newestPassingRevision = group.merged_last_passing ? Number(group.mer
ged_last_passing.blink) : undefined; | |
64 | 83 |
65 Object.keys(failuresByReason, function(reason, resultNodesByBuilder) { | 84 var oldestFailingRevision, newestPassingRevision; |
66 groupedFailures.push({ | 85 // FIXME: This is a workaround for the backend's bogus data when the bli
nk |
67 testName: reason, | 86 // regression ranges have no overlap. |
68 resultNodesByBuilder: resultNodesByBuilder, | 87 if (group.merged_last_passing && group.merged_first_failing.blink > grou
p.merged_last_passing.blink) { |
69 oldestFailingRevision: oldestFailingRevision, | 88 oldestFailingRevision = Number(group.merged_first_failing.blink); |
70 newestPassingRevision: newestPassingRevision, | 89 newestPassingRevision = Number(group.merged_last_passing.blink); |
71 }); | 90 } |
| 91 |
| 92 Object.keys(failuresByReason, function(failureKey, resultByBuilder) { |
| 93 var failure = JSON.parse(failureKey); |
| 94 groupedFailures.push(new CTFailure(failure.step, failure.reason, resul
tByBuilder, oldestFailingRevision, newestPassingRevision)); |
72 }); | 95 }); |
73 | 96 |
| 97 // FIXME: Make this a model class intead of a dumb object. |
| 98 groupedFailures.sort(this._failureComparator); |
| 99 |
74 if (groupedFailures.length) | 100 if (groupedFailures.length) |
75 this.failures.unexpected.push(groupedFailures); | 101 this.failures.push(groupedFailures); |
76 | |
77 // FIXME: Show these in the failure stream with regression ranges like | |
78 // any other kind of failure. | |
79 Object.keys(failingBuildersWithoutReasons, function(builder, steps) { | |
80 this.failures.builders[builder] = Object.keys(steps); | |
81 }.bind(this)); | |
82 }, | 102 }, |
83 }); | 103 }); |
84 </script> | 104 </script> |
85 </polymer-element> | 105 </polymer-element> |
OLD | NEW |