玩轉Elasticsearch源碼-使用Intellij IDEA和remote debug調試源代碼

開篇

學習源碼第一步就是搭建調試環境,可是看了網上大部分Elasticsearch調試方式都是配置各類環境變量而後直接啓動Main方法,並且還各類報錯。今天提供新的方式--remote debug來避免這些麻煩。html

步驟

環境

首先要安裝jdk8,gradle和Intellij IDEAjava

源碼下載

拉取代碼,checkout到想要調試的版本(這裏切到v6.1.0,須要注意的是不一樣ES分支對gradle版本要求不同,能夠到README文件中查看對應到gradle版本要求)git

git clone git@github.com/elastic/elasticsearch
cd elasticsearch
git checkout v6.1.0

導入到IDEA

執行gradle idea,成功後會提示BUILD SUCCESSFUL,而後導入到IDEAgithub

:test:fixtures:hdfs-fixture:idea
:test:fixtures:krb5kdc-fixture:ideaModule
:test:fixtures:krb5kdc-fixture:idea
:test:fixtures:old-elasticsearch:ideaModule
:test:fixtures:old-elasticsearch:idea

BUILD SUCCESSFUL

Total time: 2 mins 2.159 secs

使用gradle啓動Elasticsearch

gradle run --debug-jvm

執行成功後是這樣的,其中8000就是遠程debug端口image.png架構

配置remote debug

點擊IDEA的Edit Configurations,再點擊➕image.png
填寫主機和端口,Name是配置名稱,能夠自定義(我這裏就填es),點OK保存配置image.png
搜一下源碼裏面Elasticsearch類,,看到Main方法,先打個斷點等會看效果image.png
最後再點下綠色小蟲子啓動debugimage.png
是否是在斷點停下來了image.png
跳過斷點再看下控制檯,是否是啓動日誌都出來了image.png
再驗證下是否啓動成功image.pngjvm

原理

一切源於被稱做 Agent 的東西。JVM有一種特性,能夠容許外部的庫(Java或C++寫的libraries)在運行時注入到 JVM 中。這些外部的庫就稱做 Agents, 他們有能力修改運行中 .class 文件的內容。
這些 Agents 擁有的這些 JVM 的功能權限, 是在 JVM 內運行的 Java Code 所沒法獲取的, 他們能用來作一些有趣的事情,好比修改運行中的源碼, 性能分析等。 像 JRebel 工具就是用了這些功能達到魔術般的效果。
傳遞一個 Agent Lib 給 JVM, 經過添加 agentlib:libname[=options] 格式的啓動參數便可辦到。像上面的遠程調試咱們用的就是 -agentlib:jdwp=... 來引入 jdwp 這個 Agent 的。
jdwp 是一個 JVM 特定的 JDWP(Java Debug Wire Protocol) 可選實現,用來定義調試者與運行JVM之間的通信,它的是經過 JVM 本地庫的 jdwp.so 或者 jdwp.dll 支持實現的。簡單來講, jdwp agent 會創建運行應用的 JVM 和調試者(本地或者遠程)之間的橋樑。既然他是一個Agent Library, 它就有能力攔截運行的代碼。
在 JVM 架構裏, debugging 功能在 JVM 自己的內部是找不到的,它是一種抽象到外部工具的方式(也稱做調試者 debugger)。這些調試工具或者運行在 JVM 的本地 或者在遠程。這是一種解耦,模塊化的架構。elasticsearch

關於Agent還有不少值得研究的細節,甚至基於JVMTI本身實現。參考https://www.ibm.com/developerworks/cn/java/j-lo-jpda2/index.htmlide

相關文章
相關標籤/搜索