Allow custom revisions to be specified in A/B testing
authorrniwa@webkit.org <rniwa@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 8 Oct 2015 00:17:21 +0000 (00:17 +0000)
committerrniwa@webkit.org <rniwa@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 8 Oct 2015 00:17:21 +0000 (00:17 +0000)
https://bugs.webkit.org/show_bug.cgi?id=149905

Reviewed by Chris Dumez.

Allow custom revision number on each "repository" when creating a test group.

* public/v2/app.css:
(form .analysis-group [name=customValue]): Added.

* public/v2/app.js:
(App.AnalysisTaskController._createConfiguration): Added "Custom" as a revision option.
Also added point labels such as (point 3) on "None" for when some points are missing revision info.
(App.AnalysisTaskController._labelForPoints): Extracted from _createConfiguration.
(App.AnalysisTaskController.actions.createTestGroup): Respect the custom revision number when custom
revision option is selected.

* public/v2/index.html: Added a text field for specifying a custom revision number.

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@190696 268f45cc-cd09-0410-ab3c-d52691b4dbfc

Websites/perf.webkit.org/ChangeLog
Websites/perf.webkit.org/public/v2/app.css
Websites/perf.webkit.org/public/v2/app.js
Websites/perf.webkit.org/public/v2/index.html

index 270857f..b831475 100644 (file)
@@ -1,5 +1,26 @@
 2015-10-07  Ryosuke Niwa  <rniwa@webkit.org>
 
+        Allow custom revisions to be specified in A/B testing
+        https://bugs.webkit.org/show_bug.cgi?id=149905
+
+        Reviewed by Chris Dumez.
+
+        Allow custom revision number on each "repository" when creating a test group.
+
+        * public/v2/app.css:
+        (form .analysis-group [name=customValue]): Added.
+
+        * public/v2/app.js:
+        (App.AnalysisTaskController._createConfiguration): Added "Custom" as a revision option.
+        Also added point labels such as (point 3) on "None" for when some points are missing revision info.
+        (App.AnalysisTaskController._labelForPoints): Extracted from _createConfiguration.
+        (App.AnalysisTaskController.actions.createTestGroup): Respect the custom revision number when custom
+        revision option is selected.
+
+        * public/v2/index.html: Added a text field for specifying a custom revision number.
+
+2015-10-07  Ryosuke Niwa  <rniwa@webkit.org>
+
         Make the site name configurable in perf dashboard
         https://bugs.webkit.org/show_bug.cgi?id=149894
 
index e4a97e2..d07b27a 100644 (file)
@@ -437,6 +437,10 @@ form .analysis-group > * {
     margin: 0.5rem;
 }
 
+form .analysis-group [name=customValue] {
+    display: block;
+}
+
 #analysis-tasks,
 .analysis-group table {
     border: solid 0px #999;
index 815c286..9970690 100644 (file)
@@ -1391,12 +1391,14 @@ App.AnalysisTaskController = Ember.Controller.extend({
     _createConfiguration: function(repository, commits, analysisPoints) {
         var repositoryId = repository.get('id');
 
-        var options = [{label: 'None'}];
         var revisionToPoints = {};
+        var missingPoints = [];
         analysisPoints.forEach(function (point, pointIndex) {
             var revision = point.measurement.revisionForRepository(repositoryId);
-            if (!revision)
+            if (!revision) {
+                missingPoints.push(pointIndex);
                 return;
+            }
             if (!revisionToPoints[revision])
                 revisionToPoints[revision] = [];
             revisionToPoints[revision].push(pointIndex);
@@ -1408,15 +1410,31 @@ App.AnalysisTaskController = Ember.Controller.extend({
                 commits.push({revision: revision});
         }
 
+        var options = [{label: 'None'}, {label: 'Custom', isCustom: true}];
+        if (missingPoints.length) {
+            options[0].label += ' ' + this._labelForPoints(missingPoints);
+            options[0].points = missingPoints;
+        }
+
         for (var commit of commits) {
             var revision = commit.revision;
-            var label = Measurement.formatRevisionRange(revision).label;
             var points = revisionToPoints[revision];
-            if (points) {
-                var serializedPoints = this._serializeNumbersSkippingConsecutiveEntries(revisionToPoints[revision]);
-                label += ' ' + ['(', points.length > 1 ? 'points' : 'point', serializedPoints, ')'].join(' ');
-            }
-            options.push({value: revision, label: label});
+            var label = Measurement.formatRevisionRange(revision).label;
+            if (points)
+                label += ' ' + this._labelForPoints(points);
+            options.push({value: revision, label: label, points: points});
+        }
+
+        var firstOption = null;
+        var lastOption = null;
+        for (var option of options) {
+            var points = option.points;
+            if (!points)
+                continue;
+            if (points.indexOf(0) >= 0)
+                firstOption = option;
+            if (points.indexOf(analysisPoints.length - 1) >= 0)
+                lastOption = option;
         }
 
         return Ember.Object.create({
@@ -1425,12 +1443,17 @@ App.AnalysisTaskController = Ember.Controller.extend({
             sets: [
                 Ember.Object.create({name: 'A[' + repositoryId + ']',
                     options: options,
-                    selection: options[1]}),
+                    selection: firstOption}),
                 Ember.Object.create({name: 'B[' + repositoryId + ']',
                     options: options,
-                    selection: options[options.length - 1]}),
+                    selection: lastOption}),
             ]});
     },
+    _labelForPoints: function (points)
+    {
+        var serializedPoints = this._serializeNumbersSkippingConsecutiveEntries(points);
+        return ['(', points.length > 1 ? 'points' : 'point', serializedPoints, ')'].join(' ');
+    },
     _serializeNumbersSkippingConsecutiveEntries: function (numbers) {
         var result = numbers[0];
         for (var i = 1; i < numbers.length; i++) {
@@ -1495,14 +1518,20 @@ App.AnalysisTaskController = Ember.Controller.extend({
             var rootConfigurations = this.get('rootConfigurations').toArray();
             for (var root of rootConfigurations) {
                 var sets = root.get('sets');
-                var hasSelection = function (item) { return item.get('selection') && item.get('selection').value; };
+                var hasSelection = function (item) {
+                    var selection = item.get('selection');
+                    return selection.value || (selection.isCustom && item.get('customValue'));
+                }
                 if (!sets.any(hasSelection))
                     continue;
                 if (!sets.every(hasSelection)) {
                     alert('Only some configuration specifies ' + root.get('name'));
                     return;
                 }
-                roots[root.get('name')] = sets.map(function (item) { return item.get('selection').value; });                
+                roots[root.get('name')] = sets.map(function (item) {
+                    var selection = item.get('selection');
+                    return selection.isCustom ? item.get('customValue') : selection.value;
+                });
             }
 
             App.TestGroup.create(analysisTask, name, roots, repetitionCount).then(function () {
index a1b7bd2..8b11ece 100644 (file)
                             <tr>
                                 <th>{{name}}</th>
                                 {{#each sets}}
-                                    <td>{{view Ember.Select name=name content=options
-                                        optionValuePath="content.value" optionLabelPath="content.label"
-                                        selection=selection}}</td>
+                                    <td>
+                                        {{view Ember.Select name=name content=options
+                                            optionValuePath="content.value" optionLabelPath="content.label"
+                                            selection=selection}}
+                                        {{#if selection.isCustom}}
+                                            {{input name="customValue" type=text value=customValue}}
+                                        {{/if}}
+                                        </td>
                                 {{/each}}
                             </tr>
                         {{/each}}