跳至主要內容

springboot

HeChuangJun约 2378 字大约 8 分钟

springboot

1. SpringBoot

springboot快速创建一个独立运行、准生产级别的基于spring框架的项目
springboot其实包含了springmvc等许多的组件,还允许自动配置,省事

2. springboot2程序入门

创建maven项目,打包方式选择war,跳过骨架
配置pom.xml(注意编译jdk版本和运行的jdk版本匹配)
	<project xmlns="http://maven.apache.org/POM/4.0.0" 
		xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
		xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 
		http://maven.apache.org/xsd/maven-4.0.0.xsd">
		<modelVersion>4.0.0</modelVersion>
		<groupId>com.junye</groupId>
		<artifactId>testspringboot</artifactId>
		<version>0.0.1-SNAPSHOT</version>
		<!--打包的方式为war,自动生成jar包-->
		<packaging>war</packaging>
		<name>testspringboot</name>
		<description>AAA</description>
		<!-- 定义公共资源版本 -->
		<parent>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-parent</artifactId>
			<version>2.0.2.RELEASE</version>
		</parent>
		<!--设置资源的版本-->
		<properties>
		<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
		<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
		<java.version>1.8</java.version>
		</properties>
		
		<dependencies>
		<dependency>
		<!-- 上边引入 parent,因此 下边无需指定版本,相当于配置了springmvc -->
		<!-- 包含 mvc,aop 等jar资源 -->
		<groupId>org.springframework.boot</groupId>
		<artifactId>spring-boot-starter-web</artifactId>
		<!--使用别的服务器,如undertow
		<exclusions>
		<exclusion>
		<groupId>org.springframework.boot</groupId>
		<artifactId>spring-boot-starter-tomcat</artifactId>
		</exclusion>
		</exclusions>
		</dependency>
		指定特定的服务器
		<dependency>
		   <groupId>org.springframework.boot</groupId>
		   <artifactId>spring-boot-starter-undertow</artifactId>
		</dependency>-->
		</dependencies>
		<build>
		<!--指定springboot的maven插件-->
		<plugins>
		<plugin>
		<groupId>org.springframework.boot</groupId>
		<artifactId>spring-boot-maven-plugin</artifactId>
		</plugin>
		</plugins>
		</build>
		</project>
src/main/java下的程序入口:Chapter1Application(必须)
	run中传入的名字必须与类名一致
		package com.junye.test;
		import org.springframework.boot.SpringApplication;
		import org.springframework.boot.autoconfigure.SpringBootApplication;
		@SpringBootApplication
		public class Chapter1Application {
			public static void main(String[] args) {
				SpringApplication.run(Chapter1Application.class, args);
			}
		}


src/main/java下的controller层(必须)
	package com.junye.test;
		import org.springframework.stereotype.Controller;
		import org.springframework.ui.Model;
		import org.springframework.web.bind.annotation.RequestMapping;
		import org.springframework.web.bind.annotation.RestController;
		@RestController//自动返回json数据
		public class HelloController {
		@RequestMapping("/hello")
		public String index() {
		return "Hello World";
		}
		}
	
启动项目的方法
	Debug Run或者运行主函数或者maven的spring-boot:run
	完成上述步骤访问:http://localhost:8080/hello即可显示helloworld
springboot参数接收与返回与springmvc一致

3. Spring Boot API

入口类和@SpringBootApplication
Spring Boot的项目一般都会有*Application的入口类,入口类中会有main方法,这是一个标准的Java应用程序的入口方法。
@SpringBootApplication注解是Spring Boot的核心注解,它其实是一个组合注解

