فهرست منبع

项目模块拆分

syh 5 سال پیش
والد
کامیت
c3a735f70a
99فایلهای تغییر یافته به همراه3691 افزوده شده و 1191 حذف شده
  1. 5 6
      jeecg-boot-module-system/pom.xml
  2. 74 0
      jeecg-boot-module-system/src/main/java/org/jeecg/config/XxlJobConfig.java
  3. 2 2
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/controller/AdvertiserController.java
  4. 4 2
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/controller/ImageDownloadController.java
  5. 2 3
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/controller/MaterialPartController.java
  6. 1 1
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/controller/UReportFileBindUserController.java
  7. 1 1
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/controller/UReportFileController.java
  8. 2 3
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/job/MergeVideoJob.java
  9. 21 0
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/job/TestXxlJob.java
  10. 1 1
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/job/WatermarkVideoJob.java
  11. 0 1
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/service/impl/BidWarningServiceImpl.java
  12. 1 1
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/service/impl/UReportFileBindUserServiceImpl.java
  13. 2 2
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/service/impl/UReportFileServiceImpl.java
  14. 1 1
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/opencv/controller/ModelVideoInfoController.java
  15. 2 0
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/opencv/service/impl/FfmpegServiceImpl.java
  16. 32 9
      jeecg-boot-module-system/src/main/java/org/jeecg/modules/system/service/impl/PerformanceServiceImpl2.java
  17. 14 1
      jeecg-boot-module-system/src/main/resources/application.yml
  18. 2 110
      jeecg-boot-module-system/src/test/java/org/jeecg/SampleTest.java
  19. 3 0
      module-common/src/main/java/cn/com/ctop/common/module/enums/MaterialEnum.java
  20. 1 1
      module-common/src/main/java/cn/com/ctop/common/module/service/impl/CtopOauthTokenServiceImpl.java
  21. 2 0
      module-common/src/main/java/cn/com/ctop/common/module/service/impl/MaterialInfoServiceImpl.java
  22. 1 1
      module-common/src/main/java/cn/com/ctop/common/module/service/impl/UserAllocationServiceImpl.java
  23. 17 40
      module-common/src/main/java/cn/com/ctop/common/module/utils/MpsUtils.java
  24. 1 0
      module-crawler/src/main/java/cn/com/ctop/crawler/modules/dataeye/service/impl/DataeyeCompanyServiceImpl.java
  25. 1 0
      module-crawler/src/main/java/cn/com/ctop/crawler/modules/dataeye/service/impl/DataeyeMediaServiceImpl.java
  26. 3 2
      module-crawler/src/main/java/cn/com/ctop/crawler/modules/dataeye/service/impl/DataeyeProductServiceImpl.java
  27. 1 1
      module-crawler/src/main/java/cn/com/ctop/crawler/modules/oceanengine/service/impl/DouyinHotServiceImpl.java
  28. 2 2
      module-crawler/src/main/java/cn/com/ctop/crawler/modules/oceanengine/service/impl/EffectCaseServiceImpl.java
  29. 1 1
      module-crawler/src/main/java/cn/com/ctop/crawler/modules/oceanengine/service/impl/HotMaterialServiceImpl.java
  30. 2 1
      module-crawler/src/main/java/cn/com/ctop/crawler/modules/pangolin/service/impl/PangolinLoginServiceImpl.java
  31. 2 2
      module-ctop/src/main/java/cn/com/ctop/manage/modules/edu/service/impl/EduLessonServiceImpl.java
  32. 1 0
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/app/service/impl/KuaishouAppProductServiceImpl.java
  33. 1 1
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/app/service/impl/KuaishouAppServiceImpl.java
  34. 3 1
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/batch/service/impl/KuaishouInterfaceServiceImpl.java
  35. 0 401
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/KuaishouTest.java
  36. 2 36
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/controller/KuaishouWebController.java
  37. 0 16
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/entity/KuaishouCommentConfig.java
  38. 0 18
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/entity/KuaishouCommentKeyword.java
  39. 0 15
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/entity/KuaishouCommentStat.java
  40. 0 97
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/job/KuaishouCommentDayJob.java
  41. 0 96
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/job/KuaishouCommentHourJob.java
  42. 0 7
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/mapper/KuaishouCommentConfigMapper.java
  43. 0 7
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/mapper/KuaishouCommentKeywordMapper.java
  44. 0 7
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/mapper/KuaishouCommentStatMapper.java
  45. 0 7
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/IKuaishouCommentConfigService.java
  46. 0 7
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/IKuaishouCommentKeywordService.java
  47. 0 7
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/IKuaishouCommentStatService.java
  48. 0 11
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/impl/KuaishouCommentConfigServiceImpl.java
  49. 0 11
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/impl/KuaishouCommentKeywordServiceImpl.java
  50. 0 11
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/impl/KuaishouCommentStatServiceImpl.java
  51. 2 0
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/report/service/impl/KuaishouReportDailyAgentServiceImpl.java
  52. 2 0
      module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/report/service/impl/KuaishouReportDailyAgentSumServiceImpl.java
  53. 0 8
      module-report/src/main/java/cn/com/ctop/bytedance/entity/BytedanceAdvertiserDailyReport.java
  54. 6 1
      module-report/src/main/java/cn/com/ctop/bytedance/service/impl/BytedanceReportServiceImpl.java
  55. 1 1
      module-toutiao/src/main/java/cn/com/ctop/toutiao/entity/ByteDanceAdvertisePlan.java
  56. 2 2
      module-toutiao/src/main/java/cn/com/ctop/toutiao/service/impl/ByteDanceAdvertiserDataServiceImpl.java
  57. 0 117
      moudule-eureca/.mvn/wrapper/MavenWrapperDownloader.java
  58. BIN
      moudule-eureca/.mvn/wrapper/maven-wrapper.jar
  59. 0 2
      moudule-eureca/.mvn/wrapper/maven-wrapper.properties
  60. 0 62
      moudule-eureca/pom.xml
  61. 0 16
      moudule-eureca/src/main/java/cn/com/ctop/eureca/server/ServerApplication.java
  62. 0 14
      moudule-eureca/src/main/resources/application.yml
  63. 0 13
      moudule-eureca/src/test/java/cn/com/ctop/eureca/server/ServerApplicationTests.java
  64. 5 2
      performance-appraisal/src/main/java/cn/com/ctop/performanceappraisal/service/impl/PerformanceOptimizerServiceImpl.java
  65. 3 2
      pom.xml
  66. 55 0
      xxl-job-core/pom.xml
  67. 44 0
      xxl-job-core/src/main/java/com/xxl/job/core/biz/AdminBiz.java
  68. 49 0
      xxl-job-core/src/main/java/com/xxl/job/core/biz/ExecutorBiz.java
  69. 48 0
      xxl-job-core/src/main/java/com/xxl/job/core/biz/client/AdminBizClient.java
  70. 174 0
      xxl-job-core/src/main/java/com/xxl/job/core/biz/impl/ExecutorBizImpl.java
  71. 56 0
      xxl-job-core/src/main/java/com/xxl/job/core/biz/model/HandleCallbackParam.java
  72. 54 0
      xxl-job-core/src/main/java/com/xxl/job/core/biz/model/LogResult.java
  73. 54 0
      xxl-job-core/src/main/java/com/xxl/job/core/biz/model/RegistryParam.java
  74. 57 0
      xxl-job-core/src/main/java/com/xxl/job/core/biz/model/ReturnT.java
  75. 144 0
      xxl-job-core/src/main/java/com/xxl/job/core/biz/model/TriggerParam.java
  76. 35 0
      xxl-job-core/src/main/java/com/xxl/job/core/enums/ExecutorBlockStrategyEnum.java
  77. 13 0
      xxl-job-core/src/main/java/com/xxl/job/core/enums/RegistryConfig.java
  78. 246 0
      xxl-job-core/src/main/java/com/xxl/job/core/executor/XxlJobExecutor.java
  79. 151 0
      xxl-job-core/src/main/java/com/xxl/job/core/executor/impl/XxlJobSpringExecutor.java
  80. 90 0
      xxl-job-core/src/main/java/com/xxl/job/core/glue/GlueFactory.java
  81. 53 0
      xxl-job-core/src/main/java/com/xxl/job/core/glue/GlueTypeEnum.java
  82. 80 0
      xxl-job-core/src/main/java/com/xxl/job/core/glue/impl/SpringGlueFactory.java
  83. 49 0
      xxl-job-core/src/main/java/com/xxl/job/core/handler/IJobHandler.java
  84. 20 0
      xxl-job-core/src/main/java/com/xxl/job/core/handler/annotation/JobHandler.java
  85. 30 0
      xxl-job-core/src/main/java/com/xxl/job/core/handler/annotation/XxlJob.java
  86. 30 0
      xxl-job-core/src/main/java/com/xxl/job/core/handler/impl/GlueJobHandler.java
  87. 50 0
      xxl-job-core/src/main/java/com/xxl/job/core/handler/impl/MethodJobHandler.java
  88. 92 0
      xxl-job-core/src/main/java/com/xxl/job/core/handler/impl/ScriptJobHandler.java
  89. 225 0
      xxl-job-core/src/main/java/com/xxl/job/core/log/XxlJobFileAppender.java
  90. 84 0
      xxl-job-core/src/main/java/com/xxl/job/core/log/XxlJobLogger.java
  91. 125 0
      xxl-job-core/src/main/java/com/xxl/job/core/thread/ExecutorRegistryThread.java
  92. 124 0
      xxl-job-core/src/main/java/com/xxl/job/core/thread/JobLogFileCleanThread.java
  93. 218 0
      xxl-job-core/src/main/java/com/xxl/job/core/thread/JobThread.java
  94. 246 0
      xxl-job-core/src/main/java/com/xxl/job/core/thread/TriggerCallbackThread.java
  95. 148 0
      xxl-job-core/src/main/java/com/xxl/job/core/util/DateUtil.java
  96. 179 0
      xxl-job-core/src/main/java/com/xxl/job/core/util/FileUtil.java
  97. 228 0
      xxl-job-core/src/main/java/com/xxl/job/core/util/ScriptUtil.java
  98. 46 0
      xxl-job-core/src/main/java/com/xxl/job/core/util/ShardingUtil.java
  99. 162 0
      xxl-job-core/src/main/java/com/xxl/job/core/util/XxlJobRemotingUtil.java

+ 5 - 6
jeecg-boot-module-system/pom.xml

@@ -123,12 +123,6 @@
             <scope>compile</scope>
         </dependency>
         <dependency>
-            <groupId>org.jeecgframework.boot</groupId>
-            <artifactId>module-ctop</artifactId>
-            <version>2.0.2</version>
-            <scope>compile</scope>
-        </dependency>
-        <dependency>
             <groupId>cn.com.ctop</groupId>
             <artifactId>module-report</artifactId>
             <version>2.0.2</version>
@@ -173,6 +167,11 @@
             <artifactId>opencv</artifactId>
             <version>4.2.0</version>
         </dependency>
+        <dependency>
+            <groupId>org.jeecgframework.boot</groupId>
+            <artifactId>xxl-job-core</artifactId>
+            <version>2.0.2</version>
+        </dependency>
     </dependencies>
 
     <dependencyManagement>

+ 74 - 0
jeecg-boot-module-system/src/main/java/org/jeecg/config/XxlJobConfig.java

@@ -0,0 +1,74 @@
+package org.jeecg.config;
+
+import com.xxl.job.core.executor.impl.XxlJobSpringExecutor;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+
+/**
+ * xxl-job config
+ *
+ * @author xuxueli 2017-04-28
+ */
+@Configuration
+public class XxlJobConfig {
+    private Logger logger = LoggerFactory.getLogger(XxlJobConfig.class);
+
+    @Value("${xxl.job.admin.addresses}")
+    private String adminAddresses;
+
+    @Value("${xxl.job.executor.appname}")
+    private String appName;
+
+    @Value("${xxl.job.executor.ip}")
+    private String ip;
+
+    @Value("${xxl.job.executor.port}")
+    private int port;
+
+    @Value("${xxl.job.accessToken}")
+    private String accessToken;
+
+    @Value("${xxl.job.executor.logpath}")
+    private String logPath;
+
+    @Value("${xxl.job.executor.logretentiondays}")
+    private int logRetentionDays;
+
+
+    @Bean
+    public XxlJobSpringExecutor xxlJobExecutor() {
+        logger.info(">>>>>>>>>>> xxl-job config init.");
+        XxlJobSpringExecutor xxlJobSpringExecutor = new XxlJobSpringExecutor();
+        xxlJobSpringExecutor.setAdminAddresses(adminAddresses);
+        xxlJobSpringExecutor.setAppName(appName);
+        xxlJobSpringExecutor.setIp(ip);
+        xxlJobSpringExecutor.setPort(port);
+        xxlJobSpringExecutor.setAccessToken(accessToken);
+        xxlJobSpringExecutor.setLogPath(logPath);
+        xxlJobSpringExecutor.setLogRetentionDays(logRetentionDays);
+
+        return xxlJobSpringExecutor;
+    }
+
+    /**
+     * 针对多网卡、容器内部署等情况,可借助 "spring-cloud-commons" 提供的 "InetUtils" 组件灵活定制注册IP;
+     *
+     *      1、引入依赖:
+     *          <dependency>
+     *             <groupId>org.springframework.cloud</groupId>
+     *             <artifactId>spring-cloud-commons</artifactId>
+     *             <version>${version}</version>
+     *         </dependency>
+     *
+     *      2、配置文件,或者容器启动变量
+     *          spring.cloud.inetutils.preferred-networks: 'xxx.xxx.xxx.'
+     *
+     *      3、获取IP
+     *          String ip_ = inetUtils.findFirstNonLoopbackHostInfo().getIpAddress();
+     */
+
+
+}

+ 2 - 2
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/controller/AdvertiserController.java

