吊打 Tomcat ,Undertow 效能很炸!!
阿新 • • 發佈:2020-08-24
在 Java Web 容器的世界裡,Tomcat 和 Jetty 是大名鼎鼎的、用的最多的開源專案,也是大眾熟知的。
今天再介紹另外一款能和 Tomcat 媲美的神器:Undertow,據說效能方面還要吊打 Tomcat,如果你還不知道它,那你就 OUT 了。
我們來看下 Spring Boot 預設支援的三種 Servlet 容器:
Name | Servlet Version
---|---
Tomcat 9.0 | 4.0
Jetty 9.4 | 3.1
Undertow 2.0 | 4.0
以上來源於 Spring Boot 2.3.2 官方文件,更多資訊請點選[這裡](https://mp.weixin.qq.com/s/YfPFl1_l2sp9YirTppzRow)參考這篇文章。
Undertow 它能成為 Spring Boot 預設整合的三大容器之一,就憑這點,我想就足以說明它的地位。
## Undertow 什麼鬼?
Undertow 是 RedHat(紅帽公司)的開源產品,採用 Java 開發,是一款靈活、高效能的 Web 伺服器,提供了基於 NIO 的阻塞/非阻塞 APIs,也是 Wildfly 的預設 Web 容器。
搜尋 Undertow:
![](https://img2020.cnblogs.com/other/1218593/202008/1218593-20200824105305699-195814623.png)
頁面顯示的是 JBoss Community,因為 2006 年 RedHat 收購了 JBoss,那也就不足為怪了。
Undertow 它是一個基於組合的體系結構,可以通過組合一系列小型處理器來構建一個 Web 伺服器。這就讓我們可以靈活的在 Java EE servlet 4.0 容器和底層非阻塞處理器或者其他更多之間進行選擇。
Undertow 被設計成完全可嵌入式的,所以也叫嵌入式容器,具有易於使用的流暢構建 API,另外,Undertow 的生命週期也完全由所嵌入的應用程式所控制。
這也是為什麼 Spring Boot 可以直接嵌入 Undertow 的原因,Undertow 它就是為了嵌入而發燒的。Spring Boot 基礎知識就不介紹了,關注公眾號Java技術棧在後臺回覆boot獲取我寫的系列教程。
官方網站:
> https://undertow.io/
原始碼託管在 Github:
> https://github.com/undertow-io/undertow
## Undertow 有啥特性?
**1)HTTP/2 Support**
Undertow 支援 HTTP/2 開箱即用,不需要重寫引導類路徑。
**2)支援 HTTP 升級**
支援 HTTP 升級,允許多個協議通過 HTTP 埠上進行復用。
**3)支援 Web Socket**
Undertow 提供對 Web 套接字的全面支援,包括對 JSR-356 的支援。
**4)支援 Servlet 4.0**
Undertow 提供了對 Servlet 4.0 的支援,包括對嵌入式 Servlet 的支援,還可以混合部署 Servlet 和原生 Undertow 非阻塞處理程式。
**5)可嵌入式**
Undertow 可以嵌入到應用程式中,也可以通過幾行程式碼獨立執行。
**6)高靈活性**
一個 Undertow 伺服器是通過鏈式處理器來配置的,可以根據需要新增功能,因此可以避免新增沒有必要的功能。
## Undertow 效能如何?
國外有篇帖子做了 Tomcat vs. Jetty vs. Undertow 三者的效能比較:
> https://examples.javacodegeeks.com/enterprise-java/spring/tomcat-vs-jetty-vs-undertow-comparison-of-spring-boot-embedded-servlet-containers/
![](https://img2020.cnblogs.com/other/1218593/202008/1218593-20200824105306098-1526118676.png)
從測試結果看,這三個 Servlet 容器都具有不錯的效能,但 Undertow 效能更好,Tomcat 和 Jetty 緊隨其後。
Jetty 在啟動時的記憶體佔用最大,為:311 MB, Tomcat 和 Undertow 的初始記憶體佔用都很低,大約為:120 MB,而 Undertow 的初始記憶體佔用最低,為:114 MB。
最後,關鍵的區別在於,Undertow 響應頭引數預設包含 HTTP 持久連線資訊,這個頭引數在支援持久連線的客戶端時,可以通過重用連線來優化效能。
## Show me the code
Undertow 目前有兩個主要版本:
- 2.1:當前支援 Servlet 4.0, JDK8+ 的穩定版本;
- 1.4:當前支援 Servlet 3.1, JDK7 的穩定版本;
獨立使用 Undertow 需要新增以下依賴:
```
```
以下示例來源官網:
```
public class HelloWorldServer {
public static void main(final String[] args) {
Undertow server = Undertow.builder()
.addHttpListener(8080, "localhost")
.setHandler(new HttpHandler() {
@Override
public void handleRequest(final HttpServerExchange exchange) throws Exception {
exchange.getResponseHeaders().put(Headers.CONTENT_TYPE, "text/plain");
exchange.getResponseSender().send("Hello World");
}
}).build();
server.start();
}
}
```
這是一個使用了異常 IO 的簡單 Hello World 示例。
## Spring Boot & Undertow
上面講到,Undertow 是為嵌入式而生的 Web 容器,又是 Spring Boot 預設整合的容器之一,下面棧長帶大家來看下如何在 Spring Boot 中使用 Undertow。
因為在 `spring-boot-starter-web` 啟動器中,Tomcat 是 Spring Boot 預設的嵌入式容器,即:`spring-boot-starter-tomcat`。
Spring Boot 還提供了其他兩個啟動器以方便進行代替:
- spring-boot-starter-jetty
- spring-boot-starter-undertow
下面來簡單實戰下,如何在 Spring Boot 中使用 Undertow。Spring Boot 基礎知識就不介紹了,不熟悉的可以關注公眾號Java技術棧在後臺回覆boot獲取我寫的系列教程。
排除 Tomcat 依賴,然後加入 Undertow 依賴:
```
```
一步就完成集成了,當然實際情況還需要在 application 配置檔案中加入 Undertow 的更多自定義或者優化配置引數。
Undertow容器的具體配置可以看這兩個類:
- org.springframework.boot.autoconfigure.web.ServerProperties
- org.springframework.boot.autoconfigure.web.ServerProperties.Undertow
也可以看 Spring Boot 官方文件:
> https://docs.spring.io/spring-boot/docs/2.3.2.RELEASE/reference/htmlsingle/#server-properties
上面有所有 Server 配置引數和說明。
再寫一個測試方法測試下:
```
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
/**
* 微信公眾號:Java技術棧
*/
@RestController
@SpringBootApplication
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class);
}
@GetMapping(value = "/undertow/test")
public String undertow() {
return "hello undertow";
}
}
```
啟動 Application:
![](https://img2020.cnblogs.com/other/1218593/202008/1218593-20200824105306581-130064430.png)
如上所示,可以看到 Undertow 的啟動日誌。
訪問測試方法:
> http://localhost:8080/undertow/test
![](https://img2020.cnblogs.com/other/1218593/202008/1218593-20200824105306889-830058720.png)
輸出成功,測試完成。
## 總結
本文對 Undertow 作了一個介紹和整合實戰,雖然 Undertow 效能很炸,但你可以去網上找一圈,根本沒啥學習資料。
所以,對於學習和一般應用來說,Tomcat 足矣,一方面 Tomcat 學習資料多,另一方面 Tomcat 用的更廣泛,很多坑別人幫你踩了,很多漏洞也已經暴露出來了。
那於那些一定要追求極致效能的又不想優化 Tomcat 的,可以考慮使用 Undertow,但同時你要有能力 Hold 住它,需要一定的積累經驗,不然出一個問題你線上卡半天顯然是不願意看到的。
最後,網上很多文章說幹掉 Tomcat 而要使用 Undertow 的,這就有點誇張,我只能呵呵了,持有保留意見,用啥都行,關鍵能不能用好。
**推薦去我的部落格閱讀更多:**
1.[Java JVM、集合、多執行緒、新特性系列教程](http://www.javastack.cn/categories/Java/)
2.[Spring MVC、Spring Boot、Spring Cloud 系列教程](http://www.javastack.cn/categories/Spring/)
3.[Maven、Git、Eclipse、Intellij IDEA 系列工具教程](http://www.javastack.cn/categories/工具/)
4.[Java、後端、架構、阿里巴巴等大廠最新面試題](http://www.javastack.cn/categories/面試題/)
覺得不錯,別忘了點贊+轉發哦!