Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(355)

Side by Side Diff: Tools/GardeningServer/model/ct-failures.html

Issue 728023004: Remove GardeningServer. (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Created 6 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 <!--
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
4 found in the LICENSE file.
5 -->
6
7 <link rel="import" href="../lib/net.html">
8 <link rel="import" href="../lib/update-util.html">
9 <link rel="import" href="ct-builder-failure.html">
10 <link rel="import" href="ct-step-failure.html">
11 <link rel="import" href="ct-failure-group.html">
12 <link rel="import" href="ct-builder-failure-group-data.html">
13 <link rel="import" href="ct-master-failure.html">
14 <link rel="import" href="ct-master-failure-group-data.html">
15 <link rel="import" href="ct-step-failure-group-data.html">
16 <link rel="import" href="ct-trooper-failure-group-data.html">
17 <link rel="import" href="ct-commit-list.html">
18
19 <script>
20 function CTFailures(commitLog) {
21 this.commitLog = commitLog;
22 // Maps a tree id to an array of CTFailureGroups within that tree.
23 this.failures = null;
24 this.lastUpdateDate = null;
25 }
26
27 (function() {
28 'use strict';
29
30 // FIXME: This could potentially move onto CTStepFailureGroupData as it isn't re levant to
31 // trooper failures.
32 // Reverse sorting order, if a > b, return a negative number.
33 CTFailures.prototype._failureByTreeListComparator = function(tree, a, b) {
34 if (tree === undefined)
35 tree = 'chromium';
36
37 // Always bubble master alerts to the top
38 if (a.category =='master') {
39 if (b.category == 'master')
40 return 0;
41 return -1;
42 } else if (b.category == 'master') {
43 return 1;
44 }
45
46 if (!a.data.commitList)
47 return 1;
48 if (!b.data.commitList)
49 return -1;
50
51 var rev_a = a.data.commitList.revisions;
52 var rev_b = b.data.commitList.revisions;
53
54 if (!rev_a || !Object.keys(rev_a).length) {
55 if (!rev_b || !Object.keys(rev_b).length)
56 return 0;
57 return 1;
58 } else if (!rev_b || !Object.keys(rev_b).length) {
59 return -1;
60 }
61
62 // Prioritize the tree's revision, if they are unequal (else, fallback below)
63 if (rev_a[tree] && rev_b[tree] &&
64 rev_a[tree].last() != rev_b[tree].last()) {
65 return rev_b[tree].last() - rev_a[tree].last();
66 }
67
68 // Compare other revisions in alphabetical order.
69 var keys = Object.keys(rev_a).sort();
70 for (var i = 0; i < keys.length; i++) {
71 if (keys[i] == tree) // Already taken care of, above.
72 continue;
73
74 var a_list = rev_a[keys[i]];
75 var b_list = rev_b[keys[i]];
76 if (!b_list)
77 return -1;
78
79 if (a_list.last() != b_list.last())
80 return b_list.last() - a_list.last();
81 }
82 return 0;
83 };
84
85 // Updates the format of the alerts array to be easier to parse.
86 CTFailures.prototype._mungeAlerts = function(alerts) {
87 alerts.forEach(function(failure) {
88 // FIXME: Have the server store the actual failure type in a different
89 // field instead of smashing it into the reason.
90 if (failure.failureType) {
91 // The server has been fixed.
92 } else {
93 if (failure.reason) {
94 var parts = failure.reason.split(':');
95 failure.reason = parts[0];
96 failure.failureType = parts[1] || 'FAIL';
97 } else {
98 failure.failureType = 'UNKNOWN';
99 }
100 }
101 });
102 };
103
104 CTFailures.prototype.update = function() {
105 var annotationPromise = CTFailureGroup.fetchAnnotations();
106 return Promise.all([annotationPromise, net.json('https://sheriff-o-matic.appsp ot.com/alerts'),
107 net.json('https://trooper-o-matic.appspot.com/alerts')]).then(function(dat a_array) {
108 var annotations = data_array[0];
109 var sheriff_data = data_array[1];
110 var trooper_data = data_array[2];
111
112 var newFailures = {};
113 this.lastUpdateDate = new Date(sheriff_data.date * 1000);
114 this._mungeAlerts(sheriff_data.alerts);
115 // FIXME: Change builder_alerts to expose the alerts as a map instead of an array.
116 var alertsByKey = {}
117 sheriff_data.alerts.forEach(function(alert) {
118 alertsByKey[alert.key] = alert;
119 });
120 // Update |failures| with the appropriate CTFailureGroup's for each
121 // tree.
122 sheriff_data.range_groups.forEach(function(rangeGroup) {
123 this._processFailuresForRangeGroup(newFailures, rangeGroup, alertsByKey, a nnotations);
124 }.bind(this));
125
126 sheriff_data.stale_builder_alerts.forEach(function(alert) {
127 this._processBuilderFailure(newFailures, alert);
128 }.bind(this));
129
130 // Sort failure groups so that newer failures are shown at the top
131 // of the UI.
132 Object.keys(newFailures, function (tree, failuresByTree) {
133 failuresByTree.sort(this._failureByTreeListComparator.bind(this, tree));
134 }.bind(this));
135
136 this.failures = updateUtil.updateLeft(this.failures, newFailures);
137 this._processTrooperFailures(newFailures, trooper_data);
138 }.bind(this));
139 };
140
141 CTFailures.prototype._failureComparator = function(a, b) {
142 if (a.step > b.step)
143 return 1;
144 if (a.step < b.step)
145 return -1
146 if (a.testName > b.testName)
147 return 1;
148 if (a.testName < b.testName)
149 return -1
150 return 0;
151 };
152
153 CTFailures.prototype._processTrooperFailures = function(all_failures,
154 trooper_data) {
155 var trooper_failures = [];
156 Object.keys(trooper_data, function(failureType, failuresByTree) {
157 Object.keys(failuresByTree, function(tree, failure) {
158 if (failure.should_alert) {
159 trooper_failures.push(new CTFailureGroup('trooper',
160 new CTTrooperFailureGroupData(failure.details, failure.url, failure,
161 failureType, tree)));
162 }
163 });
164 });
165
166 Object.keys(all_failures, function(tree, failuresByTree) {
167 failuresByTree.forEach(function(failure) {
168 if (failure.category == 'builder' || failure.category == 'master') {
169 trooper_failures.push(failure);
170 }
171 });
172 });
173 this.failures['trooper'] = trooper_failures;
174 };
175
176 CTFailures.prototype._groupFailuresByTreeAndReason = function(failures, annotati ons) {
177 var failuresByTree = {};
178 failures.forEach(function(failure) {
179 // Establish the key to uniquely identify a failure by reason.
180 var failureKey = CTStepFailure.createKey(failure);
181
182 var reasonKey = JSON.stringify({
183 step: failure.step_name,
184 reason: failure.reason,
185 });
186
187 // FIXME: Use a model class instead of a dumb object.
188 if (!failuresByTree[failure.tree])
189 failuresByTree[failure.tree] = {};
190 if (!failuresByTree[failure.tree][reasonKey])
191 failuresByTree[failure.tree][reasonKey] = {};
192 failuresByTree[failure.tree][reasonKey][failure.builder_name] = {
193 key: failureKey,
194 // FIXME: Rename to failureType.
195 actual: failure.failureType,
196 lastFailingBuild: failure.last_failing_build,
197 masterUrl: failure.master_url,
198 failingBuildCount: (1 + failure.last_failing_build - failure.failing_build ),
199 annotation: annotations[failureKey],
200 isTreeCloser: failure.would_close_tree,
201 };
202 });
203 return failuresByTree
204 };
205
206 CTFailures.prototype._processFailuresForRangeGroup = function(newFailures, range Group, alerts, annotations) {
207 // A rangeGroup may be related to multiple alerts (via |failure_keys|). Catego rize
208 // these failures by reason (cause of failure), so that they can be grouped in the UI
209 // (via a CTFailureGroup).
210 var failures = rangeGroup.failure_keys.map(function(failure_key) {
211 return alerts[failure_key];
212 });
213 var failuresByTree = this._groupFailuresByTreeAndReason(failures, annotations) ;
214
215 if (Object.isEmpty(failuresByTree))
216 return;
217
218 Object.keys(failuresByTree, function(tree, resultsByReason) {
219 var treeFailures = [];
220 Object.keys(resultsByReason, function(reasonKey, resultsByBuilder) {
221 var failure = JSON.parse(reasonKey);
222 treeFailures.push(
223 new CTStepFailure(failure.step, failure.reason, resultsByBuilder));
224 })
225 treeFailures.sort(this._failureComparator);
226
227 if (!newFailures[tree])
228 newFailures[tree] = [];
229 var commitList = new CTCommitList(this.commitLog, rangeGroup.likely_revision s);
230 newFailures[tree].push(new CTFailureGroup(tree, new CTStepFailureGroupData(t reeFailures, commitList)));
231 }.bind(this));
232 };
233
234 CTFailures.prototype._processBuilderFailure = function(newFailures, alert) {
235 var timeSinceLastUpdate = (this.lastUpdateDate.valueOf() / 1000) - alert.last_ update_time;
236
237 var failure;
238 var data;
239 var category;
240 if (alert.hasOwnProperty('builder_name')) {
241 category = 'builder';
242 failure = new CTBuilderFailure(alert.tree, alert.master_url, alert.builder_n ame, alert.state,
243 timeSinceLastUpdate, alert.pending_builds, alert.hasOwnProperty('isMaste r'));
244 data = new CTBuilderFailureGroupData(failure, alert.builder_name,
245 alert.master_url + "/builders/" + alert.builder_name);
246 } else {
247 category = 'master';
248 failure = new CTMasterFailure(alert.tree, alert.master_url, timeSinceLastUpd ate);
249 data = new CTMasterFailureGroupData(failure, alert.master_url);
250 }
251 if (!newFailures[alert.tree])
252 newFailures[alert.tree] = [];
253 newFailures[alert.tree].push(new CTFailureGroup(alert.tree, data, category));
254 };
255
256 })();
257
258 </script>
OLDNEW
« no previous file with comments | « Tools/GardeningServer/model/ct-failure-group.html ('k') | Tools/GardeningServer/model/ct-master-failure.html » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698