You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ambari.apache.org by ab...@apache.org on 2014/11/07 16:14:15 UTC

ambari git commit: AMBARI-8158 create mocks for Admin Web : Stack Versions page. (ababiichuk)

Repository: ambari
Updated Branches:
  refs/heads/trunk c079e9066 -> d5d898a93


AMBARI-8158 create mocks for Admin Web : Stack Versions page. (ababiichuk)


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

Branch: refs/heads/trunk
Commit: d5d898a93184d9c62e828fde112b26cdcb1b9667
Parents: c079e90
Author: aBabiichuk <ab...@cybervisiontech.com>
Authored: Fri Nov 7 17:10:12 2014 +0200
Committer: aBabiichuk <ab...@cybervisiontech.com>
Committed: Fri Nov 7 17:10:12 2014 +0200

----------------------------------------------------------------------
 .../data/stack_versions/stack_version_all.json  | 274 ++++++++++++++++++-
 ambari-web/app/controllers.js                   |   1 +
 .../stack_upgrade/stack_versions_controller.js  |  63 +++++
 ambari-web/app/messages.js                      |   8 +
 ambari-web/app/routes/main.js                   |   9 +
 ambari-web/app/styles/application.less          |  58 ++++
 .../admin/stack_versions/stack_versions.hbs     |  90 ++++++
 ambari-web/app/views.js                         |   1 +
 ambari-web/app/views/common/sort_view.js        |  11 +
 ambari-web/app/views/main/admin.js              |   7 +
 .../admin/stack_versions/stack_version_view.js  | 152 ++++++++++
 ambari-web/app/views/main/menu.js               |   7 +
 12 files changed, 679 insertions(+), 2 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/assets/data/stack_versions/stack_version_all.json
