This is an automated email from the ASF dual-hosted git repository.

pifta pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/ozone.git


The following commit(s) were added to refs/heads/master by this push:
     new 4afa68e460 HDDS-7816. Add DataNode list to the SCM WebUI (#4289)
4afa68e460 is described below

commit 4afa68e4605dd3b0c9692877a1e9ddf85ce7a740
Author: debiswal <[email protected]>
AuthorDate: Mon Mar 6 19:28:20 2023 +0530

    HDDS-7816. Add DataNode list to the SCM WebUI (#4289)
---
 .../hadoop/hdds/scm/node/NodeManagerMXBean.java    |  7 +++
 .../hadoop/hdds/scm/node/SCMNodeManager.java       | 16 ++++++
 .../main/resources/webapps/scm/scm-overview.html   | 60 +++++++++++++++++-----
 .../src/main/resources/webapps/scm/scm.js          | 45 +++++++++++++++-
 .../hadoop/hdds/scm/container/MockNodeManager.java |  5 ++
 .../hdds/scm/container/SimpleMockNodeManager.java  |  5 ++
 .../testutils/ReplicationNodeManagerMock.java      |  5 ++
 7 files changed, 128 insertions(+), 15 deletions(-)

diff --git 
a/hadoop-hdds/server-scm/src/main/java/org/apache/hadoop/hdds/scm/node/NodeManagerMXBean.java
 
b/hadoop-hdds/server-scm/src/main/java/org/apache/hadoop/hdds/scm/node/NodeManagerMXBean.java
index c1c6d0d974..ff73ea2c14 100644
--- 
a/hadoop-hdds/server-scm/src/main/java/org/apache/hadoop/hdds/scm/node/NodeManagerMXBean.java
+++ 
b/hadoop-hdds/server-scm/src/main/java/org/apache/hadoop/hdds/scm/node/NodeManagerMXBean.java
@@ -20,6 +20,7 @@ package org.apache.hadoop.hdds.scm.node;
 
 import org.apache.hadoop.hdds.annotation.InterfaceAudience;
 
+import java.util.List;
 import java.util.Map;
 
 /**
@@ -42,4 +43,10 @@ public interface NodeManagerMXBean {
    */
   Map<String, Long> getNodeInfo();
 
+  /**
+   * @return Get the NodeStatus table information  like hostname,
+   * Commissioned State & Operational State column for dataNode
+   */
+  Map<String, List<String>> getNodeStatusInfo();
+
 }
diff --git 
a/hadoop-hdds/server-scm/src/main/java/org/apache/hadoop/hdds/scm/node/SCMNodeManager.java
 
b/hadoop-hdds/server-scm/src/main/java/org/apache/hadoop/hdds/scm/node/SCMNodeManager.java
index 791c53066f..fd1a1b699c 100644
--- 
a/hadoop-hdds/server-scm/src/main/java/org/apache/hadoop/hdds/scm/node/SCMNodeManager.java
+++ 
b/hadoop-hdds/server-scm/src/main/java/org/apache/hadoop/hdds/scm/node/SCMNodeManager.java
@@ -964,6 +964,22 @@ public class SCMNodeManager implements NodeManager {
     return nodeInfo;
   }
 
+  @Override
+  public Map<String, List<String>> getNodeStatusInfo() {
+    Map<String, List<String>> nodes = new HashMap<>();
+    for (DatanodeInfo dni : nodeStateManager.getAllNodes()) {
+      String hostName = dni.getHostName();
+      NodeStatus nodestatus = dni.getNodeStatus();
+      NodeState health = nodestatus.getHealth();
+      NodeOperationalState operationalState = nodestatus.getOperationalState();
+      List<String> ls = new ArrayList<>();
+      ls.add(health.name());
+      ls.add(operationalState.name());
+      nodes.put(hostName, ls);
+    }
+    return nodes;
+  }
+
   private enum UsageMetrics {
     DiskCapacity,
     DiskUsed,
diff --git 
a/hadoop-hdds/server-scm/src/main/resources/webapps/scm/scm-overview.html 
b/hadoop-hdds/server-scm/src/main/resources/webapps/scm/scm-overview.html
index ee5ac006bd..9521ea417f 100644
--- a/hadoop-hdds/server-scm/src/main/resources/webapps/scm/scm-overview.html
+++ b/hadoop-hdds/server-scm/src/main/resources/webapps/scm/scm-overview.html
@@ -28,25 +28,57 @@
     </tbody>
 </table>
 
-<h2>Node counts</h2>
-
-<table class="table table-bordered table-striped" class="col-md-6">
+<h2>Node Status</h2>
+<div class="row">
+    <div class="col-md-6 text-left">
+        <label>Show: </label>
+        <select class="form-select" ng-model="RecordsToDisplay" 
ng-change="UpdateRecordsToShow()">
+            <option value="10" ng-selected="{true}">10</option>
+            <option value="20">20</option>
+            <option value="50">50</option>
+            <option value="All">All</option>
+        </select>
+    </div>
+    <div class="col-md-6 text-right">
+        <label>Search: </label> <input type="text" ng-model="search">
+    </div>
+</div>
+<table class="table table-bordered table-striped col-md-6">
     <thead>
-    <tr>
-        <th class="col-md-3"></th>
-        <th>HEALTHY</th>
-        <th>STALE</th>
-        <th>DEAD</th>
-        <th>HEALTHY_READONLY</th>
-    </tr>
+        <tr>
+            <th ng-click = "columnSort('hostname')" 
class="nodeStausInfo"><span ng-class = "{'sorting' : (columnName != 
'hostname'), 'sortasc' : (columnName == 'hostname' && !reverse),
+                                        'sortdesc':(columnName == 'hostname' 
&& reverse)}">HostName</span></th>
+            <th ng-click = "columnSort('opstate')" class="nodeStausInfo" 
><span ng-class="{'sorting' : (columnName != 'opstate'), 'sortasc' : 
(columnName == 'opstate' && !reverse),
+                                        'sortdesc':(columnName == 'opstate' && 
reverse)}">Operational State</span></th>
+            <th ng-click = "columnSort('comstate')" class="nodeStausInfo">  
<span ng-class="{'sorting' : (columnName != 'comstate'), 'sortasc' : 
(columnName == 'comstate' && !reverse),
+                                        'sortdesc':(columnName == 'comstate' 
&& reverse)}">Commisioned State</span> </th>
+        </tr>
     </thead>
     <tbody>
