Spring Boot(七) 快速使用自定义日志

177 阅读4分钟

携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第14天,点击查看活动详情

大家好! 我是慕歌,一只想教你学习 Spring Boot的野生coder! 欢迎来到慕歌的 Sping boot系列教程,希望通过这个教程带大家搭建基础的 Spring Boot项目,该教程所有知识点均来源于本人的真实开发!

前言

在上一节的开发学习中,慕歌向大家介绍了如何集成现在开发中使用非常频繁的日志系统--logback 日志框架,以及log4j2 日志系统。这些日志系统已经为我们的开发记录,提供了良好的支持,基本可以记录开发的全链路。并且通过不同的日志等级,为排错提供提醒,对应日志位置锁定错误点。

但是在开发中,可能还需要一些简单的日志信息记录,我们仅需要记录一些简单的操作信息,ip 信息等... 那这种场景该如何开发呢?下面,慕歌将为分享慕歌自定义的简易日志!

引入:

给日志的信息将依赖于之前的sa-token中所记录的信息,记录数据选择存放在数据库中,这样具有更高的可读性。

        <!--   web-->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <!--   mysql-->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <scope>runtime</scope>
        </dependency>

        <!--   mybatis-->
        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-boot-starter</artifactId>
            <version>3.5.1</version>
        </dependency>
        <!-- Sa-Token 权限认证, 在线文档:http://sa-token.dev33.cn/ -->
        <dependency>
            <groupId>cn.dev33</groupId>
            <artifactId>sa-token-spring-boot-starter</artifactId>
            <version>1.30.0</version>
        </dependency>
        <!-- Sa-Token 整合 Redis (使用 jdk 默认序列化方式) -->
        <dependency>
            <groupId>cn.dev33</groupId>
            <artifactId>sa-token-dao-redis</artifactId>
            <version>1.30.0</version>
        </dependency>

        <!-- redis 缓存操作 -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-redis</artifactId>
        </dependency>
        <!--连接池依赖-->
        <dependency>
            <groupId>org.apache.commons</groupId>
            <artifactId>commons-pool2</artifactId>
        </dependency>
        <!--   hutool工具类 -->
        <dependency>
            <groupId>cn.hutool</groupId>
            <artifactId>hutool-all</artifactId>
            <version>5.7.22</version>
        </dependency>
        <!--  log4j2-->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <!--   lombok-->
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
        </dependency>

这里为大家提供一份相对全面的pom依赖包,如果大家在之前的开发中,存在依赖包的缺失,可在这里进行查找。

数据库:

这里我们先搭建一个日志数据库,记录的信息非常的简单,主要用于记录用户的关键性操作和一些登录过程中的基础信息。

create table cf_admin_log
(
    id           int unsigned auto_increment comment '后台操作日志id'
        primary key,
    user_id      int unsigned not null comment '用户id',
    user_name    varchar(255) not null comment '用户名',
    ip           varchar(255) not null comment 'ip地址',
    ip_addr      varchar(255) null comment '实际地址',
    operate_url  varchar(255) not null comment '操作的url',
    operate_name varchar(255) not null comment '操作名称',
    operate_info varchar(255) not null comment '操作信息',
    create_time  datetime     null comment '操作时间'
)
    comment '后台操作日志' collate = utf8_unicode_ci;

这里先给大家留下一个悬念,我们如何能够获取当前用户的请求,以及请求的ip与具体地址呢?我将会用一个章节专门介绍如何获取请求与ip 并解析出ip地址。

自定义开发:

之后我们可以通过代码生成器生成三层基本参考模型的代码,在该代码的基础上进一步开发。这里慕歌的思路是对日志在不同层注入的数据进行限制,指定一些日志中的部分数据是能够自定义的,其余部分数据直接根据请求进行动态获取。

service
//打日志
    void log(String name, String info);

/**
* 打日志
* @param name
* @param info
*/
@Override
public void log(String name, String info) {
	AdminLog adminLog = new AdminLog();
	//当前登录id
	Constant.USER_ID = StpUtil.getLoginIdAsInt();
	//将在用户登录的token中获取用户名
	Constant.USER_NAME = adminUserService.getById(Constant.USER_ID).getUsername();
	adminLog.setUserId(Constant.USER_ID);
	adminLog.setUserName(Constant.USER_NAME);
	//ip 通过拦截获取
	adminLog.setIp(Constant.IP);
	//IP地址解析
	adminLog.setIpAddr(Constant.IP_ADDR);
	//访问的链接
	adminLog.setOperateUrl(Constant.URL);
	//操作名
	adminLog.setOperateName(name);
	//操作详情
	adminLog.setOperateInfo(info);
	adminLog.setCreateTime(new DateTime());
	this.save(adminLog);
		}

我们大部分的数据通过拦截器已经自动进行了更新,这样我们就只需要在开发的时候,确定那些点需要用到自定义日志,注入日志服务后,再填充指定部分数据,保存到数据库,就形成了一条完整的日志数据。在这个部分,我们借助sa-token中保留的数据信息校验的同时,还可以获取其中的动态数据。通过拦截器,将一些公共信息进行前置处理到全局数据中。

/**
     * 登录
     * @param loginVo 登录表单
     * @return
     */
    @RequestMapping("/login")
    public R login(@RequestBody @Validated AdminLoginVo loginVo){
        //登录
        boolean login = adminUserService.login(loginVo);
        if(login){
            // 获取指定账号是否已被封禁 (true=已被封禁, false=未被封禁)
            if(StpUtil.isDisable(Constant.USER_ID)){
                return R.error("账号被封禁");
            }
            log.info("{}登录成功",loginVo.getUsername());
            //日志
            adminLogService.log("登录","登录成功"+loginVo.getUsername());
            // 获取 Token  相关参数
            SaTokenInfo tokenInfo = StpUtil.getTokenInfo();
            //返回token信息
            return R.success(tokenInfo);
        }
        //登录失败
        return R.error(ResultCode.ERROR_PASSWORD);
    }

可参考我的思路注入日志,为一些关键操作同时写入两份日志中,因为数据库具有更高的可读性,我们可将这部分简易的日志展示给用户,让用户清晰的看到自己的操作记录。
这种自定义日志的优势便是记录的信息少,更新频率低,使用简单,通过数据库操作即可查看日志。而系统日志记录了繁琐的报错与日志信息,专为开发人员维护系统提供帮助,不具有以上特性。

结语

这一章的分享到这里就结束了,下一节中还将带来带来IP 获取解析功能的分享!
如果您觉得本文不错,欢迎点赞支持,您的关注是我坚持的动力!