Browse Source

AMBARI-1006. Populate dashboard>HDFS section with API data. (Srimanth Gunturi via yusaku)

git-svn-id: https://svn.apache.org/repos/asf/incubator/ambari/branches/AMBARI-666@1418927 13f79535-47bb-0310-9956-ffa450edef68
Yusaku Sako 12 years ago
parent
commit
e62cdf99ba

+ 3 - 0
AMBARI-666-CHANGES.txt

@@ -12,6 +12,9 @@ AMBARI-666 branch (unreleased changes)
 
   NEW FEATURES
 
+  AMBARI-1006. Populate dashboard>HDFS section with API data.
+  (Srimanth Gunturi via yusaku)
+
   AMBARI-1004. Allow properties entered in custom config
   (ex: hdfs-site.xml) to override existing or create new properties.
   (Jaimin Jetly via yusaku)

+ 57 - 3
ambari-web/app/controllers/global/cluster_controller.js

@@ -176,7 +176,8 @@ App.ClusterController = Em.Controller.extend({
 
      var clusterUrl = this.getUrl('/data/clusters/cluster.json', '?fields=Clusters');
      var hostsUrl = this.getUrl('/data/hosts/hosts.json', '/hosts?fields=*');
-     var servicesUrl = this.getUrl('/data/dashboard/services.json', '/services?ServiceInfo/service_name!=MISCELLANEOUS&ServiceInfo/service_name!=DASHBOARD&fields=components/host_components/*');
+     var servicesUrl1 = this.getUrl('/data/dashboard/services.json', '/services?ServiceInfo/service_name!=MISCELLANEOUS&ServiceInfo/service_name!=DASHBOARD&fields=components/host_components/*');
+     var servicesUrl2 = this.getUrl('/data/dashboard/services.json', '/services?ServiceInfo/service_name!=MISCELLANEOUS&ServiceInfo/service_name!=DASHBOARD&fields=components/ServiceComponentInfo');
 
      var runsUrl = App.testMode ? "/data/apps/runs.json" : "/api/jobhistory/workflow";
 
@@ -204,11 +205,64 @@ App.ClusterController = Em.Controller.extend({
         self.updateLoadStatus('hosts');
       }
     });
-    App.HttpClient.get(servicesUrl, App.servicesMapper,{
+    
+    //////////////////////////////
+    // Hack for services START  //
+    //////////////////////////////
+    var metricsJson = null;
+    var serviceComponentJson = null;
+    var metricsMapper = {
+        map: function(data){
+          metricsJson = data;
+        }
+    };
+    var serviceComponentMapper = {
+        map: function(data){
+          serviceComponentJson = data;
+          if(metricsJson!=null && serviceComponentJson!=null){
+            var hdfsSvc1 = null;
+            var hdfsSvc2 = null;
+            metricsJson.items.forEach(function(svc){
+              if(svc.ServiceInfo.service_name=="HDFS"){
+                hdfsSvc1 = svc;
+              }
+            });
+            serviceComponentJson.items.forEach(function(svc){
+              if(svc.ServiceInfo.service_name=="HDFS"){
+                hdfsSvc2 = svc;
+              }
+            });
+            var nameNode1 = null;
+            var nameNode2 = null;
+            hdfsSvc1.components.forEach(function(c){
+              if(c.ServiceComponentInfo.component_name=="NAMENODE"){
+                nameNode1 = c;
+              }
+            });
+            hdfsSvc2.components.forEach(function(c){
+              if(c.ServiceComponentInfo.component_name=="NAMENODE"){
+                nameNode2 = c;
+              }
+            });
+            nameNode1.ServiceComponentInfo = nameNode2.ServiceComponentInfo;
+            
+            App.servicesMapper.map(metricsJson);
+            self.updateLoadStatus('services');
+          }
+        }
+    }
+    App.HttpClient.get(servicesUrl1, metricsMapper,{
       complete:function(jqXHR, textStatus){
-        self.updateLoadStatus('services');
+        App.HttpClient.get(servicesUrl2, serviceComponentMapper,{
+          complete:function(jqXHR, textStatus){
+          }
+        });
       }
     });
+    /////////////////////////////
+    // Hack for services END   //
+    /////////////////////////////
+    
   }.observes('clusterName'),
   clusterName: function(){
     return (this.get('cluster')) ? this.get('cluster').Clusters.cluster_name : 'mycluster';

+ 1 - 24
ambari-web/app/controllers/main/dashboard.js

@@ -24,29 +24,6 @@ App.MainDashboardController = Em.Controller.extend({
     return App.router.get('clusterController.alerts');
   }.property('App.router.clusterController.alerts'),
   data: {
-    HDFS:{
-      "namenode_addr":"namenode:50070",
-      "secondary_namenode_addr":"snamenode:50090",
-      "namenode_starttime":1348935028,
-      "total_nodes":"1",
-      "live_nodes":1,
-      "dead_nodes":0,
-      "decommissioning_nodes":0,
-      "dfs_blocks_underreplicated":145,
-      "safemode":false,
-      "pending_upgrades":false,
-      "dfs_configured_capacity":885570207744,
-      "dfs_percent_used":0.01,
-      "dfs_percent_remaining":95.09,
-      "dfs_total_bytes":885570207744,
-      "dfs_used_bytes":104898560,
-      "nondfs_used_bytes":43365113856,
-      "dfs_free_bytes":842100195328,
-      // additionals
-      "total_files_and_dirs": 1354,
-      "namenode_heap_used":63365113856,
-      "namenode_heap_total": 163365113856
-    },
     MAPREDUCE: {
       "jobtracker_addr": "jobtracker:50030",
       "jobtracker_starttime": 1348935243,
@@ -125,4 +102,4 @@ App.MainDashboardController = Em.Controller.extend({
     var alerts = this.get('alerts');
     return alerts ? alerts.filterProperty('status', 'corrupt').length : 0;
   }.property('alerts')
-})
+});

+ 94 - 33
ambari-web/app/mappers/services_mapper.js

@@ -1,41 +1,62 @@
 /**
- * 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
- *
+ * 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.
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
  */
 
 App.servicesMapper = App.QuickDataMapper.create({
-  model : App.Service,
-  config : {
-    id : 'ServiceInfo.service_name',
-    service_name : 'ServiceInfo.service_name',
+  model: App.Service,
+  config: {
+    id: 'ServiceInfo.service_name',
+    service_name: 'ServiceInfo.service_name',
     $work_status: 'DEAD',
-    $service_audit: [1, 2, 3],
-    $alerts: [1, 2, 3],
-    components_key : 'components',
-    components_type : 'array',
-    components : {
-        item : 'ServiceComponentInfo.component_name'
+    $service_audit: [ 1, 2, 3 ],
+    $alerts: [ 1, 2, 3 ],
+    components_key: 'components',
+    components_type: 'array',
+    components: {
+      item: 'ServiceComponentInfo.component_name'
     }
   },
+  
+  hdfsConfig : {
+    version : 'nameNodeComponent.ServiceComponentInfo.Version',
+    name_node_id: 'nameNodeComponent.host_components[0].HostRoles.host_name',
+    sname_node_id: 'snameNodeComponent.host_components[0].HostRoles.host_name',
+    data_nodes: 'data_nodes',
+    name_node_start_time: 'nameNodeComponent.ServiceComponentInfo.StartTime',
+    jvm_memory_heap_used: 'nameNodeComponent.host_components[0].metrics.jvm.memHeapUsedM',
+    jvm_memory_heap_committed: 'nameNodeComponent.host_components[0].metrics.jvm.memHeapCommittedM',
+    live_data_nodes: 'live_data_nodes',
+    dead_data_nodes: 'dead_data_nodes',
+    decommision_data_nodes: 'decommission_data_nodes',
+    capacity_used: 'nameNodeComponent.ServiceComponentInfo.CapacityUsed',
+    capacity_total: 'nameNodeComponent.ServiceComponentInfo.CapacityTotal',
+    ///// dfsTotalBlocks: 'nameNodeComponent.host_components[0].metrics.dfs.namenode.????',
+    ///// dfsCorruptBlocks: DS.attr('number'),
+    ///// dfsMissingBlocks: DS.attr('number'),
+    ///// dfsUnderReplicatedBlocks: DS.attr('number'),
+    ///// dfsTotalFiles: DS.attr('number'),
+    upgradeStatus: 'nameNodeComponent.ServiceComponentInfo.UpgradeFinalized',
+    safeModeStatus: 'nameNodeComponent.ServiceComponentInfo.Safemode'
+  },
 
-  model2 : App.Component,
+  model2: App.Component,
   config2: {
-    id : 'ServiceComponentInfo.component_name',
-    component_name : 'ServiceComponentInfo.component_name',
-    service_id : 'ServiceComponentInfo.service_name',
+    id: 'ServiceComponentInfo.component_name',
+    component_name: 'ServiceComponentInfo.component_name',
+    service_id: 'ServiceComponentInfo.service_name',
     work_status: 'host_components[0].HostRoles.state',
     host_id: 'host_components[0].HostRoles.host_name',
     $decommissioned: false
@@ -48,16 +69,56 @@ App.servicesMapper = App.QuickDataMapper.create({
 
     if (json.items) {
       var result = [];
-
       json.items.forEach(function (item) {
-        result.push(this.parseIt(item, this.config));
-      }, this)
+        var finalConfig = jQuery.extend({}, this.config);
+        if (item && item.ServiceInfo && item.ServiceInfo.service_name == "HDFS") {
+          // Change the JSON so that it is easy to map
+          var hdfsConfig = this.hdfsConfig;
+          item.components.forEach(function (component) {
+            if (component.ServiceComponentInfo && component.ServiceComponentInfo.component_name == "NAMENODE") {
+              item.nameNodeComponent = component;
+              finalConfig = jQuery.extend(finalConfig, hdfsConfig);
+              // Get the live, dead & decommision nodes from string json
+              liveNodesJson = jQuery.parseJSON(component.ServiceComponentInfo.LiveNodes);
+              deadNodesJson = jQuery.parseJSON(component.ServiceComponentInfo.DeadNodes);
+              decommisionNodesJson = jQuery.parseJSON(component.ServiceComponentInfo.DecomNodes);
+              item.live_data_nodes = [];
+              item.dead_data_nodes = [];
+              item.decommision_data_nodes = [];
+              for(var ln in liveNodesJson){
+                item.live_data_nodes.push(ln);
+              }
+              for(var dn in deadNodesJson){
+                item.dead_data_nodes.push(dn);
+              }
+              for(var dcn in decommisionNodesJson){
+                item.decommision_data_nodes.push(dcn);
+              }
+            }
+            if (component.ServiceComponentInfo && component.ServiceComponentInfo.component_name == "SECONDARY_NAMENODE") {
+              item.snameNodeComponent = component;
+            }
+            if (component.ServiceComponentInfo && component.ServiceComponentInfo.component_name == "DATANODE") {
+              if(!item.data_nodes){
+                item.data_nodes = [];
+              }
+              item.data_nodes.push(component.host_components[0].HostRoles.host_name);
+            }
+          });
+          // Map
+          var finalJson = this.parseIt(item, finalConfig);
+          result.push(finalJson);
+          App.store.load(App.HDFSService, finalJson);
+        } else {
+          result.push(this.parseIt(item, this.config));
+        }
+      }, this);
 
       App.store.loadMany(this.get('model'), result);
 
       result = [];
-      json.items.forEach(function(item){
-        item.components.forEach(function(component){
+      json.items.forEach(function (item) {
+        item.components.forEach(function (component) {
           result.push(this.parseIt(component, this.config2));
         }, this)
       }, this);

+ 9 - 4
ambari-web/app/messages.js

@@ -275,16 +275,21 @@ Em.I18n.translations = {
   'dashboard.services.hosts': 'Hosts',
   'dashboard.services.uptime': '{0} days {1} hrs {2} mins',
   'dashboard.services.hdfs.summary': '{0} of {1} nodes live, {2}% capacity free',
-  'dashboard.services.hdfs.capacity': 'HDFS Capacity',
-  'dashboard.services.hdfs.capacityUsed': '{0} of {1} ({2}% used)',
+  'dashboard.services.hdfs.nanmenode': 'NameNode',
+  'dashboard.services.hdfs.snanmenode': 'Secondary NameNode',
+  'dashboard.services.hdfs.capacity': 'HDFS Disk Capacity',
+  'dashboard.services.hdfs.capacityUsed': '{0} / {1} ({2}% used)',
   'dashboard.services.hdfs.totalFilesAndDirs': 'Total Files + Directories',
-  'dashboard.services.hdfs.nodes': 'Data Nodes',
+  'dashboard.services.hdfs.datanodes': 'DataNodes',
+  'dashboard.services.hdfs.datanodecounts': 'DataNode Status',
+  'dashboard.services.hdfs.version': 'Version',
+  'dashboard.services.hdfs.nameNodeWebUI': 'NameNode Web UI',
   'dashboard.services.hdfs.nodes.live': 'live',
   'dashboard.services.hdfs.nodes.dead': 'dead',
   'dashboard.services.hdfs.nodes.decom': 'decom',
   'dashboard.services.hdfs.nodes.uptime': 'NameNode Uptime',
   'dashboard.services.hdfs.nodes.heap': 'NameNode Heap',
-  'dashboard.services.hdfs.nodes.heapUsed': '{0} of {1}, {2}% used',
+  'dashboard.services.hdfs.nodes.heapUsed': '{0} / {1} ({2}% used)',
   'dashboard.services.hdfs.chart.label': 'Capacity (Free/Used)',
 
   'dashboard.services.mapreduce.summary': '{0} of {1} trackers live, {2} jobs running',

+ 1 - 0
ambari-web/app/models.js

@@ -29,6 +29,7 @@ require('models/component');
 require('models/service_config');
 require('models/service_audit');
 require('models/service_metrics');
+require('models/service/hdfs');
 require('models/alert');
 require('models/user');
 require('models/pagination');

+ 42 - 0
ambari-web/app/models/service/hdfs.js

@@ -0,0 +1,42 @@
+/**
+ * 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.HDFSService = App.Service.extend({
+  version: DS.attr('string'),
+  nameNode: DS.belongsTo('App.Host'),
+  snameNode: DS.belongsTo('App.Host'),
+  dataNodes: DS.hasMany('App.Host'),
+  nameNodeStartTime: DS.attr('number'),
+  jvmMemoryHeapUsed: DS.attr('number'),
+  jvmMemoryHeapCommitted: DS.attr('number'),
+  liveDataNodes: DS.hasMany('App.Host'),
+  deadDataNodes: DS.hasMany('App.Host'),
+  decommisionDataNodes: DS.hasMany('App.Host'),
+  capacityUsed: DS.attr('number'),
+  capacityTotal: DS.attr('number'),
+  dfsTotalBlocks: DS.attr('number'),
+  dfsCorruptBlocks: DS.attr('number'),
+  dfsMissingBlocks: DS.attr('number'),
+  dfsUnderReplicatedBlocks: DS.attr('number'),
+  dfsTotalFiles: DS.attr('number'),
+  upgradeStatus: DS.attr('boolean'),
+  safeModeStatus: DS.attr('string')
+});
+
+App.HDFSService.FIXTURES = [];

+ 8 - 0
ambari-web/app/routes/main.js

@@ -242,6 +242,14 @@ module.exports = Em.Route.extend({
     route:'/dashboard',
     connectOutlets:function (router, context) {
       router.get('mainController').connectOutlet('mainDashboard');
+    },
+    showDetails:function (router, event) {
+      router.get('mainHostDetailsController').setBack(true);
+      router.transitionTo('hostDetails.index', event.context)
+    },
+    filterHosts:function (router, component) {
+      router.get('mainHostController').filterByComponent(component.context);
+      router.transitionTo('hosts');
     }
   }),
 

+ 62 - 23
ambari-web/app/templates/main/dashboard/service/hdfs.hbs

@@ -31,54 +31,93 @@
 <table class="table no-borders">
   <tbody>
 
-  <!-- HDFS Capacity -->
+  <!-- NameNode -->
   <tr>
-    <td>{{t dashboard.services.hdfs.capacity}}</td>
-    <td>{{view.capacity}}</td>
+    <td>{{t dashboard.services.hdfs.nanmenode}}</td>
+    <td><a href="#" {{action showDetails view.service.nameNode}}>{{view.service.nameNode.hostName}}</a></td>
+  </tr>
+  <!-- SecondaryNameNode -->
+  <tr>
+    <td>{{t dashboard.services.hdfs.snanmenode}}</td>
+    <td><a href="#" {{action showDetails view.service.snameNode}}>{{view.service.snameNode.hostName}}</a></td>
   </tr>
-
   <!-- Data Nodes -->
   <tr>
-    <td>{{t dashboard.services.hdfs.nodes}}</td>
+    <td>{{t dashboard.services.hdfs.datanodes}}</td>
     <td>
-      {{view.data.live_nodes}} {{t dashboard.services.hdfs.nodes.live}} /
-      {{view.data.dead_nodes}} {{t dashboard.services.hdfs.nodes.dead}} /
-      {{view.data.decommissioning_nodes}} {{t dashboard.services.hdfs.nodes.decom}}
+      <a href="#" {{action filterHosts view.dataNodeComponent}}>{{view.service.dataNodes.length}} {{t dashboard.services.hdfs.datanodes}}</a>
     </td>
   </tr>
-
-  <!-- Total Files And Directories -->
+  <!-- Version -->
   <tr>
-    <td>{{t dashboard.services.hdfs.totalFilesAndDirs}}</td>
-    <td>{{view.data.total_files_and_dirs}}</td>
+    <td>{{t dashboard.services.hdfs.version}}</td>
+    <td>{{view.service.version}}</td>
+  </tr>
+  <!-- NameNode Web UI -->
+  <tr>
+    <td>{{t dashboard.services.hdfs.nameNodeWebUI}}</td>
+    <td><a {{bindAttr href="view.nodeWebUrl"}}>{{view.service.nameNode.hostName}}:50070</a>
+    </td>
   </tr>
-
   <!-- NameNode Uptime -->
   <tr>
     <td>{{t dashboard.services.hdfs.nodes.uptime}}</td>
     <td>{{view.nodeUptime}}</td>
   </tr>
-
   <!-- NameNode Heap -->
   <tr>
     <td>{{t dashboard.services.hdfs.nodes.heap}}</td>
     <td>{{view.nodeHeap}}</td>
   </tr>
-
-
-  <!-- Hosts -->
+  <!-- Data Node Counts -->
   <tr>
-    <td>{{t dashboard.services.hosts}}</td>
+    <td>{{t dashboard.services.hdfs.datanodecounts}}</td>
     <td>
-      {{#each component in view.service.components}}
-      {{#if component.type}}
-      <a href="#" {{action selectHost component.host}}>{{component.displayName}}</a>,
+      {{view.service.liveDataNodes.length}} {{t dashboard.services.hdfs.nodes.live}} /
+      {{view.service.deadDataNodes.length}} {{t dashboard.services.hdfs.nodes.dead}} /
+      {{view.service.decommisionDataNodes.length}} {{t dashboard.services.hdfs.nodes.decom}}
+    </td>
+  </tr>
+  <!-- HDFS Capacity -->
+  <tr>
+    <td>{{t dashboard.services.hdfs.capacity}}</td>
+    <td>{{view.capacity}}</td>
+  </tr>
+  <!-- Blocks Total -->
+  <tr>
+    <td>{{t services.service.summary.blocksTotal}}</td>
+    <td>{{view.service.dfsTotalBlocks}}</td>
+  </tr>
+  <!-- Block Errors -->
+  <tr>
+    <td>{{t services.service.summary.blockErrors}}</td>
+    <td>
+      {{view.service.dfsCorruptBlocks}} corrupt / 
+      {{view.service.dfsMissingBlocks}} missing / 
+      {{view.service.dfsUnderReplicatedBlocks}} under replicated
+    </td>
+  </tr>
+  <!-- Total Files And Directories -->
+  <tr>
+    <td>{{t dashboard.services.hdfs.totalFilesAndDirs}}</td>
+    <td>{{view.service.dfsTotalFiles}}</td>
+  </tr>
+  <!-- Upgrade Status -->
+  <tr>
+    <td>{{t services.service.summary.pendingUpgradeStatus}}</td>
+    <td>
+      {{#if view.service.upgradeStatus}}
+        <div>Pending upgrade</div>
       {{else}}
-      <a href="#" {{action filterHosts component}}>{{component.displayName}}</a>
+        <div>No pending upgrade</div>
       {{/if}}
-      {{/each}}
     </td>
   </tr>
+  <!-- Safe Mode Status -->
+  <tr>
+    <td>{{t services.service.summary.safeModeStatus}}</td>
+    <td>{{view.service.safeModeStatus}}</td>
+  </tr>
   </tbody>
 </table>
 <div class="chart">

+ 33 - 15
ambari-web/app/views/main/dashboard/service/hdfs.js

@@ -24,37 +24,55 @@ App.MainDashboardServiceHdfsView = App.MainDashboardServiceView.extend({
 
   Chart:App.ChartPieView.extend({
     data:function () {
-      return [ this.get('_parentView.data.dfs_used_bytes') + this.get('_parentView.data.nondfs_used_bytes'), this.get('_parentView.data.dfs_free_bytes') ];
-    }.property('_parentView.data')
+      return [ this.get('_parentView.service.capacityUsed'), this.get('_parentView.service.capacityTotal') ];
+    }.property('_parentView.service')
   }),
 
   nodeUptime:function () {
-    var uptime = this.get('data.namenode_starttime');
-    var formatted = uptime.toDaysHoursMinutes();
+    var uptime = this.get('service').get('nameNodeStartTime');
+    var formatted = (new Date().getTime() - uptime).toDaysHoursMinutes();
     return this.t('dashboard.services.uptime').format(formatted.d, formatted.h, formatted.m);
-  }.property("data"),
+  }.property("service.nameNodeStartTime"),
+  
+  service: function(){
+    return App.HDFSService.find().objectAt(0);
+  }.property('App.router.clusterController.dataLoadList.services'),
+  
+  nodeWebUrl: function(){
+    return "http://"+this.get('service').get('nameNode').get('hostName')+":50070";
+  }.property('service.nameNode'),
 
   nodeHeap:function () {
 
     var percent = this.get('data.namenode_heap_total') > 0 ? 100 * this.get('data.namenode_heap_used') / this.get('data.namenode_heap_total') : 0;
 
     return this.t('dashboard.services.hdfs.nodes.heapUsed').format(
-      this.get('data.namenode_heap_used').bytesToSize(1, 'parseFloat'),
-      this.get('data.namenode_heap_total').bytesToSize(1, 'parseFloat')
+      (this.get('service').get('jvmMemoryHeapUsed')*1000000).bytesToSize(1, 'parseFloat'),
+      (this.get('service').get('jvmMemoryHeapCommitted')*1000000).bytesToSize(1, 'parseFloat')
       , percent.toFixed(1));
 
-  }.property('data'),
+  }.property('service'),
 
   summaryHeader:function () {
     var text = this.t("dashboard.services.hdfs.summary");
-    return text.format(this.get('data.live_nodes'), this.get('data.total_nodes'), this.get('data.dfs_percent_remaining'));
-  }.property('data'),
+    var svc = this.get('service');
+    var liveCount = svc.get('liveDataNodes').get('length');
+    var totalCount = svc.get('dataNodes').get('length');
+    var total = svc.get('capacityTotal') + 0;
+    var used = svc.get('capacityUsed') + 0;
+    var percentRemaining = (100-Math.round((used*100)/total)).toFixed(1);
+    return text.format(liveCount, totalCount, percentRemaining);
+  }.property('service'),
 
   capacity:function () {
     var text = this.t("dashboard.services.hdfs.capacityUsed");
-    var total = this.get('data.dfs_total_bytes') + 0;
-    var used = this.get('data.dfs_used_bytes') + this.get('data.nondfs_used_bytes');
-
-    return text.format(used.bytesToSize(1), total.bytesToSize(1), this.get('data.dfs_percent_used'));
-  }.property('data')
+    var total = this.get('service').get('capacityTotal') + 0;
+    var used = this.get('service').get('capacityUsed') + 0;
+    var percent = Math.round((used*100)/total).toFixed(1);
+    return text.format(used.bytesToSize(1), total.bytesToSize(1), percent);
+  }.property('service'),
+  
+  dataNodeComponent: function(){
+    return App.Component.find().findProperty('componentName', 'DATANODE');
+  }.property('components')
 });