天天看點

“龍井”開箱評測 |Alibaba Dragonwell 新手上路指南Alibaba Dragonwell 8 介紹安裝 Alibaba Dragonwell 8使用  Alibaba Dragonwell 8 專有特性參與Alibaba Dragonwell 社群建設參考連結

“龍井”開箱評測 |Alibaba Dragonwell 新手上路指南Alibaba Dragonwell 8 介紹安裝 Alibaba Dragonwell 8使用  Alibaba Dragonwell 8 專有特性參與Alibaba Dragonwell 社群建設參考連結

作者|阿裡雲智能事業群 進階技術專家 陸傳勝

阿裡巴巴有着最豐富的 Java 應用場景,覆寫電商,金融,物流等衆多領域,是世界上最大的 Java 使用者之一。 2019 年 3 月 21 日,阿裡巴巴在北京阿裡雲峰會上正式宣布開源了 Alibaba Dragonwell 8 産品,并建立了 Alibaba Dragonwell 社群來為全球 Java 使用者,特别是中文社群的 Java 使用者提供長期支援的 JDK 産品。自宣布開源以來,Alibaba Dragonwell 8 受到了國内外 Java 開發者的關注,今天這篇文章就來詳解 Alibaba Dragonwell8 的快速安裝和使用,同時列出了參與社群建設的幾種方式,期望為那些即将安裝及使用 Alibaba Dragonwell 8 的開發者提供參考。

Alibaba Dragonwell 8 介紹

Alibaba Dragonwell 8 是一款免費的 OpenJDK 發行版。它提供長期支援,包括性能增強和安全修複。Alibaba Dragonwell 8 目前支援 X86-64/Linux 平台,在資料中心大規模 Java 應用部署情況下, 可以大幅度提高穩定性、效率以及性能。Alibaba Dragonwell 8 是 OpenJDK 的下遊(friendly fork),使用了和 OpenJDK 一樣的 licensing。Alibaba Dragonwell 8 與 Java SE 标準相容,使用者可以使用 Alibaba Dragonwell 8 開發和運作 Java 應用程式。此次開源的 Alibaba Dragonwell 8 是阿裡巴巴内部 OpenJDK 定制版 AJDK 的開源版本, AJDK 為線上電商,金融,物流做了結合業務場景的優化,運作在超大規模的,100,000+ 伺服器的阿裡巴巴資料中心。

安裝 Alibaba Dragonwell 8

目前 Alibaba Dragonwell 8 隻支援 Linux x86-64 平台,并且提供了二進制的預編譯 JDK 包,您可以通過下面的簡單兩步安裝 Alibaba Dragonwell 8。

  • 從 Github 上面 Alibaba Dragonwell 8 項目的下載下傳頁面下載下傳預編譯的二進制 JDK 包。

    下載下傳頁面連結 

    https://github.com/alibaba/dragonwell8/releases
  • 将下載下傳下來的 tar 包解壓到目标安裝目錄即可。

安裝完畢後,隻需要将應用引用 的 JAVA_HOME 指向 Alibaba Dragonwell 8 的安裝目錄就可以使用了。我們以Tomcat8.5.39 版本為例,為了讓 Tomcat 運作在 Alibaba Dragonwell 8上面,隻需要在啟動Tomcat時使用如下指令:

JAVA_HOME=/path/to/dragonwell8/installation  sh tomcat/bin/catalina.sh start           

為了确認是運作在 Alibaba Dragonwell 8上面,可以進一步通過給 java 指令添加 

-showversion

 參數來列印 JDK 版本資訊加以判斷。

JAVA_HOME=/path/to/dragonwell8/installation JAVA_OPTS="-showversion" sh tomcat/bin/catalina.sh start           

啟動完畢後在 tomcat/logs/catalina.out 檔案的開頭,可以看到  Alibaba Dragonwell 8 的版本資訊

“龍井”開箱評測 |Alibaba Dragonwell 新手上路指南Alibaba Dragonwell 8 介紹安裝 Alibaba Dragonwell 8使用  Alibaba Dragonwell 8 專有特性參與Alibaba Dragonwell 社群建設參考連結

使用  Alibaba Dragonwell 8 專有特性

在 8.0-preview 這個版本中, Alibaba Dragonwell 8 提供了兩個在阿裡巴巴的生産環境中進行過廣泛驗證的特性:JWarmUp 和 Java Flight Recorder。這兩個特性都已經在上遊 OpenJDK 社群送出了 JEP 或 patch,在上遊合并完成之前,我們希望讓 Alibaba  Dragonwell 8 的使用者可以提前使用到這兩個特性。

JWarmUp 快速預熱 Java 應用

