[Java EE] Spring 配置 和 日志
目录
1. 配置文件
1.1 作用
1.2 Spring Boot 配置文件
1.3 读取配置文件
1.3.1 配置对象
1.3.2 配置集合
1.3.3 配置Map
1.4 yml 优缺点
2. 日志
2.1 日志的作用
2.2 日志的使用
2.3 日志框架
2.3.1 门面模式(外观模式)
2.4 SLF4J 框架介绍
2.5 日志格式的说明
2.5.1 日志级别
2.5.3 日志级别的使用
2.5.4 日志配置
2.5.5 日志持久化
2.5.6 配置日志文件分割
2.5.7 配置日志格式
2.5.8 简单的日志输出
1. 配置文件
1.1 作用
主要是为了解决硬编码带来的问题, 把可能会发生改变的信息集中在一个地方, 当我们启动某个程序时, 应用程序从配置文件中读取数据, 并加载运行。使用配置文件, 可以使程序完成用户和应用程序的交互, 或者应用程序与其他应用程序的交互。
1.2 Spring Boot 配置文件
Spring Boot 支持并且定义了配置文件的格式, 很多项目或者框架的配置信息放在其中, 比如项目的启动端口、数据库的连接信息、第三方系统的调用密钥等信息、用于发现和定位问题的日志等。
Spring Boot 配置文件格式
大致有以下两种:
(1) application.properties
properties 配置是以 key-value 的形式配置的,key 和 value 之间使用"="连接, 每次使用都需要写前缀,会有很多的冗余的信息,当表示纯字符串的时候需要加 ' ' 单双引号。
spring.datasource.url=jdbc:mysql://127.0.0.1:3306/testdbcharacterEncoding=utf8&useSSL=false
spring.datasource.username=root
spring.datasource.password='123456'
(2) application.yml
yml 是 YAML 的缩写, 全称为 Yet Another Markup Language , yml 是树形结构的配置文件, 它的基础语法是"key: value"。key 和 value 之间使用英文冒号加空格的方式组成, 空格不能省略。
使用 yml 连接数据库:
spring:datasource:url: jdbc:mysql://127.0.0.0:3306/dbname?characterEncoding=utf8&useSSL=falseusername: rootpassword: root
1.3 读取配置文件
yml 和 properties 都是用 org 里的 @Value "${}" 格式读取, 如下代码所示
mykey.key1 = Miraitowa
package com.huangyi.test;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
public class Controller {@Value("${mykey.key1}")private String key1;@RequestMapping("/key")public String key() {return key1;}
}
运行结果:
1.3.1 配置对象
我们可以在 yml 中配置对象
student:id: 1name: Javaage: 18
这个时候我们读取对象 需要使用 @ConfigurationProperties 来读取, 代码如下
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
@ConfigurationProperties(prefix = "student")
@Component
@Data
public class Student {private int id;private String name;private int age;
}
调用类如下代码:
@RestController
public class StudentController {@Autowiredprivate Student student;@RequestMapping("/readStudent")public String readStudent(){return student.toString();}
}
访问结果如下:
1.3.2 配置集合
配置文件也可以配置 list 集合, 如下所示:
dbtypes:name:- mysql- sqlserver- db2
我们也使用 @ConfigurationProperties(prefix = “xxxxx”) 来读取集合
@Component
@ConfigurationProperties("dbtypes")
@Data
public class ListConfig {private List<String> name;
}
访问集合的实现如下:
@RestController
public class ReadYml2 {@Autowiredprivate ListConfig listConfig;@RequestMapping("/readList")public String readList(){return listConfig.toString();}
}
1.3.3 配置Map
maptypes:map:k1: kk1k2: kk2k3: kk3
Map 的读取也是使用 @ConfigurationProperties(prefix = “xxxxx”) 来读取
@Component
@ConfigurationProperties("maptypes")
@Data
public class MapConfig {private HashMap<String,String> map;
}
打印类的实现如下
@RestController
public class ReadYml2 {@Autowiredprivate MapConfig mapConfig;@RequestMapping("/readMap")public String readStudent(){return mapConfig.toString();}
}
1.4 yml 优缺点
优点:
(1) 可读性高, 写法简单, 易于理解
(2) 支持更多的数据类型, 可以简单表达对象, 数组, List, Map等数据形态
缺点:
(1) 不适合写复杂的配置文件
2. 日志
2.1 日志的作用
随着项目的复杂提升, 我们需要借助日志定位排查问题。当需要记录一些用户的操作记录时, 也可以使用日志来记录用户的一些喜好,日志主要是为了发现问题, 分析问题, 定位问题。
2.2 日志的使用
(1) 在程序中得到日志对象
private static Logger logger = LoggerFactory.getLogger(LoggerController.class);
LoggerFactory.getLogger 需要一个参数, 标识这个日志的名称, 这样就可以知道是哪个类输出的日志, 方便定位到问题类。
Logger 对象是属于 org.slf4j 包下的, 不要导⼊错包。
(2) 使用日志对象输出要打印的内容
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
public class LoggerController {private static Logger logger =LoggerFactory.getLogger(LoggerController.class);@RequestMapping("/logger")public String logger(){logger.info("--------------要输出⽇志的内容----------------");return "打印⽇志";}
}
打印日志效果展示:
2.3 日志框架
SLF4J 不同于其他日志框架, 它不是一个真正的日志实现,而是一个抽象层,对日志框架制定的一种规范标准,所有的SLF4J 不能独立使用,需要和具体的日志框架配合使用
2.3.1 门面模式(外观模式)
门面模式又称为外观模式, 提供了一个统一的接口, 用来访问子系统中的一群接口, 其主要特征是定义了一个高层接口, 让子系统更容易使用。
门面模式主要包含两种角色
1.外观角色(Facade):也称为门面角色, 系统对外的统一接口。
2.子系统角色(SubSystem): 可以同时有一个或多个 SubSystem, 每一个都不是一个单独的类,而是一个类的集合。SubSystem 不知道 Facade 的存在, 对于SubSystem 而言, Facade 只是另一个客户端(Facade 对 SubSystem 透明)
门面模式的优点
1. 减少了系统的相互依赖,实现了客户端与子系统解耦合
2. 提高了灵活性,简化了客户端对子系统的使用难度
3. 提高了安全性,可以灵活设定访问权限
2.4 SLF4J 框架介绍
SLF4J 是其他日志框架的门面,可以理解是提供日志服务的统一API接口,并不涉及到具体的日志逻辑实现,常见的日志框架有 log4J,logback 等,如果一个项目使用了 log4j,而你依赖的另一类库依赖于另外一个日志框架 logback, 那么你就需要把 logback 也加载进去,
存在问题:
1. 不同日志框架的 API 接口和配置文件不同,如果多个人日志框架共存,那么不得不维护多套配置文件
2. 如果要更换日志框架,就需要修改代码,过程中可能就会存在代码冲突
3. 如果引入的第三方框架使用了多套,那么就不得不维护多套配置
2.5 日志格式的说明
(1) 时间日期:精确到毫秒
(2) 日志级别:ERROR,WARN,INFO,DEBUG 或 TRACE
(3) 进程ID
(4) 线程名
(5) Logger名(通常使用源代码的类名)
(6) 日志内容
2.5.1 日志级别
日志级别代表着日志信息对应问题的严重性,为了更快的筛选符合目标的日志信息
• FATAL: 致命信息, 标识需要理解被处理的系统级错误
• ERROR: 错误信息, 级别较高的错误日志信息, 但仍然不影响系统的继续运行
• WARN: 警告信息, 不影响使用, 但需要注意的问题
• INFO: 普通信息, 用于记录应用程序正常运行时的一些信息
• DEBUG: 调试信息, 需要调试时候的关键信息打印
• TRACE: 追踪信息
日志的级别顺序
2.5.3 日志级别的使用
日志级别是开发人员自己设置的, 开发人员根据自己的理解来判断信息的重要程度
@RequestMapping("/printLog")public String printLog() {logger.trace("================= trace ===============");logger.debug("================= debug ===============");logger.info("================= info ===============");logger.warn("================= warn ===============");logger.error("================= error ===============");return "打印不同级别的⽇志" ;}
观察打印的日志结果:
结果发现, 只打印了INFO, WARN 和 ERROR 级别的日志
这与日志级别的配置有关, 日志的输出级别默认是 INFO 级别, 所以只会打印大于此级别的日志,
2.5.4 日志配置
日志级别配置只需要在配置文件中设置"logging.level"配置项即可
Properties 配置
logging.level.root=debug
重新运行上述代码, 观察结果:
2.5.5 日志持久化
以上的日志都是在控制台输出, 但是我们需要把日志保存下来以便追溯问题, 把日志保存下来就叫持久化
日志持久化有两种方式:
1. 配置日志文件名
2. 配置日志的存储目录
yml配置:
# 设置⽇志⽂件的⽂件名
logging:file:name: logger/springboot.logpath: D:/temp
运行程序, 该程序下多出一个日志文件: springboot.log
注意:logging.file.name 和 logging.file.path 两个配置的情况下, 只生效 logging.file.name 为准
2.5.6 配置日志文件分割
如果我们的日志都放在一个文件中, 随着项目的运行, 日志文件会越来越大, 需要对日志文件进行分割。
Properties 配置
logging.logback.rollingpolicy.file-name-pattern=${LOG_FILE}.%d{yyyy-MM-dd}.%i
logging.logback.rollingpolicy.max-file-size=1KB
项目运行, 多打印一些日志, 分割结果如下:
2.5.7 配置日志格式
logging.pattern.console='%d{yyyy-MM-dd HH:mm:ss.SSS} %c %M %L [%thread] %m%n'
• %clr(表达式){颜色} 设置输入日志的颜色
• %d{} 日期和时间
• %5p 显示日志级别
• %t 线程名, %c 类的全限定名, %M method, %L 为行号, %thread 线程名称. %m 或者 %msg 显示输出消息, %n 换行符
2.5.8 简单的日志输出
每次使用 LoggerFactory.getLogger(xxxx.class) 很繁琐, 且每个类都添加一遍, lombok 给我们提供了一种更简单的方式
(1) 添加 lombok 框架支持
<dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId><optional>true</optional></dependency>
(2) 使用 @slf4j 注解输出日志
package com.huangyi.test;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.RestController;
@Slf4j
@RestController
public class LogController {public void log(){log.info("--------------要输出⽇志的内容----------------");}
}
lombok 提供的 slf4j 会帮我们提供一个日志对象 log, 我门直接使用就可以
==============================================================================
如果觉得有帮助的话给博主点个赞吧!祝您在学习的路上顺风顺水!