Repository: ambari Updated Branches: refs/heads/trunk 9077a9d30 -> efb923547
AMBARI-10755 NodeManager Disk and Network widget appears blank. (atkach) Project: http://git-wip-us.apache.org/repos/asf/ambari/repo Commit: http://git-wip-us.apache.org/repos/asf/ambari/commit/efb92354 Tree: http://git-wip-us.apache.org/repos/asf/ambari/tree/efb92354 Diff: http://git-wip-us.apache.org/repos/asf/ambari/diff/efb92354 Branch: refs/heads/trunk Commit: efb92354748c29a13f8dbcd7ca12e092ee42f013 Parents: 9077a9d Author: Andrii Tkach <atk...@hortonworks.com> Authored: Mon Apr 27 11:50:24 2015 +0300 Committer: Andrii Tkach <atk...@hortonworks.com> Committed: Mon Apr 27 12:25:52 2015 +0300 ---------------------------------------------------------------------- ambari-web/app/assets/test/tests.js | 2 + .../service/widgets/create/step1_controller.js | 4 + .../service/widgets/create/step2_controller.js | 7 + .../main/service/widgets/create/step2.hbs | 4 +- .../views/common/widget/graph_widget_view.js | 39 +++++- .../widgets/create/step1_controller_test.js | 89 +++++++++++++ .../common/widget/graph_widget_view_test.js | 129 +++++++++++++++++++ 7 files changed, 270 insertions(+), 4 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/ambari/blob/efb92354/ambari-web/app/assets/test/tests.js ---------------------------------------------------------------------- diff --git a/ambari-web/app/assets/test/tests.js b/ambari-web/app/assets/test/tests.js index 14a0ea8..055f447 100644 --- a/ambari-web/app/assets/test/tests.js +++ b/ambari-web/app/assets/test/tests.js @@ -86,6 +86,7 @@ var files = ['test/init_model_test', 'test/controllers/main/service/reassign/step4_controller_test', 'test/controllers/main/service/reassign/step6_controller_test', 'test/controllers/main/service/reassign/step7_controller_test', + 'test/controllers/main/service/widgets/create/step1_controller_test', 'test/controllers/main/dashboard_test', 'test/controllers/main/host_test', 'test/controllers/main/service/item_test', @@ -176,6 +177,7 @@ var files = ['test/init_model_test', 'test/views/common/sort_view_test', 'test/views/common/custom_date_popup_test', 'test/views/common/progress_bar_view_test', + 'test/views/common/widget/graph_widget_view_test', 'test/views/main/admin_test', 'test/views/main/dashboard_test', 'test/views/main/menu_test', http://git-wip-us.apache.org/repos/asf/ambari/blob/efb92354/ambari-web/app/controllers/main/service/widgets/create/step1_controller.js ---------------------------------------------------------------------- diff --git a/ambari-web/app/controllers/main/service/widgets/create/step1_controller.js b/ambari-web/app/controllers/main/service/widgets/create/step1_controller.js index 92e9615..5bc6b2f 100644 --- a/ambari-web/app/controllers/main/service/widgets/create/step1_controller.js +++ b/ambari-web/app/controllers/main/service/widgets/create/step1_controller.js @@ -54,6 +54,10 @@ App.WidgetWizardStep1Controller = Em.Controller.extend({ }); }.property('widgetType'), + /** + * choose widget type and proceed to the next step + * @param {object} event + */ chooseOption: function (event) { this.set('widgetType', event.context); this.next(); http://git-wip-us.apache.org/repos/asf/ambari/blob/efb92354/ambari-web/app/controllers/main/service/widgets/create/step2_controller.js ---------------------------------------------------------------------- diff --git a/ambari-web/app/controllers/main/service/widgets/create/step2_controller.js b/ambari-web/app/controllers/main/service/widgets/create/step2_controller.js index 3051ffd..0d5f414 100644 --- a/ambari-web/app/controllers/main/service/widgets/create/step2_controller.js +++ b/ambari-web/app/controllers/main/service/widgets/create/step2_controller.js @@ -76,6 +76,13 @@ App.WidgetWizardStep2Controller = Em.Controller.extend({ widgetPropertiesViews: [], /** + * @type {boolean} + */ + isEditWidget: function () { + return this.get('content.controllerName') === 'widgetEditController'; + }.property('content.controllerName'), + + /** * metrics filtered by type * @type {Array} */ http://git-wip-us.apache.org/repos/asf/ambari/blob/efb92354/ambari-web/app/templates/main/service/widgets/create/step2.hbs ---------------------------------------------------------------------- diff --git a/ambari-web/app/templates/main/service/widgets/create/step2.hbs b/ambari-web/app/templates/main/service/widgets/create/step2.hbs index 7723995..47d206e 100644 --- a/ambari-web/app/templates/main/service/widgets/create/step2.hbs +++ b/ambari-web/app/templates/main/service/widgets/create/step2.hbs @@ -49,7 +49,9 @@ <div class="btn-area"> - <button id="add-widget-step2-back" class="btn" {{action back}}>← {{t common.back}}</button> + {{#unless isEditWidget}} + <button id="add-widget-step2-back" class="btn" {{action back}}>← {{t common.back}}</button> + {{/unless}} <button id="add-widget-step2-next" class="btn btn-success pull-right" {{bindAttr disabled="isSubmitDisabled"}} {{action "next" target="controller"}}>{{t common.next}} →</button> </div> </div> \ No newline at end of file http://git-wip-us.apache.org/repos/asf/ambari/blob/efb92354/ambari-web/app/views/common/widget/graph_widget_view.js ---------------------------------------------------------------------- diff --git a/ambari-web/app/views/common/widget/graph_widget_view.js b/ambari-web/app/views/common/widget/graph_widget_view.js index 4d170c5..9bd167e 100644 --- a/ambari-web/app/views/common/widget/graph_widget_view.js +++ b/ambari-web/app/views/common/widget/graph_widget_view.js @@ -84,15 +84,19 @@ App.GraphWidgetView = Em.View.extend(App.WidgetMixin, { var validExpression = true, value = [], dataLinks = {}, - dataLength = 0, + dataLength = -1, beforeCompute, - result = {}; + result = {}, + isDataCorrupted = false; //replace values with metrics data expression.match(this.get('VALUE_NAME_REGEX')).forEach(function (match) { if (metrics.someProperty('name', match)) { dataLinks[match] = metrics.findProperty('name', match).data; - dataLength = metrics.findProperty('name', match).data.length; + if (!isDataCorrupted) { + isDataCorrupted = (dataLength !== -1 && dataLength !== dataLinks[match].length); + } + dataLength = (dataLinks[match].length > dataLength) ? dataLinks[match].length : dataLength; } else { validExpression = false; console.error('Metrics with name "' + match + '" not found to compute expression'); @@ -100,6 +104,9 @@ App.GraphWidgetView = Em.View.extend(App.WidgetMixin, { }); if (validExpression) { + if (isDataCorrupted) { + this.adjustData(dataLinks, dataLength); + } for (var i = 0, timestamp; i < dataLength; i++) { beforeCompute = expression.replace(this.get('VALUE_NAME_REGEX'), function (match) { timestamp = dataLinks[match][i][1]; @@ -114,6 +121,32 @@ App.GraphWidgetView = Em.View.extend(App.WidgetMixin, { }, /** + * add missing points, with zero value, to series + * + * @param {object} dataLinks + * @param {number} length + */ + adjustData: function(dataLinks, length) { + //series with full data taken as original + var original = []; + var substituteValue = 0; + + for (var i in dataLinks) { + if (dataLinks[i].length === length) { + original = dataLinks[i]; + break; + } + } + original.forEach(function(point, index) { + for (var i in dataLinks) { + if (!dataLinks[i][index] || dataLinks[i][index][1] !== point[1]) { + dataLinks[i].splice(index, 0, [substituteValue, point[1]]); + } + } + }, this); + }, + + /** * make GET call to server in order to fetch service-component metrics * @param {object} request * @returns {$.ajax} http://git-wip-us.apache.org/repos/asf/ambari/blob/efb92354/ambari-web/test/controllers/main/service/widgets/create/step1_controller_test.js ---------------------------------------------------------------------- diff --git a/ambari-web/test/controllers/main/service/widgets/create/step1_controller_test.js b/ambari-web/test/controllers/main/service/widgets/create/step1_controller_test.js new file mode 100644 index 0000000..8ceb669 --- /dev/null +++ b/ambari-web/test/controllers/main/service/widgets/create/step1_controller_test.js @@ -0,0 +1,89 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +App = require('app'); + +require('controllers/main/service/widgets/create/step1_controller'); + + +describe('App.WidgetWizardStep1Controller', function () { + var controller = App.WidgetWizardStep1Controller.create(); + + describe("#isSubmitDisabled", function() { + it("disabled", function() { + controller.set('widgetType', ''); + controller.propertyDidChange('isSubmitDisabled'); + expect(controller.get('isSubmitDisabled')).to.be.true; + }); + it("enabled", function() { + controller.set('widgetType', 'w1'); + controller.propertyDidChange('isSubmitDisabled'); + expect(controller.get('isSubmitDisabled')).to.be.false; + }); + }); + + describe("#chooseOption()", function () { + before(function () { + sinon.stub(controller, 'next'); + }); + after(function () { + controller.next.restore(); + }); + it("", function () { + controller.chooseOption({context: 'type1'}); + expect(controller.get('widgetType')).to.equal('type1'); + expect(controller.next.calledOnce).to.be.true; + }); + }); + + describe("#loadStep()", function () { + before(function () { + sinon.stub(controller, 'clearStep'); + }); + after(function () { + controller.clearStep.restore(); + }); + it("", function () { + controller.loadStep(); + expect(controller.clearStep.calledOnce).to.be.true; + }); + }); + + describe("#clearStep()", function () { + it("", function () { + controller.clearStep(); + expect(controller.get('widgetType')).to.be.empty; + }); + }); + + describe("#next()", function () { + before(function () { + sinon.stub(App.router, 'send'); + }); + after(function () { + App.router.send.restore(); + }); + it("", function () { + controller.next(); + expect(App.router.send.calledWith('next')).to.be.true; + }); + }); + + + +}); http://git-wip-us.apache.org/repos/asf/ambari/blob/efb92354/ambari-web/test/views/common/widget/graph_widget_view_test.js ---------------------------------------------------------------------- diff --git a/ambari-web/test/views/common/widget/graph_widget_view_test.js b/ambari-web/test/views/common/widget/graph_widget_view_test.js new file mode 100644 index 0000000..62ac67e --- /dev/null +++ b/ambari-web/test/views/common/widget/graph_widget_view_test.js @@ -0,0 +1,129 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +var App = require('app'); +require('views/common/widget/graph_widget_view'); + +describe('App.GraphWidgetView', function () { + var view = App.GraphWidgetView.create(); + + describe("#adjustData()", function() { + var testCases = [ + { + title: 'empty data', + data: { + dataLinks: {}, + dataLength: 0 + }, + result: {} + }, + { + title: 'correct data', + data: { + dataLinks: { + s1: [[0, 0]] + }, + dataLength: 1 + }, + result: { + s1: [[0, 0]] + } + }, + { + title: 'second series empty', + data: { + dataLinks: { + s1: [[1, 0]], + s2: [] + }, + dataLength: 1 + }, + result: { + s1: [[1, 0]], + s2: [[0, 0]] + } + }, + { + title: 'second series missing data at the end', + data: { + dataLinks: { + s1: [[1, 0], [2, 1], [3, 2]], + s2: [[1, 0]] + }, + dataLength: 3 + }, + result: { + s1: [[1, 0], [2, 1], [3, 2]], + s2: [[1, 0], [0, 1], [0, 2]] + } + }, + { + title: 'second series missing data at the beginning', + data: { + dataLinks: { + s1: [[1, 0], [2, 1], [3, 2]], + s2: [[3, 2]] + }, + dataLength: 3 + }, + result: { + s1: [[1, 0], [2, 1], [3, 2]], + s2: [[0, 0], [0, 1], [3, 2]] + } + }, + { + title: 'second series missing data in the middle', + data: { + dataLinks: { + s1: [[1, 0], [2, 1], [3, 2]], + s2: [[1, 1]] + }, + dataLength: 3 + }, + result: { + s1: [[1, 0], [2, 1], [3, 2]], + s2: [[0, 0], [1, 1], [0, 2]] + } + }, + { + title: 'second and third series missing data', + data: { + dataLinks: { + s1: [[1, 0], [2, 1], [3, 2]], + s2: [[1, 1]], + s3: [[1, 2]] + }, + dataLength: 3 + }, + result: { + s1: [[1, 0], [2, 1], [3, 2]], + s2: [[0, 0], [1, 1], [0, 2]], + s3: [[0, 0], [0, 1], [1, 2]] + } + } + ]; + + testCases.forEach(function (test) { + it(test.title, function () { + view.adjustData(test.data.dataLinks, test.data.dataLength); + expect(test.data.dataLinks).to.eql(test.result); + }); + }); + }); + +}); \ No newline at end of file