一,功能点

实现管理员操作数据的记录。效果如下

二,代码实现

基于注解的Aop日志记录

1.Log实体类

package com.ideal.manage.guest.bean.log;

import javax.persistence.*;
import java.io.Serializable;
import java.util.Date; /**
* @apiNote 日志
* @author Yaming
* @since 2019-01-24
*/
@Entity
@Table(name = "visitor_sys_log")
public class Log implements Serializable { private static final long serialVersionUID = 1L; @Id
@GeneratedValue(strategy= GenerationType.IDENTITY)
private Long id; private String content; private String description; private String ip; private String module; private String username; private Date createAt; private Date updateAt; private Integer able; public String getContent() {
return content;
} public void setContent(String content) {
this.content = content;
} public String getDescription() {
return description;
} public void setDescription(String description) {
this.description = description;
} public String getIp() {
return ip;
} public void setIp(String ip) {
this.ip = ip;
} public String getModule() {
return module;
} public void setModule(String module) {
this.module = module;
} public String getUsername() {
return username;
} public void setUsername(String username) {
this.username = username;
} public static long getSerialVersionUID() {
return serialVersionUID;
} public Long getId() {
return id;
} public void setId(Long id) {
this.id = id;
} public Date getCreateAt() {
return createAt;
} public void setCreateAt(Date createAt) {
this.createAt = createAt;
} public Date getUpdateAt() {
return updateAt;
} public void setUpdateAt(Date updateAt) {
this.updateAt = updateAt;
} public Integer getAble() {
return able;
} public void setAble(Integer able) {
this.able = able;
}
}

2.定义注解

package com.ideal.manage.guest.annotation;

import java.lang.annotation.*;

/**
* @author Hao
* @create 2017-03-29
*/
@Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Log {
/**模块*/
String module() default ""; /**描述*/
String description() default "";
}

3.定义切面

package com.ideal.manage.guest.aop;

import com.ideal.manage.guest.annotation.Log;
import com.ideal.manage.guest.service.log.LogService;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import java.lang.reflect.Method; /**
* 日志切面处理类
*
* @author Yaming
* @create 2019-01-24
*/
@Aspect
@Component
public class LogAspect { @Autowired
private LogService logService; /**
* 日志切入点
*/
@Pointcut("@annotation(com.ideal.manage.guest.annotation.Log)")
public void logPointCut(){} @AfterReturning(pointcut = "logPointCut()")
public void doAfter(JoinPoint joinPoint){
/**
* 解析Log注解
*/
String methodName = joinPoint.getSignature().getName();
Method method = currentMethod(joinPoint,methodName);
Log log = method.getAnnotation(Log.class);
logService.put(joinPoint,methodName,log.module(),log.description());
} /**
* 获取当前执行的方法
*
* @param joinPoint 连接点
* @param methodName 方法名称
* @return 方法
*/
private Method currentMethod(JoinPoint joinPoint, String methodName) {
/**
* 获取目标类的所有方法,找到当前要执行的方法
*/
Method[] methods = joinPoint.getTarget().getClass().getMethods();
Method resultMethod = null;
for (Method method : methods) {
if (method.getName().equals(methodName)) {
resultMethod = method;
break;
}
}
return resultMethod;
} }

4.业务处理:LogService

package com.ideal.manage.guest.service.log;

import com.alibaba.fastjson.JSONObject;

