遠端偵錯對應用程式開發十分有用。例如,為不能託管開發平台的低端機器開發程式,或在專用的機器上(比如服務不能中斷的 Web 服務器)偵錯工具。其他情況包括:運行在記憶體小或 CUP 效能低的裝置上的 Java 應用程式(比如行動裝置),或者開發人員想要將應用程式和開發環境分開,等等。
為了進行遠端偵錯,必須使用 Java Virtual Machine (JVM) V5.0 或更新版本。
JPDA 簡介
Sun Microsystem 的 Java Platform Debugger Architecture (JPDA) 技術是一個多層架構,使您能夠在各種環境中輕鬆調試 Java 應用程式。JPDA 由兩個介面(分別是 JVM Tool Interface 和 JDI)、一個協議(Java Debug Wire Protocol)和兩個用於合并它們的軟體組件(後端和前端)組成。它的設計目的是讓調試人員在任何環境中都可以進行調試。
更詳細的介紹,您可以參考使用 Eclipse 遠端偵錯 Java 應用程式
JDWP 設定
JVM本身就支援遠端偵錯,Eclipse也支援JDWP,只需要在各模組的JVM啟動時載入以下參數:
-Xdebug -Xrunjdwp:transport=dt_socket, address=8000,server=y,suspend=y
各參數的含義:
-Xdebug啟用調試特性-Xrunjdwp啟用JDWP實現,包含若干子選項:transport=dt_socketJPDA front-end和back-end之間的傳輸方法。dt_socket表示使用通訊端傳輸。address=8000JVM在8000連接埠上監聽請求,這個設定為一個不衝突的連接埠即可。server=yy表示啟動的JVM是被調試者。如果為n,則表示啟動的JVM是調試器。suspend=yy表示啟動的JVM會暫停等待,直到調試器串連上才繼續執行。suspend=n,則JVM不會暫停等待。
配置hbase遠端偵錯
開啟/etc/hbase/conf/hbase-env.sh,找到以下內容:
# Enable remote JDWP debugging of major HBase processes. Meant for Core Developers # export HBASE_MASTER_OPTS="$HBASE_MASTER_OPTS -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=8070"# export HBASE_REGIONSERVER_OPTS="$HBASE_REGIONSERVER_OPTS -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=8071"# export HBASE_THRIFT_OPTS="$HBASE_THRIFT_OPTS -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=8072"# export HBASE_ZOOKEEPER_OPTS="$HBASE_ZOOKEEPER_OPTS -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=8073"
如果想遠程調式hbase-master進程,請去掉對HBASE_MASTER_OPTS的注釋,其他依次類推。注意,我這裡使用的是cdh-4.3.0中的hbase。
配置hive遠端偵錯
停止hive-server2進程,然後以下面命令啟動hive-server2
hive --service hiveserver --debug
進程會監聽在8000連接埠等待調試串連。如果想更改監聽連接埠,可以修改設定檔:${HIVE_HOME}bin/ext/debug.sh
如果Hadoop是0.23以上版本,debug模式啟動Cli會報錯:
ERROR: Cannot load this JVM TI agent twice, check your java command line for duplicate jdwp options.
開啟${Hadoop_HOME}/bin/hadoop,注釋掉以下代碼
# Always respect HADOOP_OPTS and HADOOP_CLIENT_OPTSHADOOP_OPTS="$HADOOP_OPTS $HADOOP_CLIENT_OPTS"
配置yarn遠端偵錯
請在以下代碼添加調試參數:
if [ "$COMMAND" = "classpath" ] ; thenif $cygwin; thenCLASSPATH=`cygpath -p -w "$CLASSPATH"`fiecho $CLASSPATHexitelif [ "$COMMAND" = "rmadmin" ] ; thenCLASS='org.apache.hadoop.yarn.client.RMAdmin'YARN_OPTS="$YARN_OPTS $YARN_CLIENT_OPTS"elif [ "$COMMAND" = "application" ] ; thenclass="org".apache.hadoop.yarn.client.cli.ApplicationCLIYARN_OPTS="$YARN_OPTS $YARN_CLIENT_OPTS"elif [ "$COMMAND" = "node" ] ; thenclass="org".apache.hadoop.yarn.client.cli.NodeCLIYARN_OPTS="$YARN_OPTS $YARN_CLIENT_OPTS"elif [ "$COMMAND" = "resourcemanager" ] ; thenCLASSPATH=${CLASSPATH}:$YARN_CONF_DIR/rm-config/log4j.propertiesCLASS='org.apache.hadoop.yarn.server.resourcemanager.ResourceManager'YARN_OPTS="$YARN_OPTS $YARN_RESOURCEMANAGER_OPTS"if [ "$YARN_RESOURCEMANAGER_HEAPSIZE" != "" ]; thenJAVA_HEAP_MAX="-Xmx""$YARN_RESOURCEMANAGER_HEAPSIZE""m"fielif [ "$COMMAND" = "nodemanager" ] ; thenCLASSPATH=${CLASSPATH}:$YARN_CONF_DIR/nm-config/log4j.propertiesCLASS='org.apache.hadoop.yarn.server.nodemanager.NodeManager'YARN_OPTS="$YARN_OPTS -server $YARN_NODEMANAGER_OPTS"if [ "$YARN_NODEMANAGER_HEAPSIZE" != "" ]; thenJAVA_HEAP_MAX="-Xmx""$YARN_NODEMANAGER_HEAPSIZE""m"fielif [ "$COMMAND" = "proxyserver" ] ; thenCLASS='org.apache.hadoop.yarn.server.webproxy.WebAppProxyServer'YARN_OPTS="$YARN_OPTS $YARN_PROXYSERVER_OPTS"if [ "$YARN_PROXYSERVER_HEAPSIZE" != "" ]; thenJAVA_HEAP_MAX="-Xmx""$YARN_PROXYSERVER_HEAPSIZE""m"fi
例如: 如果你想調試resourcemanager代碼,請在elif [ "$COMMAND" = "resourcemanager" ] 分支內添加如下代碼:
YARN_RESOURCEMANAGER_OPTS="$YARN_RESOURCEMANAGER_OPTS -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=6001"
其他進程,參照上面即可。
注意:連接埠不要衝突。
配置mapreduce遠端偵錯
如果想要調試Map 或Reduce Task,則修改bin/hadoop已經沒用了,因為bin/hadoop中沒有Map Task的啟動參數。
此時需要修改mapred-site.xml
<property> <name>mapred.child.java.opts</name> <value>-Xmx800m -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=8000</value> </property
在一個TaskTracker上,只能啟動一個Map Task或一個Reduce Task,否則啟動時會有連接埠衝突。因此要修改所有TaskTracker上的conf/hadoop-site.xml中的配置項:
<property> <name>mapred.tasktracker.map.tasks.maximum</name> <value>1</value></property><property> <name>mapred.tasktracker.reduce.tasks.maximum</name> <value>0</value></property>
在Eclipse中使用方法:
開啟eclipse,找到Debug Configurations...,添加一個Remout Java Application:
在source中可以關聯到hive的原始碼,然後,單擊Debug按鈕進入遠程debug模式。
編寫個jdbc的測試類別,運行代碼,這時候因為hive-server2端沒有設定端點,故程式可以正常運行直到結束。
在hive代碼中設定一個斷點,如ExecDriver.java的execute方法中設定斷點,然後再運行jdbc測試類別。
參考文章
- 在Eclipse中遠端偵錯Hadoop
- hive遠端偵錯
- 使用 Eclipse 遠端偵錯 Java 應用程式