zookeeper


一、zookeeper監控方式

根據官網介紹主要有兩種監控方式,
1:使用ssh建立遠程連接,然后使用"echo stat | nc ip port"命令返回結果。開源項目代表taokeeper。
2:使用JMX監控,文檔[http://zookeeper.apache.org/doc/r3.4.6/zookeeperJMX.html]
我們考慮使用JMX監控是因為運維不希望在服務器之間配置ssh連接,或者openSSH,服務器太多難以管理用戶密碼和公鑰,容易混亂。

二、zookeeper服務開啟JMX監控

修改zookeeper的啟動腳本vim zkServer.sh。找到啟動參數ZOOMAIN,修改為下面值。
其中local.only=false,設為false才能在遠程建立連接。

[java]  view plain  copy
 
  1. ZOOMAIN="-Dcom.sun.management.jmxremote  -Dcom.sun.management.jmxremote.local.only=false  
  2.  -Djava.rmi.server.hostname=127.0.0.1  
  3.  -Dcom.sun.management.jmxremote.port=9991  
  4.  -Dcom.sun.management.jmxremote.ssl=true  
  5.  -Dcom.sun.management.jmxremote.authenticate=true  
  6.  -Dcom.sun.management.jmxremote.access.file=/data/zookeeper/conf/jmxremote.access  
  7.  -Dcom.sun.management.jmxremote.password.file=/data/zookeeper/conf/jmxremote.password  
  8.  -Dzookeeper.jmx.log4j.disable=true  
  9.  org.apache.zookeeper.server.quorum.QuorumPeerMain"  

在/data/zookeeper/conf目錄下建立2個訪問授權文件, 修改文件權限chmod 600 jmxremote.*

[java]  view plain  copy
 
  1. -rw-------  1 deploy deploy  149 Aug  13:44 jmxremote.access  
  2. -rw-------  1 deploy deploy   40 Aug  13:46 jmxremote.password  
  3. [deploy@liutp conf]$ pwd  
  4. /data/zookeeper/conf  
  5. [deploy@liutp conf]$ cat jmxremote.access  
  6. monitorRole   readonly  
  7. controlRole   readwrite \  
  8.               create javax.management.monitor.*,javax.management.timer.* \  
  9.               unregister  
  10. [deploy@liutp conf]$ cat jmxremote.password  
  11. monitorRole  1234567  
  12. controlRole  1234567  
  13. [deploy@liutp conf]$  

關於權限文件內容的設置可以參考jdk里的文件:C:\Java\jdk1.7.0_79\jre\lib\management\jmxremote.password.template
重啟zk服務 :zkServer.sh restart /data/zookeeper/conf/zk1.cfg

三、使用Java自帶的JConsole

在命令行輸入JConsole,再回車。
在彈出的界面選擇“遠程進程”,輸入“服務器IP:9991”(zookeeper服務器的IP和端口)
用戶名:controlRole密碼:1234567就能查看節點數,連接數,watch數

一、背景

上一篇通過Java自帶的JConsole來獲取zookeeper狀態。主要有幾個不方便的地方,zk集群一般會部署3或者5台,在多個JConsole窗口中切換比較麻煩,各個zk服務及歷史數據之間,不能直觀比較。一般會做一個WEB管理頁面來展示集群狀態,設置報警閥值來做報警。

二、JVM平台提供Mbeans

在Java5.0以上版本,有一組API可以讓Java應用程序和允許的工具監視和管理Java虛擬機(JVM)和虛擬機所在的本機操作系統。該組API在 java.lang.management包。可以通過這些API可以監控local端JVM,同時也可以監控遠端JVM。
通過靜態工廠方法獲取MXBean實例,從本地訪問正在運行的虛擬機的MXBean接口。這些Bean我們從ManagementFactory類中定義的靜態方法獲取;如ManagementFactory.getOperatingSystemMXBean();其中不足就是只能獲取本地的JVM狀態。無法獲取遠程的虛擬機數據。

  • ClassLoadingMXBean Java虛擬機的類加載系統
  • CompilationMXBean Java虛擬機的編譯系統
  • MemoryMXBean Java虛擬機的內存系統
  • RuntimeMXBean Java虛擬機的運行時系統
  • OperatingSystemMXBean Java虛擬機在其上運行的操作系統
  • GarbageCollectorMXBean Java虛擬機中的垃圾回收器
  • MemoryManagerMXBean Java虛擬機中的內存管理器
  • MemoryPoolMXBean Java虛擬機中的內存池
三、Zookeeper提供出來的Mbeans

構造MXBean代理實例,通過代理將方法調用轉發到給定的MBeanServe。JConsole能夠監控的項目,通過API都能獲取到。
具體代碼如下:

[java]  view plain  copy
 
    1. import java.io.IOException;  
    2. import java.lang.management.ClassLoadingMXBean;  
    3. import java.lang.management.CompilationMXBean;  
    4. import java.lang.management.ManagementFactory;  
    5. import java.lang.management.OperatingSystemMXBean;  
    6. import java.lang.management.ThreadMXBean;  
    7. import java.util.ArrayList;  
    8. import java.util.Arrays;  
    9. import java.util.Collections;  
    10. import java.util.HashMap;  
    11. import java.util.Iterator;  
    12. import java.util.List;  
    13. import java.util.Map;  
    14. import java.util.Set;  
    15.   
    16. import javax.management.InstanceNotFoundException;  
    17. import javax.management.IntrospectionException;  
    18. import javax.management.JMX;  
    19. import javax.management.MBeanServerConnection;  
    20. import javax.management.MalformedObjectNameException;  
    21. import javax.management.ObjectName;  
    22. import javax.management.ReflectionException;  
    23. import javax.management.remote.JMXConnector;  
    24. import javax.management.remote.JMXConnectorFactory;  
    25. import javax.management.remote.JMXServiceURL;  
    26.   
    27. import org.apache.zookeeper.server.ConnectionMXBean;  
    28. import org.apache.zookeeper.server.DataTreeMXBean;  
    29. import org.apache.zookeeper.server.ZooKeeperServerMXBean;  
    30.   
    31. public class ZkJMXTest {  
    32.     static JMXConnector connector;  
    33.   
    34.     /** 
    35.      * @param args 
    36.      * @throws IOException 
    37.      * @throws MalformedObjectNameException 
    38.      * @throws InstanceNotFoundException 
    39.      * @throws ReflectionException 
    40.      * @throws IntrospectionException 
    41.      */  
    42.     public static void main(String[] args) throws IOException, MalformedObjectNameException,  
    43.         InstanceNotFoundException, IntrospectionException, ReflectionException {  
    44.   
    45.         OperatingSystemMXBean osbean = ManagementFactory.getOperatingSystemMXBean();  
    46.         System.out.println("體系結構:" + osbean.getArch());//操作系統體系結構  
    47.         System.out.println("處理器核數:" + osbean.getAvailableProcessors());///核數  
    48.         System.out.println("名字:" + osbean.getName());//名字  
    49.   
    50.         System.out.println(osbean.getVersion());//操作系統版本  
    51.         ThreadMXBean threadBean=ManagementFactory.getThreadMXBean();  
    52.         System.out.println("活動線程:" + threadBean.getThreadCount());//總線程數  
    53.   
    54.         ClassLoadingMXBean classLoadingMXBean = ManagementFactory.getClassLoadingMXBean();  
    55.         CompilationMXBean compilationMXBean = ManagementFactory.getCompilationMXBean();  
    56.         System.out.println("===========");  
    57.   
    58.         // 通過 MBeanServer間接地訪問 MXBean 接口  
    59.         MBeanServerConnection mbsc = createMBeanServer("192.168.1.100", "9991", "controlRole", "123456");  
    60.   
    61.         // 操作系統  
    62.         ObjectName os = new ObjectName("java.lang:type=OperatingSystem");  
    63.         System.out.println("體系結構:" + getAttribute(mbsc, os, "Arch"));//體系結構  
    64.         System.out.println("處理器核數:" + getAttribute(mbsc, os, "AvailableProcessors"));//核數  
    65.         System.out.println("總物理內存:" + getAttribute(mbsc, os, "TotalPhysicalMemorySize"));//總物理內存  
    66.         System.out.println("空閑物理內存:" + getAttribute(mbsc, os, "FreePhysicalMemorySize"));//空閑物理內存  
    67.         System.out.println("總交換空間:" + getAttribute(mbsc, os, "TotalSwapSpaceSize"));//總交換空間  
    68.         System.out.println("空閑交換空間:" + getAttribute(mbsc, os, "FreeSwapSpaceSize"));//空閑交換空間  
    69.   
    70.         System.out.println("操作系統:" + getAttribute(mbsc, os, "Name")+ getAttribute(mbsc, os, "Version"));//操作系統  
    71.         System.out.println("提交的虛擬內存:" + getAttribute(mbsc, os, "CommittedVirtualMemorySize"));//提交的虛擬內存  
    72.         System.out.println("系統cpu使用率:" + getAttribute(mbsc, os, "SystemCpuLoad"));//系統cpu使用率  
    73.         System.out.println("進程cpu使用率:" + getAttribute(mbsc, os, "ProcessCpuLoad"));//進程cpu使用率  
    74.   
    75.         System.out.println("============");//  
    76.         // 線程  
    77.         ObjectName Threading = new ObjectName("java.lang:type=Threading");  
    78.         System.out.println("活動線程:" + getAttribute(mbsc, Threading, "ThreadCount"));// 活動線程  
    79.         System.out.println("守護程序線程:" + getAttribute(mbsc, Threading, "DaemonThreadCount"));// 守護程序線程  
    80.         System.out.println("峰值:" + getAttribute(mbsc, Threading, "PeakThreadCount"));// 峰值  
    81.         System.out.println("啟動的線程總數:" + getAttribute(mbsc, Threading, "TotalStartedThreadCount"));// 啟動的線程總數  
    82.         ThreadMXBean threadBean2 = ManagementFactory.newPlatformMXBeanProxy  
    83.                 (mbsc, ManagementFactory.THREAD_MXBEAN_NAME, ThreadMXBean.class);  
    84.         System.out.println("活動線程:" + threadBean2.getThreadCount());// 活動線程  
    85.         ThreadMXBean threadBean3 = ManagementFactory.getThreadMXBean();  
    86.         System.out.println("本地活動線程:" + threadBean3.getThreadCount());// 本地活動線程  
    87.   
    88.         System.out.println("============");//  
    89.         ObjectName Compilation = new ObjectName("java.lang:type=Compilation");  
    90.         System.out.println("總編譯時間 毫秒:" + getAttribute(mbsc, Compilation, "TotalCompilationTime"));// 總編譯時間 毫秒  
    91.   
    92.         System.out.println("============");//  
    93.         ObjectName ClassLoading = new ObjectName("java.lang:type=ClassLoading");  
    94.         System.out.println("已加載類總數:" + getAttribute(mbsc, ClassLoading, "TotalLoadedClassCount"));// 已加載類總數  
    95.         System.out.println("已加裝當前類:" + getAttribute(mbsc, ClassLoading, "LoadedClassCount"));// 已加裝當前類  
    96.         System.out.println("已卸載類總數:" + getAttribute(mbsc, ClassLoading, "UnloadedClassCount"));// 已卸載類總數  
    97.   
    98.   
    99.         System.out.println("==========================================================");//  
    100.         // http://zookeeper.apache.org/doc/r3.4.6/zookeeperJMX.html  
    101.         // org.apache.ZooKeeperService:name0=ReplicatedServer_id1,name1=replica.1,name2=Follower  
    102.         ObjectName replica = new ObjectName("org.apache.ZooKeeperService:name0=ReplicatedServer_id1,name1=replica.1");  
    103.         System.out.println("replica.1運行狀態:" + getAttribute(mbsc, replica, "State"));// 運行狀態  
    104.   
    105.         mbsc = createMBeanServer("192.168.1.100", "9992", "controlRole", "123456");  
    106.         System.out.println("==============節點樹對象===========");  
    107.         ObjectName dataTreePattern = new ObjectName("org.apache.ZooKeeperService:name0=ReplicatedServer_id?,name1=replica.?,name2=*,name3=InMemoryDataTree");  
    108.         Set<ObjectName> dataTreeSets = mbsc.queryNames(dataTreePattern, null);  
    109.         Iterator<ObjectName> dataTreeIterator = dataTreeSets.iterator();  
    110.         // 只有一個  
    111.         while (dataTreeIterator.hasNext()) {  
    112.             ObjectName dataTreeObjectName = dataTreeIterator.next();  
    113.             DataTreeMXBean dataTree = JMX.newMBeanProxy(mbsc, dataTreeObjectName, DataTreeMXBean.class);  
    114.             System.out.println("節點總數:" + dataTree.getNodeCount());// 節點總數  
    115.             System.out.println("Watch總數:" + dataTree.getWatchCount());// Watch總數  
    116.             System.out.println("臨時節點總數:" + dataTree.countEphemerals());// Watch總數  
    117.             System.out.println("節點名及字符總數:" + dataTree.approximateDataSize());// 節點全路徑和值的總字符數  
    118.   
    119.             Map<String, String> dataTreeMap = dataTreeObjectName.getKeyPropertyList();  
    120.             String replicaId = dataTreeMap.get("name1").replace("replica.", "");  
    121.             String role = dataTreeMap.get("name2");// Follower,Leader,Observer,Standalone  
    122.             String canonicalName = dataTreeObjectName.getCanonicalName();  
    123.             int roleEndIndex = canonicalName.indexOf(",name3");  
    124.   
    125.             ObjectName roleObjectName = new ObjectName(canonicalName.substring(0, roleEndIndex));  
    126.             System.out.println("==============zk服務狀態===========");  
    127.             ZooKeeperServerMXBean ZooKeeperServer = JMX.newMBeanProxy(mbsc, roleObjectName, ZooKeeperServerMXBean.class);  
    128.             System.out.println(role + " 的IP和端口:" + ZooKeeperServer.getClientPort());// IP和端口  
    129.             System.out.println(role + " 活着的連接數:" + ZooKeeperServer.getNumAliveConnections());// 連接數  
    130.             System.out.println(role + " 未完成請求數:" + ZooKeeperServer.getOutstandingRequests());// 未完成的請求數  
    131.             System.out.println(role + " 接收的包:" + ZooKeeperServer.getPacketsReceived());// 收到的包  
    132.             System.out.println(role + " 發送的包:" + ZooKeeperServer.getPacketsSent());// 發送的包  
    133.             System.out.println(role + " 平均延遲(毫秒):" + ZooKeeperServer.getAvgRequestLatency());  
    134.             System.out.println(role + " 最大延遲(毫秒):" + ZooKeeperServer.getMaxRequestLatency());  
    135.   
    136.             System.out.println(role + " 每個客戶端IP允許的最大連接數:" + ZooKeeperServer.getMaxClientCnxnsPerHost());  
    137.             System.out.println(role + " 最大Session超時(毫秒):" + ZooKeeperServer.getMaxSessionTimeout());  
    138.             System.out.println(role + " 心跳時間(毫秒):" + ZooKeeperServer.getTickTime());  
    139.             System.out.println(role + " 版本:" + ZooKeeperServer.getVersion());// 版本  
    140.             // 三個重置操作  
    141. //            ZooKeeperServer.resetLatency(); //重置min/avg/max latency statistics  
    142. //            ZooKeeperServer.resetMaxLatency(); //重置最大延遲統計  
    143. //            ZooKeeperServer.resetStatistics(); // 重置包和延遲所有統計  
    144.   
    145.   
    146.             System.out.println("==============所有客戶端的連接信息===========");  
    147.             ObjectName connectionPattern = new ObjectName("org.apache.ZooKeeperService:name0=ReplicatedServer_id?,name1=replica.?,name2=*,name3=Connections,*");  
    148.             Set<ObjectName> connectionSets = mbsc.queryNames(connectionPattern, null);  
    149.             List<ObjectName> connectionList = new ArrayList<ObjectName>(connectionSets.size());  
    150.             connectionList.addAll(connectionSets);  
    151.             Collections.sort(connectionList);  
    152.             for (ObjectName connectionON : connectionList) {  
    153.                 System.out.println("=========================");  
    154.                 ConnectionMXBean connectionBean = JMX.newMBeanProxy(mbsc, connectionON, ConnectionMXBean.class);  
    155.                 System.out.println(" IP+Port:" + connectionBean.getSourceIP());//  
    156.                 System.out.println(" SessionId:" + connectionBean.getSessionId());//  
    157.                 System.out.println(" PacketsReceived:" + connectionBean.getPacketsReceived());// 收到的包  
    158.                 System.out.println(" PacketsSent:" + connectionBean.getPacketsSent());// 發送的包  
    159.                 System.out.println(" MinLatency:" + connectionBean.getMinLatency());//  
    160.                 System.out.println(" AvgLatency:" + connectionBean.getAvgLatency());//  
    161.                 System.out.println(" MaxLatency:" + connectionBean.getMaxLatency());//  
    162.                 System.out.println(" StartedTime:" + connectionBean.getStartedTime());//  
    163.                 System.out.println(" EphemeralNodes:" + connectionBean.getEphemeralNodes().length);//  
    164.                 System.out.println(" EphemeralNodes:" + Arrays.asList(connectionBean.getEphemeralNodes()));//  
    165.                 System.out.println(" OutstandingRequests:" + connectionBean.getOutstandingRequests());//  
    166.                   
    167.                 //connectionBean.resetCounters();  
    168.                 //connectionBean.terminateConnection();  
    169.                 //connectionBean.terminateSession();  
    170.             }  
    171.         }  
    172.         // close connection  
    173.         if (connector != null) {  
    174.             connector.close();  
    175.         }  
    176.     }  
    177.   
    178.     /** 
    179.      * 建立連接 
    180.      * 
    181.      * @param ip 
    182.      * @param jmxport 
    183.      * @return 
    184.      */  
    185.     public static MBeanServerConnection createMBeanServer(String ip,  
    186.             String jmxport, String userName, String password) {  
    187.         try {  
    188.             String jmxURL = "service:jmx:rmi:///jndi/rmi://" + ip + ":"  
    189.                     + jmxport + "/jmxrmi";  
    190.             // jmxurl  
    191.             JMXServiceURL serviceURL = new JMXServiceURL(jmxURL);  
    192.   
    193.             Map<String, String[]> map = new HashMap<String, String[]>();  
    194.             String[] credentials = new String[] { userName, password };  
    195.             map.put("jmx.remote.credentials", credentials);  
    196.             connector = JMXConnectorFactory.connect(serviceURL, map);  
    197.             MBeanServerConnection mbsc = connector.getMBeanServerConnection();  
    198.             return mbsc;  
    199.   
    200.         } catch (IOException ioe) {  
    201.             ioe.printStackTrace();  
    202.             System.err.println(ip + ":" + jmxport + " 連接建立失敗");  
    203.         }  
    204.         return null;  
    205.     }  
    206.   
    207.     /** 
    208.      * 使用MBeanServer獲取對象名為[objName]的MBean的[objAttr]屬性值 
    209.      * <p> 
    210.      * 靜態代碼: return MBeanServer.getAttribute(ObjectName name, String attribute) 
    211.      * 
    212.      * @param mbeanServer 
    213.      *            - MBeanServer實例 
    214.      * @param objName 
    215.      *            - MBean的對象名 
    216.      * @param objAttr 
    217.      *            - MBean的某個屬性名 
    218.      * @return 屬性值 
    219.      */  
    220.     private static String getAttribute(MBeanServerConnection mbeanServer,  
    221.             ObjectName objName, String objAttr) {  
    222.         if (mbeanServer == null || objName == null || objAttr == null)  
    223.             throw new IllegalArgumentException();  
    224.         try {  
    225.             return String.valueOf(mbeanServer.getAttribute(objName, objAttr));  
    226.         } catch (Exception e) {  
    227.             return null;  
    228.         }  
    229.     }  
    230. }  


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM