lfx 1 år sedan
förälder
incheckning
ecf1751e41

+ 65 - 0
src/main/java/com/muzhi/tianhe/controller/TBCallBackController.java

@@ -0,0 +1,65 @@
+package com.muzhi.tianhe.controller;
+
+import com.alibaba.fastjson.JSONObject;
+import com.muzhi.tianhe.service.ThTbService;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+/**
+ * TB事件回调 3_1
+ * 1. 回调可选择加密与不加密方式, tb发送成功为上游, 注册服务为下游
+ * 2. 绑定回调需要安装后才会生效, 且回调范围更新后需要重新安装才会生效 [另外接口调用修改配置需要重新发布后生效]
+ */
+@Slf4j
+@RestController
+@RequestMapping("/mc/tb")
+public class TBCallBackController {
+
+    @Autowired
+    private ThTbService thTbService;
+
+    /**
+     * * 回调说明 [ppExt: 字段更新回调, 判定字段ID, 避免循坏触发问题, 接口修改也会触发webhook]
+     * * 1. 通过接口更操作的数据,也会与手动创建一样触发相同的回调, 除了项目更新接口调用实测不会触发回调, 手动修改正常回调
+     * * 2. 项目创建会推送两次
+     * * - 1. 在第二次推送多 { data: { project: { operatorId, url }} } 这两个字段内容
+     * * - 2. 若是通过模板创建的项目,在两次项目更新回调中会回调一次 project.enable 回调, 其中任务只会回调创建, 不会回调更新
+     * * 3. 任务创建, 会先回调创建事件, 接着立即回调任务更新事件 [若是通过模板创建, 任务只会回调创建, 不会回调更新]
+     * * 4. 项目移入回收站,不会触发回调,删除后会触发项目与任务的 remove 事件; 若是将任务移入回收站, 会触发任务更新回调
+     */
+    @PostMapping("/callback")
+    public String callback(@RequestBody JSONObject eventJson) {
+        String success = "success";
+        String eventName = eventJson.getString("event");
+        if ("VERIFY_HOOK".equals(eventName)) {
+            log.info("----- [TB]验证注册 -----");
+            return success;
+        }
+
+        if (eventName.contains("task")) {
+            log.info("[TB]任务回调, {}, {}", eventName, eventJson);
+            if(eventName.equals("v3.task.taskflowstatus.update")){
+                String taskId=eventJson.getJSONObject("data").getString("taskId");
+                String projectId=eventJson.getJSONObject("data").getString("projectId");
+                if(projectId.equals("664c52c05a93ac02400705fd")||projectId.equals("65b9e2525a93ac024005cf10")){
+                    thTbService.syncTaskState(taskId);
+                }
+            }else if(eventName.equals("v3.task.archive")){
+                // 归档
+            }
+            return success;
+        }
+
+        if (eventName.contains("project")) {
+            log.info("[TB]项目回调, {}, {}", eventName, eventJson);
+            return success;
+        }
+
+        log.info("----- [TB]已注册, 未处理的其它回调 -----, {}, {}", eventName, eventJson);
+        return success;
+    }
+}

+ 7 - 0
src/main/java/com/muzhi/tianhe/service/ThTbService.java

@@ -0,0 +1,7 @@
+package com.muzhi.tianhe.service;
+
+public interface ThTbService {
+
+    void syncTaskState(String taskId);
+
+}

+ 39 - 6
src/main/java/com/muzhi/tianhe/service/impl/TbApiService.java

@@ -5,6 +5,7 @@ import cn.hutool.http.HttpUtil;
 import com.alibaba.fastjson.JSONArray;
 import com.alibaba.fastjson.JSONObject;
 import com.muzhi.tianhe.service.AccessTokenService;
