<%doc>

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.
</%doc>
<%args>
HMaster master;
HBaseAdmin admin;
Map<String, Integer> frags = null;
ServerName metaLocation = null;
List<ServerName> servers = null;
Set<ServerName> deadServers = null;
boolean catalogJanitorEnabled = true;
String filter = "general";
String format = "html";
ServerManager serverManager = null;
AssignmentManager assignmentManager = null;
</%args>
<%import>
java.util.*;
org.apache.hadoop.util.StringUtils;
org.apache.hadoop.hbase.util.Bytes;
org.apache.hadoop.hbase.util.JvmVersion;
org.apache.hadoop.hbase.util.FSUtils;
org.apache.hadoop.hbase.master.HMaster;
org.apache.hadoop.hbase.master.AssignmentManager;
org.apache.hadoop.hbase.master.ServerManager;
org.apache.hadoop.hbase.HConstants;
org.apache.hadoop.hbase.NamespaceDescriptor;
org.apache.hadoop.hbase.ServerLoad;
org.apache.hadoop.hbase.ServerName;
org.apache.hadoop.hbase.client.HBaseAdmin;
org.apache.hadoop.hbase.client.HConnectionManager;
org.apache.hadoop.hbase.HTableDescriptor;
org.apache.hadoop.hbase.HBaseConfiguration;
org.apache.hadoop.hbase.TableName;
org.apache.hadoop.hbase.protobuf.generated.HBaseProtos.SnapshotDescription;
org.apache.hadoop.hbase.master.DeadServer;
org.apache.hadoop.hbase.protobuf.ProtobufUtil;
</%import>
<%if format.equals("json") %>
  <& ../common/TaskMonitorTmpl; filter = filter; format = "json" &>
  <%java return; %>
</%if>
<%java>
ServerManager serverManager = master.getServerManager();
AssignmentManager assignmentManager = master.getAssignmentManager();
</%java>

<%class>
  public String formatZKString() {
    StringBuilder quorums = new StringBuilder();
    String zkQuorum = master.getZooKeeperWatcher().getQuorum();

    if (null == zkQuorum) {
      return quorums.toString();
    }

    String[] zks = zkQuorum.split(",");

    if (zks.length == 0) {
      return quorums.toString();
    }

    for(int i = 0; i < zks.length; ++i) {
      quorums.append(zks[i].trim()).append(",");

      if ((i+1) % 4 == 0 && i != (zks.length - 1)) {
        quorums.append("<br/>");
      }
    }

    quorums.setLength(quorums.length() - 1);
    return quorums.toString();
  }
</%class>