@SpringBootConfiguration=>@Configuration
@EnableAutoConfiguration 启用自动配置使项目中依赖的jar包自动配置项目的配置项
@ComponentScan(
    excludeFilters = {@Filter(
    type = FilterType.CUSTOM,
    classes = {TypeExcludeFilter.class}
), @Filter(
    type = FilterType.CUSTOM,
    classes = {AutoConfigurationExcludeFilter.class}
)}//默认扫描@SpringBootApplication所在类的同级目录以及它的子目录

关闭自动配置
spring-boot-autoconfigure-xxx.jar
@SpringBootApplication(exclude={RedisAutoConfiguration.class})

自定义Banner(spring启动图案)
http://patorjk.com/software/taag/#p=display&f=Graffiti&t=Type%20Something%20
拷贝生成的字符到一个文本文件中,并且将该文件命名为banner.txt,将banner.txt拷贝到maven项目的resources目录中即可
关闭Banner application.properties
spring.main.banner-mode = off

全局配置文件application.properties或者application.yml,在resources目录下或者类路径下的/config下,
server.port=8088 #tomcat端口
server.servlet-path=*.html # 修改进入DispatcherServlet的规则为:*.html
    
设置日志级别
logging.level.org.springframework=DEBUG

静态资源路径
spring.resources.static-locations=classpath:/META-INF/resources/,classpath:/resources/,classpath:/static/,classpath:/public/

mvc视图
spring.mvc.view.prefix=/WEB-INF/views/
spring.mvc.view.suffix=.jsp

# springboot设置session过期的时间
server.session.timeout=120

springbootjava配置和application.properties配置冲突优先java配置
springboot的@component配置导致数据源配置不可用,说明springboot的配置是先加载component然后再加configuration

引入xml配置文件
@ImportResource({"classpath:xxx-context.xml"})

读取外部的配置文件
@PropertySource(value = { "classpath:jdbc.properties", "classpath:env.properties"})

4. 自定义SpringMVC的配置(拦截器)

继承WebMvcConfigurerAdapter,然后重写父类中的方法进行扩展。
import java.nio.charset.Charset;
import java.util.List;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.context.annotation.Configuration;
import org.springframework.http.converter.HttpMessageConverter;
import org.springframework.http.converter.StringHttpMessageConverter;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter;

@Configuration
public class MySrpingMVCConfig extends WebMvcConfigurerAdapter{
	// 自定义拦截器
	@Override
	public void addInterceptors(InterceptorRegistry registry) {
		HandlerInterceptor handlerInterceptor = new HandlerInterceptor() {
			@Override
			public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
			throws Exception {
				System.out.println("自定义拦截器............");
				return true;
			}
			@Override
			public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,
			ModelAndView modelAndView) throws Exception {

			}

			@Override
			public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler,
			Exception ex) throws Exception {
			}
		};
		//注册拦截器     
		registry.addInterceptor(handlerInterceptor).addPathPatterns("/**");
	}

	// 自定义消息转化器的第二种方法
	@Override
	public void configureMessageConverters(List<HttpMessageConverter<?>> converters) {
		StringHttpMessageConverter converter  = new StringHttpMessageConverter(Charset.forName("UTF-8"));
		converters.add(converter);
	}

}

5. Mybatis和Spring Boot整合(两种方式)

使用mybatis官方提供的Spring Boot整合包实现https://github.com/mybatis/spring-boot-starter
<!--三包合一,包括mybatis、整合包和事务包-->
<dependency>
	<groupId>org.mybatis.spring.boot</groupId>
	<artifactId>mybatis-spring-boot-starter</artifactId>
	<version>1.3.0</version>
</dependency>
@Mapper(在接口上面注解即可)或者直接扫描包
@MapperScan(basePackages= {"com.junye.testspringbootMybaits"})
@Transactional(service层上面注册)
java配置sqlfactorysession和数据源
@Bean
//@Primary//设置优先,多数据源的时候使用就是当遇到数据对接的时候用
public ComboPooledDataSource getComboPooledDataSource() throws PropertyVetoException{
	ComboPooledDataSource cd=new ComboPooledDataSource();
	cd.setDriverClass("com.mysql.cj.jdbc.Driver");
	cd.setJdbcUrl("jdbc:mysql://localhost:3306/testmybatis?useSSL=true&serverTimezone=GMT%2B8");
	cd.setUser("root");
	cd.setPassword("1105128664");
	return cd;
}

@Bean(name="sqlSessionFactory")
public SqlSessionFactoryBean getSqlSessionFactoryBean() throws Exception{
	SqlSessionFactoryBean sf = new SqlSessionFactoryBean();
	sf.setDataSource(getComboPooledDataSource());
	sf.setMapperLocations(new PathMatchingResourcePatternResolver().getResources("classpath:match2/test/*.xml"));
	sf.setTypeAliasesPackage("com.junye.test");//设置包的别名
	//下面的配置可有可无,毕竟设置包的别名已经设计好了
	//sf.setConfigLocation(new PathMatchingResourcePatternResolver().getResource("classpath:mybatis-configuration.xml"));
	return sf;
}

使用mybatis-spring整合的方式(推荐)
<!--mybatis核心包-->
<dependency>
	<groupId>org.mybatis</groupId>
	<artifactId>mybatis</artifactId>
	<version>3.2.8</version>
</dependency>
<!--整合包-->
<dependency>
	<groupId>org.mybatis</groupId>
	<artifactId>mybatis-spring</artifactId>
	<version>1.2.2</version>