+import com.muzhi.tianhe.util.PublicUtil;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
@@ -24,10 +25,16 @@ public class TbApiService {
 
     public static String DING_CORP_ID = "dinga41ec6a58a4911d0f2c783f7214b6d69";
     public static String tbOrganizationId = "65b1dca21ab0fa13be993595";
+    public static String tbOperatorId = "65b1dc8355d0f38026a1c3db"; // guhuchen
 
     public JSONArray getProjectList(){
-        JSONObject result=header(HttpRequest.get(PRIVATE_API_URL + "/v3/project/query?pageSize=1000"));
-        return result.getJSONArray("result");
+        JSONObject result=new JSONObject();
+        JSONArray array=new JSONArray();
+        do {
+            result=header(HttpRequest.get(PRIVATE_API_URL + "/v3/project/query?pageSize=1000&pageToken="+result.getString("nextPageToken")));
+            array.addAll(result.getJSONArray("result"));
+        }while (!PublicUtil.isNull(result.getString("nextPageToken")));
+        return array;
     }
 
     public JSONArray getProjectInfo(String projectId){
@@ -45,6 +52,35 @@ public class TbApiService {
         return result.getJSONArray("result");
     }
 
+    public JSONArray getTasksInfo(String taskId){
+        JSONObject result=header(HttpRequest.get(PRIVATE_API_URL + "/v3/task/query?taskId="+taskId));
+        return result.getJSONArray("result");
+    }
+
+    public JSONArray getTasksByParent(String parentTaskId){
+        JSONObject result=header(HttpRequest.get(PRIVATE_API_URL + "/v3/task/query?parentTaskId="+parentTaskId));
+        return result.getJSONArray("result");
+    }
+
+    public JSONArray getProjectTfid(String projectId,String q){
+        JSONObject result=header(HttpRequest.get(PRIVATE_API_URL + "/v3/project/"+projectId+"/taskflow/search?q="+q));
+        return result.getJSONArray("result");
+    }
+
+    public JSONArray getProjectStateId(String projectId,String q,String tfIds,String tfsIds){
+        JSONObject result=header(HttpRequest.get(PRIVATE_API_URL + "/v3/project/"+projectId+"/taskflowstatus/search?q="+q+"&tfIds="+tfIds+"&tfsIds="+tfsIds));
+        return result.getJSONArray("result");
+    }
+
+    public Object updateTaskStatus(String taskId,String taskflowstatusId){
+        Map map=new HashMap();
+        map.put("taskflowstatusId",taskflowstatusId);
+        JSONObject result=header(HttpRequest.put(PRIVATE_API_URL + "/v3/task/{taskId}/taskflowstatus".replace("{taskId}",taskId))
+                .header("x-operator-id",tbOperatorId)
+                .body(JSONObject.toJSONString(map)));
+        return result;
+    }
+
     public JSONArray getProjectCust(String projectId){
         JSONObject result=header(HttpRequest.get(PRIVATE_API_URL + "/v3/project/"+ projectId +"/status/customfield/list"));
         return result.getJSONArray("result");
@@ -66,10 +102,7 @@ public class TbApiService {
     }
 
     public JSONArray getProjectState(String projectId){
-        Map param = new HashMap();
-        param.put("pageSize", 1000);
-        JSONObject result=header(HttpUtil.createGet(PRIVATE_API_URL + "/v3/project/{projectId}/status/list".replace("{projectId}",projectId))
-                .form(param));
+        JSONObject result=header(HttpUtil.createGet(PRIVATE_API_URL + "v3/project/{projectId}/taskflowstatus/search".replace("{projectId}",projectId)));
         return result.getJSONArray("result");
     }
 

+ 12 - 1
src/main/java/com/muzhi/tianhe/service/impl/TbServiceImpl.java

@@ -454,7 +454,18 @@ public class TbServiceImpl extends ServiceImpl<TianheMapper, Tianhe> implements
     @Override
     @Async
     public void asyncXm() {
+        long startTime = System.currentTimeMillis();
         getXiangmu();
+        long endTime = System.currentTimeMillis();
+        long executionTime = endTime - startTime;
+        System.out.println("方法执行耗时: " + formatExecutionTime(executionTime));
+    }
+    private static String formatExecutionTime(long executionTimeInMillis) {
+        long minutes = executionTimeInMillis / (60 * 1000);
+        long seconds = (executionTimeInMillis % (60 * 1000)) / 1000;
+        long milliseconds = executionTimeInMillis % 1000;
+
+        return String.format("%d分%d秒%d毫秒", minutes, seconds, milliseconds);
     }
 
     @Override
@@ -539,7 +550,7 @@ public class TbServiceImpl extends ServiceImpl<TianheMapper, Tianhe> implements
      */
     public String getProjectState(String projectId) {
         try {
-            JSONArray array=tbApiService.getProjectState(projectId);
+            JSONArray array=tbApiService.getProjectCust(projectId);
             if(array!=null&&array.size()>0){
                 return array.getJSONObject(0).getString("name");
             }

+ 97 - 0
src/main/java/com/muzhi/tianhe/service/impl/ThTbServiceImpl.java

@@ -0,0 +1,97 @@
+package com.muzhi.tianhe.service.impl;
+
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import com.muzhi.tianhe.service.ThTbService;
+import com.muzhi.tianhe.util.PublicUtil;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+@Slf4j
+@Service
+public class ThTbServiceImpl implements ThTbService {
+
+    @Autowired
+    private TbApiService tbApiService;
+
+
+    @Override
+    public void syncTaskState(String taskId) {
+        JSONObject task=tbApiService.getTasksInfo(taskId).getJSONObject(0);
+        String tfsId=task.getString("tfsId");// 状态ID
+        String projectId=task.getString("projectId");
+        JSONObject tfs=tbApiService.getProjectStateId(projectId,"","",tfsId).getJSONObject(0);
+        if(task.getJSONArray("ancestorIds").size()<3){
+            log.info("非指标任务 不处理");
+            return;
+        }
+        updateTaskState(task);
+    }
+
+    public void updateTaskState(JSONObject task){
+        String projectId=task.getString("projectId");// 项目ID
+        // 上级任务信息
+        String parentTaskId=task.getString("parentTaskId");// 上级任务ID
+        JSONObject parentTask=tbApiService.getTasksInfo(parentTaskId).getJSONObject(0);
+        JSONObject parentTaskTfs=tbApiService.getProjectStateId(projectId,"","",parentTask.getString("tfsId")).getJSONObject(0);
+        String parentTaskTfsName=parentTaskTfs.getString("name");
+        String type=getType(task.getJSONArray("ancestorIds").size());
+        String newTfsName;
+        // 循环获取其他同级任务状态,判断是否有更高级别的任务状态
+        // 同级红灯状态ID
+        JSONObject tf=tbApiService.getProjectTfid(projectId,getType(task.getJSONArray("ancestorIds").size()+1)).getJSONObject(0);
+        JSONObject redTfs=tbApiService.getProjectStateId(projectId,"红灯",tf.getString("id"),"").getJSONObject(0);
+        String redId=redTfs.getString("id");
+        // 同级黄状态ID
+        JSONObject yellowTfs=tbApiService.getProjectStateId(projectId,"黄灯",tf.getString("id"),"").getJSONObject(0);
+        String yellowId=yellowTfs.getString("id");
+        JSONArray array=tbApiService.getTasksByParent(parentTaskId);
+        String color="绿灯";
+        int redNum=0,yellowNum=0;
+        for (int i = 0; i < array.size(); i++) {
+            JSONObject taskT=array.getJSONObject(i);
+            if(redId.equals(taskT.getString("tfsId"))){
+                redNum++;
+            }else if(yellowId.equals(taskT.getString("tfsId"))){
+                yellowNum++;
+            }
+        }
+        if(yellowNum>=2){
+            color="黄灯";
+        }
+        if(redNum>=2){
+            color="红灯";
+        }
+        if(!color.equals(parentTaskTfsName)){
+            newTfsName=color;
+        }else{
+            return;
+        }
+        update(projectId,parentTaskId,newTfsName,type);
+        if(!PublicUtil.isNull(parentTask.getString("parentTaskId"))){
+            updateTaskState(parentTask);
+        }
+    }
+
+    public String getType(int size){
+        switch (size){
+            case 1:
+                return"一级任务工作流";
+            case 2:
+                return "二级任务工作流";
+            case 3:
+                return "三级任务工作流";
+            case 4:
+                return "年度指标工作流";
+            default:return "";
+        }
+    }
+
+    public void update(String projectId,String taskId,String tfsName,String type){
+        log.info("任务[{}]状态修改为[{}]",taskId,tfsName);
+        JSONObject tf=tbApiService.getProjectTfid(projectId,type).getJSONObject(0);
+        JSONObject tfsnext=tbApiService.getProjectStateId(projectId,tfsName,tf.getString("id"),"").getJSONObject(0);
+        tbApiService.updateTaskStatus(taskId,tfsnext.getString("id"));
+    }
+}

+ 17 - 5
src/test/java/com/muzhi/tianhe/TbTest.java

@@ -7,7 +7,9 @@ import com.alibaba.fastjson.JSONArray;
 import com.alibaba.fastjson.JSONObject;
 import com.muzhi.tianhe.service.AccessTokenService;
 import com.muzhi.tianhe.service.TbService;
+import com.muzhi.tianhe.service.ThTbService;
 import com.muzhi.tianhe.service.impl.TbApiService;
+import com.muzhi.tianhe.util.PublicUtil;
 import lombok.extern.slf4j.Slf4j;
 import okhttp3.OkHttpClient;
 import okhttp3.Request;
@@ -30,6 +32,8 @@ public class TbTest {
     private TbService tbService;
     @Autowired
     private TbApiService tbApiService;
+    @Autowired
+    private ThTbService thTbService;
 
     @Test
     public void test(){
@@ -38,8 +42,9 @@ public class TbTest {
 //            tbService.getXiangmu();
 //            List users=tbService.projectMember("65eefe214f2eb1fe4e88b557");
 //            log.info("u:{}",users);
-            tbService.test();
+//            tbService.test();
 //            tbService.getDingUserId("");
+            tbApiService.getProjectList();
         } catch (Exception e) {
             e.printStackTrace();
         }
@@ -47,12 +52,19 @@ public class TbTest {
 
     @Test
     public void tbTest(){
-        String projectId="65b9e2525a93ac024005cf10";
-        String taskType="";
-        JSONArray array=tbApiService.getProjectList();
-        System.out.println(array.getJSONObject(0));
+        String projectId="664c52c05a93ac02400705fd";// 三级任务测试项目
+        String taskType="664c52c158a65f33469b6749";// 三级任务
+        String taskId="664c588a58a65f33469ba2dc";// 测试三级任务-010202
+        String parentTaskId="664c5537351868a429dfd9da"; // 测试二级任务
+//        JSONArray array=tbApiService.getTasksType(projectId);
+//        JSONArray array=tbApiService.getProjectState(projectId);
+
+//        System.out.println(array);
+        thTbService.syncTaskState(taskId);
     }
 
 
 
+
+
 }