You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ambari.apache.org by at...@apache.org on 2014/04/09 14:35:47 UTC

git commit: AMBARI-5405 Cover main app with unit tests. (atkach)

Repository: ambari
Updated Branches:
  refs/heads/trunk a60d8608b -> 4b962fabc


AMBARI-5405 Cover main app with unit tests. (atkach)


Project: http://git-wip-us.apache.org/repos/asf/ambari/repo
Commit: http://git-wip-us.apache.org/repos/asf/ambari/commit/4b962fab
Tree: http://git-wip-us.apache.org/repos/asf/ambari/tree/4b962fab
Diff: http://git-wip-us.apache.org/repos/asf/ambari/diff/4b962fab

Branch: refs/heads/trunk
Commit: 4b962fabc8b141fa6805aae8fd8865f3dcd3493e
Parents: a60d860
Author: atkach <at...@hortonworks.com>
Authored: Wed Apr 9 15:32:30 2014 +0300
Committer: atkach <at...@hortonworks.com>
Committed: Wed Apr 9 15:32:30 2014 +0300

----------------------------------------------------------------------
 ambari-web/app/app.js                           |  62 +++--
 ambari-web/app/assets/test/tests.js             |  14 +-
 ambari-web/app/utils/ajax.js                    |   2 +-
 .../app/views/main/service/info/summary.js      |   8 +-
 ambari-web/test/app_test.js                     | 264 +++++++++++++++++++
 ambari-web/test/init_model_test.js              |  34 +++
 .../views/main/service/info/summary_test.js     | 105 ++++++++
 7 files changed, 442 insertions(+), 47 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/ambari/blob/4b962fab/ambari-web/app/app.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/app.js b/ambari-web/app/app.js
