admin管理员组文章数量:1594553
黑马程序员SpringBoot2课程笔记
一、基础篇
略
二、运维实用篇
1.SpringBoot运行与部署
略
2. SpringBoot配置
2.1 临时属性配置
可以在启动Boot程序时添加临时属性改变配置
2.1.1 属性加载优先级
配置是属性是存在优先级的,当项目中的配置冲突时,优先级高的配置会覆盖优先级低的配置
具体的优先级关系如下:
2.1.2 开发环境使用临时属性
在开发环境中也可以添加临时属性改变配置
临时属性会作为启动类的形参传入启动方法,为防止程序被临时属性破坏,可以通过去掉启动类的形参提高我们程序的安全性
2.1.3 小结
2.2 配置文件分类
在实际开发中,各级开发及管理人员应操作不同的配置文件,
SpringBoot中有4级配置文件,如下:
不同级别的配置文件间配置互补,冲突的配置按优先级生效
2.3 自定义配置文件
SpringBoot启动时默认加载名称为Application的配置文件,可以通过设置启动参数更换加载的配置文件名称
此处加载名称为ebank的配置文件
3. 多环境开发
在企业中不同的开发环境对应不同的配置
3.1 单yaml文件配置
可以在一个yaml配置文件中设定不同环境对应的配置,不同的环境配置用---分割
设置active属性,指定启用的环境配置
格式如下:
3.2 多yaml文件配置
使用单一yaml文件配置多环境有暴露权限的风险,不利于维护。
所以使用多个配置文件对应不同的生产环境更加合理。
3.3 多properties文件配置
properties文件配置多环境只支持多文件配置
3.4 多环境配置文件拆分
将不同技术的配置文件拆分来开,在主配置文件中引入,利于维护管理
注意引入配置文件时,配置文件的加载顺序会影响配置的生效,主配置文件必定最后一个加载
SpringBoot2.4后的多环境配置方式:
3.5 多环境开发控制
Maven和SpringBoot都存在多环境的配置管理,而SpringBoot程序依赖于Maven,所以在实际开发时应以Maven的多环境配置为准,让SpringBoot读取Maven的配置
实现步骤:
步骤①:在Maven中进行多环境配置,每个配置内设定对应的属性变量
步骤②:在Boot配置文件中使用@...@占位符,读取当前生效的Maven属性值
步骤③:执行打包操作
4. 日志
4.1 日志基础配置
4.2 快速创建日志对象
4.3 日志输出格式控制
SpringBoot默认日志格式:
自定义日志格式:
4.4 日志文件
在实际开发中,日志信息应输出到文件中以便项目的维护
三、开发实用篇
1. 热部署*
热部署指当我们对项目进行修改后,无需重启服务器即可让修改生效
1.1 手动开启热部署
步骤如下:
重启和重载的概念:
因为热部署不需要重新加载jar包,所以热部署只执行重启操作,而重启项目会执行重启和重载操作。
1.2 自动开启热部署
手动开启热部署每次都要手动的去Build工程,繁琐程度与重启项目比并无太大差别,可以通过设置让IDEA自动Build工程
步骤如下:
第①步:在设置中勾选自动构建项目开关
第②步:快捷键ctrl + alt + shift + /打开菜单,勾选自动构建
设置完成,当修改完项目代码之后,只需离开IDEA5秒后即可激活热部署
1.3 参与热部署监控的文件范围配置
通过修改项目中的文件,可以发现其实并不是所有的文件修改都会激活热部署的,原因在于在开发者工具中有一组配置,当满足了配置中的条件后,才会启动热部署
配置中默认不参与热部署的目录信息如下:
可以在Applicaiton.yml配置文件中自定义哪些文件/文件夹不参与热部署
1.4 关闭热部署
方式①:修改Application.yml配置文件
将enabled属性改为flase
注意:配置文件存在优先级,有可能在更高级别的配置文件中设置了开启热部署,覆盖了此处的设置
方式②:使用更高级别的配置关闭热部署
既然我们怕别人在优先级别高的地方启动热部署,那我们就在优先级别比较高的地方禁用热部署
配置的优先级如下:
application.yml配置文件在优先级为3的地方,我们可以在其更高的优先级位置关闭热部署
在启动类中设置系统属性(级别6)关闭热部署
在springboot启动类当中输出 System.setProperty("spring.devtools.restart.enabled","false");即可关闭热部署功能
2. 配置高级
2.1 第三方bean属性绑定(注入)
在基础篇学习了@ConfigurationProperties注解,此注解的作用是用来为bean绑定(注入)属性的。
回顾一下使用过程,开发者可以在yml配置文件中以对象的格式添加若干属性
servers:
ip-address: 192.168.0.1
port: 2345
timeout: -1
然后再定义一个用来封装数据的实体类,注意要提供属性对应的setter方法,
@Component
@Data
public class ServerConfig {
private String ipAddress;
private int port;
private long timeout;
}
最后使用@ConfigurationProperties注解就可以将配置中的属性值注入到开发的模型类上。
@Component
@Data
@ConfigurationProperties(prefix = "servers")
public class ServerConfig {
private String ipAddress;
private int port;
private long timeout;
}
这样加载对应bean的时候就可以直接加载配置属性值了。但是目前我们学的都是给自定义的bean使用这种形式加载属性值,如果是第三方的bean呢?能不能用这种形式加载属性值呢?为什么会提出这个疑问?原因就在于当前@ConfigurationProperties注解是写在类定义的上方,而第三方开发的bean源代码不是你自己书写的,你也不可能到源代码中去添加@ConfigurationProperties注解,这种问题该怎么解决呢?下面就来说说这个问题。
使用@ConfigurationProperties注解其实可以为第三方bean加载属性,格式特殊一点而已,以Druid数据源为例:
步骤①:使用@Bean注解定义第三方bean
@Bean
public DruidDataSource datasource(){
DruidDataSourceds=newDruidDataSource();
returnds;
}
步骤②:在yml中定义要绑定的属性,注意datasource此时全小写
datasource:
driverClassName: com.mysql.jdbc.Driver
步骤③:使用@ConfigurationProperties注解为第三方bean进行属性绑定,注意前缀是全小写的datasource
@Bean
@ConfigurationProperties(prefix="datasource")
publicDruidDataSourcedatasource(){
DruidDataSourceds=newDruidDataSource();
returnds;
}
操作方式完全一样,只不过@ConfigurationProperties注解不仅能添加到类上,还可以添加到方法上,添加到类上是为spring容器管理的当前类的对象绑定属性,添加到方法上是为spring容器管理的当前方法的返回值对象绑定属性,其实本质上都一样。
做到这其实就出现了一个新的问题,目前我们定义bean不是通过类注解定义就是通过@Bean定义,使用@ConfigurationProperties注解可以为bean进行属性绑定,因为这个注解不仅可以写在类上,还可以写在方法上,所以无法直观的查看到有哪些bean通过注解@ConfigurationProperties去绑定了属性,不利于开发与维护。
为了解决这个问题,spring给提供了一个全新的注解@EnableConfigurationProperties,专门标注使用@ConfigurationProperties注解绑定属性的bean是哪些,使用步骤如下
步骤①:在配置类上开启@EnableConfigurationProperties注解,并且标注要使用@ConfigurationProperties注解绑定属性的类
@SpringBootApplication
@EnableConfigurationProperties(ServerConfig.class)
public class Springboot13ConfigurationApplication {
}
步骤②:在对应的类上直接使用@ConfigurationProperties进行属性绑定
@Data
@ConfigurationProperties(prefix="servers")
publicclassServerConfig {
privateStringipAddress;
privateintport;
privatelongtimeout;
}
注意:此时在该类的上方就不能使用@Componet注解定义bean,会出现bean不唯一定义异常
@EnableConfigurationProperties告诉Spring开启配置文件属性注入功能,且有哪些类要加载配置文件中的属性,而读取Spring的配置文件的前提是这个类要被Spring容器所管理,所以Spring会自动将定义在这个注解内部的类声明为一个bean
最后再说一个小技巧,使用@ConfigurationProperties注解时,会出现一个提示信息
出现这个提示后只需要添加一个坐标此提醒就消失了
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-configuration-processor</artifactId>
</dependency>
总结
使用@ConfigurationProperties可以为使用@Bean声明的第三方bean绑定属性
当使用@EnableConfigurationProperties声明进行属性绑定的bean后,无需使用@Component注解再次进行bean声明
2.2 松散绑定
在进行属性绑定时,可能会遇到如下情况,为了进行标准命名,开发者会将属性名严格按照驼峰命名法书写,在yml配置文件中将datasource修改为dataSource,如下:
dataSource:
driverClassName: com.mysql.jdbc.Driver
此时程序可以正常运行,然后又将代码中的前缀datasource修改为dataSource,如下:
@Bean
@ConfigurationProperties(prefix="dataSource")
publicDruidDataSourcedatasource(){
DruidDataSourceds=newDruidDataSource();
returnds;
}
此时就发生了编译错误,而且并不是idea工具导致的,运行后依然会出现问题,配置属性名dataSource是无效的
Configurationpropertyname'dataSource'isnotvalid:
Invalidcharacters:'S'
Bean:datasource
Reason:Canonicalnamesshouldbekebab-case('-'separated),lowercasealpha-numericcharactersandmuststartwithaletter
Action:Modify'dataSource'sothatitconformstothecanonicalnamesrequirements.
为什么会出现这种问题,这就要来说一说springboot进行属性绑定时的一个重要知识点了,有关属性名称的宽松绑定,也可以称为宽松绑定。
宽松绑定是springboot进行编程时人性化设计的一种体现,即配置文件中的命名格式与变量名的命名格式可以进行格式上的最大化兼容。兼容到什么程度呢?几乎主流的命名格式都支持,例如:
在ServerConfig中的属性名ipAddress
@Component
@Data
@ConfigurationProperties(prefix="servers")
publicclassServerConfig {
private String ipAddress;
}
可以与下面的配置属性名规则全兼容
servers:
ipAddress: 192.168.0.2 # 驼峰模式
ip_address: 192.168.0.2 # 下划线模式
ip-address: 192.168.0.2 # 烤肉串模式
IP_ADDRESS: 192.168.0.2 # 常量模式
也可以说,以上4种模式最终都可以匹配到ipAddress这个属性名。为什么这样呢?原因就是在进行匹配时,配置中的名称要去掉中划线和下划线后,忽略大小写的情况下去与java代码中的属性名进行忽略大小写的等值匹配,以上4种命名去掉下划线中划线忽略大小写后都是一个词ipaddress,java代码中的属性名忽略大小写后也是ipaddress,这样就可以进行等值匹配了,这就是为什么这4种格式都能匹配成功的原因。不过springboot官方推荐使用烤肉串模式,也就是中划线模式。
到这里我们掌握了一个知识点,就是命名的规范问题。再来看开始出现的编程错误信息
Configurationpropertyname'dataSource'isnotvalid:
Invalidcharacters:'S'
Bean:datasource
Reason:Canonicalnamesshouldbekebab-case('-'separated),lowercasealpha-numericcharactersandmuststartwithaletter
Action:Modify'dataSource'sothatitconformstothecanonicalnamesrequirements.
其中Reason描述了报错的原因,规范的名称应该是烤肉串(kebab)模式(case),即使用-分隔,使用小写字母数字作为标准字符,且必须以字母开头。然后再看我们写的名称dataSource,就不满足上述要求。闹了半天,在书写前缀时,这个词不是随意支持的,必须使用上述标准。编程写了这么久,基本上编程习惯都养成了,到这里又被springboot教育了,没辙,谁让人家东西好用呢,按照人家的要求写吧。
注意:
以上规则仅针对springboot中@ConfigurationProperties注解进行属性绑定时有效,对@Value注解进行属性映射无效。
且@ConfigurationProperties中的前缀命名仅能使用小写的数字、字母、下划线
总结
@ConfigurationProperties绑定属性时支持属性名宽松绑定,这个宽松体现在属性名的命名规则上
@Value注解不支持松散绑定规则
绑定前缀名推荐采用烤肉串命名规则,即使用中划线做分隔符,使用小写的字母、数字、下划线
2.3 常用计量单位
在前面的配置中,我们书写了如下配置值,其中第三项超时时间timeout描述了服务器操作超时时间,当前值是-1表示永不超时。
servers:
ip-address: 192.168.0.1
port: 2345
timeout: -1
但是每个人都这个值的理解会产生不同,比如线上服务器完成一次主从备份,配置超时时间240,这个240如果单位是秒就是超时时间4分钟,如果单位是分钟就是超时时间4小时。面对一次线上服务器的主从备份,设置4分钟,简直是开玩笑,别说拷贝过程,备份之前的压缩过程4分钟也搞不定,这个时候问题就来了,怎么解决这个误会?
除了加强约定之外,springboot充分利用了JDK8中提供的全新的用来表示计量单位的新数据类型,从根本上解决这个问题。以下模型类中添加了两个JDK8中新增的类,分别是Duration和DataSize
@Component
@Data
@ConfigurationProperties(prefix="servers")
publicclassServerConfig {
@DurationUnit(ChronoUnit.HOURS)
private Duration serverTimeOut;
@DataSizeUnit(DataUnit.MEGABYTES)
private DataSize dataSize;
}
Duration:表示时间间隔,可以通过@DurationUnit注解描述时间单位,例如上例中描述的单位为小时(ChronoUnit.HOURS)
DataSize:表示存储空间,可以通过@DataSizeUnit注解描述存储空间单位,例如上例中描述的单位为MB(DataUnit.MEGABYTES)
使用上述两个单位就可以有效避免因沟通不同步或文档不健全导致的信息不对称问题,从根本上解决了问题,避免产生误读。
2.4 bean注入数据校验
目前我们在进行属性绑定时可以通过松散绑定规则在书写时放飞自我了,但是在书写时由于无法感知模型类中的数据类型,就会出现类型不匹配的问题,比如代码中需要int类型,配置中给了非法的数值,例如写一个“a",这种数据肯定无法有效的绑定,还会引发错误。
SpringBoot给出了强大的数据校验功能,可以有效的避免此类问题的发生。在JAVAEE的JSR303规范中给出了具体的数据校验标准,开发者可以根据自己的需要选择对应的校验框架,此处使用Hibernate提供的校验框架来作为实现进行数据校验。书写应用格式非常固定,话不多说,直接上步骤:
步骤①:导入校验框架坐标
<!--1.导入JSR303规范-->
<dependency>
<groupId>javax.validation</groupId>
<artifactId>validation-api</artifactId>
</dependency>
<!--使用hibernate框架提供的校验器做实现-->
<dependency>
<groupId>org.hibernate.validator</groupId>
<artifactId>hibernate-validator</artifactId>
</dependency>
步骤②:在需要开启校验功能的类上使用注解<
本文标签: 课程笔记SpringBoot
版权声明:本文标题:SpringBoot课程笔记 内容由热心网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:https://www.elefans.com/dianzi/1728195198a1149211.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论