</dependency> 
<!--整合事务-->
<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
java配置类
import javax.sql.DataSource;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.io.Resource;
import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
import org.springframework.core.io.support.ResourcePatternResolver;
import org.mybatis.spring.mapper.MapperScannerConfigurer;
@Configuration
public class MyBatisConfig {
@Bean
@ConditionalOnMissingBean //当容器里没有指定的Bean的情况下创建该对象
public SqlSessionFactoryBean sqlSessionFactory(DataSource dataSource) {
	SqlSessionFactoryBean sqlSessionFactoryBean = new SqlSessionFactoryBean();
	sqlSessionFactoryBean.setDataSource(dataSource);
	ResourcePatternResolver resolver = new PathMatchingResourcePatternResolver();
	Resource mybatisConfigXml = resolver.getResource("classpath:mybatis/mybatis-config.xml");
	sqlSessionFactoryBean.setConfigLocation(mybatisConfigXml);
	sqlSessionFactoryBean.setTypeAliasesPackage("com.taotao.cart.pojo");
	return sqlSessionFactoryBean;
}
// mapper接口的扫描器,可用@MapperScan代替
@Bean
public MapperScannerConfigurer mapperScannerConfigurer() {
	MapperScannerConfigurer mapperScannerConfigurer = new MapperScannerConfigurer();
	mapperScannerConfigurer.setBasePackage("com.taotao.cart.mapper");
	return mapperScannerConfigurer;
	}
}

事务管理
在Spring Boot中推荐使用@Transactional注解来申明事务。
当引入jdbc依赖之后,Spring Boot会自动默认分别注入DataSourceTransactionManager
或JpaTransactionManager,所以我们不需要任何额外配置就可以用@Transactional注解进行事务的使用。
在Service中添加@Transactional注解:

6. Spring的整合Redis

	在Spring Boot中提供了RedisTempplate的操作,
	import java.util.ArrayList;
	import java.util.List;

	import org.springframework.beans.factory.annotation.Value;
	import org.springframework.context.annotation.Bean;
	import org.springframework.context.annotation.Configuration;
	import org.springframework.context.annotation.PropertySource;

	import redis.clients.jedis.JedisPoolConfig;
	import redis.clients.jedis.JedisShardInfo;
	import redis.clients.jedis.ShardedJedisPool;

	@Configuration
	@PropertySource(value = "classpath:redis.properties")
	public class RedisSpringConfig {

	@Value("${redis.maxTotal}")
	private Integer redisMaxTotal;

	@Value("${redis.node1.host}")
	private String redisNode1Host;

	@Value("${redis.node1.port}")
	private Integer redisNode1Port;

	private JedisPoolConfig jedisPoolConfig() {
		JedisPoolConfig jedisPoolConfig = new JedisPoolConfig();
		jedisPoolConfig.setMaxTotal(redisMaxTotal);
		return jedisPoolConfig;
	}

	@Bean
	public ShardedJedisPool shardedJedisPool() {
		List<JedisShardInfo> jedisShardInfos = new ArrayList<JedisShardInfo>();
		jedisShardInfos.add(new JedisShardInfo(redisNode1Host, redisNode1Port));
		return new ShardedJedisPool(jedisPoolConfig(), jedisShardInfos);
		}
	}

7. Spring的整合Httpclient

import org.apache.http.client.config.RequestConfig;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.PropertySource;
import org.springframework.context.annotation.Scope;

import com.taotao.common.httpclient.IdleConnectionEvictor;

@Configuration
@PropertySource(value = "classpath:httpclient.properties")
public class HttpclientSpringConfig {

@Value("${http.maxTotal}")
private Integer httpMaxTotal;

@Value("${http.defaultMaxPerRoute}")
private Integer httpDefaultMaxPerRoute;

@Value("${http.connectTimeout}")
private Integer httpConnectTimeout;

@Value("${http.connectionRequestTimeout}")
private Integer httpConnectionRequestTimeout;

@Value("${http.socketTimeout}")
private Integer httpSocketTimeout;

@Value("${http.staleConnectionCheckEnabled}")
private Boolean httpStaleConnectionCheckEnabled;

@Autowired
private PoolingHttpClientConnectionManager manager;

@Bean
public PoolingHttpClientConnectionManager poolingHttpClientConnectionManager() {
	PoolingHttpClientConnectionManager poolingHttpClientConnectionManager = new PoolingHttpClientConnectionManager();
	// 最大连接数
	poolingHttpClientConnectionManager.setMaxTotal(httpMaxTotal);
	// 每个主机的最大并发数
	poolingHttpClientConnectionManager.setDefaultMaxPerRoute(httpDefaultMaxPerRoute);
	return poolingHttpClientConnectionManager;
}

// 定期关闭无效连接
@Bean
public IdleConnectionEvictor idleConnectionEvictor() {
	return new IdleConnectionEvictor(manager);
}

// 定义Httpclient对
@Bean
@Scope("prototype")
public CloseableHttpClient closeableHttpClient() {
	return HttpClients.custom().setConnectionManager(this.manager).build();
}

// 请求配置
@Bean
public RequestConfig requestConfig() {
	return RequestConfig.custom().setConnectTimeout(httpConnectTimeout) // 创建连接的最长时间
	.setConnectionRequestTimeout(httpConnectionRequestTimeout) // 从连接池中获取到连接的最长时间
	.setSocketTimeout(httpSocketTimeout) // 数据传输的最长时间
	.setStaleConnectionCheckEnabled(httpStaleConnectionCheckEnabled) // 提交请求前测试连接是否可用
	.build();
}

}

