您好,登錄后才能下訂單哦!
本篇內(nèi)容主要講解“springboot-starter-undertow和tomcat的區(qū)別是什么”,感興趣的朋友不妨來(lái)看看。本文介紹的方法操作簡(jiǎn)單快捷,實(shí)用性強(qiáng)。下面就讓小編來(lái)帶大家學(xué)習(xí)“springboot-starter-undertow和tomcat的區(qū)別是什么”吧!
在說(shuō)undertow和tomcat區(qū)別之前,先說(shuō)下tomcat是什么(如果知道了可以跳過(guò)哦!)
Tomcat:免費(fèi)開(kāi)源,輕量級(jí)應(yīng)用服務(wù)器,在中小型系統(tǒng)和并發(fā)訪(fǎng)問(wèn)用戶(hù)不是很多的場(chǎng)合下被普遍使用,是開(kāi)發(fā)和調(diào)試JSP 程序的首選。
實(shí)際上Tomcat 部分是Apache 服務(wù)器的擴(kuò)展,但它是獨(dú)立運(yùn)行的,所以當(dāng)你運(yùn)行tomcat 時(shí),它實(shí)際上作為一個(gè)與Apache 獨(dú)立的進(jìn)程單獨(dú)運(yùn)行的。
只實(shí)現(xiàn)了JSP/Servlet的相關(guān)規(guī)范,不支持EJB。
雖說(shuō)是tomcat服務(wù)器,但是并不是真正的硬件,它是部署在電腦上的軟件服務(wù)。
上面說(shuō)過(guò)Tomcat是一個(gè)容器,但為什么開(kāi)發(fā)出來(lái)的應(yīng)用需要裝進(jìn)Tomcat這個(gè)容器呢。忽略各個(gè)文件之間的跳轉(zhuǎn),web應(yīng)用本質(zhì)只是一個(gè)裝有很多資源(java/html/jsp/js/css等各種格式文件)的文件夾。假如我們有一個(gè)web應(yīng)用projectA,我們?cè)谀撑_(tái)計(jì)算機(jī)A把這些文件寫(xiě)好后,就希望其他設(shè)備能夠通過(guò)一些方式來(lái)訪(fǎng)問(wèn)我們的資源。一種方法是通過(guò)在瀏覽器地址欄輸入U(xiǎn)RL來(lái)實(shí)現(xiàn)資源的訪(fǎng)問(wèn)。
那么從我們?cè)谟?jì)算機(jī)A上寫(xiě)好某個(gè)文件夾到文件夾能夠被其他計(jì)算機(jī)所訪(fǎng)問(wèn),需要什么呢。首先需要我們的互聯(lián)網(wǎng)。計(jì)算機(jī)B先通過(guò)互聯(lián)網(wǎng)找到計(jì)算機(jī)A。
而這樣做的前提是你這個(gè)電腦必須在互聯(lián)網(wǎng)這個(gè)網(wǎng)絡(luò)里面,這樣別人才能訪(fǎng)問(wèn)到你。也就是說(shuō)一臺(tái)電腦必須要有IP地址才能稱(chēng)為服務(wù)器。但這樣也只是找到了IP地址而已,我們還需要找到對(duì)應(yīng)的主機(jī)(注:一般主機(jī)是指一臺(tái)電腦,但在tomcat中,虛擬主機(jī)指的是計(jì)算機(jī)中的某個(gè)文件夾)。但就算找到了計(jì)算機(jī)A,我們?cè)趺粗酪ツ睦飳ふ襴eb應(yīng)用projectA呢。Tomcat容器就是來(lái)解決這個(gè)問(wèn)題的。在我看來(lái),Tomcat的一個(gè)重要的功能就在于“映射”(通過(guò)配置文件實(shí)現(xiàn))。
其實(shí)可以不要,之前Javaweb項(xiàng)目多為jsp,而jsp需要jsp容器來(lái)解釋?zhuān)孕枰猼omcat等含有jsp容器的web服務(wù)器。使用jsp的時(shí)候,jsp沒(méi)有main方法,怎么把服務(wù)啟動(dòng)呢,這個(gè)時(shí)候tomcat容器就很有必要了。
但隨著近些年了,前后端分離導(dǎo)致不需要jsp容器來(lái)解釋jsp,于是tomcat在項(xiàng)目中完全可以不要的,可以使用JBoss、Jetty等單純Web應(yīng)用服務(wù)器。
但tomcat也可以做Web服務(wù)器,所以項(xiàng)目中還是可以繼續(xù)使用tomcat。
前端html頁(yè)面通過(guò)ajax調(diào)用后端的restuful api接口并使用json數(shù)據(jù)進(jìn)行交互。前后端分離的項(xiàng)目就可以不使用tomcat容器。
不得不說(shuō)SpringBoot的開(kāi)發(fā)者是在為大眾程序猿謀福利,把大家都慣成了懶漢,xml不配置了,連tomcat也懶的配置了,典型的一鍵啟動(dòng)系統(tǒng),那么tomcat在springboot是怎么啟動(dòng)的呢?
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> <version>2.1.6.RELEASE</version> </dependency>
@SpringBootApplication public class MySpringbootTomcatStarter{ public static void main(String[] args) { Long time=System.currentTimeMillis(); SpringApplication.run(MySpringbootTomcatStarter.class); } }
有的公司在生產(chǎn)環(huán)境不使用springboot自帶的tomcat,則需要在代碼中排出
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> <!-- 移除嵌入式tomcat插件 --> <exclusions> <exclusion> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-tomcat</artifactId> </exclusion> </exclusions> </dependency>
將項(xiàng)目打成war包(下面會(huì)講==),放到生產(chǎn)環(huán)境tomcat目錄下運(yùn)行
在 SpringBoot 框架中,使用最多的是 Tomcat,這是 SpringBoot 默認(rèn)的容器技術(shù),而且是內(nèi)嵌式的 Tomcat。
同時(shí),SpringBoot 也支持 Undertow 容器,我們可以很方便的用 Undertow 替換 Tomcat,而 Undertow 的性能和內(nèi)存使用方面都優(yōu)于 Tomcat。
在高并發(fā)系統(tǒng)中,Tomcat 相對(duì)來(lái)說(shuō)比較弱。在相同的機(jī)器配置下,模擬相等的請(qǐng)求數(shù),Undertow 在性能和內(nèi)存使用方面都是最優(yōu)的。并且 Undertow 新版本默認(rèn)使用持久連接,這將會(huì)進(jìn)一步提高它的并發(fā)吞吐能力。所以,如果是高并發(fā)的業(yè)務(wù)系統(tǒng),Undertow 是最佳選擇。
使用:
1.排除SpingBoot中自帶的tomcat
<!--springboot web--> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> <exclusions> <exclusion> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-tomcat</artifactId> </exclusion> </exclusions> </dependency>
2.添加Undertow的依賴(lài)
<!--undertow--> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-undertow</artifactId> </dependency>
這樣即可,使用默認(rèn)參數(shù)啟動(dòng)undertow服務(wù)器。如果需要修改undertow參數(shù),繼續(xù)往下看。
undertow的參數(shù)設(shè)置:
server: port: 8084 http2: enabled: true undertow: io-threads: 16 worker-threads: 256 buffer-size: 1024 buffers-per-region: 1024 direct-buffers: true
io-threads
:IO線(xiàn)程數(shù), 它主要執(zhí)行非阻塞的任務(wù),它們會(huì)負(fù)責(zé)多個(gè)連接,默認(rèn)設(shè)置每個(gè)CPU核心一個(gè)線(xiàn)程,不可設(shè)置過(guò)大,否則啟動(dòng)項(xiàng)目會(huì)報(bào)錯(cuò):打開(kāi)文件數(shù)過(guò)多。
worker-threads
:阻塞任務(wù)線(xiàn)程池,當(dāng)執(zhí)行類(lèi)似servlet請(qǐng)求阻塞IO操作,undertow會(huì)從這個(gè)線(xiàn)程池中取得線(xiàn)程。它的值取決于系統(tǒng)線(xiàn)程執(zhí)行任務(wù)的阻塞系數(shù),默認(rèn)值是 io-threads*8
以下配置會(huì)影響buffer,這些buffer會(huì)用于服務(wù)器連接的IO操作,有點(diǎn)類(lèi)似netty的池化內(nèi)存管理。
buffer-size
:每塊buffer的空間大小,越小的空間被利用越充分,不要設(shè)置太大,以免影響其他應(yīng)用,合適即可
buffers-per-region
:每個(gè)區(qū)分配的buffer數(shù)量,所以pool的大小是buffer-size * buffers-per-region
direct-buffers
:是否分配的直接內(nèi)存(NIO直接分配的堆外內(nèi)存)
3. 啟動(dòng)SpringBoot測(cè)試
Undertow啟動(dòng)成功提示語(yǔ):[INFO ] 2020-08-13 10:38:32 [main] o.s.b.w.e.u.UndertowServletWebServer - Undertow started on port(s) 80 (http) with context path ‘’
Tomcat啟動(dòng)成功提示語(yǔ): [INFO ] 2020-08-13 10:41:35 [main] o.s.b.w.e.tomcat.TomcatWebServer - Tomcat started on port(s): 80 (http) with context path ‘’
war是一個(gè)web模塊,其中需要包括WEB-INF,是可以直接運(yùn)行的WEB模塊。而jar一般只是包括一些class文件,在聲明了Main_class之后是可以用java命令運(yùn)行的.
它們都是壓縮的包,拿Tomcat來(lái)說(shuō),將war文件包放置它的\webapps\目錄下,啟動(dòng)Tomcat,這個(gè)包可以自動(dòng)進(jìn)行解壓,也就是你的web目錄,相當(dāng)于發(fā)布了。
像之前jsp頁(yè)面,項(xiàng)目必須打包成war,放置到tomcat容器中運(yùn)行。
Spring Boot支持傳統(tǒng)部署和更現(xiàn)代的部署形式。jar跟war都支持,在創(chuàng)建springboot項(xiàng)目時(shí),默認(rèn)是jar包,打成war包使用我上面說(shuō)的即可
pom.xml配置
如果使用tomcat服務(wù)器,則配置如下:
<dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-tomcat</artifactId> <scope>provided</scope> </dependency> </dependencies>
如果使用undertow服務(wù)器,則配置如下:因?yàn)閟pring boot默認(rèn)配置為tomcat:
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> <!-- 若使用log4j2 --> <exclusions> <exclusion> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-tomcat</artifactId> </exclusion> </exclusions> </dependency>
再添加dependency依賴(lài):
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-undertow</artifactId>
再在定制tomcat/undertow服務(wù)器
/** * */ package com.lz.ovuola.general.util.tomcat; import org.apache.catalina.connector.Connector; import org.apache.coyote.http11.Http11NioProtocol; import org.springframework.boot.context.embedded.EmbeddedServletContainerFactory; import org.springframework.boot.context.embedded.tomcat.TomcatConnectorCustomizer; import org.springframework.boot.context.embedded.tomcat.TomcatEmbeddedServletContainerFactory; import org.springframework.boot.context.properties.ConfigurationProperties; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; /** * 編程方式自定義內(nèi)嵌容器 * * @author fz * */ @Configuration @ConfigurationProperties(prefix = "tomcat") public class CustomTomcatEmbeddedCustomizer { private int maxThreads; private int minSpareThreads; private int acceptCount; private int connectionTimeout; private String URIEncoding = "UTF-8"; private boolean disableUploadTimeout; private boolean enableLookups; private String compression; private int compressionMinSize; private String compressableMimeType; /** * 訂制內(nèi)嵌tomcat容器 */ @Bean public EmbeddedServletContainerFactory servletContainer() { TomcatEmbeddedServletContainerFactory factory = new TomcatEmbeddedServletContainerFactory(); factory.addConnectorCustomizers(new MyTomcatConnectorCustomizer()); return factory; } class MyTomcatConnectorCustomizer implements TomcatConnectorCustomizer { public void customize(Connector connector) { Http11NioProtocol protocol = (Http11NioProtocol) connector .getProtocolHandler(); // 設(shè)置最大連接數(shù) protocol.setMaxThreads(maxThreads); protocol.setConnectionTimeout(connectionTimeout); protocol.setMinSpareThreads(minSpareThreads); protocol.setAcceptorThreadCount(acceptCount); protocol.setDisableUploadTimeout(disableUploadTimeout); protocol.setCompression(compression); protocol.setCompressionMinSize(compressionMinSize); protocol.setCompressableMimeType(compressableMimeType); // connector.setURIEncoding(URIEncoding); connector.setEnableLookups(enableLookups); } } public int getMaxThreads() { return maxThreads; } public void setMaxThreads(int maxThreads) { this.maxThreads = maxThreads; } public int getMinSpareThreads() { return minSpareThreads; } public void setMinSpareThreads(int minSpareThreads) { this.minSpareThreads = minSpareThreads; } public int getAcceptCount() { return acceptCount; } public void setAcceptCount(int acceptCount) { this.acceptCount = acceptCount; } public int getConnectionTimeout() { return connectionTimeout; } public void setConnectionTimeout(int connectionTimeout) { this.connectionTimeout = connectionTimeout; } public String getURIEncoding() { return URIEncoding; } public void setURIEncoding(String uRIEncoding) { URIEncoding = uRIEncoding; } public boolean isDisableUploadTimeout() { return disableUploadTimeout; } public void setDisableUploadTimeout(boolean disableUploadTimeout) { this.disableUploadTimeout = disableUploadTimeout; } public boolean isEnableLookups() { return enableLookups; } public void setEnableLookups(boolean enableLookups) { this.enableLookups = enableLookups; } public String getCompression() { return compression; } public void setCompression(String compression) { this.compression = compression; } public int getCompressionMinSize() { return compressionMinSize; } public void setCompressionMinSize(int compressionMinSize) { this.compressionMinSize = compressionMinSize; } public String getCompressableMimeType() { return compressableMimeType; } public void setCompressableMimeType(String compressableMimeType) { this.compressableMimeType = compressableMimeType; } }
或者是 undertow,測(cè)試只要啟動(dòng)一個(gè)就行
//package com.lz.ovuola.general.util.tomcat; // //import io.undertow.Undertow.Builder; // //import org.springframework.boot.context.embedded.EmbeddedServletContainerFactory; //import org.springframework.boot.context.embedded.undertow.UndertowBuilderCustomizer; //import org.springframework.boot.context.embedded.undertow.UndertowEmbeddedServletContainerFactory; //import org.springframework.boot.context.properties.ConfigurationProperties; //import org.springframework.context.annotation.Bean; //import org.springframework.context.annotation.Configuration; // //@Configuration //public class CustomUndertowEmbeddedCustomizer { // // @Bean // public EmbeddedServletContainerFactory servletContainer() { // UndertowEmbeddedServletContainerFactory factory = new UndertowEmbeddedServletContainerFactory(); // factory.addBuilderCustomizers(new UndertowBuilderCustomizer() { // // @Override // public void customize(Builder builder) { // builder.addHttpListener(8080, "127.0.0.1"); // } // // }); // return factory; // } // // }
在application -runAs -run as configuratuion-Arguments添加:--用于jconsole或者是visualVM監(jiān)控,推薦使用后者
-Djava.rmi.server.hostname=127.0.0.1 --ip地址 -Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.port="9093" --端口號(hào) -Dcom.sun.management.jmxremote.authenticate="false"
采用visualVM監(jiān)控同一個(gè)服務(wù),分別開(kāi)啟tomcat/undertow容器,注意兩者在application.propertites參數(shù)盡量相同,以便觀察穩(wěn)定性
打開(kāi)jemter壓力測(cè)試某一接口,觀察堆內(nèi)存、線(xiàn)程數(shù)、cpu等指標(biāo)。
到此,相信大家對(duì)“springboot-starter-undertow和tomcat的區(qū)別是什么”有了更深的了解,不妨來(lái)實(shí)際操作一番吧!這里是億速云網(wǎng)站,更多相關(guān)內(nèi)容可以進(jìn)入相關(guān)頻道進(jìn)行查詢(xún),關(guān)注我們,繼續(xù)學(xué)習(xí)!
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。