<!--[if IE]>
<!DOCTYPE html>
<![endif]-->
<?xml version="1.0" encoding="UTF-8" ?>
<html lang="en">
  <head>
    <meta charset="utf-8">
    <title>Master: <% master.getServerName().getHostname() %></title>
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta name="description" content="">
    <link href="/static/css/bootstrap.min.css" rel="stylesheet">
    <link href="/static/css/bootstrap-theme.min.css" rel="stylesheet">
    <link href="/static/css/hbase.css" rel="stylesheet">
  </head>

  <body>

    <div class="navbar  navbar-fixed-top navbar-default">
        <div class="container">
            <div class="navbar-header">
                <button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse">
                    <span class="icon-bar"></span>
                    <span class="icon-bar"></span>
                    <span class="icon-bar"></span>
                </button>
                <a class="navbar-brand" href="/master-status"><img src="/static/hbase_logo_small.png" alt="HBase Logo"/></a>
            </div>
            <div class="collapse navbar-collapse">
                <ul class="nav navbar-nav">
                <li class="active"><a href="/">Home</a></li>
                <li><a href="/tablesDetailed.jsp">Table Details</a></li>
                <li><a href="/logs/">Local logs</a></li>
                <li><a href="/logLevel">Log Level</a></li>
                <li><a href="/dump">Debug dump</a></li>
                <li><a href="/jmx">Metrics Dump</a></li>
                <%if HBaseConfiguration.isShowConfInServlet()%>
                <li><a href="/conf">HBase Configuration</a></li>
                </%if>
               </ul>
            </div><!--/.nav-collapse -->
        </div>
    </div>

    <div class="container">
	<%if master.isActiveMaster() %>
        <div class="row inner_header">
            <div class="page-header">
                <h1>Master <small><% master.getServerName().getHostname() %> </small></h1>
            </div>
        </div>

        <div class="row">
        <!-- Various warnings that cluster admins should be aware of -->
        <%if JvmVersion.isBadJvmVersion() %>
          <div class="alert alert-error">
          Your current JVM version <% System.getProperty("java.version") %> is known to be
          unstable with HBase. Please see the
          <a href="http://wiki.apache.org/hadoop/Hbase/Troubleshooting#A18">HBase wiki</a>
          for details.
          </div>
        </%if>
        <%if master.isInitialized() && !catalogJanitorEnabled %>
          <div class="alert alert-error">
          Please note that your cluster is running with the CatalogJanitor disabled. It can be
          re-enabled from the hbase shell by running the command 'catalogjanitor_switch true'
          </div>
        </%if>

        <section>
            <h2>Region Servers</h2>
            <& RegionServerListTmpl; master= master; servers = servers &>

            <%if (deadServers != null) %>
                <& deadRegionServers &>
            </%if>
        </section>
        <section>
            <& BackupMasterStatusTmpl; master = master &>
        </section>
        <section>
            <h2>Tables</h2>
            <div class="tabbable">
                <ul class="nav nav-pills">
                    <li class="active">
                        <a href="#tab_userTables" data-toggle="tab">User Tables</a>
                    </li>
                    <li class="">
                        <a href="#tab_catalogTables" data-toggle="tab">Catalog Tables</a>
                    </li>
                    <li class="">
                        <a href="#tab_userSnapshots" data-toggle="tab">Snapshots</a>
                    </li>
                </ul>
                <div class="tab-content" style="padding-bottom: 9px; border-bottom: 1px solid #ddd;">
                    <div class="tab-pane active" id="tab_userTables">
                        <%if (metaLocation != null) %>
                            <& userTables &>
                        </%if>
                    </div>
                    <div class="tab-pane" id="tab_catalogTables">
                        <%if (metaLocation != null) %>
                            <& catalogTables &>
                        </%if>
                    </div>
                    <div class="tab-pane" id="tab_userSnapshots">
                        <& userSnapshots &>
                    </div>
                </div>
            </div>
        </section>
        <& AssignmentManagerStatusTmpl; assignmentManager=master.getAssignmentManager()&>
	<%else>
        <section>
            <& BackupMasterStatusTmpl; master = master &>
        </section>
	</%if>    


        <section>
            <& ../common/TaskMonitorTmpl; filter = filter &>
        </section>

        <section>
            <h2>Software Attributes</h2>
            <table id="attributes_table" class="table table-striped">
                <tr>
                    <th>Attribute Name</th>
                    <th>Value</th>
                    <th>Description</th>
                </tr>
                <tr>
                    <td>HBase Version</td>
                    <td><% org.apache.hadoop.hbase.util.VersionInfo.getVersion() %>, r<% org.apache.hadoop.hbase.util.VersionInfo.getRevision() %></td><td>HBase version and revision</td>
                </tr>
                <tr>
                    <td>HBase Compiled</td>
                    <td><% org.apache.hadoop.hbase.util.VersionInfo.getDate() %>, <% org.apache.hadoop.hbase.util.VersionInfo.getUser() %></td>
                    <td>When HBase version was compiled and by whom</td>
                </tr>
                <tr>
                    <td>Hadoop Version</td>
                    <td><% org.apache.hadoop.util.VersionInfo.getVersion() %>, r<% org.apache.hadoop.util.VersionInfo.getRevision() %></td>
                    <td>Hadoop version and revision</td>
                </tr>
                <tr>
                    <td>Hadoop Compiled</td>
                    <td><% org.apache.hadoop.util.VersionInfo.getDate() %>, <% org.apache.hadoop.util.VersionInfo.getUser() %></td>
                    <td>When Hadoop version was compiled and by whom</td>
                </tr>
                <tr>
                    <td>Zookeeper Quorum</td>
                    <%escape #n>
                    <td> <% formatZKString() %> </td>
                    <td>Addresses of all registered ZK servers. For more, see <a href="/zk.jsp">zk dump</a>.</td>
                </tr>
                <tr>
                    <td>HBase Root Directory</td>
                    <td><% FSUtils.getRootDir(master.getConfiguration()).toString() %></td>
                    <td>Location of HBase home directory</td>
                </tr>
                <tr>
                    <td>HMaster Start Time</td>
                    <td><% new Date(master.getMasterStartTime()) %></td>
                    <td>Date stamp of when this HMaster was started</td>
                </tr>
                <%if master.isActiveMaster() %>
	                <tr>
	                    <td>HMaster Active Time</td>
	                    <td><% new Date(master.getMasterActiveTime()) %></td>
	                    <td>Date stamp of when this HMaster became active</td>
	                </tr>
	                <tr>
	                    <td>HBase Cluster ID</td>
	                    <td><% master.getClusterId() != null ? master.getClusterId() : "Not set" %></td>
	                    <td>Unique identifier generated for each HBase cluster</td>
	                </tr>
	                <tr>
	                    <td>Load average</td>
	                    <td><% StringUtils.limitDecimalTo2(master.getServerManager().getAverageLoad()) %></td>
	                    <td>Average number of regions per regionserver. Naive computation.</td>
	                </tr>
	                <%if frags != null %>
	                <tr>
	                    <td>Fragmentation</td>
	                    <td><% frags.get("-TOTAL-") != null ? frags.get("-TOTAL-").intValue() + "%" : "n/a" %></td>
	                    <td>Overall fragmentation of all tables, including hbase:meta</td>
	                </tr>
	                </%if>
	                <tr>
	                    <td>Coprocessors</td>
	                    <td><% java.util.Arrays.toString(master.getCoprocessors()) %></td>
	                    <td>Coprocessors currently loaded by the master</td>
	                </tr>
                </%if>
            </table>
        </section>
        </div>
    </div> <!-- /container -->

    <script src="/static/js/jquery.min.js" type="text/javascript"></script>
    <script src="/static/js/bootstrap.min.js" type="text/javascript"></script>
    <script src="/static/js/tab.js" type="text/javascript"></script>
  </body>
