Springboot性能优化(亲测)——SpringBoot学习
  SpringBoot 是⼀个快速开发框架,能够快速的整合第三⽅框架,简化XML配置,全部采⽤注解形式,内置Tomcat容器,帮助开发者能够实现快速开发,SpringBoot的Web组件 默认集成的是SpringMVC框架。
  尽管 SpringBoot 拥有这么多的优点,但也存在性能问题,这并不和它拥有如此多的优点相冲突,应⽤程序性能只有更优,没有最优。  对于 SpringBoot 性能优化可以从注解 @SpringBootApplication 上优化,Servlet 容器上优化, JVM 上优化等等。我们分别从这三⽅⾯进⾏优化。
测试机器信息:
OS :Windows 10 专业版
CPU :Intel® Core™ i5-3230M @2.6GHz
RAM :8 GB
ROM :120G SSD + 500G HDD
JDK :Java version “1.8.0_171”
Eclipse :Eclipse Java EE IDE for Web Developers 4.7.3a
MySQL :MySQL Version 5.6.15
⼀、优化注解@SpringBootApplication
  @SpringBootApplication 是Springboot 整合的⼀个复合注解,作⽤相当于 @Configuration + @EnableAutoConfiguration +
@ComponentScan ,这个可以查看 @SpringBootApplication 源码得知,其中有⼀句 This is a convenience annotation that is equivalent to declaring {@code @Configuration},{@code @EnableAutoConfiguration} and {@code @ComponentScan} 说的就是这个意思。
/*
* Copyright 2012-2017 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
*      /licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.boot.autoconfigure;
import java.lang.annotation.Documented;
springboot框架的作用
import java.lang.annotation.ElementType;
import java.lang.annotation.Inherited;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import org.springframework.boot.SpringBootConfiguration;
import org.t.TypeExcludeFilter;
import t.annotation.Bean;
import t.annotation.ComponentScan;
import t.annotation.ComponentScan.Filter;
import t.annotation.Configuration;
import t.annotation.Configuration;
import t.annotation.FilterType;
import annotation.AliasFor;
/**
* Indicates a {@link Configuration configuration} class that declares one or more
* {@link Bean @Bean} methods and also triggers {@link EnableAutoConfiguration
* auto-configuration} and {@link ComponentScan component scanning}. This is a convenience  * annotation that is equivalent to declaring {@code @Configuration},
* {@code @EnableAutoConfiguration} and {@code @ComponentScan}.
*
* @author Phillip Webb
* @author Stephane Nicoll
* @since 1.2.0
*/
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
@SpringBootConfiguration
@EnableAutoConfiguration
@ComponentScan(excludeFilters = {
@Filter(type = FilterType.CUSTOM, classes = TypeExcludeFilter.class),
@Filter(type = FilterType.CUSTOM, classes = AutoConfigurationExcludeFilter.class) }) public @interface SpringBootApplication {
/**
* Exclude specific auto-configuration classes such that they will never be applied.
* @return the classes to exclude
*/
@AliasFor(annotation = EnableAutoConfiguration.class)
Class<?>[] exclude() default {};
/**
* Exclude specific auto-configuration class names such that they will never be
* applied.
* @return the class names to exclude
* @since 1.3.0
*/
@AliasFor(annotation = EnableAutoConfiguration.class)
String[] excludeName() default {};
/**
* Base packages to scan for annotated components. Use {@link #scanBasePackageClasses}  * for a type-safe alternative to String-based package names.
* @return base packages to scan
* @since 1.3.0
*/
@AliasFor(annotation = ComponentScan.class, attribute = "basePackages")
String[] scanBasePackages() default {};
/**
* Type-safe alternative to {@link #scanBasePackages} for specifying the packages to
* scan for annotated components. The package of each class specified will be scanned.
* <p>
* Consider creating a special no-op marker class or interface in each package that
* serves no purpose other than being referenced by this attribute.
* @return base packages to scan
* @since 1.3.0
*/
@AliasFor(annotation = ComponentScan.class, attribute = "basePackageClasses")
Class<?>[] scanBasePackageClasses() default {};
}
  由于其中包括有包扫描的注解 @ComponentScan ,这会导致项⽬启动时间变长(启动⼀个⼤的应⽤程序或做⼤量的集成测试启动应⽤程序时,影响会特别明显),会加载⼀些多余的实例(Beans),也会增加 CPU 消耗。
  所以可以将 @SpringBootApplication 注解改为 @EnableAutoConfiguration + @Configuration + 在我们需要的 bean 上进⾏显式配置注解。
  通过实际使⽤ @SpringBootApplication 注解 和 使⽤ @EnableAutoConfiguration + @Configuration 注解分别各测试启动 5 次 记录实际启动时间,最后取 5 次的平均时间来⽐较性能的变化,JVM 各参数默认,测试的详细数据见下。