import com.ideal.manage.guest.bean.DTO.PageDto;
import com.ideal.manage.guest.bean.log.Log; import com.ideal.manage.guest.config.shiro.MyShiroRealm;
import com.ideal.manage.guest.repository.framework.MySpecification;
import com.ideal.manage.guest.repository.framework.SpecificationOperator;
import com.ideal.manage.guest.repository.log.LogRepository;
import com.ideal.manage.guest.util.Const;
import com.ideal.manage.guest.util.HttpRequests;
import com.ideal.manage.guest.util.IPUtils; /*import org.apache.ibatis.javassist.*;
import org.apache.ibatis.javassist.bytecode.CodeAttribute;
import org.apache.ibatis.javassist.bytecode.LocalVariableAttribute;
import org.apache.ibatis.javassist.bytecode.MethodInfo;*/
import javassist.*;
import javassist.bytecode.CodeAttribute;
import javassist.bytecode.LocalVariableAttribute;
import javassist.bytecode.MethodInfo;
import org.apache.shiro.SecurityUtils;
import org.aspectj.lang.JoinPoint;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes; import javax.servlet.http.HttpServletRequest;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map; /**
* <p>
* 服务实现类
* </p>
*
* @author
* @since 2017-09-05
*/
@Service
public class LogService{ private static final String LOG_CONTENT = "[类名]:%s,[方法]:%s,[参数]:%s,[IP]:%s"; private String username; @Autowired
private LogRepository logRepository; public String initUsername(String username) {
if(!StringUtils.isEmpty(username)){
this.username = username;
}
return this.username;
} public void put(JoinPoint joinPoint, String methodName, String module, String description) {
try {
HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
Log log = new Log();
//username = ((JwtClient) SecurityContextHolder.getContext().getAuthentication().getPrincipal()).getUsername();
// 获取当前登录用户
MyShiroRealm.ShiroUser shiroUser = (MyShiroRealm.ShiroUser) SecurityUtils.getSubject().getPrincipal();
// User user = userRepository.findOne(shiroUser.getId());
username = shiroUser.getUsername();
if (StringUtils.isEmpty(username)) {
username = Const.USERNAME_IN_CONTEXT != null ? Const.USERNAME_IN_CONTEXT : "未知用户";
} String ip = IPUtils.getIpAddr(request);
log.setUsername(username);
log.setModule(module);
log.setDescription(description);
log.setIp(ip);
log.setContent(operateContent(joinPoint, methodName, ip, request));
log.setAble(1);
//insert(log);
logRepository.save(log);
} catch (Exception e) {
e.printStackTrace();
}
} /*public Page<Log> page(LogRequest request, Page<Log> page) {
if(request == null){
request = new LogRequest();
}
request.setIsDeleted(Config.ABLE_CONFIG.ABLE);
List<Log> logs = baseMapper.page(request,page);
page.setRecords(logs);
return page;
}*/ /**
* 查询所有日志
* @param pageNum
* @param request
* @return
*/
public PageDto findAll(int pageNum, HttpServletRequest request) {
Sort sort = new Sort(Sort.Direction.DESC, "updateAt");
List<SpecificationOperator> operators = HttpRequests.getParametersStartingWith(request, "Q_");
//增加删除标识的过滤
SpecificationOperator isValid = new SpecificationOperator("able", "1", "EQ");
operators.add(isValid);
MySpecification<Log> mySpecifications = new MySpecification<>(operators);
Pageable pageable = new PageRequest(pageNum, 10, sort);
Page<Log> page = logRepository.findAll(mySpecifications, pageable);
//设置PageDto
List<Log> parameters = page.getContent();
long total = page.getTotalElements();
PageDto pageDto = new PageDto();
pageDto.setRows(parameters);
pageDto.setTotal(total);
return pageDto;
} public String operateContent(JoinPoint joinPoint, String methodName, String ip, HttpServletRequest request) throws ClassNotFoundException, NotFoundException {
String className = joinPoint.getTarget().getClass().getName();
Object[] params = joinPoint.getArgs();
String classType = joinPoint.getTarget().getClass().getName();
Class<?> clazz = Class.forName(classType);
String clazzName = clazz.getName();
Map<String,Object > nameAndArgs = getFieldsName(this.getClass(), clazzName, methodName,params);
StringBuffer bf = new StringBuffer();
if (!CollectionUtils.isEmpty(nameAndArgs)){
Iterator it = nameAndArgs.entrySet().iterator();
while (it.hasNext()){
Map.Entry entry = (Map.Entry) it.next();
String key = (String) entry.getKey();
String value = JSONObject.toJSONString(entry.getValue());
bf.append(key).append("=");
bf.append(value).append("&");
}
}
if (StringUtils.isEmpty(bf.toString())){
bf.append(request.getQueryString());
}
return String.format(LOG_CONTENT, className, methodName, bf.toString(), ip);
} private Map<String,Object> getFieldsName(Class cls, String clazzName, String methodName, Object[] args) throws NotFoundException {
Map<String,Object > map=new HashMap<String,Object>(); ClassPool pool = ClassPool.getDefault();
ClassClassPath classPath = new ClassClassPath(cls);
pool.insertClassPath(classPath); CtClass cc = pool.get(clazzName);
CtMethod cm = cc.getDeclaredMethod(methodName);
MethodInfo methodInfo = cm.getMethodInfo();
CodeAttribute codeAttribute = methodInfo.getCodeAttribute();
LocalVariableAttribute attr = (LocalVariableAttribute) codeAttribute.getAttribute(LocalVariableAttribute.tag);
if (attr == null) {
// exception
return map;
}
int pos = Modifier.isStatic(cm.getModifiers()) ? 0 : 1;
for (int i = 0; i < cm.getParameterTypes().length; i++){
map.put( attr.variableName(i + pos),args[i]);//paramNames即参数名
}
return map;
}
}

5.dao

package com.ideal.manage.guest.repository.log;
import com.ideal.manage.guest.bean.log.Log;
import com.ideal.manage.guest.repository.framework.BaseRepository; /**
* <p>
* Mapper 接口
* </p>
*
* @author Yankee
* @since 2017-09-05
*/ public interface LogRepository extends BaseRepository<Log,String> { /**
* 查询分页
* @param request
* @param page
* @return
*/
//List<Log> page(@Param("re") LogRequest request, Pagination page);
}

三,使用注解在需要的地方记录日志

@Log(module = "设备管理",description = "添加设备")
public Integer saveEquipment(Equipment equipment) {
equipment.setAble(1);
Equipment resultEquipment = equipmentRepository.save(equipment);
if(resultEquipment == null){
return StateUtil.RESULT_FAILED;
}
return StateUtil.RESULT_SUCCESS;
}