OpenJDK 使用了 JIT(Just-in-time) 即時編譯技術,可以動态的把 Java 位元組碼編譯成高度優化過機器碼,提高執行效率,但在編譯之前,Java 代碼是以相對低效的解釋器模式執行的。

在應用啟動完成後、業務流量剛進來的短時間内,容易出現的狀況是大量 Java 方法開始被 JIT 編譯,同時業務請求被較慢的解釋器模式執行,最終的結果就是系統負載飙高,可能導緻很多使用者請求逾時。為了解決這個問題,之前的很多做法是使用模拟流量來提前預熱應用,JWarmUp 特性提供了一個新的選擇,就是利用 Java 虛拟機前一次執行編譯得記錄來預熱本次應用的執行。

JWarmUp 的原理如下圖所示:

“龍井”開箱評測 |Alibaba Dragonwell 新手上路指南Alibaba Dragonwell 8 介紹安裝 Alibaba Dragonwell 8使用  Alibaba Dragonwell 8 專有特性參與Alibaba Dragonwell 社群建設參考連結

一個典型的應用場景是當應用需要釋出新版本的時候,

  • 首先 JWarmUp 在 Beta 環境(或者有着和生産環境類似流量的其他場景)的單台機器上短時間執行 Java 應用,并記錄、收集這段時間裡面 JIT 編譯器所做動作的一些中繼資料。
  • 然後會把這些中繼資料複制到生産環境的每一台包含了新版本代碼的機器/容器裡面。
  • 最後在生産環境機器中通過 JWarmUp 參數加載 beta 環境生成的中繼資料,來指導生産環境的機器在啟動應用的過程中就完成 JIT 預熱。

這樣當使用者請求進入的時候,應用就會處于性能最高的峰值狀态。

收集預熱資料

還以 Tomcat 應用為例,可以添加下面的指令行參數來在 beta 環境中收集 JIT 編譯時生成的中繼資料,其中參數 

-XX:CompilationWarmUpLogfile=

 指定的就是生成的 JWarmUp 檔案的路徑。

JAVA_HOME=/path/to/dragonwell8/installation JAVA_OPTS="-XX:ReservedCodeCacheSize=512m -XX:CompilationWarmUpLogfile=$PWD/jwarmup.log -XX:+CompilationWarmUpRecording -XX:+CompilationWarmUp -XX:-TieredCompilation -XX:+DeoptimizeBeforeWarmUp -XX:CompilationWarmUpDeoptTime=30 -XX:+PrintCompilationWarmUpDetail" sh bin/catalina.sh start           

生成之後可以把這個檔案通過 OSS、SFTP 等方式傳輸到生産環境的機器上。

使用記錄的資料來預熱 Java 應用

在生産環境的機器上,隻需要使用下面的參數,就可以利用之前的預熱資料來啟動一個新的 Tomcat 執行個體,其中參數  

-XX:CompilationWarmUpLogfile=

  制定的就是需要被加載的 JWarmUp 檔案路徑,這個檔案應該是上一步收集預熱資料時從 beta 環境複制過來的。

JAVA_HOME=/path/to/dragonwell8/installation JAVA_OPTS="-XX:ReservedCodeCacheSize=512m -XX:CompilationWarmUpLogfile=$PWD/jwarmup.log -XX:+CompilationWarmUp -XX:-TieredCompilation -XX:+DeoptimizeBeforeWarmUp   -XX:CompilationWarmUpDeoptTime=30 -XX:+PrintCompilationWarmUpDetail" sh bin/catalina.sh start           

使用 Java Flight Recorder 分析 Java 應用性能

JFR(Java Flight Recorder)是 JVM 内置的基于事件的性能分析特性,這是 Oracle JDK7u4 版本開始提供的商業特性,2018 年的時候在 JDK11 上開源了這個特性,但是一直沒有針對 JDK8 版本的支援。

阿裡巴巴和 RedHat、Azul、Amazon 等公司一起合作嘗試把這個特性移植回 JDK8上,不過該 patch 暫時還沒有合并回 OpenJDK8u倉庫,我們在 Alibaba Dragonwell 8 中提供了 Alibaba 移植的 JFR 版本,用于幫助使用者提前擷取這方面的支援。

JFR 的用法很簡單,使用者使用指令行參數或者 jcmd 指令控制 HotSpot 輸出性能資料到檔案中,然後就能使用開源的 jmc 工具在圖形界面中打開、分析生成的資料檔案了。

使用 JFR 收集性能資料

在  Alibaba Dragonwell 8中,預設情況下 JFR 特性是處于關閉的狀态,必須添加指令行參數 