-    <tr ng-repeat="nodeOpState in $ctrl.nodemanagermetrics.NodeCount | 
orderBy:'key':false:$ctrl.nodeOpStateOrder">
-        <td>{{nodeOpState.key}}</td>
-        <td ng-repeat="nodeState in nodeOpState.value | 
orderBy:'key':false:$ctrl.nodeStateOrder">{{nodeState.value}}</td>
-    </tr>
+        <tr ng-repeat="typestat in 
nodeStatus|filter:search|orderBy:columnName:reverse">
+            <td>{{typestat.hostname}}</td>
+            <td>{{typestat.opstate}}</td>
+            <td>{{typestat.comstate}}</td>
+        </tr>
     </tbody>
 </table>
+<div>
+    <nav aria-label="...">
+        <ul class="pagination">
+            <li class="page-item" ng-class="{disabled:currentPage==1}"
+                ng-click="handlePagination(currentPage-1,(currentPage==1))">
+                <span class="page-link" tabindex="-1">Previous</span>
+            </li>
+            <li class="page-item active">
+                <span class="page-link">{{currentPage}} </span>
+            </li>
+            <li class="page-item" ng-class="{disabled:lastIndex==currentPage}"
+                ng-click="handlePagination(currentPage+1, 
(lastIndex==currentPage))">
+                <span class="page-link" tabindex="-1">Next</span>
+            </li>
+        </ul>
+    </nav>
+</div>
 
 <h2>Status</h2>
 <table class="table table-bordered table-striped" class="col-md-6">
diff --git a/hadoop-hdds/server-scm/src/main/resources/webapps/scm/scm.js 
b/hadoop-hdds/server-scm/src/main/resources/webapps/scm/scm.js
index 9653838f94..794c57dc4a 100644
--- a/hadoop-hdds/server-scm/src/main/resources/webapps/scm/scm.js
+++ b/hadoop-hdds/server-scm/src/main/resources/webapps/scm/scm.js
@@ -24,12 +24,55 @@
         require: {
             overview: "^overview"
         },