index fb4476a..aa1f909 100644
--- a/ambari-web/app/app.js
+++ b/ambari-web/app/app.js
@@ -80,7 +80,7 @@ module.exports = Em.Application.create({
   isHaEnabled: function() {
     if (!this.get('isHadoop2Stack')) return false;
     return !this.HostComponent.find().someProperty('componentName', 'SECONDARY_NAMENODE');
-  }.property('router.clusterController.isLoaded'),
+  }.property('router.clusterController.isLoaded', 'isHadoop2Stack'),
 
   /**
    * List of disabled components for the current stack with related info.
@@ -167,57 +167,65 @@ module.exports = Em.Application.create({
     var reviewConfigsService = require('data/review_configs')
       .findProperty('config_name', 'services').config_value
       .findProperty('service_name', component.get('serviceName'));
-    reviewConfigsService.set('service_components', reviewConfigsService.get('service_components').filter(function (serviceComponent) {
-      if (serviceComponent.get('component_name') != component.get('componentName')) {
-        return true;
-      } else {
-        componentCopy.set('reviewConfigs', serviceComponent);
-        return false;
-      }
-    }));
+    //review_configs might not contain particular service
+    if (reviewConfigsService) {
+      reviewConfigsService.set('service_components', reviewConfigsService.get('service_components').filter(function (serviceComponent) {
+        if (serviceComponent.get('component_name') != component.get('componentName')) {
+          return true;
+        } else {
+          componentCopy.set('reviewConfigs', serviceComponent);
+          return false;
+        }
+      }));
+    }
     return componentCopy;
   },
   /**
-   * Resolve dependency in components. Check forbidden/allowed components and
+   * Resolve dependency in components.
+   * if component with config category from "data/service_configs" doesn't match components from stack
+   * then disable it and push to stackDependedComponents
+   * otherwise enable component and remove it from stackDependedComponents
+   * Check forbidden/allowed components and
    * remove/restore related data.
    */
-  handleStackDependedComponents: function() {
+  handleStackDependedComponents: function () {
     // need for unit testing and test mode
     if (this.get('handleStackDependencyTest') || this.testMode) return;
-    var stackDependedComponents = [];
+    var stackDependedComponents = this.get('stackDependedComponents');
     var service_configs = require('data/service_configs');
     var stackServiceComponents = this.StackServiceComponent.find();
     if (!stackServiceComponents.mapProperty('componentName').length) {
-       return;
+      return;
     }
     // disable components
-    service_configs.forEach(function(service){
-      service.configCategories.forEach(function(serviceConfigCategory){
+    service_configs.forEach(function (service) {
+      service.configCategories.forEach(function (serviceConfigCategory) {
         var categoryComponents = serviceConfigCategory.get('hostComponentNames');
         if (categoryComponents && categoryComponents.length) {
-          categoryComponents.forEach(function(categoryComponent) {
-            var stackComponent = stackServiceComponents.findProperty('componentName',categoryComponent);
-            if(!stackComponent && !this.get('stackDependedComponents').mapProperty('componentName').contains['categoryComponent'] ) {
+          categoryComponents.forEach(function (categoryComponent) {
+            var stackComponent = stackServiceComponents.findProperty('componentName', categoryComponent);
+            if (!stackComponent && !stackDependedComponents.mapProperty('componentName').contains['categoryComponent']) {
               var _stackComponent = Ember.Object.create({
                 componentName: categoryComponent,
-                serviceName:service.serviceName
+                serviceName: service.serviceName
               });
               stackDependedComponents.push(this.disableComponent(_stackComponent));
             }
-          },this);
+          }, this);
         }
-      },this);
-    },this);
+      }, this);
+    }, this);
+
     // enable components
-    if (this.get('stackDependedComponents').length > 0) {
-      this.get('stackDependedComponents').forEach(function(component) {
-        if (stackServiceComponents.findProperty('componentName',component.get('componentName'))) {
+    if (stackDependedComponents.length > 0) {
+      stackDependedComponents.forEach(function (component) {
+        if (stackServiceComponents.someProperty('componentName', component.get('componentName'))) {
           this.enableComponent(component);
-          stackDependedComponents = this.get('stackDependedComponents').removeObject(component);
+          stackDependedComponents.removeObject(component);
         }
       }, this);
     }
-    this.set('stackDependedComponents', this.get('stackDependedComponents').concat(stackDependedComponents));
+    this.set('stackDependedComponents', stackDependedComponents);
   },
 
   /**

http://git-wip-us.apache.org/repos/asf/ambari/blob/4b962fab/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 478561e..4390c02 100644
--- a/ambari-web/app/assets/test/tests.js
+++ b/ambari-web/app/assets/test/tests.js
@@ -18,19 +18,7 @@
 
 var App = require('app');
 
-require('models/stack_service_component');
-require('mappers/server_data_mapper');
-require('mappers/stack_service_component_mapper');
-
-  var a = require('test/service_components');
-  var r = Em.A([]);
-  a.items.forEach(function(i) {
-    i.serviceComponents.forEach(function(sc) {
-      r.pushObject(sc.StackServiceComponents);
-    });
-  });
-  App.stackServiceComponentMapper.map({items: r});
-
+require('test/init_model_test');
 require('test/app_test');
 require('test/data/HDP2/site_properties_test');
 require('test/controllers/global/background_operations_test');

http://git-wip-us.apache.org/repos/asf/ambari/blob/4b962fab/ambari-web/app/utils/ajax.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/utils/ajax.js b/ambari-web/app/utils/ajax.js
index cad1c3e..496d0c1 100644
--- a/ambari-web/app/utils/ajax.js
+++ b/ambari-web/app/utils/ajax.js
@@ -1232,7 +1232,7 @@ var urls = {
   },
   'wizard.service_components': {
     'real': '{stackUrl}/stackServices?fields=StackServices/comments,StackServices/service_version,serviceComponents/*',
-    'mock': '/data/wizard/stacks/HDP-2.1/service_components.json',
+    'mock': '/data/stacks/HDP-2.1/service_components.json',
     'format': function(data) {
       return {
         timeout: 10000,

http://git-wip-us.apache.org/repos/asf/ambari/blob/4b962fab/ambari-web/app/views/main/service/info/summary.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/views/main/service/info/summary.js b/ambari-web/app/views/main/service/info/summary.js
index ba4acb0..821261f 100644
--- a/ambari-web/app/views/main/service/info/summary.js
+++ b/ambari-web/app/views/main/service/info/summary.js
@@ -16,6 +16,7 @@
  */
 
 var App = require('app');
+require('views/main/dashboard/service');
 
 App.AlertItemView = Em.View.extend({
   tagName:"li",
@@ -417,12 +418,7 @@ App.MainServiceInfoSummaryView = Em.View.extend({
    * Alerts panel not display for PIG, SQOOP and TEZ Service
    */
   isNoAlertsService: function () {
-    var serviceName = this.get('service.serviceName');
-    if (!serviceName) {
-      return false;
-    }
-    var noAlertsServices = ['PIG', 'SQOOP', 'TEZ'];
-    return noAlertsServices.indexOf(serviceName) > -1;
+    return !!this.get('service.serviceName') && ['PIG', 'SQOOP', 'TEZ'].contains(this.get('service.serviceName'));
   }.property(''),
 
   gangliaUrl:function () {

http://git-wip-us.apache.org/repos/asf/ambari/blob/4b962fab/ambari-web/test/app_test.js
----------------------------------------------------------------------
diff --git a/ambari-web/test/app_test.js b/ambari-web/test/app_test.js
index 106f4ad..2a97a3f 100644
--- a/ambari-web/test/app_test.js
+++ b/ambari-web/test/app_test.js
@@ -17,6 +17,9 @@
  */
 
 var App = require('app');
+require('views/common/quick_view_link_view');
+require('models/host_component');
+require('models/stack_service_component');
 
 describe('#App', function() {
 
@@ -120,4 +123,265 @@ describe('#App', function() {
       });
     });
   });
+
+  describe('#stackVersionURL', function () {
+
+    App.QuickViewLinks.reopen({
+      loadTags: function () {}
+    });
+
+    var testCases = [
+      {
+        title: 'if currentStackVersion and defaultStackVersion are empty then stackVersionURL should contain prefix',
+        currentStackVersion: '',
+        defaultStackVersion: '',
+        result: '/stacks/HDP/version/'
+      },
+      {
+        title: 'if currentStackVersion is "HDP-1.3.1" then stackVersionURL should be "/stacks/HDP/version/1.3.1"',
+        currentStackVersion: 'HDP-1.3.1',
+        defaultStackVersion: '',
+        result: '/stacks/HDP/version/1.3.1'
+      },
+      {
+        title: 'if defaultStackVersion is "HDP-1.3.1" then stackVersionURL should be "/stacks/HDP/version/1.3.1"',
+        currentStackVersion: '',
+        defaultStackVersion: 'HDP-1.3.1',
+        result: '/stacks/HDP/version/1.3.1'
+      },
+      {
+        title: 'if defaultStackVersion and currentStackVersion are different then stackVersionURL should have currentStackVersion value',
+        currentStackVersion: 'HDP-1.3.2',
+        defaultStackVersion: 'HDP-1.3.1',
+        result: '/stacks/HDP/version/1.3.2'
+      },
+      {
+        title: 'if defaultStackVersion is "HDPLocal-1.3.1" then stackVersionURL should be "/stacks/HDPLocal/version/1.3.1"',
+        currentStackVersion: '',
+        defaultStackVersion: 'HDPLocal-1.3.1',
+        result: '/stacks/HDPLocal/version/1.3.1'
+      },
+      {
+        title: 'if currentStackVersion is "HDPLocal-1.3.1" then stackVersionURL should be "/stacks/HDPLocal/version/1.3.1"',
+        currentStackVersion: 'HDPLocal-1.3.1',
+        defaultStackVersion: '',
+        result: '/stacks/HDPLocal/version/1.3.1'
+      }
+    ];
+
+    testCases.forEach(function (test) {
+      it(test.title, function () {
+        App.set('currentStackVersion', test.currentStackVersion);
+        App.set('defaultStackVersion', test.defaultStackVersion);
+        expect(App.get('stackVersionURL')).to.equal(test.result);
+        App.set('currentStackVersion', "HDP-1.2.2");
+        App.set('defaultStackVersion', "HDP-1.2.2");
+      });
+    });
+  });
+
+  describe('#stack2VersionURL', function () {
+
+    var testCases = [
+      {
+        title: 'if currentStackVersion and defaultStackVersion are empty then stack2VersionURL should contain prefix',
+        currentStackVersion: '',
+        defaultStackVersion: '',
+        result: '/stacks2/HDP/versions/'
+      },
+      {
+        title: 'if currentStackVersion is "HDP-1.3.1" then stack2VersionURL should be "/stacks2/HDP/versions/1.3.1"',
+        currentStackVersion: 'HDP-1.3.1',
+        defaultStackVersion: '',
+        result: '/stacks2/HDP/versions/1.3.1'
+      },
+      {
+        title: 'if defaultStackVersion is "HDP-1.3.1" then stack2VersionURL should be "/stacks/HDP/versions/1.3.1"',
+        currentStackVersion: '',
+        defaultStackVersion: 'HDP-1.3.1',
+        result: '/stacks2/HDP/versions/1.3.1'
+      },
+      {
+        title: 'if defaultStackVersion and currentStackVersion are different then stack2VersionURL should have currentStackVersion value',
+        currentStackVersion: 'HDP-1.3.2',
+        defaultStackVersion: 'HDP-1.3.1',
+        result: '/stacks2/HDP/versions/1.3.2'
+      },
+      {
+        title: 'if defaultStackVersion is "HDPLocal-1.3.1" then stack2VersionURL should be "/stacks2/HDPLocal/versions/1.3.1"',
+        currentStackVersion: '',
+        defaultStackVersion: 'HDPLocal-1.3.1',
+        result: '/stacks2/HDPLocal/versions/1.3.1'
+      },
+      {
+        title: 'if currentStackVersion is "HDPLocal-1.3.1" then stack2VersionURL should be "/stacks2/HDPLocal/versions/1.3.1"',
+        currentStackVersion: 'HDPLocal-1.3.1',
+        defaultStackVersion: '',
+        result: '/stacks2/HDPLocal/versions/1.3.1'
+      }
+    ];
+
+    testCases.forEach(function (test) {
+      it(test.title, function () {
+        App.set('currentStackVersion', test.currentStackVersion);
+        App.set('defaultStackVersion', test.defaultStackVersion);
+        expect(App.get('stack2VersionURL')).to.equal(test.result);
+        App.set('currentStackVersion', "HDP-1.2.2");
+        App.set('defaultStackVersion', "HDP-1.2.2");
+      });
+    });
+  });
+
+  describe('#currentStackVersionNumber', function () {
+
+    var testCases = [
+      {
+        title: 'if currentStackVersion is empty then currentStackVersionNumber should be empty',
+        currentStackVersion: '',
+        result: ''
+      },
+      {
+        title: 'if currentStackVersion is "HDP-1.3.1" then currentStackVersionNumber should be "1.3.1',
+        currentStackVersion: 'HDP-1.3.1',
+        result: '1.3.1'
+      },
+      {
+        title: 'if currentStackVersion is "HDPLocal-1.3.1" then currentStackVersionNumber should be "1.3.1',
+        currentStackVersion: 'HDPLocal-1.3.1',
+        result: '1.3.1'
+      }
+    ];
+
+    testCases.forEach(function (test) {
+      it(test.title, function () {
+        App.set('currentStackVersion', test.currentStackVersion);
+        expect(App.get('currentStackVersionNumber')).to.equal(test.result);
+        App.set('currentStackVersion', "HDP-1.2.2");
+      });
+    });
+  });
+
+  describe('#isHadoop2Stack', function () {
+
+    var testCases = [
+      {
+        title: 'if currentStackVersion is empty then isHadoop2Stack should be false',
+        currentStackVersion: '',
+        result: false
+      },
+      {
+        title: 'if currentStackVersion is "HDP-1.9.9" then isHadoop2Stack should be false',
+        currentStackVersion: 'HDP-1.9.9',
+        result: false
+      },
+      {
+        title: 'if currentStackVersion is "HDP-2.0.0" then isHadoop2Stack should be true',
+        currentStackVersion: 'HDP-2.0.0',
+        result: true
+      },
+      {
+        title: 'if currentStackVersion is "HDP-2.0.1" then isHadoop2Stack should be true',
+        currentStackVersion: 'HDP-2.0.1',
+        result: true
+      }
+    ];
+
+    testCases.forEach(function (test) {
+      it(test.title, function () {
+        App.set('currentStackVersion', test.currentStackVersion);
+        expect(App.get('isHadoop2Stack')).to.equal(test.result);
+        App.set('currentStackVersion', "HDP-1.2.2");
+      });
+    });
+  });
+
+  describe('#isHaEnabled', function () {
+
+    it('if hadoop stack version less than 2 then isHaEnabled should be false', function () {
+      App.set('currentStackVersion', 'HDP-1.3.1');
+      expect(App.get('isHaEnabled')).to.equal(false);
+      App.set('currentStackVersion', "HDP-1.2.2");
+    });
+    it('if hadoop stack version higher than 2 then isHaEnabled should be true', function () {
+      App.set('currentStackVersion', 'HDP-2.0.1');
+      expect(App.get('isHaEnabled')).to.equal(true);
+      App.set('currentStackVersion', "HDP-1.2.2");
+    });
+    it('if cluster has SECONDARY_NAMENODE then isHaEnabled should be false', function () {
+      App.store.load(App.HostComponent, {
+        id: 'SECONDARY_NAMENODE',
+        component_name: 'SECONDARY_NAMENODE'
+      });
+      App.set('currentStackVersion', 'HDP-2.0.1');
+      expect(App.get('isHaEnabled')).to.equal(false);
+      App.set('currentStackVersion', "HDP-1.2.2");
+    });
+  });
+
+  describe('#handleStackDependedComponents()', function () {
+
+    it('if handleStackDependencyTest is true then stackDependedComponents should be unmodified', function () {
+      App.set('testMode', false);
+      App.set('handleStackDependencyTest', true);
+      App.handleStackDependedComponents();
+      expect(App.get('stackDependedComponents')).to.be.empty;
+    });
+
+    it('if testMode is true then stackDependedComponents should be unmodified', function () {
+      App.set('handleStackDependencyTest', false);
+      App.set('testMode', true);
+      App.handleStackDependedComponents();
+      expect(App.get('stackDependedComponents')).to.be.empty;
+    });
+
+    it('if stack contains all components then stackDependedComponents should be empty', function () {
+      App.set('testMode', false);
+      App.set('handleStackDependencyTest', false);
+      App.handleStackDependedComponents();
+      expect(App.get('stackDependedComponents')).to.be.empty;
+    });
+
+    it('if stack is missing component then push it to stackDependedComponents', function () {
+      App.set('testMode', false);
+      App.set('handleStackDependencyTest', false);
+      var dtRecord = App.StackServiceComponent.find('DATANODE');
+      dtRecord.deleteRecord();
+      dtRecord.get('stateManager').transitionTo('loading');
+      App.handleStackDependedComponents();
+      expect(App.get('stackDependedComponents').mapProperty('componentName')).to.eql(["DATANODE"]);
+      App.store.load(App.StackServiceComponent, {
+        id: 'DATANODE',
+        component_name: 'DATANODE',
+        service_name: 'HDFS',
+        component_category: 'SLAVE',
+        is_master: false,
+        is_client: false,
+        stack_name: 'HDP',
+        stack_version: '2.1'
+      });
+    });
+
+    it('remove stack components from stackDependedComponents', function () {
+      App.set('testMode', false);
+      App.set('handleStackDependencyTest', false);
+      App.set('stackDependedComponents', [
+        Em.Object.create({
+          componentName: "DATANODE",
+          serviceName: "HDFS",
+          properties: {},
+          reviewConfigs: {},
+          configCategory: {}
+        }),
+        Em.Object.create({
+          componentName: "categoryComponent",
+          serviceName: "",
+          properties: {},
+          reviewConfigs: {},
+          configCategory: {}
+        })
+      ]);
+      App.handleStackDependedComponents();
+      expect(App.get('stackDependedComponents').mapProperty('componentName')).to.eql(["categoryComponent"]);
+    });
+  });
 });

http://git-wip-us.apache.org/repos/asf/ambari/blob/4b962fab/ambari-web/test/init_model_test.js
----------------------------------------------------------------------
diff --git a/ambari-web/test/init_model_test.js b/ambari-web/test/init_model_test.js
new file mode 100644
index 0000000..e94753f
--- /dev/null
+++ b/ambari-web/test/init_model_test.js
@@ -0,0 +1,34 @@
+/**
+ * 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('models/stack_service_component');
+require('mappers/server_data_mapper');
+require('mappers/stack_service_component_mapper');
+
+/**
+ * initialization of App.StackServiceComponent model
+ * @type {*}
+ */
+var data = {items: Em.A([])};
+require('test/service_components').items.forEach(function(i) {
+  i.serviceComponents.forEach(function(sc) {
+    data.items.pushObject(sc.StackServiceComponents);
+  });
+});
+App.stackServiceComponentMapper.map(data);

http://git-wip-us.apache.org/repos/asf/ambari/blob/4b962fab/ambari-web/test/views/main/service/info/summary_test.js
----------------------------------------------------------------------
diff --git a/ambari-web/test/views/main/service/info/summary_test.js b/ambari-web/test/views/main/service/info/summary_test.js
new file mode 100644
index 0000000..8392ad0
--- /dev/null
+++ b/ambari-web/test/views/main/service/info/summary_test.js
@@ -0,0 +1,105 @@
+/**
+ * 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/main/service/info/summary');
+
+describe('App.MainServiceInfoSummaryView', function() {
+
+  var mainServiceInfoSummaryView = App.MainServiceInfoSummaryView.create({
+    monitorsLiveTextView: Em.View.create(),
+    controller: Em.Object.create({
+      content: Em.Object.create({
+        id: 'HDFS',
+        serviceName: 'HDFS',
+        hostComponents: []
+      })
+    })
+  });
+
+  describe('#servers', function () {
+    it('services shuldn\'t have servers except FLUME and ZOOKEEPER', function () {
+      expect(mainServiceInfoSummaryView.get('servers')).to.be.empty;
+    });
+
+    it('if one server exists then first server should have isComma and isAnd property false', function () {
+      mainServiceInfoSummaryView.set('controller.content', Em.Object.create({
+        id: 'ZOOKEEPER',
+        serviceName: 'ZOOKEEPER',
+        hostComponents: [
+          Em.Object.create({
+            displayName: '',
+            isMaster: true
+          })
+        ]
+      }));
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(0).isComma).to.equal(false);
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(0).isAnd).to.equal(false);
+    });
+
+    it('if more than one servers exist then first server should have isComma - true and isAnd - false', function () {
+      mainServiceInfoSummaryView.set('controller.content', Em.Object.create({
+        id: 'ZOOKEEPER',
+        serviceName: 'ZOOKEEPER',
+        hostComponents: [
+          Em.Object.create({
+            displayName: '',
+            isMaster: true
+          }),
+          Em.Object.create({
+            displayName: '',
+            isMaster: true
+          })
+        ]
+      }));
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(0).isComma).to.equal(true);
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(0).isAnd).to.equal(false);
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(1).isComma).to.equal(false);
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(1).isAnd).to.equal(false);
+    });
+
+    it('if more than two servers exist then second server should have isComma - false and isAnd - true', function () {
+      mainServiceInfoSummaryView.set('controller.content', Em.Object.create({
+        id: 'ZOOKEEPER',
+        serviceName: 'ZOOKEEPER',
+        hostComponents: [
+          Em.Object.create({
+            displayName: '',
+            isMaster: true
+          }),
+          Em.Object.create({
+            displayName: '',
+            isMaster: true
+          }),
+          Em.Object.create({
+            displayName: '',
+            isMaster: true
+          })
+        ]
+      }));
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(0).isComma).to.equal(true);
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(0).isAnd).to.equal(false);
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(1).isComma).to.equal(false);
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(1).isAnd).to.equal(true);
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(2).isComma).to.equal(false);
+      expect(mainServiceInfoSummaryView.get('servers').objectAt(2).isAnd).to.equal(false);
+    });
+
+  });
+});