-XX:+EnableJFR

 來允許使用 JFR 特性。 Alibaba Dragonwell 8 提供了不同的方式來使用 JFR 采集性能資料。

應用可以可以通過指令行參數指定 JFR 再啟動後立馬開始采集資料,這個對于診斷啟動階段的問題會很有幫助。下面的示例指令會在 Java 程序的 JFR 子產品初始化後就開始收集 JFR 資料,持續一分鐘,并且把資料都輸出到名為rec.jfr 的檔案中。

JAVA_HOME=/path/to/dragonwell8/installation JAVA_OPTS="-XX:+EnableJFR -XX:StartFlightRecording=duration=1m,filename=rec.jfr" sh bin/catalina.sh start           

應用也可以隻添加 

-XX:+EnableJFR

 ,然後通過 

jcmd

 指令在應用啟動後的任意時間點開始采集資料,這種情況更加靈活可控,可以滿足随時随地進行分析的需求。

以 Tomcat 為例,啟動 Tomcat 的指令可以是:

JAVA_HOME=/path/to/dragonwell8/installation JAVA_OPTS="-XX:+EnableJFR" sh bin/catalina.sh start           

當需要收集資料進行分析時,隻需要使用目标 Tomcat 程序的 PID 來執行 JFR 對應的 jcmd 指令即可。以 Tomcat 為例,如果需要在指定時刻開始收集 10 秒的資料,那麼觸發的指令如下:

$ ps ax | grep tomcat
 77522 pts/18   Sl+    0:08 /home/chuansheng.lcs/dw_test/apache-tomcat-8.5.39/../j2sdk-image/bin/java -Djava.util.logging.config.file=/home/chuansheng.lcs/dw_test/apache-tomcat-8.5.39/conf/logging.properties -Djava.util.logging.manager=org.apache.juli.ClassLoaderLogManager -XX:+EnableJFR -Djdk.tls.ephemeralDHKeySize=2048 -Djava.protocol.handler.pkgs=org.apache.catalina.webresources -Dorg.apache.catalina.security.SecurityListener.UMASK=0027 -Dignore.endorsed.dirs= -classpath /home/chuansheng.lcs/dw_test/apache-tomcat-8.5.39/bin/bootstrap.jar:/home/chuansheng.lcs/dw_test/apache-tomcat-8.5.39/bin/tomcat-juli.jar -Dcatalina.base=/home/chuansheng.lcs/dw_test/apache-tomcat-8.5.39 -Dcatalina.home=/home/chuansheng.lcs/dw_test/apache-tomcat-8.5.39 -Djava.io.tmpdir=/home/chuansheng.lcs/dw_test/apache-tomcat-8.5.39/temp org.apache.catalina.startup.Bootstrap start
 98451 pts/22   S+     0:00 grep --color=auto tomcat

$ dragonwell8_home/bin/jcmd 77522 JFR.start duration=10s filename=$PWD/rec3.jfr
77522:
Started recording 3. The result will be written to:

/home/my/workdir/rec3.jfr           

10 秒之後可以看到生成了 JFR 資料檔案/home/my/workdir/rec3.jfr,使用 JMC 即可進行分析。

也可以不指定收集資料的時間,直接啟動 JFR 收集,并且在需要的時候手動把所有生成的資料一次性 dump 到檔案,

$ dragonwell8_home/bin/jcmd 2823 JFR.start filename=$PWD/rec4.jfr
2823:
Started recording 4. No limit specified, using maxsize=250MB as default.

Use JFR.dump name=4 to copy recording data to file.

$ dragonwell8_home/bin/jcmd 2823 JFR.dump name=4 filename=rec4.jfr
2823:
Dumped recording "Recording-4", 332.7 kB written to:

/path/to/my/workdir/rec4.jfr           

使用 JMC 分析性能

JFR 記錄 Java  應用性能資料的輸出是一個二進制的檔案,我們借助于 JMC(Java Mission Control) 工具可以在圖形化界面裡面分析具體的性能資料。這個工具是開源産品,沒有包括在 Alibaba Dragonwell 8裡面,需要到 OpenJDK 的官方網站下載下傳使用,

https://jdk.java.net/jmc/

請注意, Alibaba Dragonwell8 生成的JFR資料檔案需要 7.0 或更高版本的 JMC 工具來分析。

打開 JMC 後,可以點選左側的詳細類别來詳細分析采樣時間段内發生的各種事件。

“龍井”開箱評測 |Alibaba Dragonwell 新手上路指南Alibaba Dragonwell 8 介紹安裝 Alibaba Dragonwell 8使用  Alibaba Dragonwell 8 專有特性參與Alibaba Dragonwell 社群建設參考連結

診斷調試支援

 Alibaba Dragonwell 8 還内置一些友善的診斷特性,主要包括