8. Spring的整合RabbitMQ

导入spring-boot-starter-amqp的依赖
<dependency>
	<groupId>org.springframeword.boot</groupId>
	<artifactId>spring-boot-starter-amqp</artifactId>
</dependency>
application.properties文件中配置RabbitMQ的连接信息
spring.rabbitmq.host=127.0.0.1
spring.rabbitmq.port=5672
spring.rabbitmq.password=root
spring.rabbitmq.username=test
spring.rabbitmq.virtual-hos=/test

编写Rabbit的Spring配置类
import org.springframework.amqp.core.Queue;
import org.springframework.amqp.rabbit.connection.ConnectionFactory;
import org.springframework.amqp.rabbit.core.RabbitAdmin;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class RabbitMQSpringConfig {

@Autowired
private ConnectionFactory connectionFactory;

// 管理
@Bean
public RabbitAdmin rabbitAdmin() {
	return new RabbitAdmin(connectionFactory);
}

// 声明队列
@Bean
public Queue taotaoCartLoginQueue() {
	// 默认就是自动声明的
	return new Queue("TAOTAO-CART-LOGIN-QUEUE", true);
}

// 声明队列
@Bean
public Queue taotaoCartOrderSuccessQueue() {
	// 默认就是自动声明的
	return new Queue("TAOTAO-CART-ORDER-SUCCESS-QUEUE", true);
}

}
设置监听
@Component
public class Test{
	@RabbitListener(queues = "xxxx")
	public void fun(){}
}

9. spring整合Servlet、Filter、Listener

注册Servlet
①使用ServletRegistrationBean注册
使用ServletRegistrationBean注册只需要在@Configuration类中加入即可
@Configuration
public class Registration{
@Bean  
public ServletRegistrationBean myServlet() {  
	ServletRegistrationBean myServlet = new ServletRegistrationBean();  
	myServlet.addUrlMappings("/servlet");  
	myServlet.setServlet(new MyServlet());  
	return myServlet;  
}
}
②使用@WebServlet
使用@WebServlet注册,需要在Servlet类上使用该注解即可,
但是需要在@Configuration类中使用@ServletComponentScan扫描注册相应的Servlet
注册Filter
注意注册多个filter要自己一个个注册不要挤在一起
①使用FilterRegistrationBean注册
使用FilterRegistrationBean注册Filter,只需要在@Configuration类中加入即可
@Bean  
public FilterRegistrationBean myFilter() {  
	FilterRegistrationBean myFilter = new FilterRegistrationBean();  
	myFilter.addUrlPatterns("/*");  
	myFilter.setFilter(new MyFilter());  
	return myFilter;  
}  
②使用@WebFilter
使用@WebFilter注册,需要在Filter类上使用该注解即可,
但是需要在@Configuration类中使用@ServletComponentScan扫描注册相应的Filter。
 
注册Listener
①使用ServletListenerRegistrationBean注册
使用ServletListenerRegistrationBean注册Listener只需要在@Configuration类中加入即可
@Bean  
public ServletListenerRegistrationBean<MyListener> myServletListener() {  
	ServletListenerRegistrationBean<MyListener> myListener = 
	new ServletListenerRegistrationBean<MyListener>();
	myListener.setListener(new MyListener());  
	return myListener;  
}  
②使用@WebListener
使用@WebListener注册,需要在Filter类上使用该注解即可,
但是需要在@Configuration类中使用Spring Boot提供的注解
@ServletComponentScan扫描注册相应的Listener

10. springboot常见问题

47.png
47.png
Slf4j日志警告
提示我们当前的项目中slf4j引入了2个,导致了jar冲突。
解决:删除自己引入到slf4j的依赖
<dependency>
	<groupId>org.slf4j</groupId>
	<artifactId>slf4j-log4jl2</artifactId>
</dependency>

jsp访问404的问题
由于Spring boot使用的内嵌的tomcat,而内嵌的tamcat是不支持jsp页面的,
导包
<dependency>
	<groupId>org.apache.tomcat.embed</groupId>
	<artifactId>tomcat-embed-jasper</artifactId>
	<scope>provided</scope>
</dependency>