美文网首页SpringBoot精选
Springboot整合Slf4j输出日志到控制台、文件、Mys

Springboot整合Slf4j输出日志到控制台、文件、Mys

作者: 程就人生 | 来源:发表于2020-03-28 16:03 被阅读0次

    在做项目时,日志如何输出,在何时输出,输出到哪里,这也是开发过程中,一个很重要的问题,很值得思考。不要等到项目上线了,才想到日志输出。特别是对于一些特定业务场景的跟踪,日志输出为后续的跟踪、维护,起着很大的作用。

    这里使用了SLF4J作为日志组件,先明确一下SLF4J的概念,SLF4J是Simple logging Facade for Java的简称,它不是一个真正的日志实现,而是一个抽象层( abstraction layer),它允许你在后台使用任意一个日志类库。

    日志一般有DEBUG、INFO、WARN、ERROR四个级别,日志输出按照需要的等级进行输出。现在就写一个demo,来生成日志文件,并输出到控制台、文件以及Mysql数据库。

    本demo的开发环境:

    SpringBoot2.1.4版本
    数据库:Mysql
    数据库注解:MyBatis
    数据源:DruidDataSource
    

    第一步,日志文件的配置;

    <?xml version="1.0" encoding="UTF-8"?>
    <configuration>
        <!--定义日志文件的存储地址 勿在 LogBack 的配置中使用相对路径-->
        <property name="LOG_HOME" value="c:/log"/>
        <!-- 控制台输出 -->
        <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
            <encoder class="ch.qos.logback.classic.encoder.PatternLayoutEncoder">
                <!--格式化输出:%d表示日期,%thread表示线程名,%-5level:级别从左显示5个字符宽度%msg:日志消息,%n是换行符-->
                <pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{50} - %msg%n</pattern>
            </encoder>
        </appender>
        <!-- 按照每天生成日志文件 -->
        <appender name="FILE" class="ch.qos.logback.core.rolling.RollingFileAppender">
            <rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
                <!--日志文件输出的文件名-->
                <FileNamePattern>${LOG_HOME}/log-%d{yyyy-MM-dd}.log</FileNamePattern>
                <!--日志文件保留天数-->
                <MaxHistory>30</MaxHistory>
            </rollingPolicy>
            <encoder class="ch.qos.logback.classic.encoder.PatternLayoutEncoder">
                <!--格式化输出:%d表示日期,%thread表示线程名,%-5level:级别从左显示5个字符宽度%msg:日志消息,%n是换行符-->
                <pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{50} - %msg%n</pattern>
                <!-- 设置字符集,防止乱码 -->
                <charset>UTF-8</charset>
            </encoder>
            <!--日志文件最大的大小-->
            <triggeringPolicy class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
                <MaxFileSize>10MB</MaxFileSize>
            </triggeringPolicy>
        </appender>
    
        <!--myibatis log configure-->
        <logger name="com.example.demo.mapper" level="TRACE"/><!-- TRACE会打印在控制台、写在日志文件里 -->
        <!-- <logger name="java.sql.Connection" level="DEBUG"/>
        <logger name="java.sql.Statement" level="DEBUG"/>
        <logger name="java.sql.PreparedStatement" level="DEBUG"/> -->
    
        <!--日志异步到数据库 -->
        <appender name="DbAppender" class="ch.qos.logback.classic.db.DBAppender">
            <!--数据源配置-->
            <connectionSource class="ch.qos.logback.core.db.DataSourceConnectionSource">
                <dataSource class="com.alibaba.druid.pool.DruidDataSource" >
                    <url>jdbc:mysql://localhost:3306/test?serverTimezone=GMT%2B8</url>
                    <username>root</username>
                    <password>123456</password>
                </dataSource>
            </connectionSource>
        </appender>
        
        <!-- 日志输出级别 -->
        <root level="info">
            <appender-ref ref="STDOUT"/>
            <appender-ref ref="FILE"/>
        </root>    
        <!-- 日志单独配置 -->
        <logger name="com.example.demo" level="info">      
            <appender-ref ref="DbAppender" />      
        </logger>      
    </configuration>
    

    第二步,在application.properties中对日志的配置文件进行引入;

    //数据库连接配置
    spring.datasource.type=com.alibaba.druid.pool.DruidDataSource
    spring.datasource.url=jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=GMT%2B8&allowMultiQueries=true
    spring.datasource.username=root
    spring.datasource.password=123456
    spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
    mybatis.mapper-locations=classpath:mapper/*.xml
    //日志文件路径配置
    logging.config=classpath:Logback.xml
    

    第三步,在Mysql数据库表中建立日志插入的表单;

    CREATE TABLE `logging_event`  (
      `timestmp` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
      `formatted_message` varchar(4000) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
      `logger_name` varchar(254) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
      `level_string` varchar(254) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
      `thread_name` varchar(254) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
      `reference_flag` tinyint(4) NULL DEFAULT NULL,
      `arg0` varchar(254) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
      `arg1` varchar(254) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
      `arg2` varchar(254) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
      `arg3` varchar(254) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
      `caller_filename` varchar(254) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
      `caller_class` varchar(254) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
      `caller_method` varchar(254) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
      `caller_line` tinyint(4) NOT NULL,
      `id` int(11) NOT NULL AUTO_INCREMENT,
      PRIMARY KEY (`id`) USING BTREE
    ) ENGINE = InnoDB AUTO_INCREMENT = 5 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_general_ci ROW_FORMAT = Dynamic;
    

    第四步,pom文件的配置,为了案例的完整性,这里把pom文件引入的架包也贴一下;

    <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-web</artifactId>
            </dependency>
            <!--数据源类型-->
            <dependency>
                <groupId>com.alibaba</groupId>
                <artifactId>druid</artifactId>
                <version>1.1.9</version>
            </dependency>
            <!-- 数据监控 -->
            <dependency>
                <groupId>com.alibaba</groupId>
                <artifactId>druid-spring-boot-starter</artifactId>
                <version>1.1.9</version>
            </dependency>
            <!-- Mysql数据库链接jar包 -->
            <dependency>
                <groupId>mysql</groupId>
                <artifactId>mysql-connector-java</artifactId>
                 <!-- 生命周期为runtime,以为数据库驱动在工作的时候才会用到 -->
                <scope>runtime</scope>
            </dependency>
            <!--DAO框架:Mybatis依赖-->
            <dependency>
                <groupId>org.mybatis</groupId>
                <artifactId>mybatis</artifactId>
                <version>3.4.1</version>
            </dependency>
            <!--mybatis 整合spring-->
            <dependency>
                <groupId>org.mybatis</groupId>
                <artifactId>mybatis-spring</artifactId>
                <version>1.3.0</version>
            </dependency>
            <dependency>            
             <groupId>org.mybatis.spring.boot</groupId>         
             <artifactId>mybatis-spring-boot-starter</artifactId>           
             <version>1.3.2</version>       
            </dependency>       
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-test</artifactId>
                <scope>test</scope>
            </dependency>
    

    在spring-boot-starter-web架包中已经包含了slf4j的架包,这里不在单独引入。

    在启动文件中不要忘记加入;

    @MapperScan(value = "com.example.demo.mapper")
    

    第五步,测试代码;

    import org.slf4j.Logger;
    import org.slf4j.LoggerFactory;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.PathVariable;
    import org.springframework.web.bind.annotation.RestController;
    
    import com.example.demo.mapper.Test;
    import com.example.demo.mapper.TestMapper;
    
    @RestController
    public class IndexController {
    
        private static Logger log = LoggerFactory.getLogger(IndexController.class);
        
        @Autowired
        private TestMapper testMapper;
        
        @GetMapping("/index")
        public void index(){
            log.trace("测试开始了");
            log.info("info信息");
            log.error("error信息");
            
            Test test = new Test();
            test.setUserName("操作日志測試!");
            test.setUserUid("6666222fasdfasdfasd");
            testMapper.insertSelective(test);
        }
        
        @GetMapping("/index/{aa}")
        public void index(@PathVariable String aa){
            log.info("info信息" + aa);
            log.error("error信息" + aa);
        }
    }
    

    最后,测试;
    Test类和TestMapper、TestMapper.xml的代码省略,没有什么特别之处;试着改变Logback.xml中每个日志的输出等级,然后查看响应输出。这里故意插入了一条主键冲突的语句。


    控制台输出结果
    日志文件输出结果
    数据库中查询到的日志记录

    日志输出到数据库,对于不方便到服务器查看日志文件的,提供了一些便利,对于要输出的信息,还有待进一步的优化。

    参考文档:
    https://blog.csdn.net/qq_38136705/article/details/81055458
    https://blog.csdn.net/master336/article/details/104746627
    https://www.jianshu.com/p/1e96a62c9c43
    https://www.liangzl.com/get-article-detail-138664.html
    https://blog.csdn.net/love254443233/article/details/50125615
    https://segmentfault.com/q/1010000004940708/a-1020000004980014

    相关文章

      网友评论

        本文标题:Springboot整合Slf4j输出日志到控制台、文件、Mys

        本文链接:https://www.haomeiwen.com/subject/bsxsuhtx.html