spring 自定義註解,實現日誌

 

採用自定義註解實現spring

用戶操做日誌記錄

簡介及說明:

記錄登錄用戶的操做日誌,目前只針對(運營管理平臺)itas系統
目前採用spring的切面技術來實現記錄日誌的功能,切面點在controller層,主要是針對數據庫的增刪改操做數據庫

註解類說明

@Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface OperationDescription {session

String desc() default "無描述信息";
   String uslModule() ;//操做模塊
   String uslFunction();//操做功能
   String operationType();//操做類型增刪改
   String sysId() default "01";

}app

如何使用

舉個栗子
機構新建
@RequestMapping(value = "/insert", method = RequestMethod.POST)
@ResponseBody
@OperationDescription(uslModule = "用戶模塊",uslFunction = "新建機構",operationType = "新建")
public BaseResp insert(@RequestBody Map<String,Object> map) {
BaseResp baseRsp = new BaseResp();
try {
String operUserId = CurrentUser.getCurrentUserId(request);
if (StringUtils.isEmpty(operUserId)) {
baseRsp.setState(Constants.RESP_FAIL);
baseRsp.setMsg("登陸超時,請從新登陸");
return baseRsp;
}dom

}

註解說明

uslModule="大模塊」
 例如用戶模塊管理

 uslFunction=「大模塊的子模塊具體功能"
    例如 用戶模塊新建權限

切面類ui

@Aspect
@Component
public class LogAspect {
    private final Logger logger = LoggerFactory.getLogger(this.getClass());

    private String requestPath = null ; // 請求地址
    private String userName = null ; // 用戶名
    private Map<?,?> inputParamMap = null ; // 傳入參數
    private Map<String, Object> outputParamMap = null; // 存放輸出結果
    private long startTimeMillis = 0; // 開始時間
    private long endTimeMillis = 0; // 結束時間

    @Autowired
    private UserLogService userLogService;


//    Controller層切點
    @Pointcut(value="@annotation(com.landi.common.OperationDescription)")
    public  void controllerAspect() {
    }


    /**
     *
     * @Title:doBeforeInServiceLayer
     * @Description: 方法調用前觸發
     *  記錄開始時間
     * @author pengjm
     * @param joinPoint
     */
//    @Before("controllerAspect()")
//    public void doBeforeInControllerLayer(JoinPoint joinPoint) {
//        startTimeMillis = System.currentTimeMillis(); // 記錄方法開始執行的時間
//    }

    /**
     *
     * @Title:doAround
     * @Description: 環繞觸發
     * @author hotsmile
     * @param pjp
     * @return
     * @throws Throwable
     */
    @Around(value = "@annotation(description)")
    public Object doAround(ProceedingJoinPoint pjp,OperationDescription description) throws Throwable {
        /**
         * 1.獲取request信息
         * 2.根據request獲取session
         * 3.從session中取出登陸用戶信息
         */
        RequestAttributes ra = RequestContextHolder.getRequestAttributes();
        ServletRequestAttributes sra = (ServletRequestAttributes)ra;
        HttpServletRequest request = sra.getRequest();
        // 從session中獲取用戶信息
//        String loginInfo = (String) request.getSession().getAttribute("username");
        LoginUserInfo userInfo = CurrentUser.getCurrentUser(request);
        if(userInfo != null){
            userName = userInfo.getUserId();;
        }else{
            userName = "用戶未登陸" ;
        }

          Object[] args = pjp.getArgs();
//         logger.info("params="+JSONObject.toJSONString(args));
//        String className=pjp.getTarget().getClass().getSimpleName();
//        String methodName=pjp.getSignature().getName();
//        Object[] args=pjp.getArgs();
//        Class<?> classTarget=pjp.getTarget().getClass();
//        Class<?>[] par=((MethodSignature) pjp.getSignature()).getParameterTypes();
//        Method objMethod=classTarget.getMethod(methodName, par);
//        logger.info("===="+description.uslModule());

//        Cache aCache=objMethod.getAnnotation(Cache.class);

        // 獲取輸入參數
        inputParamMap = request.getParameterMap();
        // 獲取請求地址
        requestPath = request.getRequestURI();

        // 執行完方法的返回值:調用proceed()方法,就會觸發切入點方法執行
        outputParamMap = new HashMap<String, Object>();
        Object result = pjp.proceed();// result的值就是被攔截方法的返回值
        outputParamMap.put("result", result);
        Userlog userlog=new Userlog();
        userlog.setUslId(UuidUtils.getRandomUuidWithoutSeparator());
        userlog.setSysId(description.sysId());
        userlog.setUslDate(DateUtils.curDateTime());
        userlog.setUslModule(description.uslModule());
        userlog.setUslFunction(description.uslFunction());
        userlog.setUserId(userInfo.getUserId());
        userlog.setUslParameter(JSONObject.toJSONString(args));
//        logger.info("param="+JSON.toJSONString(inputParamMap));
        if(result instanceof BaseResp){
            if(((BaseResp) result).getState().equals(Constants.RESP_SUCCESS)){
                userlog.setUslStatus(Constants.USERLOG_SUCC);
            }else{
                userlog.setUslStatus(Constants.USERLOG_FAIL);
            }

        }


//        if ("POST".equals(method)) {
//            Object[] paramsArray = joinPoint.getArgs();
//            params = argsArrayToString(paramsArray);
//        } else {
//            Map<?, ?> paramsMap = (Map<?, ?>) request.getAttribute(HandlerMapping.URI_TEMPLATE_VARIABLES_ATTRIBUTE);
//            params = paramsMap.toString();
//        }


        userLogService.save(userlog);

        return result;
    }


    /**
     *
     * @Title:doAfterInServiceLayer
     * @Description: 方法調用後觸發
     *  記錄結束時間
     * @param joinPoint
     */
//    @After("controllerAspect()")
//    public void doAfterInControllerLayer(JoinPoint joinPoint) {
//        endTimeMillis = System.currentTimeMillis(); // 記錄方法執行完成的時間
////        System.out.println("哈哈哈!");
//        this.printOptLog();
//    }

    /**
     *
     * @Title:printOptLog
     * @Description: 輸出日誌
     * @author shaojian.yu
     * @date 2014年11月2日 下午4:47:09
     */
    private void printOptLog() {
        JSONObject gson = new JSONObject(); // 須要用到google的gson解析包
        String optTime = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(startTimeMillis);
        logger.info("\n user:"+userName
                +"  url:"+requestPath+"; op_time:" + optTime + " pro_time:" + (endTimeMillis - startTimeMillis) + "ms ;"
                +" param:"+ JSON.toJSONString(inputParamMap)+";"+"\n result:"+JSON.toJSONString(outputParamMap));
    }


}
相關文章
相關標籤/搜索