大對象配置設定報警

可以通過新的 JVM 參數"-XX:ArrayAllocationWarningSize=",比如下面代碼中配置設定了比較大的數組

public static void main(String[] args) {
    doAlloc(32 * 1024 * 1024 + 1);
}
private static Object doAlloc(int size) {
    return new byte[size];
}           

執行時如果添加 ArrayAllocationWarningSize 選項就會列印出配置設定該數組時的 Java 堆棧

“龍井”開箱評測 |Alibaba Dragonwell 新手上路指南Alibaba Dragonwell 8 介紹安裝 Alibaba Dragonwell 8使用  Alibaba Dragonwell 8 專有特性參與Alibaba Dragonwell 社群建設參考連結

詳細的 ParNew GC 日志支援

 Alibaba Dragonwell 8 預設使用了 CMS (Concurrent Mark Sweep) 算法,新生代使用了 ParNew 算法,是以内置兩個針對 ParNew GC 日志的增強

  • 可以通過 jinfo 工具設定 PrintYoungGenHistoAfterParNewGC 選項來在下一次 Young GC 結束的時候列印新生代的對象類型直方圖。指令如下
jinfo -flag +PrintYoungGenHistoAfterParNewGC <pid>           

列印完成後,這個選項會被重置回 false 狀态,防止過多的輸出,一個典型的輸出例子如下:

“龍井”開箱評測 |Alibaba Dragonwell 新手上路指南Alibaba Dragonwell 8 介紹安裝 Alibaba Dragonwell 8使用  Alibaba Dragonwell 8 專有特性參與Alibaba Dragonwell 社群建設參考連結
  • 可以通過-XX:+PrintGCRootsTraceTime 來列印處理每一類 GC 根集所花費的詳細 CPU 時間,輸出示例如下:
“龍井”開箱評測 |Alibaba Dragonwell 新手上路指南Alibaba Dragonwell 8 介紹安裝 Alibaba Dragonwell 8使用  Alibaba Dragonwell 8 專有特性參與Alibaba Dragonwell 社群建設參考連結

精簡版 HeapDump 支援

 Alibaba Dragonwell 8 的 jmap 工具支援一個新的 dump 選項“mini”可以在做 heapdump 的時候跳過所有的原始類型數組的内容,進而大大減小生成的 heapdump 檔案大小,這對于隻需要排查類型、對象關系的場景會比較有幫助。

示例指令如下:

“龍井”開箱評測 |Alibaba Dragonwell 新手上路指南Alibaba Dragonwell 8 介紹安裝 Alibaba Dragonwell 8使用  Alibaba Dragonwell 8 專有特性參與Alibaba Dragonwell 社群建設參考連結

參與Alibaba Dragonwell 社群建設

 Alibaba Dragonwell 社群提供長期支援的 JDK 版本,使用者可以通過下面途徑擷取支援、參與讨論、提出意見。

  •  Alibaba Dragonwell 使用者支援釘釘群
“龍井”開箱評測 |Alibaba Dragonwell 新手上路指南Alibaba Dragonwell 8 介紹安裝 Alibaba Dragonwell 8使用  Alibaba Dragonwell 8 專有特性參與Alibaba Dragonwell 社群建設參考連結
  •  Alibaba Dragonwell 使用者郵件清單: [email protected]
  •  Alibaba Dragonwell 項目在 github.com 網站上的 Issues 頁面

參考連結

[1] Oracle Java 8 官方文檔 

https://docs.oracle.com/javase/8/

[1] OpenJDK 8 項目首頁 

https://openjdk.java.net/projects/jdk8u/

[1]  Alibaba Dragonwell 8 首頁 

https://developer.aliyun.com/opensource/project/alibabadragonwell?spm=5176.215014.963559999.23.70f23801Z02b2d

[2]  Alibaba Dragonwell 8 項目

https://github.com/alibaba/dragonwell8

[3]  Alibaba Dragonwell 8 使用者指南 

https://github.com/alibaba/dragonwell8/wiki/%E9%98%BF%E9%87%8C%E5%B7%B4%E5%B7%B4Dragonwell8%E7%94%A8%E6%88%B7%E6%8C%87%E5%8D%97

[4]  Alibaba Dragonwell 8 釋出說明 

https://github.com/alibaba/dragonwell8/wiki/%E9%98%BF%E9%87%8C%E5%B7%B4%E5%B7%B4Dragonwell8%E5%8F%91%E5%B8%83%E8%AF%B4%E6%98%8E

[5]  Alibaba Dragonwell 8 開發指南 

https://github.com/alibaba/dragonwell8/wiki/Developer-Guide