----------------------------------------------------------------------
diff --git a/ambari-web/app/assets/data/stack_versions/stack_version_all.json b/ambari-web/app/assets/data/stack_versions/stack_version_all.json
index ff8ece0..c2651ea 100644
--- a/ambari-web/app/assets/data/stack_versions/stack_version_all.json
+++ b/ambari-web/app/assets/data/stack_versions/stack_version_all.json
@@ -3,7 +3,7 @@
     {
       "StackVersion": {
         "name": "HDP 2.2.0.0",
-        "version": "2.2.0.0",
+        "version": "2.2.0.10",
         "installed_hosts": 0,
         "current_hosts": 0,
         "repositories": [
@@ -43,7 +43,7 @@
     {
       "StackVersion": {
         "name": "HDP 2.2.0.1",
-        "version": "2.2.0.1",
+        "version": "2.2.0.12",
         "installed_hosts": 2,
         "current_hosts": 3,
         "repositories": [
@@ -68,7 +68,277 @@
     {
       "StackVersion": {
         "name": "HDP 2.2.0.2",
+        "version": "2.2.0.11",
+        "installed_hosts": 5,
+        "current_hosts": 5,
+        "repositories": [
+          {
+            "os": "redhat6",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          }
+        ]
+      }
+    },
+    {
+      "StackVersion": {
+        "name": "HDP 2.2.0.0",
+        "version": "2.2.0.1",
+        "installed_hosts": 0,
+        "current_hosts": 0,
+        "repositories": [
+          {
+            "os": "redhat6",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          },
+          {
+            "os": "ubuntu12",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          }
+        ]
+      }
+    },
+    {
+      "StackVersion": {
+        "name": "HDP 2.2.0.1",
         "version": "2.2.0.2",
+        "installed_hosts": 2,
+        "current_hosts": 3,
+        "repositories": [
+          {
+            "os": "redhat6",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          }
+        ]
+      }
+    },
+    {
+      "StackVersion": {
+        "name": "HDP 2.2.0.2",
+        "version": "2.2.0.3",
+        "installed_hosts": 5,
+        "current_hosts": 5,
+        "repositories": [
+          {
+            "os": "redhat6",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          }
+        ]
+      }
+    },
+    {
+      "StackVersion": {
+        "name": "HDP 2.2.0.0",
+        "version": "2.2.0.4",
+        "installed_hosts": 0,
+        "current_hosts": 0,
+        "repositories": [
+          {
+            "os": "redhat6",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          },
+          {
+            "os": "ubuntu12",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          }
+        ]
+      }
+    },
+    {
+      "StackVersion": {
+        "name": "HDP 2.2.0.1",
+        "version": "2.2.0.5",
+        "installed_hosts": 2,
+        "current_hosts": 3,
+        "repositories": [
+          {
+            "os": "redhat6",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          }
+        ]
+      }
+    },
+    {
+      "StackVersion": {
+        "name": "HDP 2.2.0.2",
+        "version": "2.2.0.6",
+        "installed_hosts": 5,
+        "current_hosts": 5,
+        "repositories": [
+          {
+            "os": "redhat6",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          }
+        ]
+      }
+    },
+    {
+      "StackVersion": {
+        "name": "HDP 2.2.0.0",
+        "version": "2.2.0.7",
+        "installed_hosts": 0,
+        "current_hosts": 0,
+        "repositories": [
+          {
+            "os": "redhat6",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          },
+          {
+            "os": "ubuntu12",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          }
+        ]
+      }
+    },
+    {
+      "StackVersion": {
+        "name": "HDP 2.2.0.1",
+        "version": "2.2.0.8",
+        "installed_hosts": 2,
+        "current_hosts": 3,
+        "repositories": [
+          {
+            "os": "redhat6",
+            "baseurls": [
+              {
+                "id": "HDP-2.2.0.1-885",
+                "type": "HDP",
+                "baseurl": "http://host1/hdp"
+              },
+              {
+                "id": "HDP-UTILS-1.0.0.20",
+                "type": "HDP-UTILS",
+                "baseurl": "http://host1/hdp-utils"
+              }
+            ]
+          }
+        ]
+      }
+    },
+    {
+      "StackVersion": {
+        "name": "HDP 2.2.0.2",
+        "version": "2.2.0.9",
         "installed_hosts": 5,
         "current_hosts": 5,
         "repositories": [

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/controllers.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/controllers.js b/ambari-web/app/controllers.js
index ae70643..3e4e0da 100644
--- a/ambari-web/app/controllers.js
+++ b/ambari-web/app/controllers.js
@@ -53,6 +53,7 @@ require('controllers/main/admin/highAvailability/resourceManager/step3_controlle
 require('controllers/main/admin/highAvailability/resourceManager/step4_controller');
 require('controllers/main/admin/repositories');
 require('controllers/main/admin/stack_upgrade_controller');
+require('controllers/main/admin/stack_upgrade/stack_versions_controller');
 require('controllers/main/admin/serviceAccounts_controller');
 require('controllers/main/admin/advanced');
 require('utils/polling');

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/controllers/main/admin/stack_upgrade/stack_versions_controller.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/controllers/main/admin/stack_upgrade/stack_versions_controller.js b/ambari-web/app/controllers/main/admin/stack_upgrade/stack_versions_controller.js
new file mode 100644
index 0000000..7286f58
--- /dev/null
+++ b/ambari-web/app/controllers/main/admin/stack_upgrade/stack_versions_controller.js
@@ -0,0 +1,63 @@
+/**
+ * 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');
+
+App.MainStackVersionsController = Em.ArrayController.extend({
+  name: 'mainStackVersionsController',
+
+  content: App.StackVersion.find(),
+  mockUrl: '/data/stack_versions/stack_version_all.json',
+  realUrl: function () {
+    return App.apiPrefix + '/clusters/' + App.get('clusterName') + '/stack_versions&minimal_response=true';
+  }.property('App.clusterName'),
+
+  /**
+   * load all data components required by stack version table
+   * @return {*}
+   */
+  load: function () {
+    var dfd = $.Deferred();
+    var self = this;
+    this.loadStackVersionsToModel().done(function () {
+      self.set('dataIsLoaded', true);
+      dfd.resolve();
+    });
+    return dfd.promise();
+  },
+
+  /**
+   * get stack versions from server and push it to model
+   * @return {*}
+   */
+  loadStackVersionsToModel: function () {
+    var dfd = $.Deferred();
+
+    App.HttpClient.get(this.getUrl(), App.stackVersionMapper, {
+      complete: function () {
+        dfd.resolve();
+      }
+    });
+    return dfd.promise();
+  },
+
+  getUrl: function () {
+    return App.get('testMode') ? this.get('mockUrl') : this.get('realUrl');
+  }
+
+});

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/messages.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/messages.js b/ambari-web/app/messages.js
index 282fdc5..3b8bbcd 100644
--- a/ambari-web/app/messages.js
+++ b/ambari-web/app/messages.js
@@ -128,6 +128,7 @@ Em.I18n.translations = {
   'common.users': 'Users',
   'common.issues': 'Issues',
   'common.os':'OS',
+  'common.oss':'OSs',
   'common.memory':'Memory',
   'common.maximum':'Maximum',
   'common.start':'Start',
@@ -152,6 +153,7 @@ Em.I18n.translations = {
   'common.security':'Security',
   'common.cluster':'Cluster',
   'common.repositories':'Repositories',
+  'common.stack.versions':'Stack Versions',
   'common.serviceAccounts': 'Service Accounts',
   'common.add': 'Add',
   'common.edit': 'Edit',
@@ -1164,6 +1166,12 @@ Em.I18n.translations = {
   'admin.misc.header': 'Service Users and Groups',
   'admin.misc.nothingToShow': 'No user accounts to display',
 
+  'admin.stackVersions.table.header.stack': "Stack",
+  'admin.stackVersions.table.header.version': "Version",
+  'admin.stackVersions.table.header.os': "OS",
+  'admin.stackVersions.table.header.installed': "Installed on",
+  'admin.stackVersions.table.header.current': "Current on",
+
   'services.service.start':'Start',
   'services.service.stop':'Stop',
   'services.service.metrics':'Service Metrics',

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/routes/main.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/routes/main.js b/ambari-web/app/routes/main.js
index d461812..2a31ba1 100644
--- a/ambari-web/app/routes/main.js
+++ b/ambari-web/app/routes/main.js
@@ -488,6 +488,15 @@ module.exports = Em.Route.extend({
         router.get('mainAdminController').connectOutlet('mainAdminRepositories');
       }
     }),
+    adminStackVersions: Em.Route.extend({
+      route: '/versions',
+      connectOutlets: function (router) {
+        if(App.get('supports.stackUpgrade')) {
+          router.set('mainAdminController.category', "stackVersions");
+          router.get('mainAdminController').connectOutlet('mainStackVersions');
+        }
+      }
+    }),
     adminAdvanced: Em.Route.extend({
       route: '/advanced',
       connectOutlets: function (router) {

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/styles/application.less
----------------------------------------------------------------------
diff --git a/ambari-web/app/styles/application.less b/ambari-web/app/styles/application.less
index d1ecd1f..70c7271 100644
--- a/ambari-web/app/styles/application.less
+++ b/ambari-web/app/styles/application.less
@@ -4973,6 +4973,64 @@ ul.inline li {
   }
 }
 
+#stack_versions {
+  .table {
+    thead {
+      background: none repeat scroll 0 0 #F8F8F8;
+    }
+    // stack name/version
+    th:first-child,
+    td:first-child,
+    th:first-child + th,
+    td:first-child + td {
+      width: 25%;
+      select.filter-input-width{
+        width: 75%;
+      }
+      input.filter-input-width{
+        width: 75%;
+      }
+    }
+    // os
+    th:first-child + th + th,
+    td:first-child + td + td {
+      width: 20%;
+      word-wrap: break-word;
+      input.filter-input-width{
+        width: 75%;
+      }
+    }
+    // hosts column
+    th:first-child + th + th + th,
+    td:first-child + td + td + td,
+    th:first-child + th + th + th + th,
+    td:first-child + td + td + td + td {
+      width: 15%;
+      word-wrap: break-word;
+      input.filter-input-width {
+        width: 75%;
+      }
+    }
+  }
+  div.page-bar div.filtered-info {
+    margin-left: 17px;
+  }
+  a {
+    cursor: pointer;
+  }
+  .os-expander {
+    .icon-caret-right, .icon-caret-down {
+      vertical-align: middle;
+      margin-right: 5px;
+      margin-bottom: 2px;
+      text-decoration: none;
+    }
+  }
+  .operating-systems {
+    display: none;
+    padding-left: 13px;
+  }
+}
 .one-story-bar {
   margin-bottom: 60px;
 }

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/templates/main/admin/stack_versions/stack_versions.hbs
----------------------------------------------------------------------
diff --git a/ambari-web/app/templates/main/admin/stack_versions/stack_versions.hbs b/ambari-web/app/templates/main/admin/stack_versions/stack_versions.hbs
new file mode 100644
index 0000000..15eba7b
--- /dev/null
+++ b/ambari-web/app/templates/main/admin/stack_versions/stack_versions.hbs
@@ -0,0 +1,90 @@
+{{!
+* 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.
+}}
+
+<div id="stack_versions">
+  <table class="table advanced-header-table table-bordered table-striped">
+    <thead>
+    {{#view view.sortView classNames="label-row" contentBinding="view.filteredContent"}}
+      {{view view.parentView.stackNameSort}}
+      {{view view.parentView.stackVersionSort}}
+      {{view view.parentView.osSort}}
+      {{view view.parentView.istalledSort}}
+      {{view view.parentView.currentSort}}
+    {{/view}}
+
+    <tr class="filter-row">
+      <th class="first">{{view view.stackNameFilterView}}</th>
+      <th>{{view view.stackVersionFilterView}}</th>
+      <th>{{view view.osFilterView}}</th>
+      <th>{{view view.currentFilterView}}</th>
+      <th>{{view view.installedFilterView}}</th>
+    </tr>
+    </thead>
+    <tbody class="services-menu">
+      {{#if view.pageContent}}
+        {{#each item in view.pageContent}}
+          {{#view view.StackVersionView contentBinding="item"}}
+            <td class="first">
+              <span class="stack-name">{{view.content.name}}</span>
+            </td>
+            <td>
+              <span class="stack-version">{{view.content.version}}</span>
+            </td>
+            <td>
+              <a href="#" class="os-expander" {{action toggleOs target="view"}}>
+                <span {{bindAttr class="view.isOsCollapsed:icon-caret-right:icon-caret-down"}}></span>
+                {{view.content.operatingSystems.length}} {{pluralize view.content.operatingSystems.length singular="t:common.os" plural="t:common.oss"}}
+              </a>
+
+              <div id="stack-{{view.content.name}}" class="operating-systems">
+                {{{view.labels}}}
+              </div>
+            </td>
+            <td>
+              <span>{{view.content.installedHostsCount}}</span>
+            </td>
+            <td>
+              <span>{{view.content.currentHostsCount}}</span>
+            </td>
+          {{/view}}
+        {{/each}}
+      {{else}}
+        <tr>
+          <td class="first" colspan="5">
+            {{t dashboard.configHistory.table.empty}}
+          </td>
+        </tr>
+      {{/if}}
+    </tbody>
+  </table>
+
+  <div class="page-bar">
+    <div class="filtered-info span4">
+      <label>{{view.filteredContentInfo}} - <a {{action clearFilters target="view"}}
+        href="#">{{t tableView.filters.clearAllFilters}}</a></label>
+    </div>
+    <div class="items-on-page">
+      <label>{{t common.show}}: {{view view.rowsPerPageSelectView selectionBinding="view.displayLength"}}</label>
+    </div>
+    <div class="info">{{view.paginationInfo}}</div>
+    <div class="paging_two_button">
+      {{view view.paginationLeft}}
+      {{view view.paginationRight}}
+    </div>
+  </div>
+</div>

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/views.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/views.js b/ambari-web/app/views.js
index 3fc9bcb..bfc3708 100644
--- a/ambari-web/app/views.js
+++ b/ambari-web/app/views.js
@@ -94,6 +94,7 @@ require('views/main/admin/highAvailability/resourceManager/step4_view');
 require('views/main/admin/repositories');
 require('views/main/admin/serviceAccounts_view');
 require('views/main/admin/stack_upgrade');
+require('views/main/admin/stack_versions/stack_version_view');
 require('views/main/admin/advanced');
 require('views/main/admin/advanced/password');
 require('views/main/admin/audit');

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/views/common/sort_view.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/views/common/sort_view.js b/ambari-web/app/views/common/sort_view.js
index 268d953..30edb5b 100644
--- a/ambari-web/app/views/common/sort_view.js
+++ b/ambari-web/app/views/common/sort_view.js
@@ -17,6 +17,7 @@
  */
 
 var misc = require('utils/misc');
+var stringUtils = require('utils/string_utils');
 var App = require('app');
 
 /**
@@ -157,6 +158,16 @@ var wrapperView = Em.View.extend({
           }
         };
         break;
+      case 'version':
+        func = function (a, b) {
+          var res = stringUtils.compareVersions(a.get(property.get('name')), b.get(property.get('name')));
+          if (order) {
+            return res;
+          } else {
+            return -res;
+          }
+        };
+        break;
       default:
         func = function (a, b) {
           if (order) {

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/views/main/admin.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/views/main/admin.js b/ambari-web/app/views/main/admin.js
index 829da20..7c00ed8 100644
--- a/ambari-web/app/views/main/admin.js
+++ b/ambari-web/app/views/main/admin.js
@@ -28,6 +28,13 @@ App.MainAdminView = Em.View.extend({
       url: 'adminRepositories',
       label: Em.I18n.t('common.repositories')
     });
+    if (App.get('supports.stackUpgrade')) {
+      items.push({
+        name: 'stackVersions',
+        url: 'adminStackVersions',
+        label: Em.I18n.t('common.stack.versions')
+      });
+    }
     items.push({
       name: 'serviceAccounts',
       url: 'adminServiceAccounts',

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/views/main/admin/stack_versions/stack_version_view.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/views/main/admin/stack_versions/stack_version_view.js b/ambari-web/app/views/main/admin/stack_versions/stack_version_view.js
new file mode 100644
index 0000000..3ce30c2
--- /dev/null
+++ b/ambari-web/app/views/main/admin/stack_versions/stack_version_view.js
@@ -0,0 +1,152 @@
+/**
+ * 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');
+var filters = require('views/common/filter_view');
+var sort = require('views/common/sort_view');
+
+App.MainStackVersionsView = App.TableView.extend({
+  templateName: require('templates/main/admin/stack_versions/stack_versions'),
+
+  content: function () {
+    return this.get('controller.content');
+  }.property('controller.content'),
+
+  /**
+   * return filtered number of all content number information displayed on the page footer bar
+   * @returns {String}
+   */
+  filteredContentInfo: function () {
+    return this.t('tableView.filters.filteredConfigVersionInfo').format(this.get('filteredCount'), this.get('content.length'));
+  }.property('filteredCount', 'content.length'),
+
+  /**
+   * associations between stack version property and column index
+   * @type {Array}
+   */
+  colPropAssoc: function () {
+    var associations = [];
+    associations[1] = 'name';
+    associations[2] = 'version';
+    associations[3] = 'operatingSystems';
+    associations[4] = 'installedHostsCount';
+    associations[5] = 'currentHostsCount';
+    return associations;
+  }.property(),
+
+  sortView: sort.wrapperView,
+  stackNameSort: sort.fieldView.extend({
+    column: 1,
+    name: 'name',
+    displayName: Em.I18n.t('admin.stackVersions.table.header.stack'),
+    type: 'version',
+    classNames: ['first']
+  }),
+  stackVersionSort: sort.fieldView.extend({
+    column: 2,
+    name: 'version',
+    displayName: Em.I18n.t('admin.stackVersions.table.header.version'),
+    type: 'version'
+  }),
+  osSort: sort.fieldView.extend({
+    column: 3,
+    name: 'installedHostsCount',
+    displayName: Em.I18n.t('admin.stackVersions.table.header.os')
+  }),
+  istalledSort: sort.fieldView.extend({
+    column: 4,
+    name: 'currentHostsCount',
+    displayName: Em.I18n.t('admin.stackVersions.table.header.installed'),
+    type: "number"
+  }),
+  currentSort: sort.fieldView.extend({
+    column: 5,
+    name: 'currentHostsCount',
+    displayName: Em.I18n.t('admin.stackVersions.table.header.current'),
+    type: "number"
+  }),
+
+  stackNameFilterView: filters.createSelectView({
+    column: 1,
+    fieldType: 'filter-input-width',
+    content: function () {
+      return ['All'].concat(App.StackVersion.find().mapProperty('name'));
+    }.property('App.router.mainStackVersionsController.dataIsLoaded'),
+    onChangeValue: function () {
+      this.get('parentView').updateFilter(this.get('column'), this.get('actualValue'), 'select');
+    },
+    emptyValue: Em.I18n.t('common.all')
+  }),
+
+  stackVersionFilterView: filters.createTextView({
+    column: 2,
+    fieldType: 'filter-input-width',
+    onChangeValue: function () {
+      this.get('parentView').updateFilter(this.get('column'), this.get('value'), 'string');
+    }
+  }),
+
+  osFilterView: filters.createTextView({
+    column: 3,
+    fieldType: 'filter-input-width',
+    onChangeValue: function () {
+      this.get('parentView').updateFilter(this.get('column'), this.get('value'), 'string');
+    }
+  }),
+
+  currentFilterView: filters.createTextView({
+    column: 4,
+    fieldType: 'filter-input-width',
+    onChangeValue: function () {
+      this.get('parentView').updateFilter(this.get('column'), this.get('value'), 'string');
+    }
+  }),
+
+  installedFilterView: filters.createTextView({
+    column: 5,
+    fieldType: 'filter-input-width',
+    onChangeValue: function () {
+      this.get('parentView').updateFilter(this.get('column'), this.get('value'), 'string');
+    }
+  }),
+
+  StackVersionView: Em.View.extend({
+    tagName: 'tr',
+    didInsertElement: function () {
+      App.tooltip(this.$("[rel='Tooltip']"));
+      this.set('isOsCollapsed', true);
+    },
+
+    toggleOs: function(event) {
+      this.set('isOsCollapsed', !this.get('isOsCollapsed'));
+      this.$('.operating-systems').toggle();
+    },
+
+    labels: function() {
+      return this.get('content.operatingSystems').getEach('name').join("<br />");
+    }.property('content.operatingSystems.length')
+  }),
+
+
+  didInsertElement: function() {
+    this.get('controller').load().done(function(){
+      this.set('filteredContent',this.get('content'));
+    }, this);
+  }
+
+});

http://git-wip-us.apache.org/repos/asf/ambari/blob/d5d898a9/ambari-web/app/views/main/menu.js
----------------------------------------------------------------------
diff --git a/ambari-web/app/views/main/menu.js b/ambari-web/app/views/main/menu.js
index 99dd583..3358dad 100644
--- a/ambari-web/app/views/main/menu.js
+++ b/ambari-web/app/views/main/menu.js
@@ -137,6 +137,13 @@ App.MainMenuView = Em.CollectionView.extend({
           url: 'repositories',
           label: Em.I18n.t('common.repositories')
         });
+        if(App.get('supports.stackUpgrade')) {
+          categories.push({
+            name: 'stackVersions',
+            url: 'versions/',
+            label: Em.I18n.t('common.stack.versions')
+          });
+        }
         categories.push({
           name: 'adminServiceAccounts',
           url: 'serviceAccounts',