-        controller: function ($http) {
+        controller: function ($http,$scope) {
             var ctrl = this;
+            $scope.reverse = false;
+            $scope.columnName = "hostname";
+            let nodeStatusCopy = [];
+            $scope.RecordsToDisplay = "10";
+            $scope.currentPage = 1;
+            $scope.lastIndex = 0;
+
             
$http.get("jmx?qry=Hadoop:service=SCMNodeManager,name=SCMNodeManagerInfo")
                 .then(function (result) {
                     ctrl.nodemanagermetrics = result.data.beans[0];
+                    $scope.nodeStatus = ctrl.nodemanagermetrics && 
ctrl.nodemanagermetrics.NodeStatusInfo &&
+                    ctrl.nodemanagermetrics.NodeStatusInfo.map(({ key, value 
}) => {
+                                return {
+                                    hostname: key,
+                                    opstate: value[0],
+                                    comstate: value[1]
+                                }});
+                    nodeStatusCopy = [...$scope.nodeStatus];
+                    $scope.lastIndex = Math.ceil(nodeStatusCopy.length / 
$scope.RecordsToDisplay);
+                    $scope.nodeStatus = nodeStatusCopy.slice(0, 
$scope.RecordsToDisplay);
                 });
+            /*if option is 'All' display all records else display specified 
record on page*/
+            $scope.UpdateRecordsToShow = () => {
+                 if($scope.RecordsToDisplay == 'All') {
+                     $scope.lastIndex = 1;
+                     $scope.nodeStatus = nodeStatusCopy;
+                 } else {
+                     $scope.lastIndex = Math.ceil(nodeStatusCopy.length / 
$scope.RecordsToDisplay);
+                     $scope.nodeStatus = nodeStatusCopy.slice(0, 
$scope.RecordsToDisplay);
+                 }
+                 $scope.currentPage = 1;
+            }
+            /* Page Slicing  logic */
+            $scope.handlePagination = (pageIndex, isDisabled) => {
+                if(!isDisabled) {
+                    let startIndex = 0, endIndex = 0;
+                    $scope.currentPage = pageIndex;
+                    startIndex = (pageIndex * $scope.RecordsToDisplay) - 
$scope.RecordsToDisplay;
+                    endIndex = startIndex + parseInt($scope.RecordsToDisplay);
+                    $scope.nodeStatus = nodeStatusCopy.slice(startIndex, 
endIndex);
+                }
+            }
+             /*column sort logic*/
+            $scope.columnSort = (colName) => {
+                $scope.columnName = colName;
+                $scope.reverse = !$scope.reverse;
+            }
 
             const nodeOpStateSortOrder = {
                 "IN_SERVICE": "a",
diff --git 
a/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/hdds/scm/container/MockNodeManager.java
 
b/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/hdds/scm/container/MockNodeManager.java
index e1eaf251f5..ddd7ce86bf 100644
--- 
a/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/hdds/scm/container/MockNodeManager.java
+++ 
b/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/hdds/scm/container/MockNodeManager.java
@@ -802,6 +802,11 @@ public class MockNodeManager implements NodeManager {
     return nodeInfo;
   }
 
+  @Override
+  public Map<String, List<String>> getNodeStatusInfo() {
+    return null;
+  }
+
   /**
    * Makes it easy to add a container.
    *
diff --git 
a/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/hdds/scm/container/SimpleMockNodeManager.java
 
b/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/hdds/scm/container/SimpleMockNodeManager.java
index 4a4afac4f4..a692f6d924 100644
--- 
a/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/hdds/scm/container/SimpleMockNodeManager.java
+++ 
b/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/hdds/scm/container/SimpleMockNodeManager.java
@@ -372,6 +372,11 @@ public class SimpleMockNodeManager implements NodeManager {
     return null;
   }
 
+  @Override
+  public Map<String, List<String>> getNodeStatusInfo() {
+    return null;
+  }
+
   @Override
   public void onMessage(CommandForDatanode commandForDatanode,
                         EventPublisher publisher) {
diff --git 
a/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/ozone/container/testutils/ReplicationNodeManagerMock.java
 
b/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/ozone/container/testutils/ReplicationNodeManagerMock.java
index 436bccb09d..3e7c3ccc63 100644
--- 
a/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/ozone/container/testutils/ReplicationNodeManagerMock.java
+++ 
b/hadoop-hdds/server-scm/src/test/java/org/apache/hadoop/ozone/container/testutils/ReplicationNodeManagerMock.java
@@ -86,6 +86,11 @@ public class ReplicationNodeManagerMock implements 
NodeManager {
     return null;
   }
 
+  @Override
+  public Map<String, List<String>> getNodeStatusInfo() {
+    return null;
+  }
+
   /**
    * Gets all Live Datanodes that is currently communicating with SCM.
    *


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to