You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ambari.apache.org by al...@apache.org on 2015/04/06 19:04:53 UTC

[1/2] ambari git commit: AMBARI-10370. Slider View: Support multiple versions of the same app (alexantonenko)

Repository: ambari
Updated Branches:
  refs/heads/trunk 0de10b795 -> 75c9df821


AMBARI-10370. Slider View: Support multiple versions of the same app (alexantonenko)


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

Branch: refs/heads/trunk
Commit: 75c9df8216a0555023a143396bb9a218529fb043
Parents: 1afb7e6
Author: Alex Antonenko <hi...@gmail.com>
Authored: Mon Apr 6 20:01:16 2015 +0300
Committer: Alex Antonenko <hi...@gmail.com>
Committed: Mon Apr 6 20:04:48 2015 +0300

----------------------------------------------------------------------
 .../org/apache/ambari/view/slider/SliderApp.java   |  9 +++++++++
 .../view/slider/SliderAppsViewControllerImpl.java  | 15 +++++++++------
 .../resources/ui/app/mappers/application_type.js   |  3 ++-
 .../resources/ui/app/mappers/slider_apps_mapper.js |  2 +-
 .../resources/ui/app/models/slider_app_type.js     | 17 ++++++++++++++---
 5 files changed, 35 insertions(+), 11 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/ambari/blob/75c9df82/contrib/views/slider/src/main/java/org/apache/ambari/view/slider/SliderApp.java
