فهرست منبع

AMBARI-10656 If threshold is not defined then color for Gauge and Number widget type should be green. (atkach)

Andrii Tkach 10 سال پیش
والد
کامیت
7c55d5b54c

+ 21 - 120
ambari-web/app/controllers/main/service/widgets/create/step2_controller.js

@@ -75,29 +75,6 @@ App.WidgetWizardStep2Controller = Em.Controller.extend({
    */
   widgetPropertiesViews: [],
 
-  propertiesMap: {
-    "warning_threshold": {
-      name: 'threshold',
-      property: 'smallValue'
-    },
-    "error_threshold": {
-      name: 'threshold',
-      property: 'bigValue'
-    },
-    "display_unit": {
-      name: 'display-unit',
-      property: 'value'
-    },
-    "graph_type": {
-      name: 'graph_type',
-      property: 'value'
-    },
-    "time_range": {
-      name: 'time_range',
-      property: 'value'
-    }
-  },
-
   /**
    * metrics filtered by type
    * @type {Array}
@@ -338,16 +315,13 @@ App.WidgetWizardStep2Controller = Em.Controller.extend({
    * update properties of preview widget
    */
   updateProperties: function () {
-    var propertiesMap = this.get('propertiesMap');
     var result = {};
-    var widgetProperty;
 
-    for (var i in propertiesMap) {
-      widgetProperty = this.get('widgetPropertiesViews').findProperty('name', propertiesMap[i].name);
-      if (widgetProperty && widgetProperty.get('isValid')) {
-        result[i] = widgetProperty.get(propertiesMap[i].property);
+    this.get('widgetPropertiesViews').forEach(function(property){
+      for (var key in property.valueMap) {
+        result[property.valueMap[key]] = property.get(key);
       }
-    }
+    });
     this.set('widgetProperties', result);
   }.observes('widgetPropertiesViews.@each.value', 'widgetPropertiesViews.@each.bigValue', 'widgetPropertiesViews.@each.smallValue'),
 
@@ -355,97 +329,24 @@ App.WidgetWizardStep2Controller = Em.Controller.extend({
    * Generate the thresholds, unit, time range.etc object based on the widget type selected in previous step.
    */
   renderProperties: function () {
-    var widgetType = this.get('content.widgetType');
-    var widgetProperties = App.WidgetType.find().findProperty('name', widgetType).get('properties');
-    var properties = [];
-
-    switch (widgetType) {
-      case 'GAUGE':
-        properties = this.renderGaugeProperties(widgetProperties);
-        break;
-      case 'NUMBER':
-        properties = this.renderNumberProperties(widgetProperties);
-        break;
-      case 'GRAPH':
-        properties = this.renderGraphProperties(widgetProperties);
-        break;
-      case 'TEMPLATE':
-        properties = this.renderTemplateProperties(widgetProperties);
-        break;
-      default:
-        console.error('Incorrect Widget Type: ', widgetType);
-    }
-    this.set('widgetPropertiesViews', properties);
-  },
-
-  /**
-   * Render properties for gauge-type widget
-   * @method renderGaugeProperties
-   * @returns {App.WidgetProperties[]}
-   */
-  renderGaugeProperties: function () {
-    return [
-      App.WidgetProperties.Thresholds.PercentageThreshold.create({
-        smallValue: this.get('widgetProperties.warning_threshold') || '0.7',
-        bigValue: this.get('widgetProperties.error_threshold') || '0.9',
-        isRequired: true
-      })
-    ];
-  },
-
-  /**
-   * Render properties for number-type widget
-   * @method renderNumberProperties
-   * @returns {App.WidgetProperties[]}
-   */
-  renderNumberProperties: function () {
-    return [
-      App.WidgetProperties.Threshold.create({
-        smallValue: this.get('widgetProperties.warning_threshold') || '10',
-        bigValue: this.get('widgetProperties.error_threshold') || '20',
-        isRequired: false
-      }),
-      App.WidgetProperties.Unit.create({
-        value: this.get('widgetProperties.display_unit') || 'MB',
-        isRequired: false
-      })
-    ];
-  },
-
-  /**
-   * Render properties for template-type widget
-   * @method renderTemplateProperties
-   * @returns {App.WidgetProperties[]}
-   */
-  renderTemplateProperties: function (widgetProperties) {
-    return [
-      App.WidgetProperties.Unit.create({
-        value: this.get('widgetProperties.display_unit') || 'MB',
-        isRequired: false
-      })
-    ];
-  },
+    var widgetProperties = App.WidgetType.find(this.get('content.widgetType')).get('properties');
+    var propertiesData = this.get('widgetProperties');
+    var result = [];
+
+    widgetProperties.forEach(function (property) {
+      var definition = App.WidgetPropertyTypes.findProperty('name', property.name);
+      property = $.extend({}, property);
+
+      //restore previous values
+      for (var key in definition.valueMap) {
+        if (propertiesData[definition.valueMap[key]]) {
+          property[key] = propertiesData[definition.valueMap[key]];
+        }
+      }
+      result.pushObject(App.WidgetProperty.create($.extend(definition, property)));
+    });
 
-  /**
-   * Render properties for graph-type widget
-   * @method renderGraphProperties
-   * @returns {App.WidgetProperties[]}
-   */
-  renderGraphProperties: function (widgetProperties) {
-    return [
-      App.WidgetProperties.GraphType.create({
-        value: this.get('widgetProperties.graph_type') || 'LINE',
-        isRequired: true
-      }),
-      App.WidgetProperties.TimeRange.create({
-        value: this.get('widgetProperties.time_range') || 'Last 1 hour',
-        isRequired: true
-      }),
-      App.WidgetProperties.Unit.create({
-        value: this.get('widgetProperties.display_unit') || 'MB',
-        isRequired: false
-      })
-    ];
+    this.set('widgetPropertiesViews', result);
   },
 
   /**

+ 28 - 31
ambari-web/app/models/widget.js

@@ -83,79 +83,76 @@ App.WidgetType = DS.Model.extend({
 
 App.WidgetType.FIXTURES = [
   {
-    id: 1,
+    id: 'GAUGE',
     name: 'GAUGE',
     icon_path: '/img/widget-gauge.png',
     display_name: 'Gauge',
     description: Em.I18n.t('widget.type.gauge.description'),
     properties: [
       {
-        property_name : 'warning_threshold',
-        isRequired: true   // This field is used to distinguish required properties from optional. This can be used for imposing client side validation
-      },
-      {
-        property_name : 'error_threshold',
-        isRequired: true
+        name : 'threshold',
+        isRequired: true,
+        smallValue: '0.7',
+        bigValue: '0.9'
       }
     ]
   },
   {
-    id: 2,
+    id: 'NUMBER',
     name: 'NUMBER',
     icon_path: '/img/widget-number.png',
     display_name: 'Number',
     description: Em.I18n.t('widget.type.number.description'),
     properties: [
       {
-        property_name : 'warning_threshold',
-        display_name: 'warning',
-        isRequired: false
-      },
-      {
-        property_name : 'error_threshold',
-        display_name: 'critical',
-        isRequired: false
+        name : 'threshold',
+        isRequired: false,
+        smallValue: '10',
+        bigValue: '20',
+        MAX_VALUE: Infinity
       },
       {
-        property_name : 'display_unit',
-        display_name: 'unit',
-        isRequired: false
+        name : 'display_unit',
+        isRequired: false,
+        value: 'MB'
       }
     ]
   },
   {
-    id: 3,
+    id: 'GRAPH',
     name: 'GRAPH',
     display_name: 'Graph',
     icon_path: '/img/widget-graph.png',
     description: Em.I18n.t('widget.type.graph.description'),
     properties: [
       {
-        property_name : 'graph_type',
-        isRequired: true
+        name : 'graph_type',
+        isRequired: true,
+        value: 'LINE'
       },
       {
-        property_name : 'time_range',
-        isRequired: true
+        name : 'time_range',
+        isRequired: true,
+        value: 'Last 1 hour'
       },
       {
-        property_name : 'display_unit',
-        display_name: 'unit',
-        isRequired: false
+        name : 'display_unit',
+        isRequired: false,
+        value: 'MB'
       }
     ]
   },
   {
-    id: 4,
+    id: 'TEMPLATE',
     name: 'TEMPLATE',
     icon_path: '/img/widget-template.png',
     display_name: 'Template',
     description: Em.I18n.t('widget.type.template.description'),
     properties: [
       {
-        property_name : 'display_unit',
-        display_name: 'unit',
-        isRequired: false
+        name : 'display_unit',
+        isRequired: false,
+        value: 'MB'
       }
     ]
   }

+ 45 - 72
ambari-web/app/models/widget_property.js

@@ -89,39 +89,55 @@ App.WidgetProperty = Ember.Object.extend({
   isRequired: true
 });
 
-App.WidgetProperties = {
+App.WidgetPropertyTypes = [
 
-  Unit: App.WidgetProperty.extend({
-    name: 'display-unit',
+  {
+    name: 'display_unit',
     label: 'Unit',
     displayType: 'textField',
     classNames: 'widget-property-unit',
     isValid: function () {
       return this.get('isRequired') ? this.get('value') : true;
-    }.property('value')
-  }),
+    }.property('value'),
+    valueMap: {
+     "value": "display_unit"
+    }
+  },
 
-  GraphType: App.WidgetProperty.extend({
+  {
     name: 'graph_type',
     label: 'Graph Type',
     displayType: 'select',
-    options: ["LINE", "STACK"]
-  }),
+    options: ["LINE", "STACK"],
+    valueMap: {
+      "value": "graph_type"
+    }
+  },
 
-  TimeRange: App.WidgetProperty.extend({
+  {
     name: 'time_range',
     label: 'Time Range',
     displayType: 'select',
     options: ["Last 1 hour", "Last 2 hours", "Last 4 hours", "Last 12 hours", "Last 24 hours",
-    "Last 1 week", "Last 1 month", "Last 1 year"]
-  }),
-
-
-  Threshold: App.WidgetProperty.extend({
+      "Last 1 week", "Last 1 month", "Last 1 year"],
+    valueMap: {
+      "value": "time_range"
+    }
+  },
 
+  {
     name: 'threshold',
     label: 'Thresholds',
 
+    MIN_VALUE: 0,
+
+    MAX_VALUE: 1,
+
+    valueMap: {
+      "smallValue": "warning_threshold",
+      "bigValue": "error_threshold"
+    },
+
     /**
      * threshold-value
      * @type {string}
@@ -136,25 +152,12 @@ App.WidgetProperties = {
 
     classNames: 'widget-property-threshold',
 
-    apiProperty: [],
-
-    init: function () {
-      this._super();
-    },
-
     /**
      * Check if <code>smallValue</code> is valid float number
      * @return {boolean}
      */
     isSmallValueValid: function () {
-      var value = this.get('smallValue');
-      if (!this.get('isRequired') && !this.get('smallValue') && !this.get('bigValue')) {
-        return true;
-      } else if (!this.get('smallValue')) {
-        return false;
-      }
-      value = ('' + value).trim();
-      return validator.isValidFloat(value) && value > 0;
+      return this.validate(this.get('smallValue'));
     }.property('smallValue', 'bigValue'),
 
     /**
@@ -162,15 +165,23 @@ App.WidgetProperties = {
      * @return {boolean}
      */
     isBigValueValid: function () {
-      var value = this.get('bigValue');
+      return this.validate(this.get('bigValue'));
+    }.property('bigValue', 'smallValue'),
+
+    /**
+     * validate
+     * @param {string} value
+     * @returns {boolean}
+     */
+    validate: function (value) {
       if (!this.get('isRequired') && !this.get('smallValue') && !this.get('bigValue')) {
         return true;
-      } else if (!this.get('bigValue')) {
+      } else if (!value) {
         return false;
       }
       value = ('' + value).trim();
-      return validator.isValidFloat(value) && value > 0;
-    }.property('bigValue', 'smallValue'),
+      return validator.isValidFloat(value) && value > this.get('MIN_VALUE') && value <= this.get('MAX_VALUE');
+    },
 
     thresholdError: function () {
       if (this.get('isSmallValueValid') && this.get('isBigValueValid')) {
@@ -191,43 +202,5 @@ App.WidgetProperties = {
     errorMsg: function () {
       return this.get('thresholdError') ? "Threshold 1 should be smaller than threshold 2" : null;
     }.property('thresholdError')
-
-  })
-};
-
-App.WidgetProperties.Thresholds = {
-
-  PercentageThreshold: App.WidgetProperties.Threshold.extend({
-
-    /**
-     * Check if <code>smallValue</code> is valid float number
-     * @return {boolean}
-     */
-    isSmallValueValid: function () {
-      var value = this.get('smallValue');
-      if (!this.get('isRequired') && !this.get('smallValue') && !this.get('bigValue')) {
-        return true;
-      } else if (!this.get('smallValue')) {
-        return false;
-      }
-      value = ('' + value).trim();
-      return validator.isValidFloat(value) && value > 0 && value <=1;
-    }.property('smallValue', 'bigValue'),
-
-    /**
-     * Check if <code>bigValue</code> is valid float number
-     * @return {boolean}
-     */
-    isBigValueValid: function () {
-      var value = this.get('bigValue');
-      if (!this.get('isRequired') && !this.get('smallValue') && !this.get('bigValue')) {
-        return true;
-      } else if (!this.get('bigValue')) {
-        return false;
-      }
-      value = ('' + value).trim();
-      return validator.isValidFloat(value) && value > 0 && value <= 1;
-    }.property('bigValue', 'smallValue')
-
-  })
-};
+  }
+];

+ 12 - 2
ambari-web/app/views/common/widget/gauge_widget_view.js

@@ -33,11 +33,21 @@ App.GaugeWidgetView = Em.View.extend(App.WidgetMixin, {
   metrics: [],
 
   chartView: App.ChartPieView.extend({
-    stroke: '#D6DDDF', //light grey
+    stroke: '#D6DDDF',
     innerR: 25,
 
+    /**
+     * since chart widget using percentage values factor equal 100
+     * @type {number}
+     * @const
+     */
     FACTOR: 100,
 
+    /**
+     * 100 - is maximum percentage value
+     * @type {number}
+     * @const
+     */
     MAX_VALUE: 100,
 
     warningThreshold: function(){
@@ -74,7 +84,7 @@ App.GaugeWidgetView = Em.View.extend(App.WidgetMixin, {
       var color_green = App.healthStatusGreen;
       var color_red = App.healthStatusRed;
       var color_orange = App.healthStatusOrange;
-      if (used <= thresh1) {
+      if (isNaN(thresh1) || isNaN(thresh2) || used <= thresh1) {
         this.set('palette', new Rickshaw.Color.Palette({
           scheme: [ '#FFFFFF', color_green  ].reverse()
         }));

+ 1 - 1
ambari-web/app/views/common/widget/number_widget_view.js

@@ -41,7 +41,7 @@ App.NumberWidgetView = Em.View.extend(App.WidgetMixin, {
     var warningThreshold = parseFloat(this.get('content.properties.warning_threshold'));
     var errorThreshold = parseFloat(this.get('content.properties.error_threshold'));
 
-    if (value <= warningThreshold) {
+    if (isNaN(warningThreshold) || isNaN(errorThreshold) || value <= warningThreshold) {
       return 'green';
     } else if (value <= errorThreshold) {
       return 'orange';