Bläddra i källkod

新建任务时一并新建众测任务

郭超 4 år sedan
förälder
incheckning
854bedfd5b

+ 2 - 0
core/src/main/java/com/mooctest/crowd/domain/domainobject/EndPoint.java

@@ -13,4 +13,6 @@ public class EndPoint {
     private String url;
     private String token;
     private int isShowed;
+    private int collaborativeType;
+    private String threePageUrl;
 }

+ 12 - 0
core/src/main/java/com/mooctest/crowd/domain/exception/AuthorizedTimeOutException.java

@@ -0,0 +1,12 @@
+package com.mooctest.crowd.domain.exception;
+
+/**
+ * @author: Diors.Po
+ * @Email: 171256175@qq.com
+ * @date 2019-08-06 20:18
+ */
+public class AuthorizedTimeOutException extends BaseException {
+    public AuthorizedTimeOutException(String msg){
+        super(msg);
+    }
+}

+ 6 - 0
core/src/main/java/com/mooctest/crowd/domain/model/EndPointPO.java

@@ -36,6 +36,12 @@ public class EndPointPO {
     @Column(name = "EP_TOKEN")
     private String token;
 
+    @Column(name = "EP_COLLABORATIVE_TYPE")
+    private int collaborativeType;
+
+    @Column(name = "EP_THREE_PAGE_URL")
+    private String threePageUrl;
+
     @Column(name = "EP_IS_SHOWED")
     private int isShowed;
 }

+ 16 - 18
core/src/main/java/com/mooctest/crowd/domain/repository/CrowdTestProjectRepo.java