----------------------------------------------------------------------
diff --git a/contrib/views/slider/src/main/java/org/apache/ambari/view/slider/SliderApp.java b/contrib/views/slider/src/main/java/org/apache/ambari/view/slider/SliderApp.java
index d75762e..25b1e17 100644
--- a/contrib/views/slider/src/main/java/org/apache/ambari/view/slider/SliderApp.java
+++ b/contrib/views/slider/src/main/java/org/apache/ambari/view/slider/SliderApp.java
@@ -30,6 +30,7 @@ public class SliderApp {
   private String appVersion;
   private String description;
   private String type;
+  private String typeId;
   private String user;
   private String state;
   private String diagnostics;
@@ -186,4 +187,12 @@ public class SliderApp {
   public void setAlerts(Map<String, Object> alerts) {
     this.alerts = alerts;
   }
+
+  public String getTypeId() {
+    return typeId;
+  }
+
+  public void setTypeId(String typeId) {
+    this.typeId = typeId;
+  }
 }

http://git-wip-us.apache.org/repos/asf/ambari/blob/75c9df82/contrib/views/slider/src/main/java/org/apache/ambari/view/slider/SliderAppsViewControllerImpl.java
----------------------------------------------------------------------
diff --git a/contrib/views/slider/src/main/java/org/apache/ambari/view/slider/SliderAppsViewControllerImpl.java b/contrib/views/slider/src/main/java/org/apache/ambari/view/slider/SliderAppsViewControllerImpl.java
index 3b74239..339938a 100644
--- a/contrib/views/slider/src/main/java/org/apache/ambari/view/slider/SliderAppsViewControllerImpl.java
+++ b/contrib/views/slider/src/main/java/org/apache/ambari/view/slider/SliderAppsViewControllerImpl.java
@@ -625,8 +625,10 @@ public class SliderAppsViewControllerImpl implements SliderAppsViewController {
           String value = tag.substring(index + 1).trim();
           if ("name".equals(key)) {
             app.setType(value);
+            app.setTypeId(value.toUpperCase() + "-" + app.getAppVersion());
           } else if ("version".equals(key)) {
             app.setAppVersion(value);
+            app.setTypeId(app.getType() + "-" + value);
           } else if ("description".equals(key)) {
             app.setDescription(value);
           }
@@ -643,6 +645,7 @@ public class SliderAppsViewControllerImpl implements SliderAppsViewController {
               && (appType.getTypeVersion() != null && appType.getTypeVersion()
                   .equalsIgnoreCase(app.getAppVersion()))) {
             matchedAppType = appType;
+            app.setTypeId(appType.getId());
             break;
           }
         }
@@ -1040,7 +1043,7 @@ public class SliderAppsViewControllerImpl implements SliderAppsViewController {
                 throw new IllegalStateException("Slider App package '" + appZip.getName() + "' does not contain 'resources-default.json' file");
               }
               SliderAppType appType = new SliderAppType();
-              appType.setId(application.getName());
+              appType.setId(application.getName() + "-" + application.getVersion());
               appType.setTypeName(application.getName());
               appType.setTypeDescription(application.getComment());
               appType.setTypeVersion(application.getVersion());
@@ -1167,7 +1170,8 @@ public class SliderAppsViewControllerImpl implements SliderAppsViewController {
       YarnException, InterruptedException {
     if (json.has("name") && json.has("typeConfigs")
         && json.has("resources") && json.has("typeName")) {
-      final String appType = json.get("typeName").getAsString();
+      final String appTypeId = json.get("typeName").getAsString();
+      SliderAppType sliderAppType = getSliderAppType(appTypeId, null);
       final String appName = json.get("name").getAsString();
       final String queueName = json.has("queue") ? json.get("queue").getAsString() : null;
       final boolean securityEnabled = Boolean.valueOf(getHadoopConfigs().get("security_enabled"));
@@ -1202,7 +1206,7 @@ public class SliderAppsViewControllerImpl implements SliderAppsViewController {
       appCreateFolder.mkdirs();
       File appConfigJsonFile = new File(appCreateFolder, "appConfig.json");
       File resourcesJsonFile = new File(appCreateFolder, "resources.json");
-      saveAppConfigs(configs, componentsArray, appName, appType, securityEnabled, appConfigJsonFile);
+      saveAppConfigs(configs, componentsArray, appName, sliderAppType.getTypeName(), securityEnabled, appConfigJsonFile);
       saveAppResources(resourcesObj, resourcesJsonFile);
 
       final ActionCreateArgs createArgs = new ActionCreateArgs();
@@ -1213,15 +1217,14 @@ public class SliderAppsViewControllerImpl implements SliderAppsViewController {
       }
 
       final ActionInstallPackageArgs installArgs = new ActionInstallPackageArgs();
-      SliderAppType sliderAppType = getSliderAppType(appType, null);
       String localAppPackageFileName = sliderAppType.getTypePackageFileName();
-      installArgs.name = appType;
+      installArgs.name = sliderAppType.getTypeName();
       installArgs.packageURI = getAppsFolderPath() + "/" + localAppPackageFileName;
       installArgs.replacePkg = true;
 
       final List<ActionInstallKeytabArgs> installKeytabActions = new ArrayList<ActionInstallKeytabArgs>();
       if (securityEnabled) {
-        for (String keytab : getUserToRunAsKeytabs(appType)) {
+        for (String keytab : getUserToRunAsKeytabs(sliderAppType.getTypeName())) {
           ActionInstallKeytabArgs keytabArgs = new ActionInstallKeytabArgs();
           keytabArgs.keytabUri = keytab;
           keytabArgs.folder = appName;

http://git-wip-us.apache.org/repos/asf/ambari/blob/75c9df82/contrib/views/slider/src/main/resources/ui/app/mappers/application_type.js
----------------------------------------------------------------------
diff --git a/contrib/views/slider/src/main/resources/ui/app/mappers/application_type.js b/contrib/views/slider/src/main/resources/ui/app/mappers/application_type.js
index e4bdd85..9fff2e3 100644
--- a/contrib/views/slider/src/main/resources/ui/app/mappers/application_type.js
+++ b/contrib/views/slider/src/main/resources/ui/app/mappers/application_type.js
@@ -53,7 +53,8 @@ App.ApplicationTypeMapper = App.Mapper.create({
   map: {
     id: 'id',
     configs: 'typeConfigs',
-    displayName: 'typeName',
+    typeName: 'typeName',
+    typeVersion: 'typeVersion',
     index: 'id',
     description: 'typeDescription',
     version: 'typeVersion',

http://git-wip-us.apache.org/repos/asf/ambari/blob/75c9df82/contrib/views/slider/src/main/resources/ui/app/mappers/slider_apps_mapper.js
----------------------------------------------------------------------
diff --git a/contrib/views/slider/src/main/resources/ui/app/mappers/slider_apps_mapper.js b/contrib/views/slider/src/main/resources/ui/app/mappers/slider_apps_mapper.js
index 44ea18d..95750ce 100644
--- a/contrib/views/slider/src/main/resources/ui/app/mappers/slider_apps_mapper.js
+++ b/contrib/views/slider/src/main/resources/ui/app/mappers/slider_apps_mapper.js
@@ -264,7 +264,7 @@ App.SliderAppsMapper = App.Mapper.createWithMixins(App.RunPeriodically, {
           user: app.user,
           started: app.startTime || 0,
           ended: app.endTime  || 0,
-          appType: app.type.toUpperCase(),
+          appType: app.typeId,
           diagnostics: app.diagnostics || "-",
           description: app.description || "-",
           components: componentsId,

http://git-wip-us.apache.org/repos/asf/ambari/blob/75c9df82/contrib/views/slider/src/main/resources/ui/app/models/slider_app_type.js
----------------------------------------------------------------------
diff --git a/contrib/views/slider/src/main/resources/ui/app/models/slider_app_type.js b/contrib/views/slider/src/main/resources/ui/app/models/slider_app_type.js
index d161037..cb376bc 100644
--- a/contrib/views/slider/src/main/resources/ui/app/models/slider_app_type.js
+++ b/contrib/views/slider/src/main/resources/ui/app/models/slider_app_type.js
@@ -26,7 +26,12 @@ App.SliderAppType = DS.Model.extend({
   /**
    * @type {string}
    */
-  displayName: DS.attr('string'),
+  typeName: DS.attr('string'),
+
+  /**
+   * @type {string}
+   */
+  typeVersion: DS.attr('string'),
 
   /**
    * @type {App.SliderAppTypeComponent[]}
@@ -46,8 +51,14 @@ App.SliderAppType = DS.Model.extend({
   /**
    * @type {object}
    */
-  configs: DS.attr('object')
-
+  configs: DS.attr('object'),
+  
+  displayName : function() {
+    var typeName = this.get('typeName');
+    var typeVersion = this.get('typeVersion');
+    return (typeName == null ? '' : typeName) + " ("
+        + (typeVersion == null ? '' : typeVersion) + ")"
+  }.property('typeName', 'typeVersion')
 });
 
 App.SliderAppType.FIXTURES = [];
\ No newline at end of file


[2/2] ambari git commit: AMBARI-10366. Rack: ui cleanup #1 (alexantonenko)

Posted by al...@apache.org.
AMBARI-10366. Rack: ui cleanup #1 (alexantonenko)


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

Branch: refs/heads/trunk
Commit: 1afb7e6a7fa35912713b905306c35325c727ea9c
Parents: 0de10b7
Author: Alex Antonenko <hi...@gmail.com>
Authored: Mon Apr 6 18:42:16 2015 +0300
Committer: Alex Antonenko <hi...@gmail.com>
Committed: Mon Apr 6 20:04:48 2015 +0300

----------------------------------------------------------------------
 ambari-web/app/controllers/main/host.js         | 11 -------
 ambari-web/app/controllers/main/host/details.js | 11 +++++++
 ambari-web/app/messages.js                      |  7 +++--
 ambari-web/app/styles/application.less          | 28 ++++++++++++++++-
 ambari-web/app/templates/main/host.hbs          |  5 ++-
 ambari-web/app/templates/main/host/summary.hbs  |  4 +--
 ambari-web/app/utils/hosts.js                   | 16 +++++-----
 ambari-web/app/utils/validator.js               |  4 +--
 ambari-web/app/views/main/host.js               | 33 +++++++++++++++++---
 .../test/controllers/main/host/details_test.js  | 29 ++++++++++++++---
 ambari-web/test/controllers/main/host_test.js   | 26 +--------------
 ambari-web/test/utils/validator_test.js         |  1 +
 12 files changed, 111 insertions(+), 64 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/app/controllers/main/host.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/controllers/main/host.js b/ambari-web/app/controllers/main/host.js
index 9d8f9c4..aef3205 100644
--- a/ambari-web/app/controllers/main/host.js
+++ b/ambari-web/app/controllers/main/host.js
@@ -950,17 +950,6 @@ App.MainHostController = Em.ArrayController.extend(App.TableServerMixin, {
   },
 
   /**
-   * Call <code>setRackInfo</code> function to show Set Rack Id popup
-   * @param data
-   */
-  setRackId: function (data) {
-    var rack = data.context.get('rack');
-    var hosts = [data.context];
-    var operationData = {message: Em.I18n.t('hosts.host.details.setRackId')};
-    hostsManagement.setRackInfo(operationData, hosts, rack);
-  },
-
-  /**
    * associations between host property and column index
    * @type {Array}
    */

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/app/controllers/main/host/details.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/controllers/main/host/details.js b/ambari-web/app/controllers/main/host/details.js
index 40254d6..23b86bc 100644
--- a/ambari-web/app/controllers/main/host/details.js
+++ b/ambari-web/app/controllers/main/host/details.js
@@ -574,6 +574,17 @@ App.MainHostDetailsController = Em.Controller.extend({
   },
 
   /**
+   * Call <code>setRackInfo</code> function to show Set Rack Id popup
+   * @param data
+   */
+  setRackId: function (data) {
+    var rack = data.context.get('rack');
+    var hosts = [data.context];
+    var operationData = {message: Em.I18n.t('hosts.host.details.setRackId')};
+    hostsManagement.setRackInfo(operationData, hosts, rack);
+  },
+
+  /**
    * Call load tags
    * @method checkHiveDone
    */

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/app/messages.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/messages.js b/ambari-web/app/messages.js
index 6feaf0b..73691db 100644
--- a/ambari-web/app/messages.js
+++ b/ambari-web/app/messages.js
@@ -116,7 +116,8 @@ Em.I18n.translations = {
   'common.ipAddress':'IP Address',
   'common.rack':'Rack',
   'common.cpu':'CPU',
-  'common.cores': 'Cores (CPU)',
+  'common.cores': 'Cores',
+  'common.cores.cpu': 'Cores (CPU)',
   'common.ram':'RAM',
   'common.disk':'Disk',
   'common.diskUsage':'Disk Usage',
@@ -314,7 +315,7 @@ Em.I18n.translations = {
   'hostPopup.setRackId.success': 'Updating rack id to \"{0}\". It may take a few moments for it to get refreshed.',
   'hostPopup.setRackId.error': 'Updating the rack id failed.',
   'hostPopup.setRackId.invalid': 'Should start with a forward slash it may include alphanumeric chars, dots, dashes and forward slashes.',
-  'hostPopup.RackId': 'Rack Id',
+  'hostPopup.RackId': 'Rack',
   'hostPopup.recommendation.beforeDecommission': '{0} Maintenance Mode is pre required for decommissioning.',
 
   'question.sure':'Are you sure?',
@@ -2098,7 +2099,7 @@ Em.I18n.translations = {
   'hosts.host.details.restartAllComponents':'Restart All Components',
   'hosts.host.details.refreshConfigs':'Refresh configs',
   'hosts.host.details.for.postfix':'{0} for host',
-  'hosts.host.details.setRackId':'Set Rack Id',
+  'hosts.host.details.setRackId':'Set Rack',
   'host.host.details.installClients': 'Install clients',
 
   'host.host.componentFilter.master':'Master Components',

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/app/styles/application.less
----------------------------------------------------------------------
diff --git a/ambari-web/app/styles/application.less b/ambari-web/app/styles/application.less
index bfed2d9..4e986a8 100644
--- a/ambari-web/app/styles/application.less
+++ b/ambari-web/app/styles/application.less
@@ -2879,8 +2879,22 @@ table.graphs {
         padding-left: 4px;
       }
     }
-	thead {
+	  thead {
       background: none repeat scroll 0 0 #F8F8F8;
+      th {
+        //rack
+        &.sort-view-12 {
+          width: 15% !important;
+        }
+        //cpu
+        &.sort-view-3 {
+          width: 5% !important;
+        }
+        //ram
+        &.sort-view-4 {
+          width: 7% !important;
+        }
+      }
     }
 
     .set-rack-id {
@@ -2993,6 +3007,10 @@ table.graphs {
   }
   .filter-input-width{
     width:65%;
+    
+    &.rack-input {
+      width: 85%;
+    }
   }
   .table {
     input[type="checkbox"] {
@@ -4219,6 +4237,14 @@ ul.inline li {
   th, td {
     border-left-width: 0;
   }
+
+  td {
+    &.rack-id {
+      white-space: nowrap;
+      overflow: hidden;
+      text-overflow: ellipsis;
+    }
+  }
   .sorting_asc {
     background: url(data:image/png;base64,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) no-repeat right 50%;
   }

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/app/templates/main/host.hbs
----------------------------------------------------------------------
diff --git a/ambari-web/app/templates/main/host.hbs b/ambari-web/app/templates/main/host.hbs
index 0d1d068..9f3654f 100644
--- a/ambari-web/app/templates/main/host.hbs
+++ b/ambari-web/app/templates/main/host.hbs
@@ -129,8 +129,8 @@
           </td>
           <td class="host-ip">{{host.ip}}</td>
           {{#if App.supports.setRackId}}
-            <td>
-              {{host.rack}} <a class="set-rack-id" {{action setRackId host target="controller"}}><i class="icon-pencil"></i></a>
+            <td rel="UsageTooltip" {{bindAttr title="host.rack"}} class="rack-id">
+              {{host.rack}}
             </td>
           {{/if}}
           <td class="cores-formatted">{{host.coresFormatted}}</td>
@@ -204,4 +204,3 @@
     </div>
   </div>
 </div>
-

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/app/templates/main/host/summary.hbs
----------------------------------------------------------------------
diff --git a/ambari-web/app/templates/main/host/summary.hbs b/ambari-web/app/templates/main/host/summary.hbs
index 58d4cc6..3d72c2f 100644
--- a/ambari-web/app/templates/main/host/summary.hbs
+++ b/ambari-web/app/templates/main/host/summary.hbs
@@ -136,13 +136,13 @@
 
                         {{#if App.supports.setRackId}}
                           <dt>{{t common.rack}}:</dt>
-                          <dd>&nbsp;{{view.content.rack}}</dd>
+                          <dd>&nbsp;{{view.content.rack}} <a class="set-rack-id" {{action setRackId view.content target="controller"}}><i class="icon-pencil"></i></a></dd>
                         {{/if}}
 
                         <dt class="summary-os-label">{{t common.os}}:</dt>
                           <dd class="summary-os-value">&nbsp;{{view.content.osType}}&nbsp;({{view.content.osArch}})</dd>
 
-                        <dt class="summary-cores-label">{{t common.cores}}:</dt>
+                        <dt class="summary-cores-label">{{t common.cores.cpu}}:</dt>
                           <dd class="summary-cores-value">&nbsp;{{view.content.coresFormatted}}</dd>
 
                         <dt class="summary-disk-label">{{t common.disk}}:</dt>

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/app/utils/hosts.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/utils/hosts.js b/ambari-web/app/utils/hosts.js
index f2897a0..c04d519 100644
--- a/ambari-web/app/utils/hosts.js
+++ b/ambari-web/app/utils/hosts.js
@@ -5,9 +5,9 @@
  * 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
@@ -23,13 +23,13 @@ var validator = require('utils/validator');
 module.exports = {
 
   /**
-   * Launches a dialog to select hosts from the provided available hosts. 
-   * 
-   * Once the user clicks OK or Cancel, the callback is called with the 
+   * Launches a dialog to select hosts from the provided available hosts.
+   *
+   * Once the user clicks OK or Cancel, the callback is called with the
    * array of hosts (App.Host[]) selected. If the dialog was cancelled
    * or closed, <code>null</code> is provided to the callback. Else
    * an array (maybe empty) will be provided to the callback.
-   * 
+   *
    * @param initialHosts  {App.Host[]} List of hosts to pick from
    * @param selectedHosts {App.Host[]} List of hosts already selected from the available hosts
    * @param selectAtleastOneHost  {boolean} If true atleast one host has to be selected
@@ -190,7 +190,7 @@ module.exports = {
     var hostNames = hosts.mapProperty('hostName');
     return App.ModalPopup.show({
       header: Em.I18n.t('hosts.host.details.setRackId'),
-      disablePrimary: false,
+      disablePrimary: true,
       rackId: rackId,
       bodyClass: Em.View.extend({
         templateName: require('templates/main/host/rack_id_popup'),
@@ -227,4 +227,4 @@ module.exports = {
   errorRackId: function () {
     App.showAlertPopup(Em.I18n.t('common.error'), Em.I18n.t('hostPopup.setRackId.error'));
   }
-};
\ No newline at end of file
+};

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/app/utils/validator.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/utils/validator.js b/ambari-web/app/utils/validator.js
index 72b0566..fe7e286 100644
--- a/ambari-web/app/utils/validator.js
+++ b/ambari-web/app/utils/validator.js
@@ -206,7 +206,7 @@ module.exports = {
       return true;
     };
     if (/^[\?\|\*\!,]/.test(value)) return false;
-    return /^((\.\*?)?([\w\s\[\]\?\-_,\|\*\!\{\}]*)?)+(\.\*?)?$/g.test(value) && (checkPair(['[',']'])) && (checkPair(['{','}']));
+    return /^((\.\*?)?([\w\s\[\]\/\?\-_,\|\*\!\{\}]*)?)+(\.\*?)?$/g.test(value) && (checkPair(['[',']'])) && (checkPair(['{','}']));
   },
 
   /**
@@ -218,7 +218,7 @@ module.exports = {
       // true is there is no host with this component
       return hostComponents.filterProperty("componentName", item["component-name"]).filterProperty("hostName", item.host).length === 0;
     });
-  }, 
+  },
 
   isValidRackId: function(path) {
     // See app/message.js:hostPopup.setRackId.invalid

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/app/views/main/host.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/views/main/host.js b/ambari-web/app/views/main/host.js
index 883ea6a..1fee16a 100644
--- a/ambari-web/app/views/main/host.js
+++ b/ambari-web/app/views/main/host.js
@@ -362,6 +362,11 @@ App.MainHostView = App.TableView.extend(App.TableServerViewMixin, {
         break;
     }
 
+    if (operationData.action === 'SET_RACK_INFO') {
+      this.getHostsForBulkOperations(queryParams, operationData, null);
+      return;
+    }
+
     var loadingPopup = App.ModalPopup.show({
       header: Em.I18n.t('jobs.loadingTasks'),
       primary: false,
@@ -370,13 +375,22 @@ App.MainHostView = App.TableView.extend(App.TableServerViewMixin, {
         template: Ember.Handlebars.compile('<div class="spinner"></div>')
       })
     });
-    var parameters = App.router.get('updateController').computeParameters(queryParams);
-    if (!parameters.length) parameters = '&';
+
+    this.getHostsForBulkOperations(queryParams, operationData, loadingPopup);
+  },
+
+  getHostsForBulkOperations: function (queryParams, operationData, loadingPopup) {
+    var params = App.router.get('updateController').computeParameters(queryParams);
+
+    if (!params.length) {
+      params = '&';
+    }
+
     App.ajax.send({
       name: 'hosts.bulk.operations',
       sender: this,
       data: {
-        parameters: parameters.substring(0, parameters.length - 1),
+        parameters: params.substring(0, params.length - 1),
         operationData: operationData,
         loadingPopup: loadingPopup
       },
@@ -439,7 +453,16 @@ App.MainHostView = App.TableView.extend(App.TableServerViewMixin, {
     else {
       message = Em.I18n.t('hosts.bulkOperation.confirmation.hosts').format(operationData.message, hostNames.length);
     }
-    param.loadingPopup.hide();
+
+    if (param.loadingPopup) {
+      param.loadingPopup.hide();
+    }
+
+    if (operationData.action === 'SET_RACK_INFO') {
+      self.get('controller').bulkOperation(operationData, hosts);
+      return;
+    }
+
     App.ModalPopup.show({
       header: Em.I18n.t('hosts.bulkOperation.confirmation.header'),
       hostNames: hostNames.join("\n"),
@@ -853,7 +876,7 @@ App.MainHostView = App.TableView.extend(App.TableServerViewMixin, {
    */
   rackFilterView: filters.createTextView({
     column: 12,
-    fieldType: 'filter-input-width',
+    fieldType: 'filter-input-width rack-input',
     onChangeValue: function(){
       this.get('parentView').updateFilter(this.get('column'), this.get('value'), 'string');
     }

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/test/controllers/main/host/details_test.js
----------------------------------------------------------------------
diff --git a/ambari-web/test/controllers/main/host/details_test.js b/ambari-web/test/controllers/main/host/details_test.js
index 5a383a3..19a160b 100644
--- a/ambari-web/test/controllers/main/host/details_test.js
+++ b/ambari-web/test/controllers/main/host/details_test.js
@@ -24,6 +24,7 @@ require('models/host_component');
 require('models/host_stack_version');
 var batchUtils = require('utils/batch_scheduled_requests');
 var componentsUtils = require('utils/components');
+var hostsManagement = require('utils/hosts');
 var controller;
 
 describe('App.MainHostDetailsController', function () {
@@ -1702,6 +1703,26 @@ describe('App.MainHostDetailsController', function () {
     });
   });
 
+
+  describe('#setRackId', function () {
+    beforeEach(function () {
+      sinon.stub(hostsManagement, 'setRackInfo', Em.K);
+
+    });
+    afterEach(function () {
+      hostsManagement.setRackInfo.restore();
+    });
+    it('should call setRackInfo with appropriate arguments', function () {
+      var mockedHost = Em.Object.create({
+        rack: 'rackId'
+      });
+      controller.setRackId({
+        context: mockedHost
+      });
+      expect(hostsManagement.setRackInfo.calledWith({message: Em.I18n.t('hosts.host.details.setRackId')}, [mockedHost], 'rackId')).to.be.true;
+    });
+  });
+
   describe('#restartAllStaleConfigComponents()', function () {
 
     beforeEach(function () {
@@ -1911,13 +1932,13 @@ describe('App.MainHostDetailsController', function () {
 
   describe('#_doDeleteHostComponentSuccessCallback()', function () {
     beforeEach(function() {
-      sinon.stub(controller, 'removeHostComponentModel', Em.K);      
+      sinon.stub(controller, 'removeHostComponentModel', Em.K);
     });
-    
+
     afterEach(function() {
-      controller.removeHostComponentModel.restore();      
+      controller.removeHostComponentModel.restore();
     });
-    
+
     it('ZOOKEEPER_SERVER component', function () {
       var data = {
         componentName: 'ZOOKEEPER_SERVER'

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/test/controllers/main/host_test.js
----------------------------------------------------------------------
diff --git a/ambari-web/test/controllers/main/host_test.js b/ambari-web/test/controllers/main/host_test.js
index 8922f9f..54d616f 100644
--- a/ambari-web/test/controllers/main/host_test.js
+++ b/ambari-web/test/controllers/main/host_test.js
@@ -18,7 +18,6 @@
 
 var App = require('app');
 var validator = require('utils/validator');
-var hostsManagement = require('utils/hosts');
 require('utils/batch_scheduled_requests');
 require('controllers/main/host');
 require('mappers/server_data_mapper');
@@ -199,7 +198,7 @@ describe('MainHostController', function () {
         }];
       });
     });
-    
+
     afterEach(function() {
       App.db.getFilterConditions.restore();
       hostController.getRegExp.restore();
@@ -242,27 +241,4 @@ describe('MainHostController', function () {
 
   });
 
-  describe('#setRackId', function () {
-
-    beforeEach(function () {
-      sinon.stub(hostsManagement, 'setRackInfo', Em.K);
-
-    });
-
-    afterEach(function () {
-      hostsManagement.setRackInfo.restore();
-    });
-
-    it('should call setRackInfo with appropriate arguments', function () {
-      var mockedHost = Em.Object.create({
-        rack: 'rackId'
-      });
-      hostController.setRackId({
-        context: mockedHost
-      });
-      expect(hostsManagement.setRackInfo.calledWith({message: Em.I18n.t('hosts.host.details.setRackId')}, [mockedHost], 'rackId')).to.be.true;
-    });
-
-  });
-
 });

http://git-wip-us.apache.org/repos/asf/ambari/blob/1afb7e6a/ambari-web/test/utils/validator_test.js
----------------------------------------------------------------------
diff --git a/ambari-web/test/utils/validator_test.js b/ambari-web/test/utils/validator_test.js
index 93b06cc..bccb820 100644
--- a/ambari-web/test/utils/validator_test.js
+++ b/ambari-web/test/utils/validator_test.js
@@ -393,6 +393,7 @@ describe('validator', function () {
         { value: 'a1[1]asd[1]', expected: true },
         { value: 'a1[1]asd[1][', expected: false },
         { value: 'a1[1|1]asd[1]', expected: true },
+        { value: '/a1[1|1]asd[1]', expected: true },
         { value: 'a1-2!', expected: true },
         { value: '|a1-2', expected: false },
         { value: '[a1', expected: false },