测试项⽬使⽤ @SpringBootApplication 注解使⽤ @EnableAutoConfiguration + @Configuration 注解第⼀次测试耗时19.742s/20.867s18.160s/19.291s
第⼆次测试耗时19.407s/20.563s18.388s/19.496s
第三次测试耗时21.734s/22.90318.308s/19.721s
第四次测试耗时19.908s/21.090s18.576s/19.708s
第五次测试耗时19.456s/20.650s18.418s/19.699s 平均耗时20.049s/21.215s18.370s/19.583s
  表格说明:此表基于上述环境测试的真实值,平均耗时取有效⼩数5位。19.742s/20.867s :表⽰ 应⽤启动耗时19.742秒,JVM 启动耗时20.867秒。
  通过上述测试数据发现使⽤ @EnableAutoConfiguration + @Configuration 注解 可以提⾼应⽤程序启动的性能。
⼆、将 Servlet 容器由 Tomcat 变成 Undertow
  默认情况下 Spring Boot 使⽤ Tomcat 来作为内嵌的 Servlet 容器,我们可以将 Web 服务器切换到 Undertow 来提⾼应⽤性能。Undertow 是⼀个采⽤ Java 开发的灵活的⾼性能 Web 服务器,提供包括阻塞和基于 NIO 的⾮堵塞机制。接下来我们使⽤ Jmeter 分别测试使⽤ Tomcat 容器 和 Undertow 容器在同⼀个查询数据库信息的接⼝下的各⾃的并发量。设置 JVM 参数:-server -XX:+PrintGCDetails -Xms2048m -Xmx2048m,测试数据如下。
测试项⽬Tomcat 容器Undertow 容器第⼀次吞吐量测试315.3/sec395.0/sec
第⼆次吞吐量测试421.6/sec453.2/sec
第三次吞吐量测试327.8/sec448.8/sec
第四次吞吐量测试351.4/sec340.0/sec
第五次吞吐量测试431.1/sec433.2/sec
平均吞吐量369.44/sec414.04/sec
  表格说明:此表基于上述环境测试的真实值,平均吞吐量取有效⼩数5位。
  由上表数据可以看出将 Tomcat 容器换为 Undertow 容器将会提⾼应⽤性能。
三、JVM 调优
  关于 JVM 调优需要了解服务器基本参数配置,JVM 基本组成结构,垃圾回收算法,垃圾回收机制,JVM 调优⼯具,调优经验等等等,这⾥不详细列举。
  这⾥就以 JVM 参数 -server -XX:+PrintGCDetails -Xms512m -Xmx512m 和 -server -XX:+PrintGCDetails -Xms2048m -Xmx2048m 为例,还是测试吞吐量,对于参数 -server -XX:+PrintGCDetails -Xms2048m -Xmx2048m 的数据从Tomcat 容器下吞吐量的测试得来,就不做重
复测试了,然后测试参数 -server -XX:+PrintGCDetails -Xms512m -Xmx512m 在 Tomcat 容器下的吞吐量,测试数据见下表。
测试项⽬Tomcat 512M Tomcat 2048M 第⼀次吞吐量测试300.5/sec315.3/sec
第⼆次吞吐量测试293.5/sec421.6/sec
测试项⽬Tomcat 512M Tomcat 2048M 第三次吞吐量测试282.6/sec327.8/sec
第四次吞吐量测试302.8/sec351.4/sec
第五次吞吐量测试309.5/sec431.1/sec
平均吞吐量297.78/sec369.44/sec
  表格说明:此表基于上述环境测试的真实值,平均吞吐量取有效⼩数5位。
  数据说明JVM 参数 `-server -XX:+PrintGCDetails -Xms2048m -Xmx2048m` ⽐ `-server -XX:+PrintGCDetails -Xms512m -Xmx512m` 要优。进⾏ JVM 调优是⼀个谨慎细致的过程,需要慢慢的试,直到当前最优为⽌。

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。