@@ -374,7 +374,7 @@ public class AdvertiserController {
         //查询总的消耗信息
         Long projectId = data.getLong("projectId");
         String systemType = data.getString("systemType");
-        if (null == systemType || systemType.trim().equals("")) {
+        if (null == systemType || "".equals(systemType.trim())) {
             systemType = null;
         }
         SheetInfoVo totalSheetVo = advertiserService.getXxlStatisticInfo(projectId, systemType, null, "汇总表");
@@ -408,7 +408,7 @@ public class AdvertiserController {
     @ResponseBody
     public void exportXxl(HttpServletRequest request, HttpServletResponse response, Long projectId, String systemType) throws Exception {
         List<SheetInfoVo> sheets = new ArrayList<>();
-        if (null == systemType || systemType.trim().equals("")) {
+        if (null == systemType || "".equals(systemType.trim())) {
             systemType = null;
         }
         //查询总的消耗信息

+ 4 - 2
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/controller/ImageDownloadController.java

@@ -125,10 +125,12 @@ public class ImageDownloadController {
         } catch (Exception e) {
         } finally {
             try {
-                if (inputStream != null)
+                if (inputStream != null){
                     inputStream.close();
-                if (stream != null)
+                }
+                if (stream != null){
                     stream.close();
+                }
                 outStream.close();
             } catch (Exception e) {
             }

+ 2 - 3
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/controller/MaterialPartController.java

@@ -48,7 +48,6 @@ public class MaterialPartController {
         List<String> jobIdList = new ArrayList<>();
         List<VideoMerge> videoMergeList = jsonArray.toJavaList(VideoMerge.class);
         try {
-            MpsUtils mpsUtils = new MpsUtils();
             for (VideoMerge videoMerge:videoMergeList){
                 MaterialInfo start = materialInfoService.getMaterialInfoByCode(videoMerge.getStartPart());
                 MaterialInfo end = materialInfoService.getMaterialInfoByCode(videoMerge.getEndPart());
@@ -64,8 +63,8 @@ public class MaterialPartController {
                 String startPath = startUrl.substring(startUrl.indexOf("/",10)+1,startUrl.length());
                 String endUrl = end.getUrl();
                 String endPath = endUrl.substring(endUrl.indexOf("/",10)+1,endUrl.length());
-                String jobId = mpsUtils.mergeOneVideo(startPath,partUrlList,endPath);
-                QueryJobListResponse.Job job = mpsUtils.getJobStatus(jobId);
+                String jobId = MpsUtils.mergeOneVideo(startPath,partUrlList,endPath);
+                QueryJobListResponse.Job job = MpsUtils.getJobStatus(jobId);
                 VideoMergeTask videoMergeTask = new VideoMergeTask();
                 LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
                 videoMergeTask.setUserId(sysUser.getId());

+ 1 - 1
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/controller/UReportFileBindUserController.java

@@ -74,7 +74,7 @@ public class UReportFileBindUserController {
         LoginUser user = (LoginUser) SecurityUtils.getSubject().getPrincipal();
         uReportFileBindUser.setUserId(user.getId());
         String fileName = null;
-        if (null != uReportFileBindUser.getFileName() && !uReportFileBindUser.getFileName().trim().equals("")) {
+        if (null != uReportFileBindUser.getFileName() && !"".equals(uReportFileBindUser.getFileName().trim())) {
             fileName = uReportFileBindUser.getFileName();
             uReportFileBindUser.setFileName(null);
         }

+ 1 - 1
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/controller/UReportFileController.java

@@ -67,7 +67,7 @@ public class UReportFileController {
                                                     HttpServletRequest req) {
         Result<IPage<UReportFile>> result = new Result<IPage<UReportFile>>();
         String name = null;
-        if (null != uReportFile.getName() && !uReportFile.getName().trim().equals("")) {
+        if (null != uReportFile.getName() && !"".equals(uReportFile.getName().trim())) {
             name = uReportFile.getName();
             uReportFile.setName(null);
         }

+ 2 - 3
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/job/MergeVideoJob.java

@@ -30,9 +30,8 @@ public class MergeVideoJob implements Job {
         List<VideoMergeTask> list = videoMergeTaskService.list(queryWrapper);
         if (list != null && list.size() > 0) {
             for (VideoMergeTask videoMergeTask : list) {
-                MpsUtils mpsUtils = new MpsUtils();
-                QueryJobListResponse.Job job = mpsUtils.getJobStatus(videoMergeTask.getJobId());
-                if (job.getState().equals("TranscodeSuccess")) {
+                QueryJobListResponse.Job job = MpsUtils.getJobStatus(videoMergeTask.getJobId());
+                if ("TranscodeSuccess".equals(job.getState())) {
                     String url = "https://ctop-part.oss-cn-beijing.aliyuncs.com/" + job.getOutput().getOutputFile().getObject();
 
                     try {

+ 21 - 0
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/job/TestXxlJob.java

@@ -0,0 +1,21 @@
+//package org.jeecg.modules.ctop.job;
+//
+//import com.xxl.job.core.biz.model.ReturnT;
+//import com.xxl.job.core.handler.annotation.XxlJob;
+//import lombok.extern.slf4j.Slf4j;
+//import org.springframework.stereotype.Component;
+//
+//import java.util.concurrent.TimeUnit;
+//
+//@Component
+//@Slf4j
+//public class TestXxlJob{
+//
+//    @XxlJob("testJob")
+//    public ReturnT<String> execute(String s) throws Exception {
+//        log.info("开始执行");
+//        TimeUnit.SECONDS.sleep(2);
+//        log.info("执行完成");
+//        return ReturnT.SUCCESS;
+//    }
+//}

+ 1 - 1
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/job/WatermarkVideoJob.java

@@ -35,7 +35,7 @@ public class WatermarkVideoJob implements Job {
                 if (list != null && list.size() > 0) {
                     for (VideoWatermarkTask videoWatermarkTask : list) {
                         QueryJobListResponse.Job job = MpsUtils.getJobStatus(videoWatermarkTask.getJobId());
-                        if (job.getState().equals("TranscodeSuccess")) {
+                        if ("TranscodeSuccess".equals(job.getState())) {
                             String url = "https://ctop-media.oss-cn-beijing.aliyuncs.com/" + job.getOutput().getOutputFile().getObject();
 
                             try {

+ 0 - 1
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/service/impl/BidWarningServiceImpl.java

@@ -54,7 +54,6 @@ public class BidWarningServiceImpl implements IBidWarningService {
         long l = System.currentTimeMillis();
         try {
             QueryWrapper<Project> projectQueryWrapper = new QueryWrapper<>();
-            // projectQueryWrapper.eq("media_id", "1");
             List<Project> projects = projectMapper.selectList(projectQueryWrapper);
             if (!Check.isNull(projects)) {
                 for (Project project : projects) {

+ 1 - 1
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/service/impl/UReportFileBindUserServiceImpl.java

@@ -45,7 +45,7 @@ public class UReportFileBindUserServiceImpl extends ServiceImpl<UReportFileBindU
     @Override
     public Map<String, Object> getListByFileId(JSONObject data) {
         Map<String, Object> result = new HashMap<>();
-        if (null == data || null == data.getString("fileId") || data.getString("fileId").equals("")) {
+        if (null == data || null == data.getString("fileId") || "".equals(data.getString("fileId"))) {
             ResultMapUtils.setResultMap(result, StatusCode.COMMON_PARAM_ERROR);
             return result;
         }

+ 2 - 2
jeecg-boot-module-system/src/main/java/org/jeecg/modules/ctop/service/impl/UReportFileServiceImpl.java

@@ -80,7 +80,7 @@ public class UReportFileServiceImpl extends ServiceImpl<UReportFileMapper, URepo
         }
         String fileId = data.getString("fileId");
         String userIds = data.getString("userIds");
-        if (null == userIds || userIds.trim().equals("") || null == fileId || fileId.trim().equals("")) {
+        if (null == userIds || "".equals(userIds.trim()) || null == fileId || "".equals(fileId.trim())) {
             ResultMapUtils.setResultMap(result, StatusCode.COMMON_PARAM_ERROR);
             return result;
         }
@@ -126,7 +126,7 @@ public class UReportFileServiceImpl extends ServiceImpl<UReportFileMapper, URepo
         }
         String userId = data.getString("userId");
         String fileId = data.getString("fileId");
-        if (null == userId || userId.trim().equals("") || null == fileId || fileId.trim().equals("")) {
+        if (null == userId || "".equals(userId.trim()) || null == fileId || "".equals(fileId.trim())) {
             ResultMapUtils.setResultMap(result, StatusCode.COMMON_PARAM_ERROR);
             return result;
         }

+ 1 - 1
jeecg-boot-module-system/src/main/java/org/jeecg/modules/opencv/controller/ModelVideoInfoController.java

@@ -59,7 +59,7 @@ public class ModelVideoInfoController {
         } else if (orderType == 2) {
             queryWrapper.orderByDesc("id");
         }
-        if (null != title && !title.trim().equals("")) {
+        if (null != title && !"".equals(title.trim())) {
             queryWrapper.like("title", title);
         }
         Page<ModelVideoInfo> page = new Page<>(pageNo, pageSize);

+ 2 - 0
jeecg-boot-module-system/src/main/java/org/jeecg/modules/opencv/service/impl/FfmpegServiceImpl.java

@@ -228,6 +228,7 @@ public class FfmpegServiceImpl implements IFfmpegService {
             final InputStream is2 = process.getErrorStream();
             //启动两个线程,一个线程负责读标准输出流,另一个负责读标准错误流
             new Thread() {
+                @Override
                 public void run() {
                     BufferedReader br1 = new BufferedReader(new InputStreamReader(is1));
                     try {
@@ -249,6 +250,7 @@ public class FfmpegServiceImpl implements IFfmpegService {
             }.start();
 
             new Thread() {
+                @Override
                 public void run() {
                     BufferedReader br2 = new BufferedReader(new InputStreamReader(is2));
                     try {

+ 32 - 9
jeecg-boot-module-system/src/main/java/org/jeecg/modules/system/service/impl/PerformanceServiceImpl2.java

@@ -1828,6 +1828,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     //1
     //季度到前一天为止个人的有效数量、素材总数、素材有效率、总跑量
     //{"effiVideoCount有效数":70,"videoCount素材总数":200,"effiRate":40,"cost":2019;performance绩效":20000}
+    @Override
     public Map<String, Object> getPerformanceInfo() {
         Map<String, Object> performanceInfoMap = new HashMap<>();
         LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
@@ -1858,11 +1859,11 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
         //获取本人的总跑量
         BigDecimal cost = BigDecimal.ZERO;
 
-        if (roleCode.equals("plan")) {
+        if ("plan".equals(roleCode)) {
             cost = userEfficientVideoMapMapper.getTotalCostByPlanId(sysUser.getId(), startDate, endDate);
-        } else if (roleCode.equals("shot")) {
+        } else if ("shot".equals(roleCode)) {
             cost = userEfficientVideoMapMapper.getTotalCostByShotId(sysUser.getId(), startDate, endDate);
-        } else if (roleCode.equals("clip")) {
+        } else if ("clip".equals(roleCode)) {
             cost = userEfficientVideoMapMapper.getTotalCostByClipId(sysUser.getId(), startDate, endDate);
         }
 
@@ -1878,6 +1879,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     //2
     //有效率排行榜
     //{"list":[{"name":"pipi","effiRate":50},{"name":"pipixia","effiRate":40},{"name":"pipiqiu","effiRate":30}],"performance":performance}
+    @Override
     public Map<String, Object> effiRateRank(Integer size) {
         Map<String, Object> resultMap = new HashMap<>();
         LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
@@ -1897,13 +1899,13 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
 
         List<UserDto> userRoleList = new ArrayList<>();
         BigDecimal rate = BigDecimal.ZERO; //提成比例
-        if (roleCode.equals("plan")) {
+        if ("plan".equals(roleCode)) {
             userRoleList = sysRoleMapper.getUserByRoleCode("plan"); //编导
             rate = new BigDecimal("0.4");
-        } else if (roleCode.equals("shot")) {
+        } else if ("shot".equals(roleCode)) {
             userRoleList = sysRoleMapper.getUserByRoleCode("shot"); //拍摄
             rate = new BigDecimal("0.1");
-        } else if (roleCode.equals("clip")) {
+        } else if ("clip".equals(roleCode)) {
             userRoleList = sysRoleMapper.getUserByRoleCode("clip"); //剪辑
             rate = new BigDecimal("0.3");
         }
@@ -1943,7 +1945,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
             //总绩效=总消耗*提点比例(5‰)*提成比例(剪辑30%)
             BigDecimal performance = BigDecimal.ZERO; //绩效
             BigDecimal totalCost = BigDecimal.ZERO;  //总消耗
-            if (roleCode.equals("plan")) {
+            if ("plan".equals(roleCode)) {
                 totalCost = userEfficientVideoMapMapper.getTotalCostByPlanId(sysUser.getId(), startDate, endNowDate);
                 if (index <= userTopSize) {
                     performance = totalCost.multiply(new BigDecimal("0.005")).multiply(new BigDecimal("0.4"));
@@ -1952,7 +1954,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
                 } else {
                     performance = BigDecimal.ZERO;
                 }
-            } else if (roleCode.equals("shot")) {
+            } else if ("shot".equals(roleCode)) {
                 totalCost = userEfficientVideoMapMapper.getTotalCostByShotId(sysUser.getId(), startDate, endNowDate);
                 if (index <= userTopSize) {
                     performance = totalCost.multiply(new BigDecimal("0.005")).multiply(new BigDecimal("0.1"));
@@ -1991,6 +1993,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     //3
     //素材、素材跑量、封面点击数、封面曝光数、行为数
     //{"videoUrl":"http://dadfadfadf.mp4","videoCost":34.56,"pageClickCount":1200,"pageExposureCount":3939,"behaviorCount":5000}
+    @Override
     public List<DesignMaterialInfo> materialInfoList() {
         LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
         //LoginUser sysUser = new LoginUser();
@@ -2014,6 +2017,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     //4
     //点击+符号 投放账户、投放账户、跑量
     //{"videoAccount":"aabbcc","servingAccount":"ttyyhh","cost":34234.43}
+    @Override
     public List<DesignMaterialInfo> materialAccountInfo(String materialInfoId) {
         log.info("materialAccountInfo接口开始");
         Map<String, Integer> quarterMap = DateUtils.lastQuarter(new Date());
@@ -2047,6 +2051,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //获取快手上个季度的季度有效数、素材总数、上个季度的绩效
+    @Override
     public Map<String, Object> kuaishouDesignerLastQuarterPerformanceInfo() {
         LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
 
@@ -2103,6 +2108,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //获取设计师组下所有人的绩效
+    @Override
     public Map<String, Object> designerLastQuarterPerformanceInfo() {
         LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
 
@@ -2126,7 +2132,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
         //判断如果在parent_id是不是快手或者头条的
         int appType = 0; //头条1;快手2
         String parentId = userEfficientVideoMapMapper.getParentIdByDepartId(DepartId);
-        if (parentId.equals("26c10ecb5e0d416bb01f8ff983f4588c")) {
+        if ("26c10ecb5e0d416bb01f8ff983f4588c".equals(parentId)) {
             appType = 1;
         } else {
             appType = 2;
@@ -2150,6 +2156,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //平面设计师(快手、头条可能不一样,头条内广是单独的媒体不知道是怎么回事)
+    @Override
     public Map<String, Object> planeLastQuarterPerformanceInfo(int appType) {
         LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
 
@@ -2173,6 +2180,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //获取同一媒体类型下上个季度所有人的绩效
+    @Override
     public Map<String, Object> quarterUserPerformanceList(Integer appType) {
         Map<String, Object> resultMap = new HashMap<>();
 
@@ -2322,6 +2330,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //获取快手优化师所属账号的消耗等信息
+    @Override
     public List<AccountDTO> getKuaiShouYouhuaAccountsList(String userId, Integer appType, Integer year , Integer quarter){
         if(year == null || quarter == null){
             Map<String, Integer> dateMap = DateUtils.getYearQuarter(new Date());
@@ -2349,6 +2358,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //获取头条绩效实时数据
+    @Override
     public List<UserDto2> toutiaoPerformanceInfoNow() {
         //0 获取当前季度的时间
         Map<String, Integer> dateMap = DateUtils.getYearQuarter(new Date());
@@ -2418,6 +2428,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //头条绩效周报
+    @Override
     public List<UserDto2> toutiaoWeekReport(String startDate, String endDate) {
         //1 获取头条所有人
         List<UserDto2> userDto2List = userEfficientVideoMapMapper.getToutiaoDepartUserInfo();
@@ -2519,6 +2530,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //根据userid,appType,年度,季度查询有效视频列表
+    @Override
     public List<MaterialInfo> effiVideoList(Integer appType, Integer year, Integer quarter, String userId){
         if(year == null || quarter == null){
             Map<String, Integer> dateMap = DateUtils.getYearQuarter(new Date());
@@ -2530,12 +2542,14 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //根据userid,appType,年度,季度查询有效视频列表
+    @Override
     public List<MaterialInfo> getVideoList(Integer appType, String userId, String startDate, String endDate){
         List<MaterialInfo> materialInfoList = userEfficientVideoMapMapper.getVideoList(appType, userId, startDate, endDate);
         return materialInfoList;
     }
 
     //根据userid,appType,年度,季度查询有效视频列表
+    @Override
     public List<MaterialInfo> getEffiWeekVideoList(Integer appType, String startDate, String endDate, String userId){
         List<MaterialInfo> materialInfoList = userEfficientVideoMapMapper.getEffiWeekVideoList(appType, startDate, endDate, userId);
 
@@ -2600,6 +2614,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
 
     //头条优化季度绩效报表
     //@Override
+    @Override
     public List<UserDto2> toutiaoYouhuaQuarterReport(Integer year, Integer quarter) {
         Integer appType = 1;
         //1 获取快手下所有人
@@ -2625,21 +2640,25 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
         return userDto2List;
     }
 
+    @Override
     public List<PerformanceAccount> getYunyingQuarterDetailByUserId(Integer year, Integer quarter, String userId, Integer appType){
         return userEfficientVideoMapMapper.getYunyingQuarterDetailByUserId(year, quarter, userId, appType);
     }
 
     //按平台获取其下所有项目信息以及消耗
+    @Override
     public List<ProjectDTO> getProjcetListByMediaType(Integer year, Integer quarter, Integer appType ){
         return userEfficientVideoMapMapper.getProjcetListByMediaType(year, quarter, appType);
     }
 
     //根据projectId获取其下账户季度消耗信息
+    @Override
     public List<AccountDTO> getQuarterAccountDetail(Integer year, Integer quarter, Integer projectId, Integer appType){
         return userEfficientVideoMapMapper.getQuarterAccountDetail(year, quarter, projectId, appType);
     }
 
     //根据accountId获取季度视频信息
+    @Override
     public List<VideoDTO> getKuaishouQuarterVideoInfoByAccountId(Integer year, Integer quarter, Long accountId){
         Map<String,String> dateMap = DateUtils.quarterStartEndDate(year, quarter);
         String startDate = dateMap.get("startDate");
@@ -2649,6 +2668,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //根据accountId获取季度视频信息
+    @Override
     public List<VideoDTO> getToutiaoQuarterVideoInfoByAccountId(Integer year, Integer quarter, Long accountId){
         Map<String,String> dateMap = DateUtils.quarterStartEndDate(year, quarter);
         String startDate = dateMap.get("startDate");
@@ -2657,6 +2677,7 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
     }
 
     //获取快手、头条下各账户下视频的季度消耗
+    @Override
     public void getQuarterVideoInfoByAccountId(Integer year, Integer quarter){
         Map<String,String> dateMap = DateUtils.quarterStartEndDate(year, quarter);
         String startDate = dateMap.get("startDate");
@@ -2748,10 +2769,12 @@ public class PerformanceServiceImpl2 extends ServiceImpl<PerformanceMapper, Perf
         }
     }
 
+    @Override
     public List<VideoDTO> getUserQuarterVideo(Integer year, Integer quarter, String userId){
         return userEfficientVideoMapMapper.getUserQuarterVideo(userId, year, quarter);
     }
 
+    @Override
     public List<VideoDTO> getUserQuarterEffiVideo(Integer year, Integer quarter, String userId){
         return userEfficientVideoMapMapper.getUserQuarterEffiVideo(userId, year, quarter);
     }

+ 14 - 1
jeecg-boot-module-system/src/main/resources/application.yml

@@ -1,6 +1,7 @@
 spring:
   profiles:
-    active: @activatedProperties@
+#    active: @activatedProperties@
+    active: prod
   application:
     name: system-web
 eureka:
@@ -13,3 +14,15 @@ swagger:
     enable: true
     username: jeecg
     password: jeecg1314
+
+xxl:
+  job:
+    accessToken:
+    executor:
+      logpath: /data/applogs/xxl-job/jobhandler
+      logretentiondays: 30
+      appname: xxl-job-executor-jeecg-boot
+      ip:
+      port: 9998
+    admin:
+      addresses: http://127.0.0.1:8090/xxl-job-admin

+ 2 - 110
jeecg-boot-module-system/src/test/java/org/jeecg/SampleTest.java

@@ -13,7 +13,6 @@ import cn.com.ctop.kuaishou.modules.batch.service.IKuaishouInterfaceService;
 import cn.com.ctop.toutiao.service.IByteDanceAdvertiserDataService;
 import com.alibaba.fastjson.JSONArray;
 import com.alibaba.fastjson.JSONObject;
-import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import lombok.extern.slf4j.Slf4j;
 import org.jeecg.common.util.DateUtils;
 import org.jeecg.modules.ctop.service.IBytedanceFundDailyService;
@@ -26,8 +25,6 @@ import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.boot.test.context.SpringBootTest;
 import org.springframework.test.context.junit4.SpringRunner;
 
-import java.text.SimpleDateFormat;
-import java.util.ArrayList;
 import java.util.Date;
 import java.util.List;
 import java.util.concurrent.CountDownLatch;
@@ -53,87 +50,9 @@ public class SampleTest {
     @Test
     public void kuaisShouReport() {
         try {
-
-          /*  QueryWrapper<CtopOauthToken> queryWrapper = new QueryWrapper<>();
-            queryWrapper.eq("account_id", 3727345L);
-            CtopOauthToken token = tokenMapper.selectOne(queryWrapper);
-
-            SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd");
-            Date parse = simpleDateFormat.parse("2020-03-12");
-            kuaishouInterfaceService.getAdvertiserReportDaily(token, parse, parse);*/
-
-
             oauthTokenService.getKuaiShouRefreshToken(4801802L, "3874f4adb984a371cf92e5fc9a585e6b", 1);
-
-//            reportTaskService.createTask(3727345L, "871fc2c248782a94ad2962c941555abc", "");
-//            reportTaskService.getTaskList();
-
-/*
-            reportTaskService.createTask(3727345L, "871fc2c248782a94ad2962c941555abc");
-            reportTaskService.getTaskList();*/
-
-
-
-         /*   String url = "https://ad.e.kuaishou.com/rest/openapi/v1/async_task/list";
-            Map<String, String> headers = new HashMap<>();
-            headers.put("Content-Type", " application/json");
-            headers.put("Access-Token", "eb9a0d18072eabc339ee26ad010ecd6b");
-            JSONObject param = new JSONObject();
-            param.put("advertiser_id", 142402);
-            JSONArray taskIds = new JSONArray();
-            taskIds.add(1229917);
-
-            param.put("task_ids", taskIds);
-            String result = HttpUtils.kuaiShouhttpPostRequest(url, param.toJSONString(), headers);
-            JSONObject resultJson = JSONObject.parseObject(result);
-
-
-          /*  String url = "https://ad.e.kuaishou.com/rest/openapi/v1/async_task/download";
-
-            Map<String, String> headers = new HashMap<>();
-            headers.put("Access-Token", "eb9a0d18072eabc339ee26ad010ecd6b");
-
-            Map<String,Object> param = new HashMap<>();
-            param.put("advertiser_id", 142402);
-            param.put("task_id", "1229917");
-            String result = HttpUtils.KuaiShouttpGetRequest(url, param,headers);*/
-
-
-            /*URL url = new URL("https://ad.e.kuaishou.com/rest/openapi/v1/async_task/download?task_id=1229917&advertiser_id=142402");
-            HttpURLConnection conn = (HttpURLConnection) url.openConnection();
-            //设置超时间为3秒
-            conn.setConnectTimeout(10 * 1000);
-            //防止屏蔽程序抓取而返回403错误
-            conn.setRequestProperty("User-Agent", "Mozilla/4.0 (compatible; MSIE 5.0; Windows NT; DigExt)");
-            conn.setRequestProperty("Access-Token", "6a1fbe20e49fe519ec8120aac5c9e55a");
-            //得到输入流
-            InputStream inputStream = conn.getInputStream();
-            //获取自己数组
-            byte[] getData = readInputStream(inputStream);
-
-            //文件保存位置
-            File saveDir = new File("D:\\file");
-            if (!saveDir.exists()) {
-                saveDir.mkdirs();
-            }
-            String fileName = "123.csv";
-            File file = new File(saveDir + File.separator + fileName);
-            FileOutputStream fos = new FileOutputStream(file);
-            fos.write(getData);
-            if (fos != null) {
-                fos.close();
-            }
-            if (inputStream != null) {
-                inputStream.close();
-            }*/
-         /*   String localPath = "D:\\file\\123.csv";
-
-            reportDailyAccountMapper.loadAccountDailyReport(142402L,localPath);*/
-
-
         } catch (Exception e) {
             e.printStackTrace();
-
         }
     }
 
@@ -147,35 +66,8 @@ public class SampleTest {
 
     @Test
     public void testLoadJob() {
-        String endDate = "2020-04-07";
-        String startDate = "2019-09-01";
-        CtopOauthToken token = tokenService.getTokenByAccountId(1654676647522317L);
-//        List<CtopOauthToken> tokens = tokenService.getTokenListByType(CtopAdConstant.PLATFORM_TYPE_BYTEDANCE);
-        List<CtopOauthToken> tokens = new ArrayList<>();
-        tokens.add(token);
-        if (null != tokens && tokens.size() > 0) {
-            countDownLatch = new CountDownLatch(tokens.size());
-            tokens.forEach(getToken -> {
-                //拉取往期数据
-                executorService.submit(new Runnable() {
-                    @Override
-                    public void run() {
-                        try {
-                            fundDailyService.loadFundDataByPage(getToken, startDate, endDate, 1);
-                            countDownLatch.countDown();
-                        } catch (Exception e) {
-                            e.printStackTrace();
-                        }
-                    }
-                });
-            });
-            try {
-                countDownLatch.await();
-                System.out.println("数据获取完成");
-            } catch (InterruptedException e) {
-                e.printStackTrace();
-            }
-        }
+        CtopOauthToken token = tokenService.getTokenByAccountId(6308264L);
+        kuaishouInterfaceService.getAdvertiserReportHourly(token, new Date(), new Date());
     }
 
     @Test

+ 3 - 0
module-common/src/main/java/cn/com/ctop/common/module/enums/MaterialEnum.java

@@ -1,5 +1,8 @@
 package cn.com.ctop.common.module.enums;
 
+/**
+ * 素材类型
+ */
 public enum MaterialEnum {
 
 

+ 1 - 1
module-common/src/main/java/cn/com/ctop/common/module/service/impl/CtopOauthTokenServiceImpl.java

@@ -160,7 +160,7 @@ public class CtopOauthTokenServiceImpl extends ServiceImpl<CtopOauthTokenMapper,
     @Override
     public List<CtopOauthToken> getTokenListByType(String platformType) {
         QueryWrapper<CtopOauthToken> queryWrapper = new QueryWrapper<>();
-        if (null != platformType && !platformType.trim().equals("")) {
+        if (null != platformType && !"".equals(platformType.trim())) {
             queryWrapper.eq("media_id", platformType);
         }
         queryWrapper.orderByDesc("account_id");

+ 2 - 0
module-common/src/main/java/cn/com/ctop/common/module/service/impl/MaterialInfoServiceImpl.java

@@ -546,10 +546,12 @@ public class MaterialInfoServiceImpl extends ServiceImpl<MaterialInfoMapper, Mat
         return resultMap;
     }
 
+    @Override
     public List<String> getEffiCode(){
         return materialInfoMapper.getEffiSignature();
     }
 
+    @Override
     public List<MaterialInfo> effiMaterialInfo(){
         List<MaterialInfo> materialInfoList = new ArrayList<>();
         List<String> effiSignatureList = materialInfoMapper.getEffiSignature();

+ 1 - 1
module-common/src/main/java/cn/com/ctop/common/module/service/impl/UserAllocationServiceImpl.java

@@ -31,7 +31,7 @@ public class UserAllocationServiceImpl extends ServiceImpl<UserAllocationMapper,
         if (null != projectId && projectId != 0) {
             queryWrapper.eq("project_id", projectId);
         }
-        if (null != systemType && !systemType.trim().equals("")) {
+        if (null != systemType && !"".equals(systemType.trim())) {
             queryWrapper.eq("system_type", systemType);
         }
         queryWrapper.orderByDesc("id");

+ 17 - 40
module-common/src/main/java/cn/com/ctop/common/module/utils/MpsUtils.java

@@ -8,45 +8,22 @@ import com.aliyuncs.exceptions.ClientException;
 import com.aliyuncs.exceptions.ServerException;
 import com.aliyuncs.mts.model.v20140618.*;
 import com.aliyuncs.profile.DefaultProfile;
-import com.google.gson.Gson;
 import org.springframework.context.annotation.Configuration;
 import org.springframework.context.annotation.PropertySource;
 
 import java.io.UnsupportedEncodingException;
 import java.net.URLEncoder;
 import java.text.SimpleDateFormat;
-import java.util.*;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+import java.util.UUID;
 
 @Configuration
 @PropertySource("classpath:config.properties")
 public class MpsUtils {
-    public static final String ossLocation = "oss-cn-beijing";
-    public static final String ossBucket = "ctop-part";
-    public static void main(String[] args) throws ClientException {
-//        String[] a = {"1","2","3","4","5"};
-//        combinationSelect(a,3);
-//        arrangementSelect(a,3);
-//        String t = "https://ctop-part.oss-cn-beijing.aliyuncs.com/input/VIDEO_HEAD/2019-12-11/25-1576044510677.mp4";
-//        int i = t.indexOf("/",10);
-
-       // MpsUtils mpsUtils = new MpsUtils();
-       // mpsUtils.videoWaterMark("video/2019-12-20/20%E7%BD%91%E6%9C%8D-1576822566069.mp4","watermark/water1080-1920.png","8bcf0c98021c40fc96a95d60f55b1f10",720);
-//        List<String> list = new ArrayList<>();
-//        list.add("v1.mp4");
-//        String jobId = mpsUtils.mergeOneVideo("v1.mp4",list,"v1.mp4");
-//        try {
-//            while (true){
-//                QueryJobListResponse.Job job = mpsUtils.getJobStatus(jobId);
-//                job.getOutput().getOutputFile().getObject();
-//                Thread.sleep(5000L);
-//            }
-//        } catch (InterruptedException e) {
-//            e.printStackTrace();
-//        }
-
-    }
-
-
+    public static final String OSS_LOCATION = "oss-cn-beijing";
+    public static final String OSS_BUCKET = "ctop-part";
 
     public static QueryJobListResponse.Job getJobStatus(String jobId){
         QueryJobListResponse.Job job = null;
@@ -176,7 +153,7 @@ public class MpsUtils {
         return client;
     }
 
-    public String mergeOneVideo(String startPart,List<String> videoPart,String endPart){
+    public static String mergeOneVideo(String startPart, List<String> videoPart, String endPart){
         IAcsClient client = getClient();
         String pipelineId = getPipelineId(client);
         SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
@@ -188,7 +165,7 @@ public class MpsUtils {
         return mergeVideo(client,pipelineId,videos,outputFilename);
     }
 
-    public String mergeVideo(IAcsClient client, String pipelineId, List<String> videos, String outputName){
+    public static String mergeVideo(IAcsClient client, String pipelineId, List<String> videos, String outputName){
         String jobId = null;
         SubmitJobsRequest request = new SubmitJobsRequest();
         JSONArray mergeList = new JSONArray();
@@ -197,8 +174,8 @@ public class MpsUtils {
                 String url = videos.get(i);
                 if (i == 0){
                     JSONObject input = new JSONObject();
-                    input.put("Location", ossLocation);
-                    input.put("Bucket", ossBucket);
+                    input.put("Location", OSS_LOCATION);
+                    input.put("Bucket", OSS_BUCKET);
                     try {
                         input.put("Object", URLEncoder.encode(url, "utf-8"));
                     } catch (UnsupportedEncodingException e) {
@@ -211,8 +188,8 @@ public class MpsUtils {
                     try {
                         mergeVideoUrl = String.format(
                                 "http://%s.%s.aliyuncs.com/%s",
-                                ossBucket,
-                                ossLocation,
+                                OSS_BUCKET,
+                                OSS_LOCATION,
                                 URLEncoder.encode(url, "utf-8"));
                     } catch (UnsupportedEncodingException e) {
                         throw new RuntimeException("mergeVideoURL encode failed");
@@ -240,8 +217,8 @@ public class MpsUtils {
         JSONArray outputs = new JSONArray();
         outputs.add(output);
         request.setOutputs(outputs.toJSONString());
-        request.setOutputBucket(ossBucket);
-        request.setOutputLocation(ossLocation);
+        request.setOutputBucket(OSS_BUCKET);
+        request.setOutputLocation(OSS_LOCATION);
         // PipelineId
         request.setPipelineId(pipelineId);
         // call api
@@ -268,12 +245,12 @@ public class MpsUtils {
         String pipelineId = getPipelineId(client);
         SubmitJobsRequest request = new SubmitJobsRequest();
         JSONObject input = new JSONObject();
-        input.put("Location", ossLocation);
+        input.put("Location", OSS_LOCATION);
         input.put("Bucket", "ctop-media");
         input.put("Object", videoPath);
         request.setInput(input.toJSONString());
         JSONObject videoWatermarkInput = new JSONObject();
-        videoWatermarkInput.put("Location", ossLocation);
+        videoWatermarkInput.put("Location", OSS_LOCATION);
         videoWatermarkInput.put("Bucket", "ctop-media");
         videoWatermarkInput.put("Object", waterMarkPath);
         JSONObject videoWatermark = new JSONObject();
@@ -294,7 +271,7 @@ public class MpsUtils {
         outputs.add(output);
         request.setOutputs(outputs.toJSONString());
         request.setOutputBucket("ctop-media");
-        request.setOutputLocation(ossLocation);
+        request.setOutputLocation(OSS_LOCATION);
         // PipelineId
         request.setPipelineId(pipelineId);
         SubmitJobsResponse response;

+ 1 - 0
module-crawler/src/main/java/cn/com/ctop/crawler/modules/dataeye/service/impl/DataeyeCompanyServiceImpl.java

@@ -30,6 +30,7 @@ import java.util.Map;
 public class DataeyeCompanyServiceImpl extends ServiceImpl<DataeyeCompanyMapper, DataeyeCompany> implements DataeyeCompanyService {
     @Autowired
     private DataeyeProductService dataeyeProductService;
+    @Override
     public void getCompanyInfo(Integer companyId){
         Map<String,Object> paramMap = new HashMap<>();
         paramMap.put("companyId",companyId);

+ 1 - 0
module-crawler/src/main/java/cn/com/ctop/crawler/modules/dataeye/service/impl/DataeyeMediaServiceImpl.java

@@ -21,6 +21,7 @@ import java.util.*;
 public class DataeyeMediaServiceImpl extends ServiceImpl<DataeyeMediaMapper, DataeyeMedia> implements DataeyeMediaService {
     @Autowired
     private DataeyeCompanyService dataeyeCompanyService;
+    @Override
     public void getMediaList(){
         String response = HttpUtils.httpPostFormRequest("https://blzs.dataeye.com/common/listMedia",null,null);
         System.out.println(response);

+ 3 - 2
module-crawler/src/main/java/cn/com/ctop/crawler/modules/dataeye/service/impl/DataeyeProductServiceImpl.java

@@ -34,7 +34,8 @@ public class DataeyeProductServiceImpl extends ServiceImpl<DataeyeProductMapper,
     @Autowired
     private DataeyeCompanyProductService dataeyeCompanyProductService;
 
-    public void getProductInfo(Long companyId,Long productId){
+    @Override
+    public void getProductInfo(Long companyId, Long productId){
         Map<String,Object> paramMap = new HashMap<>();
         paramMap.put("productId",productId);
         String response = HttpUtils.httpPostFormRequest("https://blzs.dataeye.com/product/getProductInfo",paramMap,null);
@@ -47,7 +48,7 @@ public class DataeyeProductServiceImpl extends ServiceImpl<DataeyeProductMapper,
             if (statusCode == 200){
                 String content = rootNode.get("content").toString();
                 DataeyeProduct product = mapper.readValue(content,DataeyeProduct.class);
-                if(product != null && product.getProductName() != null && !product.getProductName().equals("")){
+                if(product != null && product.getProductName() != null && !"".equals(product.getProductName())){
                     this.saveOrUpdate(product);
                 }
                 QueryWrapper<DataeyeCompanyProduct> queryWrapper1 = new QueryWrapper<>();

+ 1 - 1
module-crawler/src/main/java/cn/com/ctop/crawler/modules/oceanengine/service/impl/DouyinHotServiceImpl.java

@@ -31,7 +31,7 @@ public class DouyinHotServiceImpl extends ServiceImpl<DouyinHotMapper, DouyinHot
         if (null != start && !"".equals(start) && null != end && !"".equals(end)) {
             queryWrapper.between("create_time", start, end);
         }
-        if (null != orderByType && orderByType.equals("desc")) {
+        if (null != orderByType && "desc".equals(orderByType)) {
             queryWrapper.orderByDesc(orderByColumn);
         } else {
             queryWrapper.orderByAsc(orderByColumn);

+ 2 - 2
module-crawler/src/main/java/cn/com/ctop/crawler/modules/oceanengine/service/impl/EffectCaseServiceImpl.java

@@ -40,7 +40,7 @@ public class EffectCaseServiceImpl extends ServiceImpl<EffectCaseMapper, EffectC
         if (null != start && !"".equals(start) && null != end && !"".equals(end)) {
             queryWrapper.between("create_time", start, end);
         }
-        if (null != orderByType && orderByType.equals("desc")) {
+        if (null != orderByType && "desc".equals(orderByType)) {
             queryWrapper.orderByDesc(orderByColumn);
         } else {
             queryWrapper.orderByAsc(orderByColumn);
@@ -68,7 +68,7 @@ public class EffectCaseServiceImpl extends ServiceImpl<EffectCaseMapper, EffectC
             vid = hotMaterial.getVid();
         }
         url = getRealVideoUrl("https://aweme.snssdk.com/aweme/v1/playwm/?video_id=" + vid + "&line=0");
-        if (null == url || url.trim().equals("")) {
+        if (null == url || "".equals(url.trim())) {
             url = getVideoUrl(vid);
         }
         result.put("url", url);

+ 1 - 1
module-crawler/src/main/java/cn/com/ctop/crawler/modules/oceanengine/service/impl/HotMaterialServiceImpl.java

@@ -20,7 +20,7 @@ public class HotMaterialServiceImpl extends ServiceImpl<HotMaterialMapper, HotMa
         if (null != start && !"".equals(start) && null != end && !"".equals(end)) {
             queryWrapper.between("create_time", start, end);
         }
-        if (null != orderByType && orderByType.equals("desc")) {
+        if (null != orderByType && "desc".equals(orderByType)) {
             queryWrapper.orderByDesc(orderByColumn);
         } else {
             queryWrapper.orderByAsc(orderByColumn);

+ 2 - 1
module-crawler/src/main/java/cn/com/ctop/crawler/modules/pangolin/service/impl/PangolinLoginServiceImpl.java

@@ -33,7 +33,8 @@ public class PangolinLoginServiceImpl implements PangolinLoginService {
         String result = HttpUtils2.httpGetRequest("https://pangolin.bytedance.com/api/search/external_default");
         System.out.println(result);
     }
-    public void pangolinLogin(String username,String password) {
+    @Override
+    public void pangolinLogin(String username, String password) {
         System.getProperties().setProperty("webdriver.chrome.driver", chromeDriver);
         String url = "https://pangolin.bytedance.com/auth/login";
         ChromeOptions chromeOptions = new ChromeOptions();

+ 2 - 2
module-ctop/src/main/java/cn/com/ctop/manage/modules/edu/service/impl/EduLessonServiceImpl.java

@@ -106,7 +106,7 @@ public class EduLessonServiceImpl extends ServiceImpl<EduLessonMapper, EduLesson
         try {
             JsonNode rootNode = mapper.readTree(result);
             String status = rootNode.get("status").asText();
-            if (status == null || !status.equals("success")) {
+            if (status == null || !"success".equals(status)) {
                 return;
             }
             String title = rootNode.get("data").get("title").asText();
@@ -124,7 +124,7 @@ public class EduLessonServiceImpl extends ServiceImpl<EduLessonMapper, EduLesson
                     System.out.println(detailResult);
                     JsonNode detailNode = mapper.readTree(detailResult);
                     status = detailNode.get("status").asText();
-                    if (status == null || !status.equals("success")) {
+                    if (status == null || !"success".equals(status)) {
                         return;
                     }
                     JsonNode courseNode = detailNode.get("data").get("course_data");

+ 1 - 0
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/app/service/impl/KuaishouAppProductServiceImpl.java

@@ -18,6 +18,7 @@ import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 public class KuaishouAppProductServiceImpl extends ServiceImpl<KuaishouAppProductMapper, KuaishouAppProduct> implements IKuaishouAppProductService {
     @Autowired
     private KuaishouAppProductMapper kuaishouAppProductMapper;
+    @Override
     public void selectInto(){
         kuaishouAppProductMapper.selectInto();
     }

+ 1 - 1
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/app/service/impl/KuaishouAppServiceImpl.java

@@ -175,7 +175,7 @@ public class KuaishouAppServiceImpl implements IKuaishouAppService {
                         ad.setHeight(ad.getAdCover().getHeight());
                         ad.setType(appFeeds.getType());
                         String appName = ad.getAppName();
-                        if (null != appName && !appName.trim().equals("")) {
+                        if (null != appName && !"".equals(appName.trim())) {
                             ad.setAppName(ad.getAppName().replace(".apk", "").replace(".APK", "").replace("ios", "").replace("IOS", ""));
                         }
                         appAdService.saveOrUpdate(ad);

+ 3 - 1
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/batch/service/impl/KuaishouInterfaceServiceImpl.java

@@ -141,6 +141,7 @@ public class KuaishouInterfaceServiceImpl implements IKuaishouInterfaceService {
 
     private void getAdvertiserReportHourlyByPage(CtopOauthToken token, Date startDate, Date endDate, int page) {
         String url = PropertiesUtils.getConfig("kuaishou_api_url") + KuaishouInterfaceConstant.ACCOUNT_REPORT;
+        System.out.println(url);
         Map<String, String> headers = new HashMap<>();
         headers.put("Access-Token", token.getAccessToken());
         Map<String, Object> param = new HashMap<>();
@@ -150,8 +151,9 @@ public class KuaishouInterfaceServiceImpl implements IKuaishouInterfaceService {
         param.put("temporal_granularity", "HOURLY");
         param.put("page_size", 500);
         param.put("page", page);
-
+        System.out.println(param.toString());
         String result = HttpUtils.httpPostRequest(url, param, headers);
+        System.out.println(result);
         JSONObject resultJson = JSONObject.parseObject(result);
         Integer code = resultJson.getInteger("code");
         String message = resultJson.getString("message");

تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 0 - 401
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/KuaishouTest.java


+ 2 - 36
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/controller/KuaishouWebController.java

@@ -1,8 +1,8 @@
 package cn.com.ctop.kuaishou.modules.graphql.controller;
 
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentConfig;
 import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouUserCookie;
-import cn.com.ctop.kuaishou.modules.graphql.service.*;
+import cn.com.ctop.kuaishou.modules.graphql.service.IKuaishouUserCookieService;
+import cn.com.ctop.kuaishou.modules.graphql.service.IKuaishouWebInterfaceService;
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import org.apache.shiro.SecurityUtils;
 import org.jeecg.common.api.vo.Result;
@@ -24,12 +24,6 @@ public class KuaishouWebController {
     private IKuaishouWebInterfaceService kuaishouWebInterfaceService;
     @Autowired
     private IKuaishouUserCookieService kuaishouUserCookieService;
-    @Autowired
-    private IKuaishouCommentStatService kuaishouCommentStatService;
-    @Autowired
-    private IKuaishouCommentKeywordService kuaishouCommentKeywordService;
-    @Autowired
-    private IKuaishouCommentConfigService kuaishouCommentConfigService;
 
     @PostMapping(value = "/login/qr")
     public Result<Map<String, Object>> getQrCode() {
@@ -66,35 +60,7 @@ public class KuaishouWebController {
         return result;
     }
 
-    @PostMapping(value = "/comment/config/detail")
-    public Result<KuaishouCommentConfig> getCommentConfig(String ksid) {
-        Result<KuaishouCommentConfig> result = new Result<>();
-        KuaishouCommentConfig kuaishouCommentConfig = kuaishouCommentConfigService.getById(ksid);
-        result.setSuccess(true);
-        result.setResult(kuaishouCommentConfig);
-        return result;
-    }
 
-    @PostMapping(value = "/comment/config/save")
-    public Result<Object> saveCommentConfig(KuaishouCommentConfig kuaishouCommentConfig) {
-        Result<Object> result = new Result<>();
-        kuaishouCommentConfigService.saveOrUpdate(kuaishouCommentConfig);
-        result.setSuccess(true);
-        return result;
-    }
-
-    @PostMapping(value = "/test")
-    public Result<Object> test(KuaishouCommentConfig kuaishouCommentConfig) {
-        Result<Object> result = new Result<>();
-        try {
-            kuaishouWebInterfaceService.adekuaishouWebLogin("19845004383", "a123456");
-            kuaishouWebInterfaceService.sendPreview(106126205, "xuzuoyun");
-        } catch (Exception e) {
-            e.printStackTrace();
-        }
-        result.setSuccess(true);
-        return result;
-    }
 
     @PostMapping(value = "/login/status")
     public Result<Map<String, Object>> getStatus(String requestId) {

+ 0 - 16
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/entity/KuaishouCommentConfig.java

@@ -1,16 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.entity;
-
-import com.baomidou.mybatisplus.annotation.IdType;
-import com.baomidou.mybatisplus.annotation.TableId;
-import com.baomidou.mybatisplus.annotation.TableName;
-import lombok.Data;
-
-@Data
-@TableName("ctop_kuaishou_comment_config")
-public class KuaishouCommentConfig {
-    @TableId(value = "ksid", type = IdType.INPUT)
-    private String ksid;
-    private Integer autoDelete;
-    private String strategy;
-    private String cycle;
-}

+ 0 - 18
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/entity/KuaishouCommentKeyword.java

@@ -1,18 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.entity;
-
-import com.baomidou.mybatisplus.annotation.IdType;
-import com.baomidou.mybatisplus.annotation.TableId;
-import com.baomidou.mybatisplus.annotation.TableName;
-import lombok.Data;
-
-@Data
-@TableName("ctop_kuaishou_comment_keyword")
-public class KuaishouCommentKeyword {
-    @TableId(value = "id", type = IdType.INPUT)
-    private Long id;
-    private String ksid;
-    private String keyword;
-    private Integer deleteCount;
-    private Integer status;
-
-}

+ 0 - 15
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/entity/KuaishouCommentStat.java

@@ -1,15 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.entity;
-
-import com.baomidou.mybatisplus.annotation.IdType;
-import com.baomidou.mybatisplus.annotation.TableId;
-import com.baomidou.mybatisplus.annotation.TableName;
-import lombok.Data;
-
-@Data
-@TableName("ctop_kuaishou_comment_stat")
-public class KuaishouCommentStat {
-    @TableId(value = "comment_id", type = IdType.INPUT)
-    private Long commentId;
-    private String ksid;
-    private Integer deleteCount;
-}

+ 0 - 97
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/job/KuaishouCommentDayJob.java

@@ -1,97 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.job;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentConfig;
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentStat;
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouUserCookie;
-import cn.com.ctop.kuaishou.modules.graphql.service.*;
-import com.alibaba.fastjson.JSONArray;
-import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
-import com.fasterxml.jackson.databind.JsonNode;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import org.quartz.Job;
-import org.quartz.JobExecutionContext;
-import org.quartz.JobExecutionException;
-import org.springframework.beans.factory.annotation.Autowired;
-
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-
-public class KuaishouCommentDayJob implements Job {
-    @Autowired
-    private IKuaishouCommentConfigService kuaishouCommentConfigService;
-    @Autowired
-    private IKuaishouCommentKeywordService kuaishouCommentKeywordService;
-    @Autowired
-    private IKuaishouCommentStatService kuaishouCommentStatService;
-    @Autowired
-    private IKuaishouUserCookieService kuaishouUserCookieService;
-    @Autowired
-    private IKuaishouWebInterfaceService kuaishouWebInterfaceService;
-
-    @Override
-    public void execute(JobExecutionContext jobExecutionContext) throws JobExecutionException {
-        QueryWrapper<KuaishouCommentConfig> queryWrapper = new QueryWrapper<>();
-        queryWrapper.eq("auto_delete", 1);
-        queryWrapper.eq("cycle", "DAY");
-        List<KuaishouCommentConfig> kuaishouCommentConfigList = kuaishouCommentConfigService.list(queryWrapper);
-        if (kuaishouCommentConfigList != null && kuaishouCommentConfigList.size() > 0) {
-            for (KuaishouCommentConfig config : kuaishouCommentConfigList) {
-                QueryWrapper<KuaishouUserCookie> queryWrapper1 = new QueryWrapper<>();
-                queryWrapper1.eq("ksid", config.getKsid());
-                KuaishouUserCookie kuaishouUserCookie = kuaishouUserCookieService.getOne(queryWrapper1);
-
-                try {
-                    String pcursor = "";
-                    do {
-                        Map<String, Object> videoMap = kuaishouWebInterfaceService.videoList(kuaishouUserCookie.getUserId(), config.getKsid(), pcursor);
-                        JsonNode videoNode = mapToJson(videoMap);
-                        pcursor = videoNode.get("data").get("publicFeeds").get("pcursor").asText();
-                        Iterator<JsonNode> list = videoNode.get("data").get("publicFeeds").get("list").iterator();
-                        while (list.hasNext()) {
-                            JsonNode node = list.next();
-                            Integer commentCount = node.get("commentCount").asInt();
-                            if (commentCount > 0) {
-                                String photoId = node.get("photoId").asText();
-                                String commentPcursor = "";
-                                do {
-                                    Map<String, Object> commentMap = kuaishouWebInterfaceService.commentList(kuaishouUserCookie.getUserId(), config.getKsid(), photoId, commentPcursor);
-                                    JsonNode commentNode = mapToJson(commentMap);
-                                    commentPcursor = commentNode.get("data").get("shortVideoCommentList").get("pcursor").asText();
-                                    Iterator<JsonNode> commentList = commentNode.get("data").get("shortVideoCommentList").get("commentList").iterator();
-                                    while (commentList.hasNext()) {
-                                        JsonNode commentListNode = commentList.next();
-                                        Long commentId = commentListNode.get("commentId").asLong();
-                                        Map<String, Object> deleteMap = kuaishouWebInterfaceService.commentDelete(kuaishouUserCookie.getUserId(), config.getKsid(), photoId, commentId);
-                                        if ((int) deleteMap.get("result") == 1) {
-                                            KuaishouCommentStat kuaishouCommentStat = kuaishouCommentStatService.getById(commentId);
-                                            if (kuaishouCommentStat == null) {
-                                                kuaishouCommentStat = new KuaishouCommentStat();
-                                                kuaishouCommentStat.setCommentId(commentId);
-                                                kuaishouCommentStat.setDeleteCount(1);
-                                                kuaishouCommentStat.setKsid(config.getKsid());
-                                                kuaishouCommentStatService.save(kuaishouCommentStat);
-                                            } else {
-                                                kuaishouCommentStat.setDeleteCount(kuaishouCommentStat.getDeleteCount() + 1);
-                                                kuaishouCommentStatService.updateById(kuaishouCommentStat);
-                                            }
-                                        }
-                                    }
-                                } while (commentPcursor != null && !"no_more".equals(commentPcursor));
-                            }
-                        }
-                    } while (pcursor != null && !"no_more".equals(pcursor));
-
-                } catch (Exception e) {
-                    e.printStackTrace();
-                }
-            }
-        }
-    }
-
-    public JsonNode mapToJson(Map<String, Object> map) throws Exception {
-        ObjectMapper mapper = new ObjectMapper();
-        String json = mapper.writeValueAsString(map);
-        return mapper.readTree(json);
-    }
-}

+ 0 - 96
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/job/KuaishouCommentHourJob.java

@@ -1,96 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.job;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentConfig;
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentStat;
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouUserCookie;
-import cn.com.ctop.kuaishou.modules.graphql.service.*;
-import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
-import com.fasterxml.jackson.databind.JsonNode;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import org.quartz.Job;
-import org.quartz.JobExecutionContext;
-import org.quartz.JobExecutionException;
-import org.springframework.beans.factory.annotation.Autowired;
-
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-
-public class KuaishouCommentHourJob implements Job {
-    @Autowired
-    private IKuaishouCommentConfigService kuaishouCommentConfigService;
-    @Autowired
-    private IKuaishouCommentKeywordService kuaishouCommentKeywordService;
-    @Autowired
-    private IKuaishouCommentStatService kuaishouCommentStatService;
-    @Autowired
-    private IKuaishouUserCookieService kuaishouUserCookieService;
-    @Autowired
-    private IKuaishouWebInterfaceService kuaishouWebInterfaceService;
-
-    @Override
-    public void execute(JobExecutionContext jobExecutionContext) throws JobExecutionException {
-        QueryWrapper<KuaishouCommentConfig> queryWrapper = new QueryWrapper<>();
-        queryWrapper.eq("auto_delete", 1);
-        queryWrapper.eq("cycle", "HOUR");
-        List<KuaishouCommentConfig> kuaishouCommentConfigList = kuaishouCommentConfigService.list(queryWrapper);
-        if (kuaishouCommentConfigList != null && kuaishouCommentConfigList.size() > 0) {
-            for (KuaishouCommentConfig config : kuaishouCommentConfigList) {
-                QueryWrapper<KuaishouUserCookie> queryWrapper1 = new QueryWrapper<>();
-                queryWrapper1.eq("ksid", config.getKsid());
-                KuaishouUserCookie kuaishouUserCookie = kuaishouUserCookieService.getOne(queryWrapper1);
-
-                try {
-                    String pcursor = "";
-                    do {
-                        Map<String, Object> videoMap = kuaishouWebInterfaceService.videoList(kuaishouUserCookie.getUserId(), config.getKsid(), pcursor);
-                        JsonNode videoNode = mapToJson(videoMap);
-                        pcursor = videoNode.get("data").get("publicFeeds").get("pcursor").asText();
-                        Iterator<JsonNode> list = videoNode.get("data").get("publicFeeds").get("list").iterator();
-                        while (list.hasNext()) {
-                            JsonNode node = list.next();
-                            Integer commentCount = node.get("commentCount").asInt();
-                            if (commentCount > 0) {
-                                String photoId = node.get("photoId").asText();
-                                String commentPcursor = "";
-                                do {
-                                    Map<String, Object> commentMap = kuaishouWebInterfaceService.commentList(kuaishouUserCookie.getUserId(), config.getKsid(), photoId, commentPcursor);
-                                    JsonNode commentNode = mapToJson(commentMap);
-                                    commentPcursor = commentNode.get("data").get("shortVideoCommentList").get("pcursor").asText();
-                                    Iterator<JsonNode> commentList = commentNode.get("data").get("shortVideoCommentList").get("commentList").iterator();
-                                    while (commentList.hasNext()) {
-                                        JsonNode commentListNode = commentList.next();
-                                        Long commentId = commentListNode.get("commentId").asLong();
-                                        Map<String, Object> deleteMap = kuaishouWebInterfaceService.commentDelete(kuaishouUserCookie.getUserId(), config.getKsid(), photoId, commentId);
-                                        if ((int) deleteMap.get("result") == 1) {
-                                            KuaishouCommentStat kuaishouCommentStat = kuaishouCommentStatService.getById(commentId);
-                                            if (kuaishouCommentStat == null) {
-                                                kuaishouCommentStat = new KuaishouCommentStat();
-                                                kuaishouCommentStat.setCommentId(commentId);
-                                                kuaishouCommentStat.setDeleteCount(1);
-                                                kuaishouCommentStat.setKsid(config.getKsid());
-                                                kuaishouCommentStatService.save(kuaishouCommentStat);
-                                            } else {
-                                                kuaishouCommentStat.setDeleteCount(kuaishouCommentStat.getDeleteCount() + 1);
-                                                kuaishouCommentStatService.updateById(kuaishouCommentStat);
-                                            }
-                                        }
-                                    }
-                                } while (commentPcursor != null && !"no_more".equals(commentPcursor));
-                            }
-                        }
-                    } while (pcursor != null && !"no_more".equals(pcursor));
-
-                } catch (Exception e) {
-                    e.printStackTrace();
-                }
-            }
-        }
-    }
-
-    public JsonNode mapToJson(Map<String, Object> map) throws Exception {
-        ObjectMapper mapper = new ObjectMapper();
-        String json = mapper.writeValueAsString(map);
-        return mapper.readTree(json);
-    }
-}

+ 0 - 7
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/mapper/KuaishouCommentConfigMapper.java

@@ -1,7 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.mapper;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentConfig;
-import com.baomidou.mybatisplus.core.mapper.BaseMapper;
-
-public interface KuaishouCommentConfigMapper extends BaseMapper<KuaishouCommentConfig> {
-}

+ 0 - 7
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/mapper/KuaishouCommentKeywordMapper.java

@@ -1,7 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.mapper;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentKeyword;
-import com.baomidou.mybatisplus.core.mapper.BaseMapper;
-
-public interface KuaishouCommentKeywordMapper extends BaseMapper<KuaishouCommentKeyword> {
-}

+ 0 - 7
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/mapper/KuaishouCommentStatMapper.java

@@ -1,7 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.mapper;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentStat;
-import com.baomidou.mybatisplus.core.mapper.BaseMapper;
-
-public interface KuaishouCommentStatMapper extends BaseMapper<KuaishouCommentStat> {
-}

+ 0 - 7
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/IKuaishouCommentConfigService.java

@@ -1,7 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.service;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentConfig;
-import com.baomidou.mybatisplus.extension.service.IService;
-
-public interface IKuaishouCommentConfigService extends IService<KuaishouCommentConfig> {
-}

+ 0 - 7
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/IKuaishouCommentKeywordService.java

@@ -1,7 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.service;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentKeyword;
-import com.baomidou.mybatisplus.extension.service.IService;
-
-public interface IKuaishouCommentKeywordService extends IService<KuaishouCommentKeyword> {
-}

+ 0 - 7
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/IKuaishouCommentStatService.java

@@ -1,7 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.service;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentStat;
-import com.baomidou.mybatisplus.extension.service.IService;
-
-public interface IKuaishouCommentStatService extends IService<KuaishouCommentStat> {
-}

+ 0 - 11
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/impl/KuaishouCommentConfigServiceImpl.java

@@ -1,11 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.service.impl;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentConfig;
-import cn.com.ctop.kuaishou.modules.graphql.mapper.KuaishouCommentConfigMapper;
-import cn.com.ctop.kuaishou.modules.graphql.service.IKuaishouCommentConfigService;
-import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
-import org.springframework.stereotype.Service;
-
-@Service
-public class KuaishouCommentConfigServiceImpl extends ServiceImpl<KuaishouCommentConfigMapper, KuaishouCommentConfig> implements IKuaishouCommentConfigService {
-}

+ 0 - 11
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/impl/KuaishouCommentKeywordServiceImpl.java

@@ -1,11 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.service.impl;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentKeyword;
-import cn.com.ctop.kuaishou.modules.graphql.mapper.KuaishouCommentKeywordMapper;
-import cn.com.ctop.kuaishou.modules.graphql.service.IKuaishouCommentKeywordService;
-import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
-import org.springframework.stereotype.Service;
-
-@Service
-public class KuaishouCommentKeywordServiceImpl extends ServiceImpl<KuaishouCommentKeywordMapper, KuaishouCommentKeyword> implements IKuaishouCommentKeywordService {
-}

+ 0 - 11
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/graphql/service/impl/KuaishouCommentStatServiceImpl.java

@@ -1,11 +0,0 @@
-package cn.com.ctop.kuaishou.modules.graphql.service.impl;
-
-import cn.com.ctop.kuaishou.modules.graphql.entity.KuaishouCommentStat;
-import cn.com.ctop.kuaishou.modules.graphql.mapper.KuaishouCommentStatMapper;
-import cn.com.ctop.kuaishou.modules.graphql.service.IKuaishouCommentStatService;
-import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
-import org.springframework.stereotype.Service;
-
-@Service
-public class KuaishouCommentStatServiceImpl extends ServiceImpl<KuaishouCommentStatMapper, KuaishouCommentStat> implements IKuaishouCommentStatService {
-}

+ 2 - 0
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/report/service/impl/KuaishouReportDailyAgentServiceImpl.java

@@ -117,6 +117,7 @@ public class KuaishouReportDailyAgentServiceImpl extends ServiceImpl<KuaishouRep
         return loginStatus;
     }
 
+    @Override
     public boolean getAccount(int currentPage) {
         boolean hasNextPage = false;
         try {
@@ -172,6 +173,7 @@ public class KuaishouReportDailyAgentServiceImpl extends ServiceImpl<KuaishouRep
         return hasNextPage;
     }
 
+    @Override
     public void getReport(String startDate, String endDate) {
         try {
             if (!loginAgent()) {

+ 2 - 0
module-kuaishou/src/main/java/cn/com/ctop/kuaishou/modules/report/service/impl/KuaishouReportDailyAgentSumServiceImpl.java

@@ -24,11 +24,13 @@ public class KuaishouReportDailyAgentSumServiceImpl extends ServiceImpl<Kuaishou
     private KuaishouReportDailyAgentSumMapper kuaishouReportDailyAgentSumMapper;
 
     //公司报表
+    @Override
     public List<KuaishouReportDailyAgentSum> companyReport(String startDate, String endDate){
         return kuaishouReportDailyAgentSumMapper.companyReport(startDate,endDate);
     }
 
     //公司报表汇总
+    @Override
     public KuaishouReportDailyAgentSum companyReportSum(String startDate, String endDate){
         return kuaishouReportDailyAgentSumMapper.companyReportSum(startDate, endDate);
     }

+ 0 - 8
module-report/src/main/java/cn/com/ctop/bytedance/entity/BytedanceAdvertiserDailyReport.java

@@ -567,10 +567,6 @@ public class BytedanceAdvertiserDailyReport {
         if (null != follow) {
             this.follow = follow;
         }
-//		Long message = data.getLong("message");
-//		if(null!=message){
-//			this.message = message;
-//		}
         Long inAppDetailUv = data.getLong("in_app_detail_uv");
         if (null != inAppDetailUv) {
             this.inAppDetailUv = inAppDetailUv;
@@ -579,10 +575,6 @@ public class BytedanceAdvertiserDailyReport {
         if (null != form) {
             this.form = form;
         }
-//		BigDecimal convert_cost = data.getBigDecimal("convert_cost");
-//		if(null!=convert_cost){
-//			this.convertCost = convert_cost;
-//		}
         Long comment = data.getLong("comment");
         if (null != comment) {
             this.comment = comment;

+ 6 - 1
module-report/src/main/java/cn/com/ctop/bytedance/service/impl/BytedanceReportServiceImpl.java

@@ -677,6 +677,7 @@ public class BytedanceReportServiceImpl implements IBytedanceReportService {
 
     /////////////////////////////////////////////////////////////////////////////////////////////////
     //创建异步任务
+    @Override
     public void bytedanceAsyncTaskCreate (String startDate, String endDate, CtopOauthToken token, Integer type) throws ParseException {
         int diffMonths = DateUtils.calDiffMonth(DateUtils.parseDate(startDate,"yyyy-MM-dd"),DateUtils.parseDate(endDate,"yyyy-MM-dd"));
         if (diffMonths == 0) {
@@ -819,6 +820,7 @@ public class BytedanceReportServiceImpl implements IBytedanceReportService {
     }
 
     //获取任务列表
+    @Override
     public void bytedanceAsyncTaskGet(){
         QueryWrapper<BytedanceDailyReportTask> taskQueryWrapper = new QueryWrapper<>();
         //查询三种状态的信息--任务已创建、任务执行中、任务处理中
@@ -906,7 +908,7 @@ public class BytedanceReportServiceImpl implements IBytedanceReportService {
                                     if (!Check.isNull(detailJson)) {
                                         String taskStatus = detailJson.getString("task_status");
 
-                                        if (taskStatus .equals( "ASYNC_TASK_STATUS_COMPLETED")) {
+                                        if ("ASYNC_TASK_STATUS_COMPLETED".equals(taskStatus)) {
                                             bytedanceAsyncTaskDownload(task,token,task.getType());
                                             task.setIsDownload(1);
                                         }
@@ -971,6 +973,7 @@ public class BytedanceReportServiceImpl implements IBytedanceReportService {
 
     /////////////////////////////////////////////////////////\
     //素材报表
+    @Override
     public void bytedanceMaterialReportRetry(CtopOauthToken token, String startDate, String endDate){
         Long accountId = token.getAccountId();
         log.info("头条素材报表当前accountId为:" + accountId);
@@ -992,6 +995,7 @@ public class BytedanceReportServiceImpl implements IBytedanceReportService {
         }
     }
 
+    @Override
     public void bytedanceMaterialReport(CtopOauthToken token, String startDate, String endDate){
         Long accountId = token.getAccountId();
         log.info("头条素材报表当前accountId为:" + accountId);
@@ -1251,6 +1255,7 @@ public class BytedanceReportServiceImpl implements IBytedanceReportService {
         return returnCode;
     }
 
+    @Override
     public List<BytedanceReportMaterialRetry> getRetryList(){
         return bytedanceReportMaterialDailyMapper.getRetryList();
     }

+ 1 - 1
module-toutiao/src/main/java/cn/com/ctop/toutiao/entity/ByteDanceAdvertisePlan.java

@@ -254,7 +254,7 @@ public class ByteDanceAdvertisePlan {
                 String plat = "";
                 for (int i = 0; i < platform.size(); i++) {
                     String platformStr = platform.getString(i);
-                    if (platformStr.equals("IOS")) {
+                    if ("IOS".equals(platformStr)) {
                         plat += "ios,";
                     } else {
                         plat += "安卓,";

+ 2 - 2
module-toutiao/src/main/java/cn/com/ctop/toutiao/service/impl/ByteDanceAdvertiserDataServiceImpl.java

@@ -81,7 +81,7 @@ public class ByteDanceAdvertiserDataServiceImpl implements IByteDanceAdvertiserD
 
     public void getAd(CtopOauthToken token, int pageNum, String ids, String date, String updateDate) {
         JSONArray getIds = null;
-        if (null != ids && !ids.equals("")) {
+        if (null != ids && !"".equals(ids)) {
             String[] idString = ids.split(StringUtils.COMMA);
             if (null != idString && idString.length > 0) {
                 for (int i = 0; i < idString.length; i++) {
@@ -274,7 +274,7 @@ public class ByteDanceAdvertiserDataServiceImpl implements IByteDanceAdvertiserD
         param.put("advertiser_id", advertiser_id);
         param.put("page", pageNumber);
         param.put("page_size", 100);
-        if (null != date && !date.trim().equals("")) {
+        if (null != date && !"".equals(date.trim())) {
             JSONObject filtering = new JSONObject();
             filtering.put("creative_modify_time", date);
             param.put("filtering", filtering);

+ 0 - 117
moudule-eureca/.mvn/wrapper/MavenWrapperDownloader.java

@@ -1,117 +0,0 @@
-/*
- * Copyright 2007-present the original author or authors.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      https://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-import java.net.*;
-import java.io.*;
-import java.nio.channels.*;
-import java.util.Properties;
-
-public class MavenWrapperDownloader {
-
-    private static final String WRAPPER_VERSION = "0.5.6";
-    /**
-     * Default URL to download the maven-wrapper.jar from, if no 'downloadUrl' is provided.
-     */
-    private static final String DEFAULT_DOWNLOAD_URL = "https://repo.maven.apache.org/maven2/io/takari/maven-wrapper/"
-            + WRAPPER_VERSION + "/maven-wrapper-" + WRAPPER_VERSION + ".jar";
-
-    /**
-     * Path to the maven-wrapper.properties file, which might contain a downloadUrl property to
-     * use instead of the default one.
-     */
-    private static final String MAVEN_WRAPPER_PROPERTIES_PATH =
-            ".mvn/wrapper/maven-wrapper.properties";
-
-    /**
-     * Path where the maven-wrapper.jar will be saved to.
-     */
-    private static final String MAVEN_WRAPPER_JAR_PATH =
-            ".mvn/wrapper/maven-wrapper.jar";
-
-    /**
-     * Name of the property which should be used to override the default download url for the wrapper.
-     */
-    private static final String PROPERTY_NAME_WRAPPER_URL = "wrapperUrl";
-
-    public static void main(String args[]) {
-        File baseDirectory = new File(args[0]);
-        System.out.println("- Using base directory: " + baseDirectory.getAbsolutePath());
-
-        // If the maven-wrapper.properties exists, read it and check if it contains a custom
-        // wrapperUrl parameter.
-        File mavenWrapperPropertyFile = new File(baseDirectory, MAVEN_WRAPPER_PROPERTIES_PATH);
-        String url = DEFAULT_DOWNLOAD_URL;
-        if (mavenWrapperPropertyFile.exists()) {
-            FileInputStream mavenWrapperPropertyFileInputStream = null;
-            try {
-                mavenWrapperPropertyFileInputStream = new FileInputStream(mavenWrapperPropertyFile);
-                Properties mavenWrapperProperties = new Properties();
-                mavenWrapperProperties.load(mavenWrapperPropertyFileInputStream);
-                url = mavenWrapperProperties.getProperty(PROPERTY_NAME_WRAPPER_URL, url);
-            } catch (IOException e) {
-                System.out.println("- ERROR loading '" + MAVEN_WRAPPER_PROPERTIES_PATH + "'");
-            } finally {
-                try {
-                    if (mavenWrapperPropertyFileInputStream != null) {
-                        mavenWrapperPropertyFileInputStream.close();
-                    }
-                } catch (IOException e) {
-                    // Ignore ...
-                }
-            }
-        }
-        System.out.println("- Downloading from: " + url);
-
-        File outputFile = new File(baseDirectory.getAbsolutePath(), MAVEN_WRAPPER_JAR_PATH);
-        if (!outputFile.getParentFile().exists()) {
-            if (!outputFile.getParentFile().mkdirs()) {
-                System.out.println(
-                        "- ERROR creating output directory '" + outputFile.getParentFile().getAbsolutePath() + "'");
-            }
-        }
-        System.out.println("- Downloading to: " + outputFile.getAbsolutePath());
-        try {
-            downloadFileFromURL(url, outputFile);
-            System.out.println("Done");
-            System.exit(0);
-        } catch (Throwable e) {
-            System.out.println("- Error downloading");
-            e.printStackTrace();
-            System.exit(1);
-        }
-    }
-
-    private static void downloadFileFromURL(String urlString, File destination) throws Exception {
-        if (System.getenv("MVNW_USERNAME") != null && System.getenv("MVNW_PASSWORD") != null) {
-            String username = System.getenv("MVNW_USERNAME");
-            char[] password = System.getenv("MVNW_PASSWORD").toCharArray();
-            Authenticator.setDefault(new Authenticator() {
-                @Override
-                protected PasswordAuthentication getPasswordAuthentication() {
-                    return new PasswordAuthentication(username, password);
-                }
-            });
-        }
-        URL website = new URL(urlString);
-        ReadableByteChannel rbc;
-        rbc = Channels.newChannel(website.openStream());
-        FileOutputStream fos = new FileOutputStream(destination);
-        fos.getChannel().transferFrom(rbc, 0, Long.MAX_VALUE);
-        fos.close();
-        rbc.close();
-    }
-
-}

BIN
moudule-eureca/.mvn/wrapper/maven-wrapper.jar


+ 0 - 2
moudule-eureca/.mvn/wrapper/maven-wrapper.properties

@@ -1,2 +0,0 @@
-distributionUrl=https://repo.maven.apache.org/maven2/org/apache/maven/apache-maven/3.6.3/apache-maven-3.6.3-bin.zip
-wrapperUrl=https://repo.maven.apache.org/maven2/io/takari/maven-wrapper/0.5.6/maven-wrapper-0.5.6.jar

+ 0 - 62
moudule-eureca/pom.xml

@@ -1,62 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
-         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
-    <modelVersion>4.0.0</modelVersion>
-    <parent>
-        <groupId>org.springframework.boot</groupId>
-        <artifactId>spring-boot-starter-parent</artifactId>
-        <version>2.2.2.RELEASE</version>
-        <relativePath/>
-    </parent>
-    <groupId>cn.com.ctop.eureca</groupId>
-    <artifactId>server</artifactId>
-    <version>0.0.1-SNAPSHOT</version>
-    <name>server</name>
-    <description>Demo project for Spring Boot</description>
-
-    <properties>
-        <java.version>1.8</java.version>
-        <spring-cloud.version>Hoxton.SR1</spring-cloud.version>
-    </properties>
-
-    <dependencies>
-        <dependency>
-            <groupId>org.springframework.cloud</groupId>
-            <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
-        </dependency>
-
-        <dependency>
-            <groupId>org.springframework.boot</groupId>
-            <artifactId>spring-boot-starter-test</artifactId>
-            <scope>test</scope>
-            <exclusions>
-                <exclusion>
-                    <groupId>org.junit.vintage</groupId>
-                    <artifactId>junit-vintage-engine</artifactId>
-                </exclusion>
-            </exclusions>
-        </dependency>
-    </dependencies>
-
-    <dependencyManagement>
-        <dependencies>
-            <dependency>
-                <groupId>org.springframework.cloud</groupId>
-                <artifactId>spring-cloud-dependencies</artifactId>
-                <version>${spring-cloud.version}</version>
-                <type>pom</type>
-                <scope>import</scope>
-            </dependency>
-        </dependencies>
-    </dependencyManagement>
-
-    <build>
-        <plugins>
-            <plugin>
-                <groupId>org.springframework.boot</groupId>
-                <artifactId>spring-boot-maven-plugin</artifactId>
-            </plugin>
-        </plugins>
-    </build>
-
-</project>

+ 0 - 16
moudule-eureca/src/main/java/cn/com/ctop/eureca/server/ServerApplication.java

@@ -1,16 +0,0 @@
-/*
-package cn.com.ctop.eureca.server;
-
-import org.springframework.boot.SpringApplication;
-import org.springframework.boot.autoconfigure.SpringBootApplication;
-import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
-
-@SpringBootApplication
-@EnableEurekaServer
-public class ServerApplication {
-
-    public static void main(String[] args) {
-        SpringApplication.run(ServerApplication.class, args);
-    }
-}
-*/

+ 0 - 14
moudule-eureca/src/main/resources/application.yml

@@ -1,14 +0,0 @@
-server:
-  port: 8761
-
-eureka:
-  instance:
-    hostname: localhost
-  client:
-    registerWithEureka: false
-    fetchRegistry: false
-    serviceUrl:
-      defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/
-spring:
-  application:
-    name: eurka-server

+ 0 - 13
moudule-eureca/src/test/java/cn/com/ctop/eureca/server/ServerApplicationTests.java

@@ -1,13 +0,0 @@
-package cn.com.ctop.eureca.server;
-
-import org.junit.jupiter.api.Test;
-import org.springframework.boot.test.context.SpringBootTest;
-
-@SpringBootTest
-class ServerApplicationTests {
-
-    @Test
-    void contextLoads() {
-    }
-
-}

+ 5 - 2
performance-appraisal/src/main/java/cn/com/ctop/performanceappraisal/service/impl/PerformanceOptimizerServiceImpl.java

@@ -67,6 +67,7 @@ public class PerformanceOptimizerServiceImpl extends ServiceImpl<PerformanceOpti
 
 
     //快手运营季度绩效计算
+    @Override
     public Map<String, Object> kuaishouYunyingQuarterPerformance(Integer year, Integer quarter, String startDate, String endDate){
         Map<String, Object> result = new HashMap<>();
         //获取快手所有运营的数据
@@ -253,7 +254,7 @@ public class PerformanceOptimizerServiceImpl extends ServiceImpl<PerformanceOpti
                 BigDecimal personalTask = config.getPersonalTask();
                 //判断个人任务是否完成 ,如果完成则给到千分之5,如果未完成,则给到千分之3的绩效
                 String roleCode = userEfficientVideoMapMapper.getRoleCodeByUserId(userAccountKey);
-                if(!roleCode.equals("operationAssistant")){
+                if(!"operationAssistant".equals(roleCode)){
                     if (totalCharge.compareTo(personalTask) > 0 ) {
                         totalPerformance = totalCharge.multiply(config.getMediaTaskFinishRate()).divide(new BigDecimal("1000")).setScale(2, RoundingMode.HALF_UP);
                     } else {
@@ -267,6 +268,7 @@ public class PerformanceOptimizerServiceImpl extends ServiceImpl<PerformanceOpti
     }
 
     //头条运营季度绩效计算
+    @Override
     public void toutiaoYunyingQuarterPerformance(Integer year, Integer quarter, String startDate, String endDate){
         //方法
         //1。获取所有头条账户
@@ -443,7 +445,7 @@ public class PerformanceOptimizerServiceImpl extends ServiceImpl<PerformanceOpti
             BigDecimal personalTask = config.getPersonalTask();
             //判断个人任务是否完成 ,如果完成则给到千分之5,如果未完成,则给到千分之3的绩效
             String roleCode = userEfficientVideoMapMapper.getRoleCodeByUserId(userAccountKey);
-            if(!roleCode.equals("operationAssistant")){
+            if(!"operationAssistant".equals(roleCode)){
                 if (totalCharge.compareTo(personalTask) > 0 ) {
                     totalPerformance = totalCharge.multiply(config.getMediaTaskFinishRate()).divide(new BigDecimal("1000")).setScale(2, RoundingMode.HALF_UP);
                 } else {
@@ -458,6 +460,7 @@ public class PerformanceOptimizerServiceImpl extends ServiceImpl<PerformanceOpti
     }
 
     //快手运营leader绩效计算
+    @Override
     public void kuaishouYunyingLeaderQuarterPerformance(Integer year, Integer quarter){
         Integer mediaType = 2;
         //获取快手组下所有运营组长信息列表

+ 3 - 2
pom.xml

@@ -9,7 +9,7 @@
     <parent>
         <groupId>org.springframework.boot</groupId>
         <artifactId>spring-boot-starter-parent</artifactId>
-        <version>2.1.3.RELEASE</version>
+        <version>2.2.3.RELEASE</version>
         <relativePath/>
     </parent>
 
@@ -25,7 +25,8 @@
         <module>module-ctop</module>
         <module>performance-appraisal</module>
         <module>jeecg-boot-module-system</module>
-<!--        <module>moudule-eureca</module>-->
+        <module>xxl-job-core</module>
+        <!--        <module>moudule-eureca</module>-->
 
     </modules>
 

+ 55 - 0
xxl-job-core/pom.xml

@@ -0,0 +1,55 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+    <parent>
+        <artifactId>jeecg-boot-parent</artifactId>
+        <groupId>org.jeecgframework.boot</groupId>
+        <version>2.0.2</version>
+    </parent>
+    <modelVersion>4.0.0</modelVersion>
+    <artifactId>xxl-job-core</artifactId>
+
+    <name>${project.artifactId}</name>
+    <description>A distributed task scheduling framework.</description>
+    <url>https://www.xuxueli.com/</url>
+    <properties>
+        <xxl-rpc.version>1.5.0</xxl-rpc.version>
+
+        <spring.version>5.2.3.RELEASE</spring.version>
+        <groovy.version>2.5.9</groovy.version>
+    </properties>
+    <dependencies>
+
+        <!-- xxl-rpc-core -->
+        <dependency>
+            <groupId>com.xuxueli</groupId>
+            <artifactId>xxl-rpc-core</artifactId>
+            <version>${xxl-rpc.version}</version>
+        </dependency>
+
+        <!-- groovy-all -->
+        <dependency>
+            <groupId>org.codehaus.groovy</groupId>
+            <artifactId>groovy</artifactId>
+            <version>3.0.2</version>
+        </dependency>
+
+        <!-- spring-context -->
+        <dependency>
+            <groupId>org.springframework</groupId>
+            <artifactId>spring-context</artifactId>
+            <version>${spring.version}</version>
+            <scope>provided</scope>
+        </dependency>
+
+        <!-- junit -->
+        <dependency>
+            <groupId>junit</groupId>
+            <artifactId>junit</artifactId>
+            <version>4.11</version>
+            <scope>test</scope>
+        </dependency>
+
+    </dependencies>
+</project>

+ 44 - 0
xxl-job-core/src/main/java/com/xxl/job/core/biz/AdminBiz.java

@@ -0,0 +1,44 @@
+package com.xxl.job.core.biz;
+
+import com.xxl.job.core.biz.model.HandleCallbackParam;
+import com.xxl.job.core.biz.model.RegistryParam;
+import com.xxl.job.core.biz.model.ReturnT;
+
+import java.util.List;
+
+/**
+ * @author xuxueli 2017-07-27 21:52:49
+ */
+public interface AdminBiz {
+
+
+    // ---------------------- callback ----------------------
+
+    /**
+     * callback
+     *
+     * @param callbackParamList
+     * @return
+     */
+    public ReturnT<String> callback(List<HandleCallbackParam> callbackParamList);
+
+
+    // ---------------------- registry ----------------------
+
+    /**
+     * registry
+     *
+     * @param registryParam
+     * @return
+     */
+    public ReturnT<String> registry(RegistryParam registryParam);
+
+    /**
+     * registry remove
+     *
+     * @param registryParam
+     * @return
+     */
+    public ReturnT<String> registryRemove(RegistryParam registryParam);
+
+}

+ 49 - 0
xxl-job-core/src/main/java/com/xxl/job/core/biz/ExecutorBiz.java

@@ -0,0 +1,49 @@
+package com.xxl.job.core.biz;
+
+import com.xxl.job.core.biz.model.LogResult;
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.job.core.biz.model.TriggerParam;
+
+/**
+ * Created by xuxueli on 17/3/1.
+ */
+public interface ExecutorBiz {
+
+    /**
+     * beat
+     * @return
+     */
+    public ReturnT<String> beat();
+
+    /**
+     * idle beat
+     *
+     * @param jobId
+     * @return
+     */
+    public ReturnT<String> idleBeat(int jobId);
+
+    /**
+     * kill
+     * @param jobId
+     * @return
+     */
+    public ReturnT<String> kill(int jobId);
+
+    /**
+     * log
+     * @param logDateTim
+     * @param logId
+     * @param fromLineNum
+     * @return
+     */
+    public ReturnT<LogResult> log(long logDateTim, long logId, int fromLineNum);
+
+    /**
+     * run
+     * @param triggerParam
+     * @return
+     */
+    public ReturnT<String> run(TriggerParam triggerParam);
+
+}

+ 48 - 0
xxl-job-core/src/main/java/com/xxl/job/core/biz/client/AdminBizClient.java

@@ -0,0 +1,48 @@
+package com.xxl.job.core.biz.client;
+
+import com.xxl.job.core.biz.AdminBiz;
+import com.xxl.job.core.biz.model.HandleCallbackParam;
+import com.xxl.job.core.biz.model.RegistryParam;
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.job.core.util.XxlJobRemotingUtil;
+
+import java.util.List;
+
+/**
+ * admin api test
+ *
+ * @author xuxueli 2017-07-28 22:14:52
+ */
+public class AdminBizClient implements AdminBiz {
+
+    public AdminBizClient() {
+    }
+    public AdminBizClient(String addressUrl, String accessToken) {
+        this.addressUrl = addressUrl;
+        this.accessToken = accessToken;
+
+        // valid
+        if (!this.addressUrl.endsWith("/")) {
+            this.addressUrl = this.addressUrl + "/";
+        }
+    }
+
+    private String addressUrl ;
+    private String accessToken;
+
+
+    @Override
+    public ReturnT<String> callback(List<HandleCallbackParam> callbackParamList) {
+        return XxlJobRemotingUtil.postBody(addressUrl+"api/callback", accessToken, callbackParamList, 3);
+    }
+
+    @Override
+    public ReturnT<String> registry(RegistryParam registryParam) {
+        return XxlJobRemotingUtil.postBody(addressUrl + "api/registry", accessToken, registryParam, 3);
+    }
+
+    @Override
+    public ReturnT<String> registryRemove(RegistryParam registryParam) {
+        return XxlJobRemotingUtil.postBody(addressUrl + "api/registryRemove", accessToken, registryParam, 3);
+    }
+}

+ 174 - 0
xxl-job-core/src/main/java/com/xxl/job/core/biz/impl/ExecutorBizImpl.java

@@ -0,0 +1,174 @@
+package com.xxl.job.core.biz.impl;
+
+import com.xxl.job.core.biz.ExecutorBiz;
+import com.xxl.job.core.biz.model.LogResult;
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.job.core.biz.model.TriggerParam;
+import com.xxl.job.core.enums.ExecutorBlockStrategyEnum;
+import com.xxl.job.core.executor.XxlJobExecutor;
+import com.xxl.job.core.glue.GlueFactory;
+import com.xxl.job.core.glue.GlueTypeEnum;
+import com.xxl.job.core.handler.IJobHandler;
+import com.xxl.job.core.handler.impl.GlueJobHandler;
+import com.xxl.job.core.handler.impl.ScriptJobHandler;
+import com.xxl.job.core.log.XxlJobFileAppender;
+import com.xxl.job.core.thread.JobThread;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.Date;
+
+/**
+ * Created by xuxueli on 17/3/1.
+ */
+public class ExecutorBizImpl implements ExecutorBiz {
+    private static Logger logger = LoggerFactory.getLogger(ExecutorBizImpl.class);
+
+    @Override
+    public ReturnT<String> beat() {
+        return ReturnT.SUCCESS;
+    }
+
+    @Override
+    public ReturnT<String> idleBeat(int jobId) {
+
+        // isRunningOrHasQueue
+        boolean isRunningOrHasQueue = false;
+        JobThread jobThread = XxlJobExecutor.loadJobThread(jobId);
+        if (jobThread != null && jobThread.isRunningOrHasQueue()) {
+            isRunningOrHasQueue = true;
+        }
+
+        if (isRunningOrHasQueue) {
+            return new ReturnT<String>(ReturnT.FAIL_CODE, "job thread is running or has trigger queue.");
+        }
+        return ReturnT.SUCCESS;
+    }
+
+    @Override
+    public ReturnT<String> kill(int jobId) {
+        // kill handlerThread, and create new one
+        JobThread jobThread = XxlJobExecutor.loadJobThread(jobId);
+        if (jobThread != null) {
+            XxlJobExecutor.removeJobThread(jobId, "scheduling center kill job.");
+            return ReturnT.SUCCESS;
+        }
+
+        return new ReturnT<String>(ReturnT.SUCCESS_CODE, "job thread already killed.");
+    }
+
+    @Override
+    public ReturnT<LogResult> log(long logDateTim, long logId, int fromLineNum) {
+        // log filename: logPath/yyyy-MM-dd/9999.log
+        String logFileName = XxlJobFileAppender.makeLogFileName(new Date(logDateTim), logId);
+
+        LogResult logResult = XxlJobFileAppender.readLog(logFileName, fromLineNum);
+        return new ReturnT<LogResult>(logResult);
+    }
+
+    @Override
+    public ReturnT<String> run(TriggerParam triggerParam) {
+        // load old:jobHandler + jobThread
+        JobThread jobThread = XxlJobExecutor.loadJobThread(triggerParam.getJobId());
+        IJobHandler jobHandler = jobThread!=null?jobThread.getHandler():null;
+        String removeOldReason = null;
+
+        // valid:jobHandler + jobThread
+        GlueTypeEnum glueTypeEnum = GlueTypeEnum.match(triggerParam.getGlueType());
+        if (GlueTypeEnum.BEAN == glueTypeEnum) {
+
+            // new jobhandler
+            IJobHandler newJobHandler = XxlJobExecutor.loadJobHandler(triggerParam.getExecutorHandler());
+
+            // valid old jobThread
+            if (jobThread!=null && jobHandler != newJobHandler) {
+                // change handler, need kill old thread
+                removeOldReason = "change jobhandler or glue type, and terminate the old job thread.";
+
+                jobThread = null;
+                jobHandler = null;
+            }
+
+            // valid handler
+            if (jobHandler == null) {
+                jobHandler = newJobHandler;
+                if (jobHandler == null) {
+                    return new ReturnT<String>(ReturnT.FAIL_CODE, "job handler [" + triggerParam.getExecutorHandler() + "] not found.");
+                }
+            }
+
+        } else if (GlueTypeEnum.GLUE_GROOVY == glueTypeEnum) {
+
+            // valid old jobThread
+            if (jobThread != null &&
+                    !(jobThread.getHandler() instanceof GlueJobHandler
+                        && ((GlueJobHandler) jobThread.getHandler()).getGlueUpdatetime()==triggerParam.getGlueUpdatetime() )) {
+                // change handler or gluesource updated, need kill old thread
+                removeOldReason = "change job source or glue type, and terminate the old job thread.";
+
+                jobThread = null;
+                jobHandler = null;
+            }
+
+            // valid handler
+            if (jobHandler == null) {
+                try {
+                    IJobHandler originJobHandler = GlueFactory.getInstance().loadNewInstance(triggerParam.getGlueSource());
+                    jobHandler = new GlueJobHandler(originJobHandler, triggerParam.getGlueUpdatetime());
+                } catch (Exception e) {
+                    logger.error(e.getMessage(), e);
+                    return new ReturnT<String>(ReturnT.FAIL_CODE, e.getMessage());
+                }
+            }
+        } else if (glueTypeEnum!=null && glueTypeEnum.isScript()) {
+
+            // valid old jobThread
+            if (jobThread != null &&
+                    !(jobThread.getHandler() instanceof ScriptJobHandler
+                            && ((ScriptJobHandler) jobThread.getHandler()).getGlueUpdatetime()==triggerParam.getGlueUpdatetime() )) {
+                // change script or gluesource updated, need kill old thread
+                removeOldReason = "change job source or glue type, and terminate the old job thread.";
+
+                jobThread = null;
+                jobHandler = null;
+            }
+
+            // valid handler
+            if (jobHandler == null) {
+                jobHandler = new ScriptJobHandler(triggerParam.getJobId(), triggerParam.getGlueUpdatetime(), triggerParam.getGlueSource(), GlueTypeEnum.match(triggerParam.getGlueType()));
+            }
+        } else {
+            return new ReturnT<String>(ReturnT.FAIL_CODE, "glueType[" + triggerParam.getGlueType() + "] is not valid.");
+        }
+
+        // executor block strategy
+        if (jobThread != null) {
+            ExecutorBlockStrategyEnum blockStrategy = ExecutorBlockStrategyEnum.match(triggerParam.getExecutorBlockStrategy(), null);
+            if (ExecutorBlockStrategyEnum.DISCARD_LATER == blockStrategy) {
+                // discard when running
+                if (jobThread.isRunningOrHasQueue()) {
+                    return new ReturnT<String>(ReturnT.FAIL_CODE, "block strategy effect:"+ExecutorBlockStrategyEnum.DISCARD_LATER.getTitle());
+                }
+            } else if (ExecutorBlockStrategyEnum.COVER_EARLY == blockStrategy) {
+                // kill running jobThread
+                if (jobThread.isRunningOrHasQueue()) {
+                    removeOldReason = "block strategy effect:" + ExecutorBlockStrategyEnum.COVER_EARLY.getTitle();
+
+                    jobThread = null;
+                }
+            } else {
+                // just queue trigger
+            }
+        }
+
+        // replace thread (new or exists invalid)
+        if (jobThread == null) {
+            jobThread = XxlJobExecutor.registJobThread(triggerParam.getJobId(), jobHandler, removeOldReason);
+        }
+
+        // push data to queue
+        ReturnT<String> pushResult = jobThread.pushTriggerQueue(triggerParam);
+        return pushResult;
+    }
+
+}

+ 56 - 0
xxl-job-core/src/main/java/com/xxl/job/core/biz/model/HandleCallbackParam.java

@@ -0,0 +1,56 @@
+package com.xxl.job.core.biz.model;
+
+import java.io.Serializable;
+
+/**
+ * Created by xuxueli on 17/3/2.
+ */
+public class HandleCallbackParam implements Serializable {
+    private static final long serialVersionUID = 42L;
+
+    private long logId;
+    private long logDateTim;
+
+    private ReturnT<String> executeResult;
+
+    public HandleCallbackParam(){}
+    public HandleCallbackParam(long logId, long logDateTim, ReturnT<String> executeResult) {
+        this.logId = logId;
+        this.logDateTim = logDateTim;
+        this.executeResult = executeResult;
+    }
+
+    public long getLogId() {
+        return logId;
+    }
+
+    public void setLogId(long logId) {
+        this.logId = logId;
+    }
+
+    public long getLogDateTim() {
+        return logDateTim;
+    }
+
+    public void setLogDateTim(long logDateTim) {
+        this.logDateTim = logDateTim;
+    }
+
+    public ReturnT<String> getExecuteResult() {
+        return executeResult;
+    }
+
+    public void setExecuteResult(ReturnT<String> executeResult) {
+        this.executeResult = executeResult;
+    }
+
+    @Override
+    public String toString() {
+        return "HandleCallbackParam{" +
+                "logId=" + logId +
+                ", logDateTim=" + logDateTim +
+                ", executeResult=" + executeResult +
+                '}';
+    }
+
+}

+ 54 - 0
xxl-job-core/src/main/java/com/xxl/job/core/biz/model/LogResult.java

@@ -0,0 +1,54 @@
+package com.xxl.job.core.biz.model;
+
+import java.io.Serializable;
+
+/**
+ * Created by xuxueli on 17/3/23.
+ */
+public class LogResult implements Serializable {
+    private static final long serialVersionUID = 42L;
+
+    public LogResult(int fromLineNum, int toLineNum, String logContent, boolean isEnd) {
+        this.fromLineNum = fromLineNum;
+        this.toLineNum = toLineNum;
+        this.logContent = logContent;
+        this.isEnd = isEnd;
+    }
+
+    private int fromLineNum;
+    private int toLineNum;
+    private String logContent;
+    private boolean isEnd;
+
+    public int getFromLineNum() {
+        return fromLineNum;
+    }
+
+    public void setFromLineNum(int fromLineNum) {
+        this.fromLineNum = fromLineNum;
+    }
+
+    public int getToLineNum() {
+        return toLineNum;
+    }
+
+    public void setToLineNum(int toLineNum) {
+        this.toLineNum = toLineNum;
+    }
+
+    public String getLogContent() {
+        return logContent;
+    }
+
+    public void setLogContent(String logContent) {
+        this.logContent = logContent;
+    }
+
+    public boolean isEnd() {
+        return isEnd;
+    }
+
+    public void setEnd(boolean end) {
+        isEnd = end;
+    }
+}

+ 54 - 0
xxl-job-core/src/main/java/com/xxl/job/core/biz/model/RegistryParam.java

@@ -0,0 +1,54 @@
+package com.xxl.job.core.biz.model;
+
+import java.io.Serializable;
+
+/**
+ * Created by xuxueli on 2017-05-10 20:22:42
+ */
+public class RegistryParam implements Serializable {
+    private static final long serialVersionUID = 42L;
+
+    private String registryGroup;
+    private String registryKey;
+    private String registryValue;
+
+    public RegistryParam(){}
+    public RegistryParam(String registryGroup, String registryKey, String registryValue) {
+        this.registryGroup = registryGroup;
+        this.registryKey = registryKey;
+        this.registryValue = registryValue;
+    }
+
+    public String getRegistryGroup() {
+        return registryGroup;
+    }
+
+    public void setRegistryGroup(String registryGroup) {
+        this.registryGroup = registryGroup;
+    }
+
+    public String getRegistryKey() {
+        return registryKey;
+    }
+
+    public void setRegistryKey(String registryKey) {
+        this.registryKey = registryKey;
+    }
+
+    public String getRegistryValue() {
+        return registryValue;
+    }
+
+    public void setRegistryValue(String registryValue) {
+        this.registryValue = registryValue;
+    }
+
+    @Override
+    public String toString() {
+        return "RegistryParam{" +
+                "registryGroup='" + registryGroup + '\'' +
+                ", registryKey='" + registryKey + '\'' +
+                ", registryValue='" + registryValue + '\'' +
+                '}';
+    }
+}

+ 57 - 0
xxl-job-core/src/main/java/com/xxl/job/core/biz/model/ReturnT.java

@@ -0,0 +1,57 @@
+package com.xxl.job.core.biz.model;
+
+import java.io.Serializable;
+
+/**
+ * common return
+ * @author xuxueli 2015-12-4 16:32:31
+ * @param <T>
+ */
+public class ReturnT<T> implements Serializable {
+	public static final long serialVersionUID = 42L;
+
+	public static final int SUCCESS_CODE = 200;
+	public static final int FAIL_CODE = 500;
+
+	public static final ReturnT<String> SUCCESS = new ReturnT<String>(null);
+	public static final ReturnT<String> FAIL = new ReturnT<String>(FAIL_CODE, null);
+
+	private int code;
+	private String msg;
+	private T content;
+
+	public ReturnT(){}
+	public ReturnT(int code, String msg) {
+		this.code = code;
+		this.msg = msg;
+	}
+	public ReturnT(T content) {
+		this.code = SUCCESS_CODE;
+		this.content = content;
+	}
+	
+	public int getCode() {
+		return code;
+	}
+	public void setCode(int code) {
+		this.code = code;
+	}
+	public String getMsg() {
+		return msg;
+	}
+	public void setMsg(String msg) {
+		this.msg = msg;
+	}
+	public T getContent() {
+		return content;
+	}
+	public void setContent(T content) {
+		this.content = content;
+	}
+
+	@Override
+	public String toString() {
+		return "ReturnT [code=" + code + ", msg=" + msg + ", content=" + content + "]";
+	}
+
+}

+ 144 - 0
xxl-job-core/src/main/java/com/xxl/job/core/biz/model/TriggerParam.java

@@ -0,0 +1,144 @@
+package com.xxl.job.core.biz.model;
+
+import java.io.Serializable;
+
+/**
+ * Created by xuxueli on 16/7/22.
+ */
+public class TriggerParam implements Serializable{
+    private static final long serialVersionUID = 42L;
+
+    private int jobId;
+
+    private String executorHandler;
+    private String executorParams;
+    private String executorBlockStrategy;
+    private int executorTimeout;
+
+    private long logId;
+    private long logDateTime;
+
+    private String glueType;
+    private String glueSource;
+    private long glueUpdatetime;
+
+    private int broadcastIndex;
+    private int broadcastTotal;
+
+
+    public int getJobId() {
+        return jobId;
+    }
+
+    public void setJobId(int jobId) {
+        this.jobId = jobId;
+    }
+
+    public String getExecutorHandler() {
+        return executorHandler;
+    }
+
+    public void setExecutorHandler(String executorHandler) {
+        this.executorHandler = executorHandler;
+    }
+
+    public String getExecutorParams() {
+        return executorParams;
+    }
+
+    public void setExecutorParams(String executorParams) {
+        this.executorParams = executorParams;
+    }
+
+    public String getExecutorBlockStrategy() {
+        return executorBlockStrategy;
+    }
+
+    public void setExecutorBlockStrategy(String executorBlockStrategy) {
+        this.executorBlockStrategy = executorBlockStrategy;
+    }
+
+    public int getExecutorTimeout() {
+        return executorTimeout;
+    }
+
+    public void setExecutorTimeout(int executorTimeout) {
+        this.executorTimeout = executorTimeout;
+    }
+
+    public long getLogId() {
+        return logId;
+    }
+
+    public void setLogId(long logId) {
+        this.logId = logId;
+    }
+
+    public long getLogDateTime() {
+        return logDateTime;
+    }
+
+    public void setLogDateTime(long logDateTime) {
+        this.logDateTime = logDateTime;
+    }
+
+    public String getGlueType() {
+        return glueType;
+    }
+
+    public void setGlueType(String glueType) {
+        this.glueType = glueType;
+    }
+
+    public String getGlueSource() {
+        return glueSource;
+    }
+
+    public void setGlueSource(String glueSource) {
+        this.glueSource = glueSource;
+    }
+
+    public long getGlueUpdatetime() {
+        return glueUpdatetime;
+    }
+
+    public void setGlueUpdatetime(long glueUpdatetime) {
+        this.glueUpdatetime = glueUpdatetime;
+    }
+
+    public int getBroadcastIndex() {
+        return broadcastIndex;
+    }
+
+    public void setBroadcastIndex(int broadcastIndex) {
+        this.broadcastIndex = broadcastIndex;
+    }
+
+    public int getBroadcastTotal() {
+        return broadcastTotal;
+    }
+
+    public void setBroadcastTotal(int broadcastTotal) {
+        this.broadcastTotal = broadcastTotal;
+    }
+
+
+    @Override
+    public String toString() {
+        return "TriggerParam{" +
+                "jobId=" + jobId +
+                ", executorHandler='" + executorHandler + '\'' +
+                ", executorParams='" + executorParams + '\'' +
+                ", executorBlockStrategy='" + executorBlockStrategy + '\'' +
+                ", executorTimeout=" + executorTimeout +
+                ", logId=" + logId +
+                ", logDateTime=" + logDateTime +
+                ", glueType='" + glueType + '\'' +
+                ", glueSource='" + glueSource + '\'' +
+                ", glueUpdatetime=" + glueUpdatetime +
+                ", broadcastIndex=" + broadcastIndex +
+                ", broadcastTotal=" + broadcastTotal +
+                '}';
+    }
+
+}

+ 35 - 0
xxl-job-core/src/main/java/com/xxl/job/core/enums/ExecutorBlockStrategyEnum.java

@@ -0,0 +1,35 @@
+package com.xxl.job.core.enums;
+
+/**
+ * Created by xuxueli on 17/5/9.
+ */
+public enum ExecutorBlockStrategyEnum {
+
+    SERIAL_EXECUTION("Serial execution"),
+    /*CONCURRENT_EXECUTION("并行"),*/
+    DISCARD_LATER("Discard Later"),
+    COVER_EARLY("Cover Early");
+
+    private String title;
+    private ExecutorBlockStrategyEnum (String title) {
+        this.title = title;
+    }
+
+    public void setTitle(String title) {
+        this.title = title;
+    }
+    public String getTitle() {
+        return title;
+    }
+
+    public static ExecutorBlockStrategyEnum match(String name, ExecutorBlockStrategyEnum defaultItem) {
+        if (name != null) {
+            for (ExecutorBlockStrategyEnum item:ExecutorBlockStrategyEnum.values()) {
+                if (item.name().equals(name)) {
+                    return item;
+                }
+            }
+        }
+        return defaultItem;
+    }
+}

+ 13 - 0
xxl-job-core/src/main/java/com/xxl/job/core/enums/RegistryConfig.java

@@ -0,0 +1,13 @@
+package com.xxl.job.core.enums;
+
+/**
+ * Created by xuxueli on 17/5/10.
+ */
+public class RegistryConfig {
+
+    public static final int BEAT_TIMEOUT = 30;
+    public static final int DEAD_TIMEOUT = BEAT_TIMEOUT * 3;
+
+    public enum RegistType{ EXECUTOR, ADMIN }
+
+}

+ 246 - 0
xxl-job-core/src/main/java/com/xxl/job/core/executor/XxlJobExecutor.java

@@ -0,0 +1,246 @@
+package com.xxl.job.core.executor;
+
+import com.xxl.job.core.biz.AdminBiz;
+import com.xxl.job.core.biz.ExecutorBiz;
+import com.xxl.job.core.biz.client.AdminBizClient;
+import com.xxl.job.core.biz.impl.ExecutorBizImpl;
+import com.xxl.job.core.handler.IJobHandler;
+import com.xxl.job.core.log.XxlJobFileAppender;
+import com.xxl.job.core.thread.ExecutorRegistryThread;
+import com.xxl.job.core.thread.JobLogFileCleanThread;
+import com.xxl.job.core.thread.JobThread;
+import com.xxl.job.core.thread.TriggerCallbackThread;
+import com.xxl.rpc.registry.ServiceRegistry;
+import com.xxl.rpc.remoting.net.impl.netty_http.server.NettyHttpServer;
+import com.xxl.rpc.remoting.provider.XxlRpcProviderFactory;
+import com.xxl.rpc.serialize.Serializer;
+import com.xxl.rpc.serialize.impl.HessianSerializer;
+import com.xxl.rpc.util.IpUtil;
+import com.xxl.rpc.util.NetUtil;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.*;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ConcurrentMap;
+
+/**
+ * Created by xuxueli on 2016/3/2 21:14.
+ */
+public class XxlJobExecutor  {
+    private static final Logger logger = LoggerFactory.getLogger(XxlJobExecutor.class);
+
+    // ---------------------- param ----------------------
+    private String adminAddresses;
+    private String appName;
+    private String ip;
+    private int port;
+    private String accessToken;
+    private String logPath;
+    private int logRetentionDays;
+
+    public void setAdminAddresses(String adminAddresses) {
+        this.adminAddresses = adminAddresses;
+    }
+    public void setAppName(String appName) {
+        this.appName = appName;
+    }
+    public void setIp(String ip) {
+        this.ip = ip;
+    }
+    public void setPort(int port) {
+        this.port = port;
+    }
+    public void setAccessToken(String accessToken) {
+        this.accessToken = accessToken;
+    }
+    public void setLogPath(String logPath) {
+        this.logPath = logPath;
+    }
+    public void setLogRetentionDays(int logRetentionDays) {
+        this.logRetentionDays = logRetentionDays;
+    }
+
+
+    // ---------------------- start + stop ----------------------
+    public void start() throws Exception {
+
+        // init logpath
+        XxlJobFileAppender.initLogPath(logPath);
+
+        // init invoker, admin-client
+        initAdminBizList(adminAddresses, accessToken);
+
+
+        // init JobLogFileCleanThread
+        JobLogFileCleanThread.getInstance().start(logRetentionDays);
+
+        // init TriggerCallbackThread
+        TriggerCallbackThread.getInstance().start();
+
+        // init executor-server
+        port = port>0?port: NetUtil.findAvailablePort(9999);
+        ip = (ip!=null&&ip.trim().length()>0)?ip: IpUtil.getIp();
+        initRpcProvider(ip, port, appName, accessToken);
+    }
+    public void destroy(){
+        // destory executor-server
+        stopRpcProvider();
+
+        // destory jobThreadRepository
+        if (jobThreadRepository.size() > 0) {
+            for (Map.Entry<Integer, JobThread> item: jobThreadRepository.entrySet()) {
+                removeJobThread(item.getKey(), "web container destroy and kill the job.");
+            }
+            jobThreadRepository.clear();
+        }
+        jobHandlerRepository.clear();
+
+
+        // destory JobLogFileCleanThread
+        JobLogFileCleanThread.getInstance().toStop();
+
+        // destory TriggerCallbackThread
+        TriggerCallbackThread.getInstance().toStop();
+
+    }
+
+
+    // ---------------------- admin-client (rpc invoker) ----------------------
+    private static List<AdminBiz> adminBizList;
+    private static Serializer serializer = new HessianSerializer();
+    private void initAdminBizList(String adminAddresses, String accessToken) throws Exception {
+        if (adminAddresses!=null && adminAddresses.trim().length()>0) {
+            for (String address: adminAddresses.trim().split(",")) {
+                if (address!=null && address.trim().length()>0) {
+
+                    AdminBiz adminBiz = new AdminBizClient(address.trim(), accessToken);
+
+                    if (adminBizList == null) {
+                        adminBizList = new ArrayList<AdminBiz>();
+                    }
+                    adminBizList.add(adminBiz);
+                }
+            }
+        }
+    }
+    public static List<AdminBiz> getAdminBizList(){
+        return adminBizList;
+    }
+    public static Serializer getSerializer() {
+        return serializer;
+    }
+
+
+    // ---------------------- executor-server (rpc provider) ----------------------
+    private XxlRpcProviderFactory xxlRpcProviderFactory = null;
+
+    private void initRpcProvider(String ip, int port, String appName, String accessToken) throws Exception {
+
+        // init, provider factory
+        String address = IpUtil.getIpPort(ip, port);
+        Map<String, String> serviceRegistryParam = new HashMap<String, String>();
+        serviceRegistryParam.put("appName", appName);
+        serviceRegistryParam.put("address", address);
+
+        xxlRpcProviderFactory = new XxlRpcProviderFactory();
+
+        xxlRpcProviderFactory.setServer(NettyHttpServer.class);
+        xxlRpcProviderFactory.setSerializer(HessianSerializer.class);
+        xxlRpcProviderFactory.setCorePoolSize(20);
+        xxlRpcProviderFactory.setMaxPoolSize(200);
+        xxlRpcProviderFactory.setIp(ip);
+        xxlRpcProviderFactory.setPort(port);
+        xxlRpcProviderFactory.setAccessToken(accessToken);
+        xxlRpcProviderFactory.setServiceRegistry(ExecutorServiceRegistry.class);
+        xxlRpcProviderFactory.setServiceRegistryParam(serviceRegistryParam);
+
+        // add services
+        xxlRpcProviderFactory.addService(ExecutorBiz.class.getName(), null, new ExecutorBizImpl());
+
+        // start
+        xxlRpcProviderFactory.start();
+
+    }
+
+    public static class ExecutorServiceRegistry extends ServiceRegistry {
+
+        @Override
+        public void start(Map<String, String> param) {
+            // start registry
+            ExecutorRegistryThread.getInstance().start(param.get("appName"), param.get("address"));
+        }
+        @Override
+        public void stop() {
+            // stop registry
+            ExecutorRegistryThread.getInstance().toStop();
+        }
+
+        @Override
+        public boolean registry(Set<String> keys, String value) {
+            return false;
+        }
+        @Override
+        public boolean remove(Set<String> keys, String value) {
+            return false;
+        }
+        @Override
+        public Map<String, TreeSet<String>> discovery(Set<String> keys) {
+            return null;
+        }
+        @Override
+        public TreeSet<String> discovery(String key) {
+            return null;
+        }
+
+    }
+
+    private void stopRpcProvider() {
+        // stop provider factory
+        try {
+            xxlRpcProviderFactory.stop();
+        } catch (Exception e) {
+            logger.error(e.getMessage(), e);
+        }
+    }
+
+
+    // ---------------------- job handler repository ----------------------
+    private static ConcurrentMap<String, IJobHandler> jobHandlerRepository = new ConcurrentHashMap<String, IJobHandler>();
+    public static IJobHandler registJobHandler(String name, IJobHandler jobHandler){
+        logger.info(">>>>>>>>>>> xxl-job register jobhandler success, name:{}, jobHandler:{}", name, jobHandler);
+        return jobHandlerRepository.put(name, jobHandler);
+    }
+    public static IJobHandler loadJobHandler(String name){
+        return jobHandlerRepository.get(name);
+    }
+
+
+    // ---------------------- job thread repository ----------------------
+    private static ConcurrentMap<Integer, JobThread> jobThreadRepository = new ConcurrentHashMap<Integer, JobThread>();
+    public static JobThread registJobThread(int jobId, IJobHandler handler, String removeOldReason){
+        JobThread newJobThread = new JobThread(jobId, handler);
+        newJobThread.start();
+        logger.info(">>>>>>>>>>> xxl-job regist JobThread success, jobId:{}, handler:{}", new Object[]{jobId, handler});
+
+        JobThread oldJobThread = jobThreadRepository.put(jobId, newJobThread);	// putIfAbsent | oh my god, map's put method return the old value!!!
+        if (oldJobThread != null) {
+            oldJobThread.toStop(removeOldReason);
+            oldJobThread.interrupt();
+        }
+
+        return newJobThread;
+    }
+    public static void removeJobThread(int jobId, String removeOldReason){
+        JobThread oldJobThread = jobThreadRepository.remove(jobId);
+        if (oldJobThread != null) {
+            oldJobThread.toStop(removeOldReason);
+            oldJobThread.interrupt();
+        }
+    }
+    public static JobThread loadJobThread(int jobId){
+        JobThread jobThread = jobThreadRepository.get(jobId);
+        return jobThread;
+    }
+
+}

+ 151 - 0
xxl-job-core/src/main/java/com/xxl/job/core/executor/impl/XxlJobSpringExecutor.java

@@ -0,0 +1,151 @@
+package com.xxl.job.core.executor.impl;
+
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.job.core.executor.XxlJobExecutor;
+import com.xxl.job.core.glue.GlueFactory;
+import com.xxl.job.core.handler.IJobHandler;
+import com.xxl.job.core.handler.annotation.JobHandler;
+import com.xxl.job.core.handler.annotation.XxlJob;
+import com.xxl.job.core.handler.impl.MethodJobHandler;
+import org.springframework.beans.BeansException;
+import org.springframework.beans.factory.DisposableBean;
+import org.springframework.beans.factory.InitializingBean;
+import org.springframework.context.ApplicationContext;
+import org.springframework.context.ApplicationContextAware;
+import org.springframework.core.annotation.AnnotationUtils;
+
+import java.lang.reflect.Method;
+import java.util.Map;
+
+/**
+ * xxl-job executor (for spring)
+ *
+ * @author xuxueli 2018-11-01 09:24:52
+ */
+public class XxlJobSpringExecutor extends XxlJobExecutor implements ApplicationContextAware, InitializingBean, DisposableBean {
+
+
+    // start
+    @Override
+    public void afterPropertiesSet() throws Exception {
+
+        // init JobHandler Repository
+        initJobHandlerRepository(applicationContext);
+
+        // init JobHandler Repository (for method)
+        initJobHandlerMethodRepository(applicationContext);
+
+        // refresh GlueFactory
+        GlueFactory.refreshInstance(1);
+
+        // super start
+        super.start();
+    }
+
+    // destroy
+    @Override
+    public void destroy() {
+        super.destroy();
+    }
+
+
+    private void initJobHandlerRepository(ApplicationContext applicationContext) {
+        if (applicationContext == null) {
+            return;
+        }
+
+        // init job handler action
+        Map<String, Object> serviceBeanMap = applicationContext.getBeansWithAnnotation(JobHandler.class);
+
+        if (serviceBeanMap != null && serviceBeanMap.size() > 0) {
+            for (Object serviceBean : serviceBeanMap.values()) {
+                if (serviceBean instanceof IJobHandler) {
+                    String name = serviceBean.getClass().getAnnotation(JobHandler.class).value();
+                    IJobHandler handler = (IJobHandler) serviceBean;
+                    if (loadJobHandler(name) != null) {
+                        throw new RuntimeException("xxl-job jobhandler[" + name + "] naming conflicts.");
+                    }
+                    registJobHandler(name, handler);
+                }
+            }
+        }
+    }
+
+    private void initJobHandlerMethodRepository(ApplicationContext applicationContext) {
+        if (applicationContext == null) {
+            return;
+        }
+
+        // init job handler from method
+        String[] beanDefinitionNames = applicationContext.getBeanDefinitionNames();
+        if (beanDefinitionNames!=null && beanDefinitionNames.length>0) {
+            for (String beanDefinitionName : beanDefinitionNames) {
+                Object bean = applicationContext.getBean(beanDefinitionName);
+                Method[] methods = bean.getClass().getDeclaredMethods();
+                for (Method method: methods) {
+                    XxlJob xxlJob = AnnotationUtils.findAnnotation(method, XxlJob.class);
+                    if (xxlJob != null) {
+
+                        // name
+                        String name = xxlJob.value();
+                        if (name.trim().length() == 0) {
+                            throw new RuntimeException("xxl-job method-jobhandler name invalid, for[" + bean.getClass() + "#"+ method.getName() +"] .");
+                        }
+                        if (loadJobHandler(name) != null) {
+                            throw new RuntimeException("xxl-job jobhandler[" + name + "] naming conflicts.");
+                        }
+
+                        // execute method
+                        if (!(method.getParameterTypes()!=null && method.getParameterTypes().length==1 && method.getParameterTypes()[0].isAssignableFrom(String.class))) {
+                            throw new RuntimeException("xxl-job method-jobhandler param-classtype invalid, for[" + bean.getClass() + "#"+ method.getName() +"] , " +
+                                    "The correct method format like \" public ReturnT<String> execute(String param) \" .");
+                        }
+                        if (!method.getReturnType().isAssignableFrom(ReturnT.class)) {
+                            throw new RuntimeException("xxl-job method-jobhandler return-classtype invalid, for[" + bean.getClass() + "#"+ method.getName() +"] , " +
+                                    "The correct method format like \" public ReturnT<String> execute(String param) \" .");
+                        }
+                        method.setAccessible(true);
+
+                        // init and destory
+                        Method initMethod = null;
+                        Method destroyMethod = null;
+
+                        if(xxlJob.init().trim().length() > 0) {
+                            try {
+                                initMethod = bean.getClass().getDeclaredMethod(xxlJob.init());
+                                initMethod.setAccessible(true);
+                            } catch (NoSuchMethodException e) {
+                                throw new RuntimeException("xxl-job method-jobhandler initMethod invalid, for[" + bean.getClass() + "#"+ method.getName() +"] .");
+                            }
+                        }
+                        if(xxlJob.destroy().trim().length() > 0) {
+                            try {
+                                destroyMethod = bean.getClass().getDeclaredMethod(xxlJob.destroy());
+                                destroyMethod.setAccessible(true);
+                            } catch (NoSuchMethodException e) {
+                                throw new RuntimeException("xxl-job method-jobhandler destroyMethod invalid, for[" + bean.getClass() + "#"+ method.getName() +"] .");
+                            }
+                        }
+
+                        // registry jobhandler
+                        registJobHandler(name, new MethodJobHandler(bean, method, initMethod, destroyMethod));
+                    }
+                }
+            }
+        }
+
+    }
+
+    // ---------------------- applicationContext ----------------------
+    private static ApplicationContext applicationContext;
+
+    @Override
+    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
+        XxlJobSpringExecutor.applicationContext = applicationContext;
+    }
+
+    public static ApplicationContext getApplicationContext() {
+        return applicationContext;
+    }
+
+}

+ 90 - 0
xxl-job-core/src/main/java/com/xxl/job/core/glue/GlueFactory.java

@@ -0,0 +1,90 @@
+package com.xxl.job.core.glue;
+
+import com.xxl.job.core.glue.impl.SpringGlueFactory;
+import com.xxl.job.core.handler.IJobHandler;
+import groovy.lang.GroovyClassLoader;
+
+import java.math.BigInteger;
+import java.security.MessageDigest;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ConcurrentMap;
+
+/**
+ * glue factory, product class/object by name
+ *
+ * @author xuxueli 2016-1-2 20:02:27
+ */
+public class GlueFactory {
+
+
+	private static GlueFactory glueFactory = new GlueFactory();
+	public static GlueFactory getInstance(){
+		return glueFactory;
+	}
+	public static void refreshInstance(int type){
+		if (type == 0) {
+			glueFactory = new GlueFactory();
+		} else if (type == 1) {
+			glueFactory = new SpringGlueFactory();
+		}
+	}
+
+
+	/**
+	 * groovy class loader
+	 */
+	private GroovyClassLoader groovyClassLoader = new GroovyClassLoader();
+	private ConcurrentMap<String, Class<?>> CLASS_CACHE = new ConcurrentHashMap<>();
+
+	/**
+	 * load new instance, prototype
+	 *
+	 * @param codeSource
+	 * @return
+	 * @throws Exception
+	 */
+	public IJobHandler loadNewInstance(String codeSource) throws Exception{
+		if (codeSource!=null && codeSource.trim().length()>0) {
+			Class<?> clazz = getCodeSourceClass(codeSource);
+			if (clazz != null) {
+				Object instance = clazz.newInstance();
+				if (instance!=null) {
+					if (instance instanceof IJobHandler) {
+						this.injectService(instance);
+						return (IJobHandler) instance;
+					} else {
+						throw new IllegalArgumentException(">>>>>>>>>>> xxl-glue, loadNewInstance error, "
+								+ "cannot convert from instance["+ instance.getClass() +"] to IJobHandler");
+					}
+				}
+			}
+		}
+		throw new IllegalArgumentException(">>>>>>>>>>> xxl-glue, loadNewInstance error, instance is null");
+	}
+	private Class<?> getCodeSourceClass(String codeSource){
+		try {
+			// md5
+			byte[] md5 = MessageDigest.getInstance("MD5").digest(codeSource.getBytes());
+			String md5Str = new BigInteger(1, md5).toString(16);
+
+			Class<?> clazz = CLASS_CACHE.get(md5Str);
+			if(clazz == null){
+				clazz = groovyClassLoader.parseClass(codeSource);
+				CLASS_CACHE.putIfAbsent(md5Str, clazz);
+			}
+			return clazz;
+		} catch (Exception e) {
+			return groovyClassLoader.parseClass(codeSource);
+		}
+	}
+
+	/**
+	 * inject service of bean field
+	 *
+	 * @param instance
+	 */
+	public void injectService(Object instance) {
+		// do something
+	}
+
+}

+ 53 - 0
xxl-job-core/src/main/java/com/xxl/job/core/glue/GlueTypeEnum.java

@@ -0,0 +1,53 @@
+package com.xxl.job.core.glue;
+
+/**
+ * Created by xuxueli on 17/4/26.
+ */
+public enum GlueTypeEnum {
+
+    BEAN("BEAN", false, null, null),
+    GLUE_GROOVY("GLUE(Java)", false, null, null),
+    GLUE_SHELL("GLUE(Shell)", true, "bash", ".sh"),
+    GLUE_PYTHON("GLUE(Python)", true, "python", ".py"),
+    GLUE_PHP("GLUE(PHP)", true, "php", ".php"),
+    GLUE_NODEJS("GLUE(Nodejs)", true, "node", ".js"),
+    GLUE_POWERSHELL("GLUE(PowerShell)", true, "powershell", ".ps1");
+
+    private String desc;
+    private boolean isScript;
+    private String cmd;
+    private String suffix;
+
+    private GlueTypeEnum(String desc, boolean isScript, String cmd, String suffix) {
+        this.desc = desc;
+        this.isScript = isScript;
+        this.cmd = cmd;
+        this.suffix = suffix;
+    }
+
+    public String getDesc() {
+        return desc;
+    }
+
+    public boolean isScript() {
+        return isScript;
+    }
+
+    public String getCmd() {
+        return cmd;
+    }
+
+    public String getSuffix() {
+        return suffix;
+    }
+
+    public static GlueTypeEnum match(String name){
+        for (GlueTypeEnum item: GlueTypeEnum.values()) {
+            if (item.name().equals(name)) {
+                return item;
+            }
+        }
+        return null;
+    }
+
+}

+ 80 - 0
xxl-job-core/src/main/java/com/xxl/job/core/glue/impl/SpringGlueFactory.java

@@ -0,0 +1,80 @@
+package com.xxl.job.core.glue.impl;
+
+import com.xxl.job.core.executor.impl.XxlJobSpringExecutor;
+import com.xxl.job.core.glue.GlueFactory;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Qualifier;
+import org.springframework.core.annotation.AnnotationUtils;
+
+import javax.annotation.Resource;
+import java.lang.reflect.Field;
+import java.lang.reflect.Modifier;
+
+/**
+ * @author xuxueli 2018-11-01
+ */
+public class SpringGlueFactory extends GlueFactory {
+    private static Logger logger = LoggerFactory.getLogger(SpringGlueFactory.class);
+
+
+    /**
+     * inject action of spring
+     * @param instance
+     */
+    @Override
+    public void injectService(Object instance){
+        if (instance==null) {
+            return;
+        }
+
+        if (XxlJobSpringExecutor.getApplicationContext() == null) {
+            return;
+        }
+
+        Field[] fields = instance.getClass().getDeclaredFields();
+        for (Field field : fields) {
+            if (Modifier.isStatic(field.getModifiers())) {
+                continue;
+            }
+
+            Object fieldBean = null;
+            // with bean-id, bean could be found by both @Resource and @Autowired, or bean could only be found by @Autowired
+
+            if (AnnotationUtils.getAnnotation(field, Resource.class) != null) {
+                try {
+                    Resource resource = AnnotationUtils.getAnnotation(field, Resource.class);
+                    if (resource.name()!=null && resource.name().length()>0){
+                        fieldBean = XxlJobSpringExecutor.getApplicationContext().getBean(resource.name());
+                    } else {
+                        fieldBean = XxlJobSpringExecutor.getApplicationContext().getBean(field.getName());
+                    }
+                } catch (Exception e) {
+                }
+                if (fieldBean==null ) {
+                    fieldBean = XxlJobSpringExecutor.getApplicationContext().getBean(field.getType());
+                }
+            } else if (AnnotationUtils.getAnnotation(field, Autowired.class) != null) {
+                Qualifier qualifier = AnnotationUtils.getAnnotation(field, Qualifier.class);
+                if (qualifier!=null && qualifier.value()!=null && qualifier.value().length()>0) {
+                    fieldBean = XxlJobSpringExecutor.getApplicationContext().getBean(qualifier.value());
+                } else {
+                    fieldBean = XxlJobSpringExecutor.getApplicationContext().getBean(field.getType());
+                }
+            }
+
+            if (fieldBean!=null) {
+                field.setAccessible(true);
+                try {
+                    field.set(instance, fieldBean);
+                } catch (IllegalArgumentException e) {
+                    logger.error(e.getMessage(), e);
+                } catch (IllegalAccessException e) {
+                    logger.error(e.getMessage(), e);
+                }
+            }
+        }
+    }
+
+}

+ 49 - 0
xxl-job-core/src/main/java/com/xxl/job/core/handler/IJobHandler.java

@@ -0,0 +1,49 @@
+package com.xxl.job.core.handler;
+
+import com.xxl.job.core.biz.model.ReturnT;
+
+import java.lang.reflect.InvocationTargetException;
+
+/**
+ * job handler
+ *
+ * @author xuxueli 2015-12-19 19:06:38
+ */
+public abstract class IJobHandler {
+
+
+	/** success */
+	public static final ReturnT<String> SUCCESS = new ReturnT<String>(200, null);
+	/** fail */
+	public static final ReturnT<String> FAIL = new ReturnT<String>(500, null);
+	/** fail timeout */
+	public static final ReturnT<String> FAIL_TIMEOUT = new ReturnT<String>(502, null);
+
+
+	/**
+	 * execute handler, invoked when executor receives a scheduling request
+	 *
+	 * @param param
+	 * @return
+	 * @throws Exception
+	 */
+	public abstract ReturnT<String> execute(String param) throws Exception;
+
+
+	/**
+	 * init handler, invoked when JobThread init
+	 */
+	public void init() throws InvocationTargetException, IllegalAccessException {
+		// do something
+	}
+
+
+	/**
+	 * destroy handler, invoked when JobThread destroy
+	 */
+	public void destroy() throws InvocationTargetException, IllegalAccessException {
+		// do something
+	}
+
+
+}

+ 20 - 0
xxl-job-core/src/main/java/com/xxl/job/core/handler/annotation/JobHandler.java

@@ -0,0 +1,20 @@
+package com.xxl.job.core.handler.annotation;
+
+import java.lang.annotation.*;
+
+/**
+ * annotation for job handler
+ *
+ * will be replaced by {@link com.xxl.job.core.handler.annotation.XxlJob}
+ *
+ * @author 2016-5-17 21:06:49
+ */
+@Target({ElementType.TYPE})
+@Retention(RetentionPolicy.RUNTIME)
+@Inherited
+@Deprecated
+public @interface JobHandler {
+
+    String value();
+
+}

+ 30 - 0
xxl-job-core/src/main/java/com/xxl/job/core/handler/annotation/XxlJob.java

@@ -0,0 +1,30 @@
+package com.xxl.job.core.handler.annotation;
+
+import java.lang.annotation.*;
+
+/**
+ * annotation for method jobhandler
+ *
+ * @author xuxueli 2019-12-11 20:50:13
+ */
+@Target({ElementType.METHOD})
+@Retention(RetentionPolicy.RUNTIME)
+@Inherited
+public @interface XxlJob {
+
+    /**
+     * jobhandler name
+     */
+    String value();
+
+    /**
+     * init handler, invoked when JobThread init
+     */
+    String init() default "";
+
+    /**
+     * destroy handler, invoked when JobThread destroy
+     */
+    String destroy() default "";
+
+}

+ 30 - 0
xxl-job-core/src/main/java/com/xxl/job/core/handler/impl/GlueJobHandler.java

@@ -0,0 +1,30 @@
+package com.xxl.job.core.handler.impl;
+
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.job.core.handler.IJobHandler;
+import com.xxl.job.core.log.XxlJobLogger;
+
+/**
+ * glue job handler
+ *
+ * @author xuxueli 2016-5-19 21:05:45
+ */
+public class GlueJobHandler extends IJobHandler {
+
+	private long glueUpdatetime;
+	private IJobHandler jobHandler;
+	public GlueJobHandler(IJobHandler jobHandler, long glueUpdatetime) {
+		this.jobHandler = jobHandler;
+		this.glueUpdatetime = glueUpdatetime;
+	}
+	public long getGlueUpdatetime() {
+		return glueUpdatetime;
+	}
+
+	@Override
+	public ReturnT<String> execute(String param) throws Exception {
+		XxlJobLogger.log("----------- glue.version:"+ glueUpdatetime +" -----------");
+		return jobHandler.execute(param);
+	}
+
+}

+ 50 - 0
xxl-job-core/src/main/java/com/xxl/job/core/handler/impl/MethodJobHandler.java

@@ -0,0 +1,50 @@
+package com.xxl.job.core.handler.impl;
+
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.job.core.handler.IJobHandler;
+
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+
+/**
+ * @author xuxueli 2019-12-11 21:12:18
+ */
+public class MethodJobHandler extends IJobHandler {
+
+    private final Object target;
+    private final Method method;
+    private Method initMethod;
+    private Method destroyMethod;
+
+    public MethodJobHandler(Object target, Method method, Method initMethod, Method destroyMethod) {
+        this.target = target;
+        this.method = method;
+
+        this.initMethod =initMethod;
+        this.destroyMethod =destroyMethod;
+    }
+
+    @Override
+    public ReturnT<String> execute(String param) throws Exception {
+        return (ReturnT<String>) method.invoke(target, new Object[]{param});
+    }
+
+    @Override
+    public void init() throws InvocationTargetException, IllegalAccessException {
+        if(initMethod != null) {
+            initMethod.invoke(target);
+        }
+    }
+
+    @Override
+    public void destroy() throws InvocationTargetException, IllegalAccessException {
+        if(destroyMethod != null) {
+            destroyMethod.invoke(target);
+        }
+    }
+
+    @Override
+    public String toString() {
+        return super.toString()+"["+ target.getClass() + "#" + method.getName() +"]";
+    }
+}

+ 92 - 0
xxl-job-core/src/main/java/com/xxl/job/core/handler/impl/ScriptJobHandler.java

@@ -0,0 +1,92 @@
+package com.xxl.job.core.handler.impl;
+
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.job.core.glue.GlueTypeEnum;
+import com.xxl.job.core.handler.IJobHandler;
+import com.xxl.job.core.log.XxlJobFileAppender;
+import com.xxl.job.core.log.XxlJobLogger;
+import com.xxl.job.core.util.ScriptUtil;
+import com.xxl.job.core.util.ShardingUtil;
+
+import java.io.File;
+
+/**
+ * Created by xuxueli on 17/4/27.
+ */
+public class ScriptJobHandler extends IJobHandler {
+
+    private int jobId;
+    private long glueUpdatetime;
+    private String gluesource;
+    private GlueTypeEnum glueType;
+
+    public ScriptJobHandler(int jobId, long glueUpdatetime, String gluesource, GlueTypeEnum glueType){
+        this.jobId = jobId;
+        this.glueUpdatetime = glueUpdatetime;
+        this.gluesource = gluesource;
+        this.glueType = glueType;
+
+        // clean old script file
+        File glueSrcPath = new File(XxlJobFileAppender.getGlueSrcPath());
+        if (glueSrcPath.exists()) {
+            File[] glueSrcFileList = glueSrcPath.listFiles();
+            if (glueSrcFileList!=null && glueSrcFileList.length>0) {
+                for (File glueSrcFileItem : glueSrcFileList) {
+                    if (glueSrcFileItem.getName().startsWith(String.valueOf(jobId)+"_")) {
+                        glueSrcFileItem.delete();
+                    }
+                }
+            }
+        }
+
+    }
+
+    public long getGlueUpdatetime() {
+        return glueUpdatetime;
+    }
+
+    @Override
+    public ReturnT<String> execute(String param) throws Exception {
+
+        if (!glueType.isScript()) {
+            return new ReturnT<String>(FAIL.getCode(), "glueType["+ glueType +"] invalid.");
+        }
+
+        // cmd
+        String cmd = glueType.getCmd();
+
+        // make script file
+        String scriptFileName = XxlJobFileAppender.getGlueSrcPath()
+                .concat(File.separator)
+                .concat(String.valueOf(jobId))
+                .concat("_")
+                .concat(String.valueOf(glueUpdatetime))
+                .concat(glueType.getSuffix());
+        File scriptFile = new File(scriptFileName);
+        if (!scriptFile.exists()) {
+            ScriptUtil.markScriptFile(scriptFileName, gluesource);
+        }
+
+        // log file
+        String logFileName = XxlJobFileAppender.contextHolder.get();
+
+        // script params:0=param、1=分片序号、2=分片总数
+        ShardingUtil.ShardingVO shardingVO = ShardingUtil.getShardingVo();
+        String[] scriptParams = new String[3];
+        scriptParams[0] = param;
+        scriptParams[1] = String.valueOf(shardingVO.getIndex());
+        scriptParams[2] = String.valueOf(shardingVO.getTotal());
+
+        // invoke
+        XxlJobLogger.log("----------- script file:"+ scriptFileName +" -----------");
+        int exitValue = ScriptUtil.execToFile(cmd, scriptFileName, logFileName, scriptParams);
+
+        if (exitValue == 0) {
+            return SUCCESS;
+        } else {
+            return new ReturnT<String>(FAIL.getCode(), "script exit value("+exitValue+") is failed");
+        }
+
+    }
+
+}

+ 225 - 0
xxl-job-core/src/main/java/com/xxl/job/core/log/XxlJobFileAppender.java

@@ -0,0 +1,225 @@
+package com.xxl.job.core.log;
+
+import com.xxl.job.core.biz.model.LogResult;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.*;
+import java.text.SimpleDateFormat;
+import java.util.Date;
+
+/**
+ * store trigger log in each log-file
+ * @author xuxueli 2016-3-12 19:25:12
+ */
+public class XxlJobFileAppender {
+	private static Logger logger = LoggerFactory.getLogger(XxlJobFileAppender.class);
+	
+	// for JobThread (support log for child thread of job handler)
+	//public static ThreadLocal<String> contextHolder = new ThreadLocal<String>();
+	public static final InheritableThreadLocal<String> contextHolder = new InheritableThreadLocal<String>();
+
+
+	/**
+	 * log base path
+	 *
+	 * strut like:
+	 * 	---/
+	 * 	---/gluesource/
+	 * 	---/gluesource/10_1514171108000.js
+	 * 	---/gluesource/10_1514171108000.js
+	 * 	---/2017-12-25/
+	 * 	---/2017-12-25/639.log
+	 * 	---/2017-12-25/821.log
+	 *
+	 */
+	private static String logBasePath = "/data/applogs/xxl-job/jobhandler";
+	private static String glueSrcPath = logBasePath.concat("/gluesource");
+	public static void initLogPath(String logPath){
+		// init
+		if (logPath!=null && logPath.trim().length()>0) {
+			logBasePath = logPath;
+		}
+		// mk base dir
+		File logPathDir = new File(logBasePath);
+		if (!logPathDir.exists()) {
+			logPathDir.mkdirs();
+		}
+		logBasePath = logPathDir.getPath();
+
+		// mk glue dir
+		File glueBaseDir = new File(logPathDir, "gluesource");
+		if (!glueBaseDir.exists()) {
+			glueBaseDir.mkdirs();
+		}
+		glueSrcPath = glueBaseDir.getPath();
+	}
+	public static String getLogPath() {
+		return logBasePath;
+	}
+	public static String getGlueSrcPath() {
+		return glueSrcPath;
+	}
+
+	/**
+	 * log filename, like "logPath/yyyy-MM-dd/9999.log"
+	 *
+	 * @param triggerDate
+	 * @param logId
+	 * @return
+	 */
+	public static String makeLogFileName(Date triggerDate, long logId) {
+
+		// filePath/yyyy-MM-dd
+		SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");	// avoid concurrent problem, can not be static
+		File logFilePath = new File(getLogPath(), sdf.format(triggerDate));
+		if (!logFilePath.exists()) {
+			logFilePath.mkdir();
+		}
+
+		// filePath/yyyy-MM-dd/9999.log
+		String logFileName = logFilePath.getPath()
+				.concat(File.separator)
+				.concat(String.valueOf(logId))
+				.concat(".log");
+		return logFileName;
+	}
+
+	/**
+	 * append log
+	 *
+	 * @param logFileName
+	 * @param appendLog
+	 */
+	public static void appendLog(String logFileName, String appendLog) {
+
+		// log file
+		if (logFileName==null || logFileName.trim().length()==0) {
+			return;
+		}
+		File logFile = new File(logFileName);
+
+		if (!logFile.exists()) {
+			try {
+				logFile.createNewFile();
+			} catch (IOException e) {
+				logger.error(e.getMessage(), e);
+				return;
+			}
+		}
+
+		// log
+		if (appendLog == null) {
+			appendLog = "";
+		}
+		appendLog += "\r\n";
+		
+		// append file content
+		FileOutputStream fos = null;
+		try {
+			fos = new FileOutputStream(logFile, true);
+			fos.write(appendLog.getBytes("utf-8"));
+			fos.flush();
+		} catch (Exception e) {
+			logger.error(e.getMessage(), e);
+		} finally {
+			if (fos != null) {
+				try {
+					fos.close();
+				} catch (IOException e) {
+					logger.error(e.getMessage(), e);
+				}
+			}
+		}
+		
+	}
+
+	/**
+	 * support read log-file
+	 *
+	 * @param logFileName
+	 * @return log content
+	 */
+	public static LogResult readLog(String logFileName, int fromLineNum){
+
+		// valid log file
+		if (logFileName==null || logFileName.trim().length()==0) {
+            return new LogResult(fromLineNum, 0, "readLog fail, logFile not found", true);
+		}
+		File logFile = new File(logFileName);
+
+		if (!logFile.exists()) {
+            return new LogResult(fromLineNum, 0, "readLog fail, logFile not exists", true);
+		}
+
+		// read file
+		StringBuffer logContentBuffer = new StringBuffer();
+		int toLineNum = 0;
+		LineNumberReader reader = null;
+		try {
+			//reader = new LineNumberReader(new FileReader(logFile));
+			reader = new LineNumberReader(new InputStreamReader(new FileInputStream(logFile), "utf-8"));
+			String line = null;
+
+			while ((line = reader.readLine())!=null) {
+				toLineNum = reader.getLineNumber();		// [from, to], start as 1
+				if (toLineNum >= fromLineNum) {
+					logContentBuffer.append(line).append("\n");
+				}
+			}
+		} catch (IOException e) {
+			logger.error(e.getMessage(), e);
+		} finally {
+			if (reader != null) {
+				try {
+					reader.close();
+				} catch (IOException e) {
+					logger.error(e.getMessage(), e);
+				}
+			}
+		}
+
+		// result
+		LogResult logResult = new LogResult(fromLineNum, toLineNum, logContentBuffer.toString(), false);
+		return logResult;
+
+		/*
+        // it will return the number of characters actually skipped
+        reader.skip(Long.MAX_VALUE);
+        int maxLineNum = reader.getLineNumber();
+        maxLineNum++;	// 最大行号
+        */
+	}
+
+	/**
+	 * read log data
+	 * @param logFile
+	 * @return log line content
+	 */
+	public static String readLines(File logFile){
+		BufferedReader reader = null;
+		try {
+			reader = new BufferedReader(new InputStreamReader(new FileInputStream(logFile), "utf-8"));
+			if (reader != null) {
+				StringBuilder sb = new StringBuilder();
+				String line = null;
+				while ((line = reader.readLine()) != null) {
+					sb.append(line).append("\n");
+				}
+				return sb.toString();
+			}
+		} catch (IOException e) {
+			logger.error(e.getMessage(), e);
+		} finally {
+			if (reader != null) {
+				try {
+					reader.close();
+				} catch (IOException e) {
+					logger.error(e.getMessage(), e);
+				}
+			}
+		}
+		return null;
+	}
+
+}

+ 84 - 0
xxl-job-core/src/main/java/com/xxl/job/core/log/XxlJobLogger.java

@@ -0,0 +1,84 @@
+package com.xxl.job.core.log;
+
+import com.xxl.job.core.util.DateUtil;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.helpers.FormattingTuple;
+import org.slf4j.helpers.MessageFormatter;
+
+import java.io.PrintWriter;
+import java.io.StringWriter;
+import java.util.Date;
+
+/**
+ * Created by xuxueli on 17/4/28.
+ */
+public class XxlJobLogger {
+    private static Logger logger = LoggerFactory.getLogger("xxl-job logger");
+
+    /**
+     * append log
+     *
+     * @param callInfo
+     * @param appendLog
+     */
+    private static void logDetail(StackTraceElement callInfo, String appendLog) {
+
+
+        /*// "yyyy-MM-dd HH:mm:ss [ClassName]-[MethodName]-[LineNumber]-[ThreadName] log";
+        StackTraceElement[] stackTraceElements = new Throwable().getStackTrace();
+        StackTraceElement callInfo = stackTraceElements[1];*/
+
+        StringBuffer stringBuffer = new StringBuffer();
+        stringBuffer.append(DateUtil.formatDateTime(new Date())).append(" ")
+            .append("["+ callInfo.getClassName() + "#" + callInfo.getMethodName() +"]").append("-")
+            .append("["+ callInfo.getLineNumber() +"]").append("-")
+            .append("["+ Thread.currentThread().getName() +"]").append(" ")
+            .append(appendLog!=null?appendLog:"");
+        String formatAppendLog = stringBuffer.toString();
+
+        // appendlog
+        String logFileName = XxlJobFileAppender.contextHolder.get();
+        if (logFileName!=null && logFileName.trim().length()>0) {
+            XxlJobFileAppender.appendLog(logFileName, formatAppendLog);
+        } else {
+            logger.info(">>>>>>>>>>> {}", formatAppendLog);
+        }
+    }
+
+    /**
+     * append log with pattern
+     *
+     * @param appendLogPattern  like "aaa {} bbb {} ccc"
+     * @param appendLogArguments    like "111, true"
+     */
+    public static void log(String appendLogPattern, Object ... appendLogArguments) {
+
+    	FormattingTuple ft = MessageFormatter.arrayFormat(appendLogPattern, appendLogArguments);
+        String appendLog = ft.getMessage();
+
+        /*appendLog = appendLogPattern;
+        if (appendLogArguments!=null && appendLogArguments.length>0) {
+            appendLog = MessageFormat.format(appendLogPattern, appendLogArguments);
+        }*/
+
+        StackTraceElement callInfo = new Throwable().getStackTrace()[1];
+        logDetail(callInfo, appendLog);
+    }
+
+    /**
+     * append exception stack
+     *
+     * @param e
+     */
+    public static void log(Throwable e) {
+
+        StringWriter stringWriter = new StringWriter();
+        e.printStackTrace(new PrintWriter(stringWriter));
+        String appendLog = stringWriter.toString();
+
+        StackTraceElement callInfo = new Throwable().getStackTrace()[1];
+        logDetail(callInfo, appendLog);
+    }
+
+}

+ 125 - 0
xxl-job-core/src/main/java/com/xxl/job/core/thread/ExecutorRegistryThread.java

@@ -0,0 +1,125 @@
+package com.xxl.job.core.thread;
+
+import com.xxl.job.core.biz.AdminBiz;
+import com.xxl.job.core.biz.model.RegistryParam;
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.job.core.enums.RegistryConfig;
+import com.xxl.job.core.executor.XxlJobExecutor;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.concurrent.TimeUnit;
+
+/**
+ * Created by xuxueli on 17/3/2.
+ */
+public class ExecutorRegistryThread {
+    private static Logger logger = LoggerFactory.getLogger(ExecutorRegistryThread.class);
+
+    private static ExecutorRegistryThread instance = new ExecutorRegistryThread();
+    public static ExecutorRegistryThread getInstance(){
+        return instance;
+    }
+
+    private Thread registryThread;
+    private volatile boolean toStop = false;
+    public void start(final String appName, final String address){
+
+        // valid
+        if (appName==null || appName.trim().length()==0) {
+            logger.warn(">>>>>>>>>>> xxl-job, executor registry config fail, appName is null.");
+            return;
+        }
+        if (XxlJobExecutor.getAdminBizList() == null) {
+            logger.warn(">>>>>>>>>>> xxl-job, executor registry config fail, adminAddresses is null.");
+            return;
+        }
+
+        registryThread = new Thread(new Runnable() {
+            @Override
+            public void run() {
+
+                // registry
+                while (!toStop) {
+                    try {
+                        RegistryParam registryParam = new RegistryParam(RegistryConfig.RegistType.EXECUTOR.name(), appName, address);
+                        for (AdminBiz adminBiz: XxlJobExecutor.getAdminBizList()) {
+                            try {
+                                ReturnT<String> registryResult = adminBiz.registry(registryParam);
+                                if (registryResult!=null && ReturnT.SUCCESS_CODE == registryResult.getCode()) {
+                                    registryResult = ReturnT.SUCCESS;
+                                    logger.debug(">>>>>>>>>>> xxl-job registry success, registryParam:{}, registryResult:{}", new Object[]{registryParam, registryResult});
+                                    break;
+                                } else {
+                                    logger.info(">>>>>>>>>>> xxl-job registry fail, registryParam:{}, registryResult:{}", new Object[]{registryParam, registryResult});
+                                }
+                            } catch (Exception e) {
+                                logger.info(">>>>>>>>>>> xxl-job registry error, registryParam:{}", registryParam, e);
+                            }
+
+                        }
+                    } catch (Exception e) {
+                        if (!toStop) {
+                            logger.error(e.getMessage(), e);
+                        }
+
+                    }
+
+                    try {
+                        if (!toStop) {
+                            TimeUnit.SECONDS.sleep(RegistryConfig.BEAT_TIMEOUT);
+                        }
+                    } catch (InterruptedException e) {
+                        if (!toStop) {
+                            logger.warn(">>>>>>>>>>> xxl-job, executor registry thread interrupted, error msg:{}", e.getMessage());
+                        }
+                    }
+                }
+
+                // registry remove
+                try {
+                    RegistryParam registryParam = new RegistryParam(RegistryConfig.RegistType.EXECUTOR.name(), appName, address);
+                    for (AdminBiz adminBiz: XxlJobExecutor.getAdminBizList()) {
+                        try {
+                            ReturnT<String> registryResult = adminBiz.registryRemove(registryParam);
+                            if (registryResult!=null && ReturnT.SUCCESS_CODE == registryResult.getCode()) {
+                                registryResult = ReturnT.SUCCESS;
+                                logger.info(">>>>>>>>>>> xxl-job registry-remove success, registryParam:{}, registryResult:{}", new Object[]{registryParam, registryResult});
+                                break;
+                            } else {
+                                logger.info(">>>>>>>>>>> xxl-job registry-remove fail, registryParam:{}, registryResult:{}", new Object[]{registryParam, registryResult});
+                            }
+                        } catch (Exception e) {
+                            if (!toStop) {
+                                logger.info(">>>>>>>>>>> xxl-job registry-remove error, registryParam:{}", registryParam, e);
+                            }
+
+                        }
+
+                    }
+                } catch (Exception e) {
+                    if (!toStop) {
+                        logger.error(e.getMessage(), e);
+                    }
+                }
+                logger.info(">>>>>>>>>>> xxl-job, executor registry thread destory.");
+
+            }
+        });
+        registryThread.setDaemon(true);
+        registryThread.setName("xxl-job, executor ExecutorRegistryThread");
+        registryThread.start();
+    }
+
+    public void toStop() {
+        toStop = true;
+        // interrupt and wait
+        registryThread.interrupt();
+        try {
+            registryThread.join();
+        } catch (InterruptedException e) {
+            logger.error(e.getMessage(), e);
+        }
+    }
+
+}

+ 124 - 0
xxl-job-core/src/main/java/com/xxl/job/core/thread/JobLogFileCleanThread.java

@@ -0,0 +1,124 @@
+package com.xxl.job.core.thread;
+
+import com.xxl.job.core.log.XxlJobFileAppender;
+import com.xxl.job.core.util.FileUtil;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.File;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.Calendar;
+import java.util.Date;
+import java.util.concurrent.TimeUnit;
+
+/**
+ * job file clean thread
+ *
+ * @author xuxueli 2017-12-29 16:23:43
+ */
+public class JobLogFileCleanThread {
+    private static Logger logger = LoggerFactory.getLogger(JobLogFileCleanThread.class);
+
+    private static JobLogFileCleanThread instance = new JobLogFileCleanThread();
+    public static JobLogFileCleanThread getInstance(){
+        return instance;
+    }
+
+    private Thread localThread;
+    private volatile boolean toStop = false;
+    public void start(final long logRetentionDays){
+
+        // limit min value
+        if (logRetentionDays < 3 ) {
+            return;
+        }
+
+        localThread = new Thread(new Runnable() {
+            @Override
+            public void run() {
+                while (!toStop) {
+                    try {
+                        // clean log dir, over logRetentionDays
+                        File[] childDirs = new File(XxlJobFileAppender.getLogPath()).listFiles();
+                        if (childDirs!=null && childDirs.length>0) {
+
+                            // today
+                            Calendar todayCal = Calendar.getInstance();
+                            todayCal.set(Calendar.HOUR_OF_DAY,0);
+                            todayCal.set(Calendar.MINUTE,0);
+                            todayCal.set(Calendar.SECOND,0);
+                            todayCal.set(Calendar.MILLISECOND,0);
+
+                            Date todayDate = todayCal.getTime();
+
+                            for (File childFile: childDirs) {
+
+                                // valid
+                                if (!childFile.isDirectory()) {
+                                    continue;
+                                }
+                                if (childFile.getName().indexOf("-") == -1) {
+                                    continue;
+                                }
+
+                                // file create date
+                                Date logFileCreateDate = null;
+                                try {
+                                    SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd");
+                                    logFileCreateDate = simpleDateFormat.parse(childFile.getName());
+                                } catch (ParseException e) {
+                                    logger.error(e.getMessage(), e);
+                                }
+                                if (logFileCreateDate == null) {
+                                    continue;
+                                }
+
+                                if ((todayDate.getTime()-logFileCreateDate.getTime()) >= logRetentionDays * (24 * 60 * 60 * 1000) ) {
+                                    FileUtil.deleteRecursively(childFile);
+                                }
+
+                            }
+                        }
+
+                    } catch (Exception e) {
+                        if (!toStop) {
+                            logger.error(e.getMessage(), e);
+                        }
+
+                    }
+
+                    try {
+                        TimeUnit.DAYS.sleep(1);
+                    } catch (InterruptedException e) {
+                        if (!toStop) {
+                            logger.error(e.getMessage(), e);
+                        }
+                    }
+                }
+                logger.info(">>>>>>>>>>> xxl-job, executor JobLogFileCleanThread thread destory.");
+
+            }
+        });
+        localThread.setDaemon(true);
+        localThread.setName("xxl-job, executor JobLogFileCleanThread");
+        localThread.start();
+    }
+
+    public void toStop() {
+        toStop = true;
+
+        if (localThread == null) {
+            return;
+        }
+
+        // interrupt and wait
+        localThread.interrupt();
+        try {
+            localThread.join();
+        } catch (InterruptedException e) {
+            logger.error(e.getMessage(), e);
+        }
+    }
+
+}

+ 218 - 0
xxl-job-core/src/main/java/com/xxl/job/core/thread/JobThread.java

@@ -0,0 +1,218 @@
+package com.xxl.job.core.thread;
+
+import com.xxl.job.core.biz.model.HandleCallbackParam;
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.job.core.biz.model.TriggerParam;
+import com.xxl.job.core.executor.XxlJobExecutor;
+import com.xxl.job.core.handler.IJobHandler;
+import com.xxl.job.core.log.XxlJobFileAppender;
+import com.xxl.job.core.log.XxlJobLogger;
+import com.xxl.job.core.util.ShardingUtil;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.PrintWriter;
+import java.io.StringWriter;
+import java.util.Collections;
+import java.util.Date;
+import java.util.HashSet;
+import java.util.Set;
+import java.util.concurrent.*;
+
+
+/**
+ * handler thread
+ * @author xuxueli 2016-1-16 19:52:47
+ */
+public class JobThread extends Thread{
+	private static Logger logger = LoggerFactory.getLogger(JobThread.class);
+
+	private int jobId;
+	private IJobHandler handler;
+	private LinkedBlockingQueue<TriggerParam> triggerQueue;
+	private Set<Long> triggerLogIdSet;		// avoid repeat trigger for the same TRIGGER_LOG_ID
+
+	private volatile boolean toStop = false;
+	private String stopReason;
+
+    private boolean running = false;    // if running job
+	private int idleTimes = 0;			// idel times
+
+
+	public JobThread(int jobId, IJobHandler handler) {
+		this.jobId = jobId;
+		this.handler = handler;
+		this.triggerQueue = new LinkedBlockingQueue<TriggerParam>();
+		this.triggerLogIdSet = Collections.synchronizedSet(new HashSet<Long>());
+	}
+	public IJobHandler getHandler() {
+		return handler;
+	}
+
+    /**
+     * new trigger to queue
+     *
+     * @param triggerParam
+     * @return
+     */
+	public ReturnT<String> pushTriggerQueue(TriggerParam triggerParam) {
+		// avoid repeat
+		if (triggerLogIdSet.contains(triggerParam.getLogId())) {
+			logger.info(">>>>>>>>>>> repeate trigger job, logId:{}", triggerParam.getLogId());
+			return new ReturnT<String>(ReturnT.FAIL_CODE, "repeate trigger job, logId:" + triggerParam.getLogId());
+		}
+
+		triggerLogIdSet.add(triggerParam.getLogId());
+		triggerQueue.add(triggerParam);
+        return ReturnT.SUCCESS;
+	}
+
+    /**
+     * kill job thread
+     *
+     * @param stopReason
+     */
+	public void toStop(String stopReason) {
+		/**
+		 * Thread.interrupt只支持终止线程的阻塞状态(wait、join、sleep),
+		 * 在阻塞出抛出InterruptedException异常,但是并不会终止运行的线程本身;
+		 * 所以需要注意,此处彻底销毁本线程,需要通过共享变量方式;
+		 */
+		this.toStop = true;
+		this.stopReason = stopReason;
+	}
+
+    /**
+     * is running job
+     * @return
+     */
+    public boolean isRunningOrHasQueue() {
+        return running || triggerQueue.size()>0;
+    }
+
+    @Override
+	public void run() {
+
+    	// init
+    	try {
+			handler.init();
+		} catch (Throwable e) {
+    		logger.error(e.getMessage(), e);
+		}
+
+		// execute
+		while(!toStop){
+			running = false;
+			idleTimes++;
+
+            TriggerParam triggerParam = null;
+            ReturnT<String> executeResult = null;
+            try {
+				// to check toStop signal, we need cycle, so wo cannot use queue.take(), instand of poll(timeout)
+				triggerParam = triggerQueue.poll(3L, TimeUnit.SECONDS);
+				if (triggerParam!=null) {
+					running = true;
+					idleTimes = 0;
+					triggerLogIdSet.remove(triggerParam.getLogId());
+
+					// log filename, like "logPath/yyyy-MM-dd/9999.log"
+					String logFileName = XxlJobFileAppender.makeLogFileName(new Date(triggerParam.getLogDateTime()), triggerParam.getLogId());
+					XxlJobFileAppender.contextHolder.set(logFileName);
+					ShardingUtil.setShardingVo(new ShardingUtil.ShardingVO(triggerParam.getBroadcastIndex(), triggerParam.getBroadcastTotal()));
+
+					// execute
+					XxlJobLogger.log("<br>----------- xxl-job job execute start -----------<br>----------- Param:" + triggerParam.getExecutorParams());
+
+					if (triggerParam.getExecutorTimeout() > 0) {
+						// limit timeout
+						Thread futureThread = null;
+						try {
+							final TriggerParam triggerParamTmp = triggerParam;
+							FutureTask<ReturnT<String>> futureTask = new FutureTask<ReturnT<String>>(new Callable<ReturnT<String>>() {
+								@Override
+								public ReturnT<String> call() throws Exception {
+									return handler.execute(triggerParamTmp.getExecutorParams());
+								}
+							});
+							futureThread = new Thread(futureTask);
+							futureThread.start();
+
+							executeResult = futureTask.get(triggerParam.getExecutorTimeout(), TimeUnit.SECONDS);
+						} catch (TimeoutException e) {
+
+							XxlJobLogger.log("<br>----------- xxl-job job execute timeout");
+							XxlJobLogger.log(e);
+
+							executeResult = new ReturnT<String>(IJobHandler.FAIL_TIMEOUT.getCode(), "job execute timeout ");
+						} finally {
+							futureThread.interrupt();
+						}
+					} else {
+						// just execute
+						executeResult = handler.execute(triggerParam.getExecutorParams());
+					}
+
+					if (executeResult == null) {
+						executeResult = IJobHandler.FAIL;
+					} else {
+						executeResult.setMsg(
+								(executeResult!=null&&executeResult.getMsg()!=null&&executeResult.getMsg().length()>50000)
+										?executeResult.getMsg().substring(0, 50000).concat("...")
+										:executeResult.getMsg());
+						executeResult.setContent(null);	// limit obj size
+					}
+					XxlJobLogger.log("<br>----------- xxl-job job execute end(finish) -----------<br>----------- ReturnT:" + executeResult);
+
+				} else {
+					if (idleTimes > 30) {
+						if(triggerQueue.size() == 0) {	// avoid concurrent trigger causes jobId-lost
+							XxlJobExecutor.removeJobThread(jobId, "excutor idel times over limit.");
+						}
+					}
+				}
+			} catch (Throwable e) {
+				if (toStop) {
+					XxlJobLogger.log("<br>----------- JobThread toStop, stopReason:" + stopReason);
+				}
+
+				StringWriter stringWriter = new StringWriter();
+				e.printStackTrace(new PrintWriter(stringWriter));
+				String errorMsg = stringWriter.toString();
+				executeResult = new ReturnT<String>(ReturnT.FAIL_CODE, errorMsg);
+
+				XxlJobLogger.log("<br>----------- JobThread Exception:" + errorMsg + "<br>----------- xxl-job job execute end(error) -----------");
+			} finally {
+                if(triggerParam != null) {
+                    // callback handler info
+                    if (!toStop) {
+                        // commonm
+                        TriggerCallbackThread.pushCallBack(new HandleCallbackParam(triggerParam.getLogId(), triggerParam.getLogDateTime(), executeResult));
+                    } else {
+                        // is killed
+                        ReturnT<String> stopResult = new ReturnT<String>(ReturnT.FAIL_CODE, stopReason + " [job running, killed]");
+                        TriggerCallbackThread.pushCallBack(new HandleCallbackParam(triggerParam.getLogId(), triggerParam.getLogDateTime(), stopResult));
+                    }
+                }
+            }
+        }
+
+		// callback trigger request in queue
+		while(triggerQueue !=null && triggerQueue.size()>0){
+			TriggerParam triggerParam = triggerQueue.poll();
+			if (triggerParam!=null) {
+				// is killed
+				ReturnT<String> stopResult = new ReturnT<String>(ReturnT.FAIL_CODE, stopReason + " [job not executed, in the job queue, killed.]");
+				TriggerCallbackThread.pushCallBack(new HandleCallbackParam(triggerParam.getLogId(), triggerParam.getLogDateTime(), stopResult));
+			}
+		}
+
+		// destroy
+		try {
+			handler.destroy();
+		} catch (Throwable e) {
+			logger.error(e.getMessage(), e);
+		}
+
+		logger.info(">>>>>>>>>>> xxl-job JobThread stoped, hashCode:{}", Thread.currentThread());
+	}
+}

+ 246 - 0
xxl-job-core/src/main/java/com/xxl/job/core/thread/TriggerCallbackThread.java

@@ -0,0 +1,246 @@
+package com.xxl.job.core.thread;
+
+import com.xxl.job.core.biz.AdminBiz;
+import com.xxl.job.core.biz.model.HandleCallbackParam;
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.job.core.enums.RegistryConfig;
+import com.xxl.job.core.executor.XxlJobExecutor;
+import com.xxl.job.core.log.XxlJobFileAppender;
+import com.xxl.job.core.log.XxlJobLogger;
+import com.xxl.job.core.util.FileUtil;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.File;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+import java.util.concurrent.LinkedBlockingQueue;
+import java.util.concurrent.TimeUnit;
+
+/**
+ * Created by xuxueli on 16/7/22.
+ */
+public class TriggerCallbackThread {
+    private static Logger logger = LoggerFactory.getLogger(TriggerCallbackThread.class);
+
+    private static TriggerCallbackThread instance = new TriggerCallbackThread();
+    public static TriggerCallbackThread getInstance(){
+        return instance;
+    }
+
+    /**
+     * job results callback queue
+     */
+    private LinkedBlockingQueue<HandleCallbackParam> callBackQueue = new LinkedBlockingQueue<HandleCallbackParam>();
+    public static void pushCallBack(HandleCallbackParam callback){
+        getInstance().callBackQueue.add(callback);
+        logger.debug(">>>>>>>>>>> xxl-job, push callback request, logId:{}", callback.getLogId());
+    }
+
+    /**
+     * callback thread
+     */
+    private Thread triggerCallbackThread;
+    private Thread triggerRetryCallbackThread;
+    private volatile boolean toStop = false;
+    public void start() {
+
+        // valid
+        if (XxlJobExecutor.getAdminBizList() == null) {
+            logger.warn(">>>>>>>>>>> xxl-job, executor callback config fail, adminAddresses is null.");
+            return;
+        }
+
+        // callback
+        triggerCallbackThread = new Thread(new Runnable() {
+
+            @Override
+            public void run() {
+
+                // normal callback
+                while(!toStop){
+                    try {
+                        HandleCallbackParam callback = getInstance().callBackQueue.take();
+                        if (callback != null) {
+
+                            // callback list param
+                            List<HandleCallbackParam> callbackParamList = new ArrayList<HandleCallbackParam>();
+                            int drainToNum = getInstance().callBackQueue.drainTo(callbackParamList);
+                            callbackParamList.add(callback);
+
+                            // callback, will retry if error
+                            if (callbackParamList!=null && callbackParamList.size()>0) {
+                                doCallback(callbackParamList);
+                            }
+                        }
+                    } catch (Exception e) {
+                        if (!toStop) {
+                            logger.error(e.getMessage(), e);
+                        }
+                    }
+                }
+
+                // last callback
+                try {
+                    List<HandleCallbackParam> callbackParamList = new ArrayList<HandleCallbackParam>();
+                    int drainToNum = getInstance().callBackQueue.drainTo(callbackParamList);
+                    if (callbackParamList!=null && callbackParamList.size()>0) {
+                        doCallback(callbackParamList);
+                    }
+                } catch (Exception e) {
+                    if (!toStop) {
+                        logger.error(e.getMessage(), e);
+                    }
+                }
+                logger.info(">>>>>>>>>>> xxl-job, executor callback thread destory.");
+
+            }
+        });
+        triggerCallbackThread.setDaemon(true);
+        triggerCallbackThread.setName("xxl-job, executor TriggerCallbackThread");
+        triggerCallbackThread.start();
+
+
+        // retry
+        triggerRetryCallbackThread = new Thread(new Runnable() {
+            @Override
+            public void run() {
+                while(!toStop){
+                    try {
+                        retryFailCallbackFile();
+                    } catch (Exception e) {
+                        if (!toStop) {
+                            logger.error(e.getMessage(), e);
+                        }
+
+                    }
+                    try {
+                        TimeUnit.SECONDS.sleep(RegistryConfig.BEAT_TIMEOUT);
+                    } catch (InterruptedException e) {
+                        if (!toStop) {
+                            logger.error(e.getMessage(), e);
+                        }
+                    }
+                }
+                logger.info(">>>>>>>>>>> xxl-job, executor retry callback thread destory.");
+            }
+        });
+        triggerRetryCallbackThread.setDaemon(true);
+        triggerRetryCallbackThread.start();
+
+    }
+    public void toStop(){
+        toStop = true;
+        // stop callback, interrupt and wait
+        if (triggerCallbackThread != null) {    // support empty admin address
+            triggerCallbackThread.interrupt();
+            try {
+                triggerCallbackThread.join();
+            } catch (InterruptedException e) {
+                logger.error(e.getMessage(), e);
+            }
+        }
+
+        // stop retry, interrupt and wait
+        if (triggerRetryCallbackThread != null) {
+            triggerRetryCallbackThread.interrupt();
+            try {
+                triggerRetryCallbackThread.join();
+            } catch (InterruptedException e) {
+                logger.error(e.getMessage(), e);
+            }
+        }
+
+    }
+
+    /**
+     * do callback, will retry if error
+     * @param callbackParamList
+     */
+    private void doCallback(List<HandleCallbackParam> callbackParamList){
+        boolean callbackRet = false;
+        // callback, will retry if error
+        for (AdminBiz adminBiz: XxlJobExecutor.getAdminBizList()) {
+            try {
+                ReturnT<String> callbackResult = adminBiz.callback(callbackParamList);
+                if (callbackResult!=null && ReturnT.SUCCESS_CODE == callbackResult.getCode()) {
+                    callbackLog(callbackParamList, "<br>----------- xxl-job job callback finish.");
+                    callbackRet = true;
+                    break;
+                } else {
+                    callbackLog(callbackParamList, "<br>----------- xxl-job job callback fail, callbackResult:" + callbackResult);
+                }
+            } catch (Exception e) {
+                callbackLog(callbackParamList, "<br>----------- xxl-job job callback error, errorMsg:" + e.getMessage());
+            }
+        }
+        if (!callbackRet) {
+            appendFailCallbackFile(callbackParamList);
+        }
+    }
+
+    /**
+     * callback log
+     */
+    private void callbackLog(List<HandleCallbackParam> callbackParamList, String logContent){
+        for (HandleCallbackParam callbackParam: callbackParamList) {
+            String logFileName = XxlJobFileAppender.makeLogFileName(new Date(callbackParam.getLogDateTim()), callbackParam.getLogId());
+            XxlJobFileAppender.contextHolder.set(logFileName);
+            XxlJobLogger.log(logContent);
+        }
+    }
+
+
+    // ---------------------- fail-callback file ----------------------
+
+    private static String failCallbackFilePath = XxlJobFileAppender.getLogPath().concat(File.separator).concat("callbacklog").concat(File.separator);
+    private static String failCallbackFileName = failCallbackFilePath.concat("xxl-job-callback-{x}").concat(".log");
+
+    private void appendFailCallbackFile(List<HandleCallbackParam> callbackParamList){
+        // valid
+        if (callbackParamList==null || callbackParamList.size()==0) {
+            return;
+        }
+
+        // append file
+        byte[] callbackParamList_bytes = XxlJobExecutor.getSerializer().serialize(callbackParamList);
+
+        File callbackLogFile = new File(failCallbackFileName.replace("{x}", String.valueOf(System.currentTimeMillis())));
+        if (callbackLogFile.exists()) {
+            for (int i = 0; i < 100; i++) {
+                callbackLogFile = new File(failCallbackFileName.replace("{x}", String.valueOf(System.currentTimeMillis()).concat("-").concat(String.valueOf(i)) ));
+                if (!callbackLogFile.exists()) {
+                    break;
+                }
+            }
+        }
+        FileUtil.writeFileContent(callbackLogFile, callbackParamList_bytes);
+    }
+
+    private void retryFailCallbackFile(){
+
+        // valid
+        File callbackLogPath = new File(failCallbackFilePath);
+        if (!callbackLogPath.exists()) {
+            return;
+        }
+        if (callbackLogPath.isFile()) {
+            callbackLogPath.delete();
+        }
+        if (!(callbackLogPath.isDirectory() && callbackLogPath.list()!=null && callbackLogPath.list().length>0)) {
+            return;
+        }
+
+        // load and clear file, retry
+        for (File callbaclLogFile: callbackLogPath.listFiles()) {
+            byte[] callbackParamList_bytes = FileUtil.readFileContent(callbaclLogFile);
+            List<HandleCallbackParam> callbackParamList = (List<HandleCallbackParam>) XxlJobExecutor.getSerializer().deserialize(callbackParamList_bytes, HandleCallbackParam.class);
+
+            callbaclLogFile.delete();
+            doCallback(callbackParamList);
+        }
+
+    }
+
+}

+ 148 - 0
xxl-job-core/src/main/java/com/xxl/job/core/util/DateUtil.java

@@ -0,0 +1,148 @@
+package com.xxl.job.core.util;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.text.DateFormat;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.Calendar;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * date util
+ *
+ * @author xuxueli 2018-08-19 01:24:11
+ */
+public class DateUtil {
+
+    // ---------------------- format parse ----------------------
+    private static Logger logger = LoggerFactory.getLogger(DateUtil.class);
+
+    private static final String DATE_FORMAT = "yyyy-MM-dd";
+    private static final String DATETIME_FORMAT = "yyyy-MM-dd HH:mm:ss";
+
+    private static final ThreadLocal<Map<String, DateFormat>> dateFormatThreadLocal = new ThreadLocal<Map<String, DateFormat>>();
+    private static DateFormat getDateFormat(String pattern) {
+        if (pattern==null || pattern.trim().length()==0) {
+            throw new IllegalArgumentException("pattern cannot be empty.");
+        }
+
+        Map<String, DateFormat> dateFormatMap = dateFormatThreadLocal.get();
+        if(dateFormatMap!=null && dateFormatMap.containsKey(pattern)){
+            return dateFormatMap.get(pattern);
+        }
+
+        synchronized (dateFormatThreadLocal) {
+            if (dateFormatMap == null) {
+                dateFormatMap = new HashMap<String, DateFormat>();
+            }
+            dateFormatMap.put(pattern, new SimpleDateFormat(pattern));
+            dateFormatThreadLocal.set(dateFormatMap);
+        }
+
+        return dateFormatMap.get(pattern);
+    }
+
+    /**
+     * format datetime. like "yyyy-MM-dd"
+     *
+     * @param date
+     * @return
+     * @throws ParseException
+     */
+    public static String formatDate(Date date) {
+        return format(date, DATE_FORMAT);
+    }
+
+    /**
+     * format date. like "yyyy-MM-dd HH:mm:ss"
+     *
+     * @param date
+     * @return
+     * @throws ParseException
+     */
+    public static String formatDateTime(Date date) {
+        return format(date, DATETIME_FORMAT);
+    }
+
+    /**
+     * format date
+     *
+     * @param date
+     * @param patten
+     * @return
+     * @throws ParseException
+     */
+    public static String format(Date date, String patten) {
+        return getDateFormat(patten).format(date);
+    }
+
+    /**
+     * parse date string, like "yyyy-MM-dd HH:mm:s"
+     *
+     * @param dateString
+     * @return
+     * @throws ParseException
+     */
+    public static Date parseDate(String dateString){
+        return parse(dateString, DATE_FORMAT);
+    }
+
+    /**
+     * parse datetime string, like "yyyy-MM-dd HH:mm:ss"
+     *
+     * @param dateString
+     * @return
+     * @throws ParseException
+     */
+    public static Date parseDateTime(String dateString) {
+        return parse(dateString, DATETIME_FORMAT);
+    }
+
+    /**
+     * parse date
+     *
+     * @param dateString
+     * @param pattern
+     * @return
+     * @throws ParseException
+     */
+    public static Date parse(String dateString, String pattern) {
+        try {
+            Date date = getDateFormat(pattern).parse(dateString);
+            return date;
+        } catch (Exception e) {
+            logger.warn("parse date error, dateString = {}, pattern={}; errorMsg = {}", dateString, pattern, e.getMessage());
+            return null;
+        }
+    }
+
+
+    // ---------------------- add date ----------------------
+
+    public static Date addYears(final Date date, final int amount) {
+        return add(date, Calendar.YEAR, amount);
+    }
+
+    public static Date addMonths(final Date date, final int amount) {
+        return add(date, Calendar.MONTH, amount);
+    }
+
+    public static Date addDays(final Date date, final int amount) {
+        return add(date, Calendar.DAY_OF_MONTH, amount);
+    }
+
+    private static Date add(final Date date, final int calendarField, final int amount) {
+        if (date == null) {
+            return null;
+        }
+        final Calendar c = Calendar.getInstance();
+        c.setTime(date);
+        c.add(calendarField, amount);
+        return c.getTime();
+    }
+
+}

+ 179 - 0
xxl-job-core/src/main/java/com/xxl/job/core/util/FileUtil.java

@@ -0,0 +1,179 @@
+package com.xxl.job.core.util;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+
+/**
+ * file tool
+ *
+ * @author xuxueli 2017-12-29 17:56:48
+ */
+public class FileUtil {
+    private static Logger logger = LoggerFactory.getLogger(FileUtil.class);
+
+
+    /**
+     * delete recursively
+     *
+     * @param root
+     * @return
+     */
+    public static boolean deleteRecursively(File root) {
+        if (root != null && root.exists()) {
+            if (root.isDirectory()) {
+                File[] children = root.listFiles();
+                if (children != null) {
+                    for (File child : children) {
+                        deleteRecursively(child);
+                    }
+                }
+            }
+            return root.delete();
+        }
+        return false;
+    }
+
+
+    public static void deleteFile(String fileName) {
+        // file
+        File file = new File(fileName);
+        if (file.exists()) {
+            file.delete();
+        }
+    }
+
+
+    public static void writeFileContent(File file, byte[] data) {
+
+        // file
+        if (!file.exists()) {
+            file.getParentFile().mkdirs();
+        }
+
+        // append file content
+        FileOutputStream fos = null;
+        try {
+            fos = new FileOutputStream(file);
+            fos.write(data);
+            fos.flush();
+        } catch (Exception e) {
+            logger.error(e.getMessage(), e);
+        } finally {
+            if (fos != null) {
+                try {
+                    fos.close();
+                } catch (IOException e) {
+                    logger.error(e.getMessage(), e);
+                }
+            }
+        }
+
+    }
+
+    public static byte[] readFileContent(File file) {
+        Long filelength = file.length();
+        byte[] filecontent = new byte[filelength.intValue()];
+
+        FileInputStream in = null;
+        try {
+            in = new FileInputStream(file);
+            in.read(filecontent);
+            in.close();
+        } catch (Exception e) {
+            logger.error(e.getMessage(), e);
+        } finally {
+            if (in != null) {
+                try {
+                    in.close();
+                } catch (IOException e) {
+                    logger.error(e.getMessage(), e);
+                }
+            }
+        }
+        return filecontent;
+    }
+
+
+    /*public static void appendFileLine(String fileName, String content) {
+
+        // file
+        File file = new File(fileName);
+        if (!file.exists()) {
+            try {
+                file.createNewFile();
+            } catch (IOException e) {
+                logger.error(e.getMessage(), e);
+                return;
+            }
+        }
+
+        // content
+        if (content == null) {
+            content = "";
+        }
+        content += "\r\n";
+
+        // append file content
+        FileOutputStream fos = null;
+        try {
+            fos = new FileOutputStream(file, true);
+            fos.write(content.getBytes("utf-8"));
+            fos.flush();
+        } catch (Exception e) {
+            logger.error(e.getMessage(), e);
+        } finally {
+            if (fos != null) {
+                try {
+                    fos.close();
+                } catch (IOException e) {
+                    logger.error(e.getMessage(), e);
+                }
+            }
+        }
+
+    }
+
+    public static List<String> loadFileLines(String fileName){
+
+        List<String> result = new ArrayList<>();
+
+        // valid log file
+        File file = new File(fileName);
+        if (!file.exists()) {
+            return result;
+        }
+
+        // read file
+        StringBuffer logContentBuffer = new StringBuffer();
+        int toLineNum = 0;
+        LineNumberReader reader = null;
+        try {
+            //reader = new LineNumberReader(new FileReader(logFile));
+            reader = new LineNumberReader(new InputStreamReader(new FileInputStream(file), "utf-8"));
+            String line = null;
+            while ((line = reader.readLine())!=null) {
+                if (line!=null && line.trim().length()>0) {
+                    result.add(line);
+                }
+            }
+        } catch (IOException e) {
+            logger.error(e.getMessage(), e);
+        } finally {
+            if (reader != null) {
+                try {
+                    reader.close();
+                } catch (IOException e) {
+                    logger.error(e.getMessage(), e);
+                }
+            }
+        }
+
+        return result;
+    }*/
+
+}

+ 228 - 0
xxl-job-core/src/main/java/com/xxl/job/core/util/ScriptUtil.java

@@ -0,0 +1,228 @@
+package com.xxl.job.core.util;
+
+import com.xxl.job.core.log.XxlJobLogger;
+
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ *  1、内嵌编译器如"PythonInterpreter"无法引用扩展包,因此推荐使用java调用控制台进程方式"Runtime.getRuntime().exec()"来运行脚本(shell或python);
+ *  2、因为通过java调用控制台进程方式实现,需要保证目标机器PATH路径正确配置对应编译器;
+ *  3、暂时脚本执行日志只能在脚本执行结束后一次性获取,无法保证实时性;因此为确保日志实时性,可改为将脚本打印的日志存储在指定的日志文件上;
+ *  4、python 异常输出优先级高于标准输出,体现在Log文件中,因此推荐通过logging方式打日志保持和异常信息一致;否则用prinf日志顺序会错乱
+ *
+ * Created by xuxueli on 17/2/25.
+ */
+public class ScriptUtil {
+
+    /**
+     * make script file
+     *
+     * @param scriptFileName
+     * @param content
+     * @throws IOException
+     */
+    public static void markScriptFile(String scriptFileName, String content) throws IOException {
+        // make file,   filePath/gluesource/666-123456789.py
+        FileOutputStream fileOutputStream = null;
+        try {
+            fileOutputStream = new FileOutputStream(scriptFileName);
+            fileOutputStream.write(content.getBytes("UTF-8"));
+            fileOutputStream.close();
+        } catch (Exception e) {
+            throw e;
+        }finally{
+            if(fileOutputStream != null){
+                fileOutputStream.close();
+            }
+        }
+    }
+
+    /**
+     * 脚本执行,日志文件实时输出
+     *
+     * @param command
+     * @param scriptFile
+     * @param logFile
+     * @param params
+     * @return
+     * @throws IOException
+     */
+    public static int execToFile(String command, String scriptFile, String logFile, String... params) throws IOException {
+
+        FileOutputStream fileOutputStream = null;
+        Thread inputThread = null;
+        Thread errThread = null;
+        try {
+            // file
+            fileOutputStream = new FileOutputStream(logFile, true);
+
+            // command
+            List<String> cmdarray = new ArrayList<>();
+            cmdarray.add(command);
+            cmdarray.add(scriptFile);
+            if (params!=null && params.length>0) {
+                for (String param:params) {
+                    cmdarray.add(param);
+                }
+            }
+            String[] cmdarrayFinal = cmdarray.toArray(new String[cmdarray.size()]);
+
+            // process-exec
+            final Process process = Runtime.getRuntime().exec(cmdarrayFinal);
+
+            // log-thread
+            final FileOutputStream finalFileOutputStream = fileOutputStream;
+            inputThread = new Thread(new Runnable() {
+                @Override
+                public void run() {
+                    try {
+                        copy(process.getInputStream(), finalFileOutputStream, new byte[1024]);
+                    } catch (IOException e) {
+                        XxlJobLogger.log(e);
+                    }
+                }
+            });
+            errThread = new Thread(new Runnable() {
+                @Override
+                public void run() {
+                    try {
+                        copy(process.getErrorStream(), finalFileOutputStream, new byte[1024]);
+                    } catch (IOException e) {
+                        XxlJobLogger.log(e);
+                    }
+                }
+            });
+            inputThread.start();
+            errThread.start();
+
+            // process-wait
+            int exitValue = process.waitFor();      // exit code: 0=success, 1=error
+
+            // log-thread join
+            inputThread.join();
+            errThread.join();
+
+            return exitValue;
+        } catch (Exception e) {
+            XxlJobLogger.log(e);
+            return -1;
+        } finally {
+            if (fileOutputStream != null) {
+                try {
+                    fileOutputStream.close();
+                } catch (IOException e) {
+                    XxlJobLogger.log(e);
+                }
+
+            }
+            if (inputThread != null && inputThread.isAlive()) {
+                inputThread.interrupt();
+            }
+            if (errThread != null && errThread.isAlive()) {
+                errThread.interrupt();
+            }
+        }
+    }
+
+    /**
+     * 数据流Copy(Input自动关闭,Output不处理)
+     *
+     * @param inputStream
+     * @param outputStream
+     * @param buffer
+     * @return
+     * @throws IOException
+     */
+    private static long copy(InputStream inputStream, OutputStream outputStream, byte[] buffer) throws IOException {
+        try {
+            long total = 0;
+            for (;;) {
+                int res = inputStream.read(buffer);
+                if (res == -1) {
+                    break;
+                }
+                if (res > 0) {
+                    total += res;
+                    if (outputStream != null) {
+                        outputStream.write(buffer, 0, res);
+                    }
+                }
+            }
+            outputStream.flush();
+            //out = null;
+            inputStream.close();
+            inputStream = null;
+            return total;
+        } finally {
+            if (inputStream != null) {
+                inputStream.close();
+            }
+        }
+    }
+
+    /**
+     * 脚本执行,日志文件实时输出
+     *
+     * 优点:支持将目标数据实时输出到指定日志文件中去
+     * 缺点:
+     *      标准输出和错误输出优先级固定,可能和脚本中顺序不一致
+     *      Java无法实时获取
+     *
+     *      <!-- commons-exec -->
+     * 		<dependency>
+     * 			<groupId>org.apache.commons</groupId>
+     * 			<artifactId>commons-exec</artifactId>
+     * 			<version>${commons-exec.version}</version>
+     * 		</dependency>
+     *
+     * @param command
+     * @param scriptFile
+     * @param logFile
+     * @param params
+     * @return
+     * @throws IOException
+     */
+    /*public static int execToFileB(String command, String scriptFile, String logFile, String... params) throws IOException {
+        // 标准输出:print (null if watchdog timeout)
+        // 错误输出:logging + 异常 (still exists if watchdog timeout)
+        // 标准输入
+
+        FileOutputStream fileOutputStream = null;   //
+        try {
+            fileOutputStream = new FileOutputStream(logFile, true);
+            PumpStreamHandler streamHandler = new PumpStreamHandler(fileOutputStream, fileOutputStream, null);
+
+            // command
+            CommandLine commandline = new CommandLine(command);
+            commandline.addArgument(scriptFile);
+            if (params!=null && params.length>0) {
+                commandline.addArguments(params);
+            }
+
+            // exec
+            DefaultExecutor exec = new DefaultExecutor();
+            exec.setExitValues(null);
+            exec.setStreamHandler(streamHandler);
+            int exitValue = exec.execute(commandline);  // exit code: 0=success, 1=error
+            return exitValue;
+        } catch (Exception e) {
+            XxlJobLogger.log(e);
+            return -1;
+        } finally {
+            if (fileOutputStream != null) {
+                try {
+                    fileOutputStream.close();
+                } catch (IOException e) {
+                    XxlJobLogger.log(e);
+                }
+
+            }
+        }
+    }*/
+
+}

+ 46 - 0
xxl-job-core/src/main/java/com/xxl/job/core/util/ShardingUtil.java

@@ -0,0 +1,46 @@
+package com.xxl.job.core.util;
+
+/**
+ * sharding vo
+ * @author xuxueli 2017-07-25 21:26:38
+ */
+public class ShardingUtil {
+
+    private static InheritableThreadLocal<ShardingVO> contextHolder = new InheritableThreadLocal<ShardingVO>();
+
+    public static class ShardingVO {
+
+        private int index;  // sharding index
+        private int total;  // sharding total
+
+        public ShardingVO(int index, int total) {
+            this.index = index;
+            this.total = total;
+        }
+
+        public int getIndex() {
+            return index;
+        }
+
+        public void setIndex(int index) {
+            this.index = index;
+        }
+
+        public int getTotal() {
+            return total;
+        }
+
+        public void setTotal(int total) {
+            this.total = total;
+        }
+    }
+
+    public static void setShardingVo(ShardingVO shardingVo){
+        contextHolder.set(shardingVo);
+    }
+
+    public static ShardingVO getShardingVo(){
+        return contextHolder.get();
+    }
+
+}

+ 162 - 0
xxl-job-core/src/main/java/com/xxl/job/core/util/XxlJobRemotingUtil.java

@@ -0,0 +1,162 @@
+package com.xxl.job.core.util;
+
+import com.xxl.job.core.biz.model.ReturnT;
+import com.xxl.registry.client.util.json.BasicJson;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import javax.net.ssl.*;
+import java.io.BufferedReader;
+import java.io.DataOutputStream;
+import java.io.InputStreamReader;
+import java.net.HttpURLConnection;
+import java.net.URL;
+import java.security.cert.CertificateException;
+import java.security.cert.X509Certificate;
+import java.util.Map;
+
+/**
+ * @author xuxueli 2018-11-25 00:55:31
+ */
+public class XxlJobRemotingUtil {
+    private static Logger logger = LoggerFactory.getLogger(XxlJobRemotingUtil.class);
+    public static String XXL_RPC_ACCESS_TOKEN = "XXL-RPC-ACCESS-TOKEN";
+
+
+    // trust-https start
+    private static void trustAllHosts(HttpsURLConnection connection) {
+        try {
+            SSLContext sc = SSLContext.getInstance("TLS");
+            sc.init(null, trustAllCerts, new java.security.SecureRandom());
+            SSLSocketFactory newFactory = sc.getSocketFactory();
+
+            connection.setSSLSocketFactory(newFactory);
+        } catch (Exception e) {
+            logger.error(e.getMessage(), e);
+        }
+        connection.setHostnameVerifier(new HostnameVerifier() {
+            public boolean verify(String hostname, SSLSession session) {
+                return true;
+            }
+        });
+    }
+    private static final TrustManager[] trustAllCerts = new TrustManager[]{new X509TrustManager() {
+        public X509Certificate[] getAcceptedIssuers() {
+            return new X509Certificate[]{};
+        }
+        public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException {
+        }
+        public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException {
+        }
+    }};
+    // trust-https end
+
+
+    /**
+     * post
+     *
+     * @param url
+     * @param accessToken
+     * @param requestObj
+     * @return
+     */
+    public static ReturnT<String> postBody(String url, String accessToken, Object requestObj, int timeout) {
+        HttpURLConnection connection = null;
+        BufferedReader bufferedReader = null;
+        try {
+            // connection
+            URL realUrl = new URL(url);
+            connection = (HttpURLConnection) realUrl.openConnection();
+
+            // trust-https
+            boolean useHttps = url.startsWith("https");
+            if (useHttps) {
+                HttpsURLConnection https = (HttpsURLConnection) connection;
+                trustAllHosts(https);
+            }
+
+            // connection setting
+            connection.setRequestMethod("POST");
+            connection.setDoOutput(true);
+            connection.setDoInput(true);
+            connection.setUseCaches(false);
+            connection.setReadTimeout(timeout * 1000);
+            connection.setConnectTimeout(3 * 1000);
+            connection.setRequestProperty("connection", "Keep-Alive");
+            connection.setRequestProperty("Content-Type", "application/json;charset=UTF-8");
+            connection.setRequestProperty("Accept-Charset", "application/json;charset=UTF-8");
+
+            if(accessToken!=null && accessToken.trim().length()>0){
+                connection.setRequestProperty(XXL_RPC_ACCESS_TOKEN, accessToken);
+            }
+
+            // do connection
+            connection.connect();
+
+            // write requestBody
+            String requestBody = BasicJson.toJson(requestObj);
+
+            DataOutputStream dataOutputStream = new DataOutputStream(connection.getOutputStream());
+            dataOutputStream.write(requestBody.getBytes("UTF-8"));
+            dataOutputStream.flush();
+            dataOutputStream.close();
+
+            /*byte[] requestBodyBytes = requestBody.getBytes("UTF-8");
+            connection.setRequestProperty("Content-Length", String.valueOf(requestBodyBytes.length));
+            OutputStream outwritestream = connection.getOutputStream();
+            outwritestream.write(requestBodyBytes);
+            outwritestream.flush();
+            outwritestream.close();*/
+
+            // valid StatusCode
+            int statusCode = connection.getResponseCode();
+            if (statusCode != 200) {
+                return new ReturnT<String>(ReturnT.FAIL_CODE, "xxl-rpc remoting fail, StatusCode("+ statusCode +") invalid. for url : " + url);
+            }
+
+            // result
+            bufferedReader = new BufferedReader(new InputStreamReader(connection.getInputStream()));
+            StringBuilder result = new StringBuilder();
+            String line;
+            while ((line = bufferedReader.readLine()) != null) {
+                result.append(line);
+            }
+            String resultJson = result.toString();
+
+            // parse returnT
+            try {
+                Map<String, Object> resultMap = BasicJson.parseMap(resultJson);
+
+                ReturnT<String> returnT = new ReturnT<String>();
+                if (resultMap==null) {
+                    returnT.setCode(ReturnT.FAIL_CODE);
+                    returnT.setMsg("AdminBizClient Remoting call fail.");
+                } else {
+                    returnT.setCode(Integer.valueOf(String.valueOf(resultMap.get("code"))));
+                    returnT.setMsg(String.valueOf(resultMap.get("msg")));
+                    returnT.setContent(String.valueOf(resultMap.get("content")));
+                }
+                return returnT;
+            } catch (Exception e) {
+                logger.error("xxl-rpc remoting (url="+url+") response content invalid("+ resultJson +").", e);
+                return new ReturnT<String>(ReturnT.FAIL_CODE, "xxl-rpc remoting (url="+url+") response content invalid("+ resultJson +").");
+            }
+
+        } catch (Exception e) {
+            logger.error(e.getMessage(), e);
+            return new ReturnT<String>(ReturnT.FAIL_CODE, "xxl-rpc remoting error("+ e.getMessage() +"), for url : " + url);
+        } finally {
+            try {
+                if (bufferedReader != null) {
+                    bufferedReader.close();
+                }
+                if (connection != null) {
+                    connection.disconnect();
+                }
+            } catch (Exception e2) {
+                logger.error(e2.getMessage(), e2);
+            }
+        }
+    }
+
+}