@@ -178,29 +178,27 @@ public class CrowdTestProjectRepo implements ICrowdTestProjectRepo {
                     if(crowdTestTask.getEndPoint() != null){
                         Optional<EndPointPO> endPointPO = endPointDao.findByTaskCode(crowdTestTask.getCode());
                         EndPoint endPoint = crowdTestTask.getEndPoint();
+                        EndPointPO addEndPointPO = new EndPointPO();
                         if(endPointPO.isPresent()){
-                            EndPointPO addEndPointPO = Converter.convert(EndPointPO.class, endPoint);
+                            addEndPointPO = Converter.convert(EndPointPO.class, endPoint);
                             addEndPointPO.setId(endPointPO.get().getId());
-                            addEndPointPO.setProjectCode(crowdTestProject.getCode());
-                            addEndPointPO.setTaskCode(crowdTestTask.getCode());
-                            if(endPoint.getToken() != null && endPoint.getToken() != ""){
-                                addEndPointPO.setToken(endPoint.getToken());
-                            }
-                            endPointDao.save(addEndPointPO);
-                        }else{
-                            EndPointPO addEndPointPO = new EndPointPO();
-                            if(endPoint.getExamId() != null){
-                                addEndPointPO.setExamId(endPoint.getExamId());
-                            }
-                            if(endPoint.getCaseId() != null){
-                                addEndPointPO.setCaseId(endPoint.getCaseId());
-                            }
-                            addEndPointPO.setProjectCode(crowdTestProject.getCode());
-                            addEndPointPO.setTaskCode(crowdTestTask.getCode());
+                        }
+                        addEndPointPO.setProjectCode(crowdTestProject.getCode());
+                        addEndPointPO.setTaskCode(crowdTestTask.getCode());
+                        addEndPointPO.setCollaborativeType(endPoint.getCollaborativeType());
+                        if(endPoint.getServerCode() != null && endPoint.getServerCode() != ""){
                             addEndPointPO.setServerCode(endPoint.getServerCode());
+                        }
+                        if(endPoint.getToken() != null && endPoint.getToken() != ""){
+                            addEndPointPO.setToken(endPoint.getToken());
+                        }
+                        if(endPoint.getUrl() != null && endPoint.getUrl() != ""){
                             addEndPointPO.setUrl(endPoint.getUrl());
-                            endPointDao.save(addEndPointPO);
                         }
+                        if(endPoint.getThreePageUrl() != null && endPoint.getThreePageUrl() != ""){
+                            addEndPointPO.setThreePageUrl(endPoint.getThreePageUrl());
+                        }
+                        endPointDao.save(addEndPointPO);
                     }
                 }else{
                     Optional<EndPointPO> endPointPO = endPointDao.findByTaskCode(crowdTestTask.getCode());

+ 12 - 0
site/pom.xml

@@ -203,6 +203,18 @@
 			<artifactId>reflections</artifactId>
 			<version>0.9.11</version>
 		</dependency>
+
+		<!-- aop -->
+		<dependency>
+			<groupId>org.springframework.boot</groupId>
+			<artifactId>spring-boot-starter-aop</artifactId>
+		</dependency>
+
+		<!-- log,logback -->
+		<dependency>
+			<groupId>org.springframework.boot</groupId>
+			<artifactId>spring-boot-starter-logging</artifactId>
+		</dependency>
 	</dependencies>
 	<build>
 		<plugins>

+ 106 - 0
site/src/main/java/com/mooctest/crowd/site/anticorruption/WebLogAspect.java

@@ -0,0 +1,106 @@
+package com.mooctest.crowd.site.anticorruption;
+
+import com.fasterxml.jackson.databind.ObjectMapper;
+import org.aspectj.lang.JoinPoint;
+import org.aspectj.lang.annotation.AfterReturning;
+import org.aspectj.lang.annotation.Aspect;
+import org.aspectj.lang.annotation.Before;
+import org.aspectj.lang.annotation.Pointcut;
+import org.aspectj.lang.reflect.MethodSignature;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.core.annotation.Order;
+import org.springframework.stereotype.Component;
+import org.springframework.web.context.request.RequestContextHolder;
+import org.springframework.web.context.request.ServletRequestAttributes;
+import org.springframework.web.multipart.MultipartFile;
+
+import javax.servlet.ServletRequest;
+import javax.servlet.ServletResponse;
+import javax.servlet.http.HttpServletRequest;
+import java.lang.reflect.Method;
+import java.util.UUID;
+
+/**
+ * Web层日志切面
+ */
+@Aspect
+@Order(5)
+@Component
+public class WebLogAspect {
+
+	private Logger logger = LoggerFactory.getLogger(getClass());
+
+	private String uuid = UUID.randomUUID().toString();
+
+	ThreadLocal<Long> startTime = new ThreadLocal<>();
+
+	/**
+	 * A join point is in the web layer if the method is defined
+	 * in a type in the com.xyz.someapp.web package or any sub-package
+	 * under that.
+	 */
+	// Pointcut与 joinpoint 匹配的正则表达式。每次连接点与切入点匹配时, 都将执行与该切入点关联的指定建议。
+	@Pointcut("within(com.mooctest.crowd.site.controller..*)")
+	public void webLog(){}
+
+	@Before("webLog()")
+	// JoinPoint它是执行程序 (如方法执行、构造函数调用或字段分配) 期间的特定点
+	public void doBefore(JoinPoint joinPoint) throws Throwable {
+		startTime.set(System.currentTimeMillis());
+
+		/**
+		 * 获取 request 中包含的请求参数
+		 */
+		HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
+
+		/**
+		 * 获取切点请求参数(class,method)
+		 */
+		MethodSignature signature = (MethodSignature) joinPoint.getSignature();
+		Method method = signature.getMethod();
+
+		StringBuilder params = new StringBuilder();
+		ObjectMapper mapper = new ObjectMapper();
+		if ("POST".equalsIgnoreCase(request.getMethod())) {
+			Object[] objects = joinPoint.getArgs();
+			for (Object arg : objects) {
+				// args还包含了一些其他的内容,比如ServletRequest\ServletResponse\MultipartFile等,而这些入参并不能进行序列化,所以JSON.toJSONString时报错;
+				if (arg instanceof ServletRequest || arg instanceof ServletResponse){
+					continue;
+				}
+				if (arg instanceof MultipartFile){
+					params.append("File ");
+				}
+				try {
+					params.append(mapper.writeValueAsString(arg));
+				} catch (Exception e) {
+
+				}
+			}
+			if(params == null || params.equals("")){
+				params.append(objects.toString());
+			}
+		}
+
+
+		if ("GET".equalsIgnoreCase(request.getMethod())) {
+			params.append(request.getQueryString());
+		}
+		/**
+		 * 入参日志
+		 */
+		logger.info("[AOP-LOG-START] {}\n\ttraceId: {}\n\trequestIP: {}\n\tcontentType:{}\n\trequestUrl: {}\n\t" +
+						"requestMethod: {}\n\trequestParams: {}\n\ttargetClassAndMethod: {}#{}", uuid,uuid,request.getRemoteAddr(),
+				request.getHeader("Content-Type"),request.getRequestURL(), request.getMethod(), params.toString(),
+				method.getDeclaringClass().getName(), method.getName());
+
+	}
+
+	@AfterReturning(returning = "ret", pointcut = "webLog()")
+	public void doAfterReturning(Object ret) throws Throwable {
+		// 处理完请求,返回内容
+		logger.info("[AOP-LOG-END] {}\n\t{}", uuid, ret);
+		logger.info("SPEND TIME : " + (System.currentTimeMillis() - startTime.get()));
+	}
+}

+ 29 - 29
site/src/main/java/com/mooctest/crowd/site/command/CrowdTestTaskCommand.java

@@ -2,15 +2,11 @@ package com.mooctest.crowd.site.command;
 
 import com.mooctest.crowd.domain.domainobject.CrowdTestTask;
 import com.mooctest.crowd.domain.domainobject.EndPoint;
-import com.mooctest.crowd.domain.exception.CrowdTestEndPointException;
 import lombok.Data;
 import org.springframework.beans.BeanUtils;
 
 import javax.validation.constraints.NotNull;
-import java.io.UnsupportedEncodingException;
-import java.net.URLDecoder;
 import java.sql.Timestamp;
-import java.util.Base64;
 import java.util.Map;
 
 /**
@@ -48,6 +44,10 @@ public class CrowdTestTaskCommand {
 
     private int participantCount;
 
+    private int collaborativeType;
+
+    private String threePageUrl;
+
     private EndPoint endPoint;
 
     public boolean isLegal(){
@@ -75,31 +75,31 @@ public class CrowdTestTaskCommand {
         crowdTestTask.setFixedPrice(fixedPrice);
         crowdTestTask.setRequirementFile(requirementFile);
         crowdTestTask.setParticipantCount(participantCount);
-
-        if(endPoint.getServerCode() != null && endPoint.getServerCode() != ""){
-            String serverCode = endPoint.getServerCode();
-            try {
-                String decodeUrl;
-                decodeUrl = URLDecoder.decode(serverCode,"UTF-8");
-                byte[] decodedBytes = Base64.getDecoder().decode(decodeUrl);
-                String url = new String(decodedBytes);
-
-                if(url.contains("examId_")){
-                    endPoint.setExamId(url.split("examId_")[1].split("/")[0]);
-                    url = url.replaceFirst("examId_","");
-                }
-                if(url.contains("caseId_")){
-                    endPoint.setCaseId(url.split("caseId_")[1].split("/")[0]);
-                    url = url.replaceFirst("caseId_","");
-                }
-                endPoint.setUrl(url);
-                crowdTestTask.setEndPoint(endPoint);
-            }catch (IllegalArgumentException e){
-                throw new CrowdTestEndPointException();
-            }catch (UnsupportedEncodingException e){
-                e.printStackTrace();
-            }
-        }
+        crowdTestTask.setEndPoint(endPoint);
+//        if(endPoint.getServerCode() != null && endPoint.getServerCode() != ""){
+//            String serverCode = endPoint.getServerCode();
+//            try {
+//                String decodeUrl;
+//                decodeUrl = URLDecoder.decode(serverCode,"UTF-8");
+//                byte[] decodedBytes = Base64.getDecoder().decode(decodeUrl);
+//                String url = new String(decodedBytes);
+//
+//                if(url.contains("examId_")){
+//                    endPoint.setExamId(url.split("examId_")[1].split("/")[0]);
+//                    url = url.replaceFirst("examId_","");
+//                }
+//                if(url.contains("caseId_")){
+//                    endPoint.setCaseId(url.split("caseId_")[1].split("/")[0]);
+//                    url = url.replaceFirst("caseId_","");
+//                }
+//                endPoint.setUrl(url);
+//                crowdTestTask.setEndPoint(endPoint);
+//            }catch (IllegalArgumentException e){
+//                throw new CrowdTestEndPointException();
+//            }catch (UnsupportedEncodingException e){
+//                e.printStackTrace();
+//            }
+//        }
         return crowdTestTask;
     }
 

+ 5 - 1
site/src/main/java/com/mooctest/crowd/site/controller/CrowdTaskController.java

@@ -1,5 +1,6 @@
 package com.mooctest.crowd.site.controller;
 
+import com.mooctest.crowd.domain.exception.AuthorizedTimeOutException;
 import com.mooctest.crowd.domain.exception.BaseException;
 import com.mooctest.crowd.domain.exception.UnauthorizedException;
 import com.mooctest.crowd.site.annotation.LoginRequired;
@@ -53,7 +54,10 @@ public class CrowdTaskController{
             throw new BaseException(result.getFieldError().getDefaultMessage());
         else if (!command.isLegal())
             throw new BaseException("信息不合法,项目可见性选择存在问题");
-        return taskService.createTask(projectCode, command, Long.parseLong((String)session.getAttribute("userId")));
+        if(session.getAttribute("userId") == null){
+            throw new AuthorizedTimeOutException("登录信息已失效,请重新登录");
+        }
+        return taskService.createTask(projectCode, command, Long.parseLong((String) session.getAttribute("userId")));
     }
 
     @RequestMapping(value = "/task/{taskCode}", method = RequestMethod.DELETE)

+ 2 - 0
site/src/main/java/com/mooctest/crowd/site/data/vo/EndPointVO.java

@@ -14,6 +14,8 @@ import org.springframework.beans.BeanUtils;
 public class EndPointVO {
     private String serverCode;
     private String token;
+    private int collaborativeType;
+    private String threePageUrl;
 
     public EndPointVO(EndPoint endPoint){
         BeanUtils.copyProperties(endPoint, this);

+ 2 - 2
site/src/main/java/com/mooctest/crowd/site/mediator/impl/WebMediatorImpl.java

@@ -610,7 +610,7 @@ public class WebMediatorImpl implements ViewMediator {
                         }).filter(Objects::nonNull).collect(Collectors.toList());
                 if(allTaskOfAgency != null && allTaskOfAgency.size() > 0){
                     unfinishedTasks = allTaskOfAgency.stream()
-                            .filter(crowdTestTask -> crowdTestTask.getStatus() >= CrowdTestTaskStatus.HAS_RELEASED && crowdTestTask.getStatus() < CrowdTestTaskStatus.HAS_FINISHED)
+                            .filter(crowdTestTask -> crowdTestTask.getStatus() >= CrowdTestTaskStatus.HAS_RELEASED && (crowdTestTask.getStatus() < CrowdTestTaskStatus.HAS_FINISHED || crowdTestTask.getStatus() == CrowdTestTaskStatus.HAS_TIME_OUT))
                             .sorted(Comparator.comparing(CrowdTestTask::getCreateTime).reversed())
                             .map(CrowdTaskVO::new).collect(Collectors.toList());
 
@@ -623,7 +623,7 @@ public class WebMediatorImpl implements ViewMediator {
         }
         myCrowdDTO.setFinishedTasks(finishedTasks);
         myCrowdDTO.setUnfinishedTasks(unfinishedTasks);
-        myCrowdDTO.setUnfinishedTaskNoticeCount((long) unfinishedTasks.size());
+        myCrowdDTO.setUnfinishedTaskNoticeCount(unfinishedTasks == null ? 0 : (long) unfinishedTasks.size());
         myCrowdDTO.setFinishedTaskCount((long) (myCrowdDTO.getFinishedTasks() == null ? 0 : myCrowdDTO.getFinishedTasks().size()));
         myCrowdDTO.setUnfinishedTaskCount((long) (myCrowdDTO.getUnfinishedTasks() == null ? 0 : myCrowdDTO.getUnfinishedTasks().size()));
         return myCrowdDTO;

+ 49 - 0
site/src/main/java/com/mooctest/crowd/site/service/impl/CrowdTaskServiceImpl.java

@@ -33,11 +33,18 @@ import net.lingala.zip4j.util.Zip4jConstants;
 import org.jetbrains.annotations.NotNull;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.beans.factory.annotation.Value;
+import org.springframework.http.HttpStatus;
+import org.springframework.http.ResponseEntity;
+import org.springframework.http.converter.StringHttpMessageConverter;
 import org.springframework.mock.web.MockMultipartFile;
 import org.springframework.stereotype.Service;
+import org.springframework.util.LinkedMultiValueMap;
+import org.springframework.util.MultiValueMap;
+import org.springframework.web.client.RestTemplate;
 import org.springframework.web.multipart.MultipartFile;
 
 import java.io.*;
+import java.nio.charset.StandardCharsets;
 import java.sql.Timestamp;
 import java.util.*;
 import java.util.stream.Collectors;
@@ -205,6 +212,26 @@ public class CrowdTaskServiceImpl implements CrowdTaskService {
         CrowdTestProject project = projectRepo.getByProjectCode(projectCode);
         String taskCode = GenerateFlowCodeUtil.generateFlowCode("TASK-" + ProjectType.getCode(command.getType()));
         task.create(taskCode);
+
+        // 配置endpoint
+        EndPoint endPoint = task.getEndPoint();
+        String endPointData;
+        // 众测服务同步新建任务
+        if(command.getEndPoint().getThreePageUrl() != null){
+            endPointData = createTaskToCrowdService(command.getName(), command.getDesc(), command.getEndPoint().getCollaborativeType(), command.getEndPoint().getThreePageUrl());
+            System.out.println(endPointData);
+            if(endPointData.equals("")){
+                throw new BaseException("创建失败,众测端调用出错");
+            }
+            Map<String, Object> dataMap = (Map<String, Object>) JSON.parse(endPointData);
+            System.out.println(dataMap.get("encodedUrl").toString());
+            System.out.println(dataMap.get("taskDaPanUrl").toString());
+            System.out.println(dataMap.get("writeReportUrl").toString());
+            endPoint.setServerCode(dataMap.get("encodedUrl").toString());
+            endPoint.setUrl(dataMap.get("writeReportUrl").toString());
+            endPoint.setToken(dataMap.get("taskDaPanUrl").toString());
+        }
+        task.setEndPoint(endPoint);
         project.addTask(task);
         projectRepo.saveCrowdTestProject(project);
 
@@ -214,6 +241,28 @@ public class CrowdTaskServiceImpl implements CrowdTaskService {
         return getTaskDetails(projectCode, taskCode, userId);
     }
 
+    private String createTaskToCrowdService(String name, String desc, int collaborativeType, String threePageUrl) {
+        MultiValueMap<String, String> params = new LinkedMultiValueMap<>();
+        params.add("name", name);
+        params.add("description", desc);
+        params.add("collaborativeType", collaborativeType + "");
+        params.add("threePageUrl", threePageUrl);
+        params.add("fileName", threePageUrl.substring(threePageUrl.lastIndexOf("/")+1));
+        RestTemplate restTemplate = new RestTemplate();
+        restTemplate.getMessageConverters().set(1, new StringHttpMessageConverter(StandardCharsets.UTF_8));
+        ResponseEntity<String> responseEntity = restTemplate.postForEntity
+                ("http://" + "localhost:9004"  + "/addCrowdTaskDefault", params, String.class);
+        if (responseEntity.getStatusCode().equals(HttpStatus.OK)){
+            String responseEntityBody = responseEntity.getBody();
+            Map<String, Object> resultMap = (Map<String, Object>) JSON.parse(responseEntityBody);
+            if((int)resultMap.get("status") == 200){
+                return resultMap.get("data").toString();
+            }
+        }
+        return "";
+    }
+
+
     @Override
     public TaskDetailsDTO updateTask(String projectCode, String taskCode, CrowdTestTaskCommand command, Long userId) {
         CrowdTestProject project = projectRepo.getByProjectCode(projectCode);

+ 112 - 0
site/src/main/resources/logback.xml

@@ -0,0 +1,112 @@
+<?xml version="1.0" encoding="UTF-8"?>
+
+<configuration scan="true" scanPeriod="60 seconds" debug="false">
+    <!-- 属性定义 -->
+    <property name="LOG_HOME" value="../logs" />
+    <property name="maxHistory" value="90" />
+
+    <!-- ConsoleAppender 控制台输出日志 -->
+    <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
+        <!-- 对日志进行格式化 -->
+        <encoder>
+            <pattern>%d{yyyy-MM-dd HH:mm:ss:SSS} [%thread] %-5level %logger{50}\(%F %L\) -%msg%n </pattern>
+        </encoder>
+    </appender>
+
+    <!-- DEBUG日志 -->
+    <!-- 滚动记录文件,先将日志记录到指定文件,当符合某个条件时,将日志记录到其他文件 RollingFileAppender-->
+    <appender name="DEBUG" class="ch.qos.logback.core.rolling.RollingFileAppender">
+        <!-- 过滤器,记录「所有」级别的日志 -->
+        <filter class="ch.qos.logback.classic.filter.LevelFilter">
+            <level>DEBUG</level>
+            <onMatch>ACCEPT</onMatch>
+            <onMismatch>ACCEPT</onMismatch>
+        </filter>
+        <!-- 滚动策略: 时间 和 大小 -->
+        <rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
+            <fileNamePattern>${LOG_HOME}/debug/debugLog-%d{yyyy-MM-dd}.%i.txt</fileNamePattern>
+            <maxFileSize>10MB</maxFileSize>
+            <maxHistory>${maxHistory}</maxHistory>
+            <totalSizeCap>20GB</totalSizeCap>
+        </rollingPolicy>
+        <encoder>
+            <pattern>%d{yyyy-MM-dd HH:mm:ss:SSS} [%thread] %-5level %logger{50}\(%F %L\) -%msg%n </pattern>
+        </encoder>
+    </appender>
+
+    <!-- INFO级别日志 -->
+    <appender name="INFO" class="ch.qos.logback.core.rolling.RollingFileAppender">
+        <!-- 过滤器,只记录「INFO」级别的日志 -->
+        <filter class="ch.qos.logback.classic.filter.LevelFilter">
+            <level>INFO</level>
+            <onMatch>ACCEPT</onMatch>
+            <onMismatch>DENY</onMismatch>
+        </filter>
+        <rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
+            <fileNamePattern>${LOG_HOME}/info/infoLog-%d{yyyy-MM-dd}.%i.txt</fileNamePattern>
+            <maxFileSize>10MB</maxFileSize>
+            <maxHistory>${maxHistory}</maxHistory>
+            <totalSizeCap>20GB</totalSizeCap>
+        </rollingPolicy>
+        <encoder>
+            <pattern>%d{yyyy-MM-dd HH:mm:ss:SSS} [%thread] %-5level %logger{50}\(%F %L\) -%msg%n </pattern>
+        </encoder>
+    </appender>
+
+    <!-- WARN级别日志 -->
+    <appender name="WARN" class="ch.qos.logback.core.rolling.RollingFileAppender">
+        <!-- 过滤器,只记录「WARN」级别的日志 -->
+        <filter class="ch.qos.logback.classic.filter.LevelFilter">
+            <level>WARN</level>
+            <onMatch>ACCEPT</onMatch>
+            <onMismatch>DENY</onMismatch>
+        </filter>
+        <rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
+            <fileNamePattern>${LOG_HOME}/warn/warnLog-%d{yyyy-MM-dd}.%i.txt</fileNamePattern>
+            <maxFileSize>10MB</maxFileSize>
+            <maxHistory>${maxHistory}</maxHistory>
+            <totalSizeCap>20GB</totalSizeCap>
+        </rollingPolicy>
+        <encoder>
+            <pattern>%d{yyyy-MM-dd HH:mm:ss:SSS} [%thread] %-5level %logger{50}\(%F %L\) -%msg%n </pattern>
+        </encoder>
+    </appender>
+
+    <!-- ERROR级别日志 -->
+    <appender name="ERROR" class="ch.qos.logback.core.rolling.RollingFileAppender">
+        <!-- 过滤器,只记录「ERROR」级别的日志 -->
+        <filter class="ch.qos.logback.classic.filter.LevelFilter">
+            <level>ERROR</level>
+            <onMatch>ACCEPT</onMatch>
+            <onMismatch>DENY</onMismatch>
+        </filter>
+        <rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
+            <fileNamePattern>${LOG_HOME}/error/errorLog-%d{yyyy-MM-dd}.%i.txt</fileNamePattern>
+            <maxFileSize>10MB</maxFileSize>
+            <maxHistory>${maxHistory}</maxHistory>
+            <totalSizeCap>20GB</totalSizeCap>
+        </rollingPolicy>
+        <encoder>
+            <pattern>%d{yyyy-MM-dd HH:mm:ss:SSS} [%thread] %-5level %logger{50}\(%F %L\) -%msg%n </pattern>
+        </encoder>
+    </appender>
+
+    <!-- eg: com.ljq.test 类的日志输出 info 及以上级别的日志 -->
+    <!--<logger name="com.ljq.test" level="info" />-->
+    <!-- eg: com.ljq.test1 类的日志不输出 -->
+    <!--<logger name="com.ljq.test1" additivity="false" />-->
+<!--    <logger name="org.apache.ibatis.io" level="info" />-->
+<!--    <logger name="org.mybatis.spring" level="info" />-->
+<!--    <logger name="org.springframework" level="info" />-->
+<!--    <logger name="io.lettuce" level="info"/>-->
+<!--    <logger name="io.netty" level="info" />-->
+
+    <!-- 根日志,所有日志appender都必须包含在root/logger中,否则不会起作用 -->
+    <root level="INFO">
+        <appender-ref ref="STDOUT" />
+        <appender-ref ref="DEBUG" />
+        <appender-ref ref="INFO" />
+        <appender-ref ref="WARN" />
+        <appender-ref ref="ERROR" />
+    </root>
+</configuration>