后台管理系统之系统操作日志开发(Java实现)的更多相关文章

  1. asp.net mvc 系统操作日志设计

    第一步.系统登录日志 通过signalr来管理用户的登录情况,并保存用户的登录记录. 第二步 通过mvc过滤器,来横切路由访问记录. 保存方式:通过httpclient异步请求webapi 数据通过m ...

  2. 后台管理系统之系统运行日志开发(Java实现)

    一,实现运行日志记录在文件中,并实现日志分包记录,项目出问题后方便定位分析.效果如图: 二,代码实现(springboot项目) 只需要在resources目录下新建:logback-spring.x ...

  3. springboot—spring aop 实现系统操作日志记录存储到数据库

    原文:https://www.jianshu.com/p/d0bbdf1974bd 采用方案: 使用spring 的 aop 技术切到自定义注解上,针对不同注解标志进行参数解析,记录日志 缺点是要针对 ...

  4. 033 SSM综合练习09--数据后台管理系统--基于AOP的日志处理

    1.数据库与表结构 (1)日志表信息描述sysLog (2)Sql语句 CREATE TABLE sysLog ( id ) DEFAULT SYS_GUID () PRIMARY KEY, visi ...

  5. 030 SSM综合练习06--数据后台管理系统--SSM权限操作及Spring Security入门

    1.权限操作涉及的三张表 (1)用户表信息描述users sql语句: CREATE TABLE users ( id ) DEFAULT SYS_GUID () PRIMARY KEY, email ...

  6. 028 SSM综合练习04--数据后台管理系统--订单相关操作

    1.订单表及其关联表的关系分析 2.数据库表对应实体类 (1)Orders.java package lucky.domain; import lucky.utils.DateUtils; impor ...

  7. ASP.NET MVC5+EF6+EasyUI 后台管理系统--任务调度系统解析

    1.任务主界面.任务可以被挂起,启动,和删除.来自著名Quartz扩展 2.任务可以是执行的SQL命令,存储过程,或者是一个后台方法 3.极其复杂的调度任务,循环次数,可以自行设置.并可以间隔执行,比 ...

  8. vue开发后台管理系统小结

    最近工作需要用vue开发了后台管理系统,由于是第一次开发后台管理系统,中间也遇到了一些坑,想在这里做个总结,也算是对于自己工作的一个肯定.我们金融性质的网站所以就不将代码贴出来哈 一.项目概述 首先工 ...

  9. Struts2拦截器记录系统操作日志

    前言 最近开发了一个项目,由于项目在整个开发过程中处于赶时间状态(每个项目都差不多如此)所以项目在收尾阶段发现缺少记录系统日志功能,以前系统都是直接写在每个模块的代码中,然后存入表单,在页面可以查看部 ...

随机推荐

  1. maven与jdk版本对应关系

    Maven发布历史 发布日期 版 必需的Java版本 链接 2018年6月21日 3.5.4 Java 7 宣布,发布说明,参考文档 2018年3月8日 3.5.3 宣布,发布说明,参考文档 2017 ...

  2. Java中输入字符的排列以及按从小到大的顺序输出

    今天笔试,遇到一个问题,大意就是输入一行字符,例如a b c ,按从小到大的顺序输出它们排列而成的字符串,输出就是abc acb bac bca cba cab.求这个程序怎么实现. 其实这个题很简单 ...

  3. 《Linux服务器的监控》

    本文地址:http://www.cnblogs.com/aiweixiao/p/7131532.html 原文地址(公众号):http://t.cn/RKwmqUs 点击关注 微信公众号 1. 监控概 ...

  4. ZooKeeper Administrator's Guide A Guide to Deployment and Administration(吃别人嚼过的馍没意思,直接看官网资料)

    Deployment System Requirements Supported Platforms Required Software Clustered (Multi-Server) Setup ...

  5. Nginx 安装配置

    Nginx("engine x")是一款是由俄罗斯的程序设计师Igor Sysoev所开发高性能的 Web和 反向代理 服务器,也是一个 IMAP/POP3/SMTP 代理服务器. ...

  6. 【转】vue父子组件之间的通信

    vue父子组件之间的通信 在vue组件通信中其中最常见通信方式就是父子组件之中的通性,而父子组件的设定方式在不同情况下又各有不同.最常见的就是父组件为控制组件子组件为视图组件.父组件传递数据给子组件使 ...

  7. postgreSQL 应用case when的例子

    selectname,md5(indvl_id_nbr) as indvl_id_nbr,case when char_length(indvl_id_nbr)=18 or char_length(i ...

  8. 8.04-book

    import requests from lxml import etree from bs4 import BeautifulSoup import json class BookSpider(ob ...

  9. JS函数防抖与函数节流

    概念 函数防抖(debounce) 当调用动作过n毫秒后,才会执行该动作,若在这n毫秒内又调用此动作则将重新计算执行时间 函数节流(throttle) 预先设定一个执行周期,当调用动作的时刻大于等于执 ...

  10. 001学习Python的ABC模块(转)

    http://yansu.org/2013/06/09/learn-Python-abc-module.html 1.abc模块作用 Python本身不提供抽象类和接口机制,要想实现抽象类,可以借助a ...