</html>

<%def catalogTables>
<%java>
 HTableDescriptor[] sysTables = admin.listTableDescriptorsByNamespace(NamespaceDescriptor
 .SYSTEM_NAMESPACE_NAME_STR);
</%java>

<table class="table table-striped">
<tr>
    <th>Table Name</th>
    <%if (frags != null) %>
        <th title="Fragmentation - Will be 0% after a major compaction and fluctuate during normal usage.">Frag.</th>
    </%if>
    <th>Description</th>
</tr>
<%for HTableDescriptor systemTable : sysTables%>
<tr>
<%java>TableName tableName = systemTable.getTableName();</%java>
    <td><a href="table.jsp?name=<% tableName %>"><% tableName %></a></td>
    <%if (frags != null)%>
        <td align="center"><% frags.get(tableName.getNameAsString()) != null ? frags.get(tableName.getNameAsString())
        .intValue() + "%" : "n/a" %></td>
    </%if>
    <%java>String description = null;
        if (tableName.equals(TableName.META_TABLE_NAME)){
            description = "The hbase:meta table holds references to all User Table regions";
        } else {
            description = "The .NAMESPACE. table holds information about namespaces.";
        }
    </%java>
    <td><% description %></td>
</tr>
</%for>
</table>
</%def>

<%def userTables>
<%java>
   HTableDescriptor[] tables = admin.listTables();
</%java>
<%if (tables != null && tables.length > 0)%>
<table class="table table-striped">
    <tr>
        <th>Table Name</th>
        <%if (frags != null) %>
            <th title="Fragmentation - Will be 0% after a major compaction and fluctuate during normal usage.">Frag.</th>
        </%if>
        <th>Online Regions</th>
        <th>Description</th>
    </tr>
    <%for HTableDescriptor htDesc : tables%>
    <tr>
        <td><a href=table.jsp?name=<% htDesc.getTableName().getNameAsString() %>><% htDesc.getTableName().getNameAsString() %></a> </td>
        <%if (frags != null) %>
            <td align="center"><% frags.get(htDesc.getTableName().getNameAsString()) != null ? frags.get(htDesc.getTableName().getNameAsString()).intValue() + "%" : "n/a" %></td>
        </%if>
        <td><% master.getAssignmentManager().getRegionStates().getRegionsOfTable(htDesc
        .getTableName()).size() %>
        <td><% htDesc.toStringCustomizedValues() %></td>
    </tr>
    </%for>
    <p><% tables.length %> table(s) in set. [<a href=tablesDetailed.jsp>Details</a>]</p>
</table>
</%if>
</%def>

<%def userSnapshots>
<%java>
   List<SnapshotDescription> snapshots = admin.listSnapshots();
</%java>
<%if (snapshots != null && snapshots.size() > 0)%>
<table class="table table-striped">
    <tr>
        <th>Snapshot Name</th>
        <th>Table</th>
        <th>Creation Time</th>
    </tr>
    <%for SnapshotDescription snapshotDesc : snapshots%>
    <%java>
        TableName snapshotTable = TableName.valueOf(snapshotDesc.getTable());
    </%java>
    <tr>
        <td><a href="snapshot.jsp?name=<% snapshotDesc.getName() %>"><% snapshotDesc.getName() %></a> </td>
        <td><a href="table.jsp?name=<% snapshotTable.getNameAsString() %>"><% snapshotTable.getNameAsString() %></a>
        </td>
        <td><% new Date(snapshotDesc.getCreationTime()) %></td>
    </tr>
    </%for>
    <p><% snapshots.size() %> snapshot(s) in set.</p>
</table>
</%if>
</%def>


<%def deadRegionServers>

<%if (deadServers != null && deadServers.size() > 0)%>
<h2>Dead Region Servers</h2>
<table class="table table-striped">
    <tr>
        <th></th>
        <th>ServerName</th>
        <th>Stop time</th>
    </tr>
    <%java>
       DeadServer deadServerUtil = master.getServerManager().getDeadServers();
       ServerName [] deadServerNames = deadServers.toArray(new ServerName[deadServers.size()]);
         Arrays.sort(deadServerNames);
         for (ServerName deadServerName: deadServerNames) {
    </%java>
    <tr>
    	<th></th>
        <td><% deadServerName %></td>
        <td><% deadServerUtil.getTimeOfDeath(deadServerName) %></td>
    </tr>
    <%java>
        }
    </%java>
    <tr>
        <th>Total: </th>
        <td>servers: <% deadServers.size() %></td>
        <th></th>
    </tr>
</table>
</%if>
<%java>
   HConnectionManager.deleteConnection(admin.getConfiguration());
</%java>
</%def>
