فهرست منبع

fix: improve code structure of code commit module

claws 4 سال پیش
والد
کامیت
f1441dfe7e
19فایلهای تغییر یافته به همراه769 افزوده شده و 659 حذف شده
  1. 3 3
      web/src/main/java/cn/seecoder/web/controller/commit/BranchController.java
  2. 70 0
      web/src/main/java/cn/seecoder/web/controller/commit/CommitController.java
  3. 85 0
      web/src/main/java/cn/seecoder/web/controller/commit/CommitLinkController.java
  4. 46 0
      web/src/main/java/cn/seecoder/web/controller/commit/CommitQualityController.java
  5. 0 256
      web/src/main/java/cn/seecoder/web/controller/gitlab/CommitController.java
  6. 2 1
      web/src/main/java/cn/seecoder/web/core/pipeline/handler/JavaImageBuildHandler.java
  7. 2 3
      web/src/main/java/cn/seecoder/web/core/pipeline/handler/SonarJavaImageBuildHandler.java
  8. 1 1
      web/src/main/java/cn/seecoder/web/model/po/commit/CommitPO.java
  9. 1 1
      web/src/main/java/cn/seecoder/web/model/vo/commit/GitWebHookVO.java
  10. 2 2
      web/src/main/java/cn/seecoder/web/service/branch/BranchService.java
  11. 36 0
      web/src/main/java/cn/seecoder/web/service/commit/CommitLinkService.java
  12. 28 0
      web/src/main/java/cn/seecoder/web/service/commit/CommitQualityService.java
  13. 24 0
      web/src/main/java/cn/seecoder/web/service/commit/CommitService.java
  14. 3 3
      web/src/main/java/cn/seecoder/web/service/impl/branch/BranchServiceImpl.java
  15. 216 0
      web/src/main/java/cn/seecoder/web/service/impl/commit/CommitLinkServiceImpl.java
  16. 126 0
      web/src/main/java/cn/seecoder/web/service/impl/commit/CommitQualityServiceImpl.java
  17. 124 0
      web/src/main/java/cn/seecoder/web/service/impl/commit/CommitServiceImpl.java
  18. 0 322
      web/src/main/java/cn/seecoder/web/service/impl/project/CommitServiceImpl.java
  19. 0 67
      web/src/main/java/cn/seecoder/web/service/project/CommitService.java

+ 3 - 3
web/src/main/java/cn/seecoder/web/controller/gitlab/BranchController.java → web/src/main/java/cn/seecoder/web/controller/commit/BranchController.java

@@ -1,7 +1,7 @@
-package cn.seecoder.web.controller.gitlab;
+package cn.seecoder.web.controller.commit;
 
 import cn.seecoder.web.model.vo.Response;
-import cn.seecoder.web.service.project.BranchService;
+import cn.seecoder.web.service.branch.BranchService;
 import com.nju.edu.gitlab.vo.BranchVO;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiImplicitParam;
@@ -25,7 +25,7 @@ import java.util.List;
 public class BranchController {
     final static String GET_BRANCHES_ERROR = "Fail to search all branches";
 
-    final BranchService branchService;
+    private final BranchService branchService;
 
     @Autowired
     public BranchController(BranchService branchService) {

+ 70 - 0
web/src/main/java/cn/seecoder/web/controller/commit/CommitController.java

@@ -0,0 +1,70 @@
+package cn.seecoder.web.controller.commit;
+
+import cn.seecoder.web.model.vo.Response;
+import cn.seecoder.web.model.vo.commit.CommitVO;
+import cn.seecoder.web.service.commit.CommitService;
+import com.nju.edu.gitlab.vo.DiffVO;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiImplicitParam;
+import io.swagger.annotations.ApiImplicitParams;
+import io.swagger.annotations.ApiOperation;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+import java.util.Set;
+
+/**
+ * @author chenyz
+ * @date 2021/2/4
+ * @description: 提交管理接口
+ */
+@Api(tags = "Commit Manage API")
+@RestController
+@Slf4j
+public class CommitController {
+    private final CommitService commitService;
+
+    @Autowired
+    public CommitController(CommitService commitService) {
+        this.commitService = commitService;
+    }
+
+    @ApiOperation(value = "获取指定项目指定分支所有的commit信息", httpMethod = "GET")
+    @GetMapping("/commits/by_branch")
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query"),
+            @ApiImplicitParam(name = "branchName", dataType = "String", paramType = "query")
+    })
+    public Response<List<CommitVO>> getCommitsByBranch(@RequestParam("projectId") Integer projectId,
+                                                                                    @RequestParam("branchName") String branchName){
+        return Response.buildSuccess(commitService.getCommitsByBranchName(projectId, branchName));
+    }
+
+    @ApiOperation(value = "获得一个commit的信息", httpMethod = "GET")
+    @GetMapping("/commit")
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query"),
+            @ApiImplicitParam(name = "hash", dataType = "String", paramType = "query")
+    })
+    public Response<CommitVO> getCommitByHash(@RequestParam("projectId") Integer projectId,
+                                              @RequestParam("hash") String hash)
+    {
+        return Response.buildSuccess(commitService.getCommitByHash(projectId, hash));
+    }
+
+    @ApiOperation(value = "获得两个提交之间的差异", httpMethod = "GET")
+    @GetMapping("/commits/diff")
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query"),
+            @ApiImplicitParam(name = "from", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "to", dataType = "String", paramType = "query")
+    })
+    public Response<Set<DiffVO>> getDiff(@RequestParam("projectId") Integer projectId,
+                                         @RequestParam("from") String from,
+                                         @RequestParam("to") String to)
+    {
+        return Response.buildSuccess(commitService.getDiff(projectId, from, to));
+    }
+}

+ 85 - 0
web/src/main/java/cn/seecoder/web/controller/commit/CommitLinkController.java

@@ -0,0 +1,85 @@
+package cn.seecoder.web.controller.commit;
+
+import cn.seecoder.common.exceptions.ServiceException;
+import cn.seecoder.web.model.enums.CommitRelatedEnum;
+import cn.seecoder.web.model.vo.commit.GitWebHookVO;
+import cn.seecoder.web.model.vo.Response;
+import cn.seecoder.web.model.vo.commit.CommitVO;
+import cn.seecoder.web.service.commit.CommitLinkService;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiImplicitParam;
+import io.swagger.annotations.ApiImplicitParams;
+import io.swagger.annotations.ApiOperation;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+
+@Api(tags = "Commit Link Manage API")
+@RestController
+@Slf4j
+public class CommitLinkController {
+    private final static String LINK_FAIL_ERROR = "Commit Link Failed! No Such Bug or Task!";
+
+    @Autowired
+    CommitLinkService commitLinkService;
+    /**
+     * @author chenyz
+     * @date 2021/2/4
+     * @description: 此接口挂载在webhooks的push回调中
+     * todo webhook最多只能获取20个commit
+     *  因为gitlab官方,考虑性能原因导致
+     *  详见 https://docs.gitlab.com/ee/user/project/integrations/webhooks.html push event内容
+     *  暂时无解
+     * 只关注push event
+     * 所有分支的push都分析
+     */
+    @ApiOperation(value = "push回调接口", httpMethod = "POST")
+    @PostMapping("/hook")
+    @ApiImplicitParam(name = "gitWebHookVO",dataType = "object", paramType = "body")
+    public void pushHook(@RequestBody GitWebHookVO gitWebHookVO) throws ServiceException {
+        commitLinkService.linkCommitByInfoFromGitlab(gitWebHookVO);
+    }
+
+    @ApiOperation(value = "获取某个需求树结点的所有commit信息", httpMethod = "GET")
+    @GetMapping("/commits/tree")
+    @ApiImplicitParam(name = "treeId",dataType = "int", paramType = "query")
+    public Response<List<CommitVO>> getTreeCommits(@RequestParam("treeId") Integer treeId){
+        return Response.buildSuccess(commitLinkService.getTreeLinkedCommits(treeId));
+    }
+
+    @ApiOperation(value = "获取bug list中一个bug关联的所有commit信息", httpMethod = "GET")
+    @GetMapping("/commits/bug_list")
+    @ApiImplicitParam(name = "bugId",dataType = "int", paramType = "query")
+    public Response<List<CommitVO>> getBugCommits(@RequestParam("bugId") Integer bugId){
+        return Response.buildSuccess(commitLinkService.getBugLinkedCommits(bugId));
+    }
+
+    @ApiOperation(value = "获取指定项目的所有commit信息", httpMethod = "GET")
+    @GetMapping("/commits/list")
+    @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query")
+    public Response<List<CommitVO>> getCommits(@RequestParam("projectId") Integer projectId) {
+        return Response.buildSuccess(commitLinkService.getLinkedCommits(projectId));
+    }
+
+    @ApiOperation(value = "关联commit和缺陷、任务节点", httpMethod = "GET")
+    @GetMapping("/commits/link")
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query"),
+            @ApiImplicitParam(name = "commitId", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "relatedType", dataType = "String", paramType = "query"),
+            @ApiImplicitParam(name = "relatedId", dataType = "int", paramType = "query")
+    })
+    public Response<Object> linkCommit(@RequestParam("projectId") Integer projectId,
+                                       @RequestParam("commitId") String commitId,
+                                       @RequestParam("relatedType") CommitRelatedEnum relatedType,
+                                       @RequestParam("relatedId") Integer relatedId)
+    {
+        if (commitLinkService.link(projectId, commitId, relatedType, relatedId)) {
+            return Response.buildSuccess(null);
+        } else {
+            return Response.buildFailure(404, LINK_FAIL_ERROR);
+        }
+    }
+}

+ 46 - 0
web/src/main/java/cn/seecoder/web/controller/commit/CommitQualityController.java

@@ -0,0 +1,46 @@
+package cn.seecoder.web.controller.commit;
+
+import cn.seecoder.common.exceptions.ServiceException;
+import cn.seecoder.web.model.vo.Response;
+import cn.seecoder.web.model.vo.commit.CommitQualityVO;
+import cn.seecoder.web.model.vo.hook.SonarResultHookVO;
+import cn.seecoder.web.service.commit.CommitQualityService;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiImplicitParam;
+import io.swagger.annotations.ApiImplicitParams;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+@Api(tags = "Commit Quality Manage API")
+@RestController
+public class CommitQualityController {
+    private final static String QUALITY_QUERY_ERROR = "查询代码版本质量失败";
+
+    @Autowired
+    CommitQualityService commitQualityService;
+
+    @ApiOperation(value = "sonarqube回调接口", httpMethod = "POST")
+    @PostMapping("/sonar_hook")
+    @ApiImplicitParam(name = "sonarResultHookVO", dataType = "SonarResultHookVO", paramType = "body")
+    public Response<Object> sonarHook(@RequestBody SonarResultHookVO sonarResultHookVO) throws ServiceException {
+        if (commitQualityService.processSonarResult(sonarResultHookVO)) {
+            return Response.buildSuccess("ok");
+        } else {
+            return Response.buildFailure(500, "Post Body Process Error!");
+        }
+    }
+
+    @ApiOperation(value = "查询代码版本质量", httpMethod = "GET")
+    @GetMapping("commit/quality")
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query"),
+            @ApiImplicitParam(name = "commitId", dataType = "String", paramType = "query")
+    })
+    public Response<CommitQualityVO> getQualityByProjectIdAndCommit(@RequestParam("projectId") Integer projectId,
+                                                                    @RequestParam("commitId") String commitId)
+    {
+        CommitQualityVO quality = commitQualityService.getQualityByCommit(projectId, commitId);
+        return Response.buildSuccess(quality);
+    }
+}

+ 0 - 256
web/src/main/java/cn/seecoder/web/controller/gitlab/CommitController.java

@@ -1,256 +0,0 @@
-package cn.seecoder.web.controller.gitlab;
-
-import cn.seecoder.common.exceptions.ServiceException;
-import cn.seecoder.common.util.LogTrackingUtil;
-import cn.seecoder.common.util.OpType;
-import cn.seecoder.web.core.commit.CommitResolver;
-import cn.seecoder.web.core.commit.model.CommitRule;
-import cn.seecoder.web.dao.user.UserMapper;
-import cn.seecoder.web.model.enums.CommitRelatedEnum;
-import cn.seecoder.web.model.po.commit.CommitPO;
-import cn.seecoder.web.model.vo.GitWebHookVO;
-import cn.seecoder.web.model.vo.Response;
-import cn.seecoder.web.model.vo.commit.CommitQualityVO;
-import cn.seecoder.web.model.vo.hook.SonarResultHookVO;
-import cn.seecoder.web.model.vo.commit.CommitVO;
-import cn.seecoder.web.service.bug_list.BugListService;
-import cn.seecoder.web.service.project.CommitService;
-import cn.seecoder.web.service.tree.TreeNodeService;
-import com.alibaba.fastjson.JSONObject;
-import com.nju.edu.gitlab.SeecoderGitlabApi;
-import com.nju.edu.gitlab.vo.DiffVO;
-import io.swagger.annotations.Api;
-import io.swagger.annotations.ApiImplicitParam;
-import io.swagger.annotations.ApiImplicitParams;
-import io.swagger.annotations.ApiOperation;
-import lombok.extern.slf4j.Slf4j;
-import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.web.bind.annotation.*;
-
-import java.util.List;
-import java.util.Set;
-
-/**
- * @author chenyz
- * @date 2021/2/4
- * @description: 与GitLab进行交互的接口
- */
-@Api(tags = "GitLab Hook API")
-@RestController
-@Slf4j
-public class CommitController {
-
-    private final static String LINK_FAIL_ERROR = "Commit Link Failed! No Such Bug or Task Found!";
-    private final static String QUALITY_QUERY_ERROR = "查询代码版本质量失败";
-
-    private final BugListService bugListService;
-
-    private final TreeNodeService treeNodeService;
-
-    private final CommitService commitService;
-
-    private final SeecoderGitlabApi seecoderGitlabApi;
-
-    // 赶时间暂时这么写
-    @Autowired
-    UserMapper userMapper;
-
-    @Autowired
-    public CommitController(BugListService bugListService, TreeNodeService treeNodeService, CommitService commitService, SeecoderGitlabApi seecoderGitlabApi) {
-        this.bugListService = bugListService;
-        this.treeNodeService = treeNodeService;
-        this.commitService = commitService;
-        this.seecoderGitlabApi = seecoderGitlabApi;
-    }
-
-    @ApiOperation(value = "sonarqube回调接口", httpMethod = "POST")
-    @PostMapping("/sonar_hook")
-    @ApiImplicitParam(name = "hahaVO", dataType = "object", paramType = "body")
-    public Response<Object> sonarHook(@RequestBody SonarResultHookVO sonarResultHookVO) throws ServiceException{
-        if (commitService.processSonarResult(sonarResultHookVO)) {
-            return Response.buildSuccess("ok");
-        } else {
-            return Response.buildFailure(500, "Post Body Process Error!");
-        }
-    }
-
-
-    /**
-     * @author chenyz
-     * @date 2021/2/4
-     * @description: 此接口挂载在webhooks的push回调中
-     * todo webhook最多只能获取20个commit
-     *  因为gitlab官方,考虑性能原因导致
-     *  详见 https://docs.gitlab.com/ee/user/project/integrations/webhooks.html push event内容
-     *  暂时无解
-     * 只关注push event
-     * 所有分支的push都分析
-     */
-    @ApiOperation(value = "push回调接口", httpMethod = "POST")
-    @PostMapping("/hook")
-    @ApiImplicitParam(name = "gitWebHookVO",dataType = "object", paramType = "body")
-    public void pushHook(@RequestBody GitWebHookVO gitWebHookVO) throws ServiceException {
-
-//
-//        List<String> emails = new ArrayList<>();
-//        emails.add(gitWebHookVO.getUser_email());
-//        List<GitlabUserEmailDTO> users;
-//        try {
-//            users = seecoderGitlabApi.findUserByEmails(emails);
-//        } catch (SeecoderGitlabException e) {
-//            throw new ServiceException("统一代码服务出现访问错误,无法正确分析webhook信息");
-//        }
-//        Integer userId = users.size()!=0 ? users.get(0).getUserId() : null;
-
-        Integer projectId = gitWebHookVO.getProject_id();
-        for (GitWebHookVO.Commit commit: gitWebHookVO.getCommits()){
-            if (commitService.isResolved(commit.getId())){
-                //已经解析过了
-                log.info("Commits 已经解析过了, id: {}", commit.getId());
-                continue;
-            }
-            //ANA 日志需要打出用户的commit信息
-            JSONObject object = new JSONObject();
-            try{
-                object.put("commit_id",commit.getId());
-                object.put("user_id",userMapper.selectIdByEmail(commit.getAuthor().getEmail()));
-                object.put("project_id",projectId);
-                object.put("commit_time",commit.getTimestamp());
-                object.put("message",commit.getMessage());
-            }catch (Exception ignored){}
-
-
-            log.info("resolving commit id : {}, title : {}, message : {}", commit.getId(), commit.getTitle(), commit.getMessage());
-            //todo 注意目前分析的是 message
-            // 应该分析 title 还是 message 与学生的提交规范有关
-            CommitRule rule = CommitResolver.resolve(commit.getMessage());
-            if (rule == null){
-                log.info("Commits 不符合规范, id: {}", commit.getId());
-                //ANA
-                try {
-                    object.put("type","不合规范");
-                    String data = JSONObject.toJSONString(object);
-                    LogTrackingUtil.log(data, OpType.COMMIT);
-                } catch (Exception ignored) {}
-                continue;
-            }
-            switch (rule.getType()){
-                case FEAT:
-                    treeNodeService.updateNodeState(rule.getId(),rule.getState());
-                    commitService.save(new CommitPO(commit,projectId, CommitRelatedEnum.TREE_ID, rule.getId()));
-                    log.info("Commits 关联tree节点, id: {}", commit.getId());
-                    //ANA
-                    try {
-                        object.put("type","关联tree");
-                        String data = JSONObject.toJSONString(object);
-                        LogTrackingUtil.log(data, OpType.COMMIT);
-                    } catch (Exception ignored) {}
-                    break;
-                case FIX:
-                    bugListService.updateState(rule.getState(), rule.getId());
-                    commitService.save(new CommitPO(commit,projectId, CommitRelatedEnum.BUG_ID, rule.getId()));
-                    log.info("Commits 关联bug节点, id: {}", commit.getId());
-                    //ANA
-                    try {
-                        object.put("type","关联bug");
-                        String data = JSONObject.toJSONString(object);
-                        LogTrackingUtil.log(data, OpType.COMMIT);
-                    } catch (Exception ignored) {}
-                    break;
-                case UNKNOWN:
-                    break;
-            }
-        }
-    }
-
-    @ApiOperation(value = "获取某个需求树结点的所有commit信息", httpMethod = "GET")
-    @GetMapping("/commits/tree")
-    @ApiImplicitParam(name = "treeId",dataType = "int", paramType = "query")
-    public Response<List<CommitVO>> getTreeCommits(@RequestParam("treeId") Integer treeId){
-        return Response.buildSuccess(commitService.getTreeCommit(treeId));
-    }
-
-    @ApiOperation(value = "获取bug list中一个bug关联的所有commit信息", httpMethod = "GET")
-    @GetMapping("/commits/bug_list")
-    @ApiImplicitParam(name = "bugId",dataType = "int", paramType = "query")
-    public Response<List<CommitVO>> getBugCommits(@RequestParam("bugId") Integer bugId){
-        return Response.buildSuccess(commitService.getBugCommit(bugId));
-    }
-
-    @ApiOperation(value = "获取指定项目的所有commit信息", httpMethod = "GET")
-    @GetMapping("/commits/list")
-    @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query")
-    public Response<List<CommitVO>> getCommits(@RequestParam("projectId") Integer projectId) {
-        return Response.buildSuccess(commitService.getCommits(projectId));
-    }
-
-    @ApiOperation(value = "获取指定项目指定分支所有的commit信息", httpMethod = "GET")
-    @GetMapping("/commits/by_branch")
-    @ApiImplicitParams({
-            @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query"),
-            @ApiImplicitParam(name = "branchName", dataType = "String", paramType = "query")
-    })
-    public Response<List<CommitVO>> getCommitsByBranch(@RequestParam("projectId") Integer projectId,
-                                                                                    @RequestParam("branchName") String branchName){
-        return Response.buildSuccess(commitService.getCommitsByBranchName(projectId, branchName));
-    }
-
-    @ApiOperation(value = "获得一个commit的信息", httpMethod = "GET")
-    @GetMapping("/commit")
-    @ApiImplicitParams({
-            @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query"),
-            @ApiImplicitParam(name = "hash", dataType = "String", paramType = "query")
-    })
-    public Response<CommitVO> getCommitByHash(@RequestParam("projectId") Integer projectId,
-                                              @RequestParam("hash") String hash)
-    {
-        return Response.buildSuccess(commitService.getCommitByHash(projectId, hash));
-    }
-
-    @ApiOperation(value = "获得两个提交之间的差异", httpMethod = "GET")
-    @GetMapping("/commits/diff")
-    @ApiImplicitParams({
-            @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query"),
-            @ApiImplicitParam(name = "from", dataType = "String", paramType = "query"),
-            @ApiImplicitParam(name = "to", dataType = "String", paramType = "query")
-    })
-    public Response<Set<DiffVO>> getDiff(@RequestParam("projectId") Integer projectId,
-                                         @RequestParam("from") String from,
-                                         @RequestParam("to") String to)
-    {
-        return Response.buildSuccess(commitService.getDiff(projectId, from, to));
-    }
-
-    @ApiOperation(value = "关联commit和缺陷、任务节点", httpMethod = "GET")
-    @GetMapping("/commits/link")
-    @ApiImplicitParams({
-            @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query"),
-            @ApiImplicitParam(name = "commitId", dataType = "String", paramType = "query"),
-            @ApiImplicitParam(name = "relatedType", dataType = "String", paramType = "query"),
-            @ApiImplicitParam(name = "relatedId", dataType = "int", paramType = "query")
-    })
-    public Response<Object> linkCommit(@RequestParam("projectId") Integer projectId,
-                                       @RequestParam("commitId") String commitId,
-                                       @RequestParam("relatedType") CommitRelatedEnum relatedType,
-                                       @RequestParam("relatedId") Integer relatedId)
-    {
-        if (commitService.link(projectId, commitId, relatedType, relatedId)){
-            return Response.buildSuccess(null);
-        } else {
-            return Response.buildFailure(404, LINK_FAIL_ERROR);
-        }
-    }
-
-    @ApiOperation(value = "查询代码版本质量", httpMethod = "GET")
-    @GetMapping("commit/quality")
-    @ApiImplicitParams({
-            @ApiImplicitParam(name = "projectId", dataType = "int", paramType = "query"),
-            @ApiImplicitParam(name = "commitId", dataType = "String", paramType = "query")
-    })
-    public Response<CommitQualityVO> getQualityByProjectIdAndCommit(@RequestParam("projectId") Integer projectId,
-                                                                    @RequestParam("commitId") String commitId)
-    {
-        CommitQualityVO quality = commitService.getQualityByCommit(projectId, commitId);
-        return Response.buildSuccess(quality);
-    }
-}

+ 2 - 1
web/src/main/java/cn/seecoder/web/core/pipeline/handler/JavaImageBuildHandler.java

@@ -29,7 +29,8 @@ import java.util.List;
 /**
  * @author PuHong Weng
  * @date 2021/1/18
- * @description: docker镜像构建
+ * @description: docker镜像构建。构建Java版的质量检查镜像,需要maven作为base,直接在上面运行maven的命令即可完成检查。如果需要构建其他语言
+ * 的检查镜像,需要使用 SonarQube 官方提供的带有可执行 client 的镜像,在其中运行 client 的检查命令。后续步骤都是一致的。
  */
 @Slf4j
 @Data

+ 2 - 3
web/src/main/java/cn/seecoder/web/core/pipeline/handler/SonarJavaImageBuildHandler.java

@@ -8,7 +8,7 @@ import cn.seecoder.web.core.pipeline.Context;
 import cn.seecoder.web.core.pipeline.PipelineException;
 import cn.seecoder.web.core.pipeline.template.PipelineTemplateTable;
 import cn.seecoder.web.model.vo.project.ProjectVO;
-import cn.seecoder.web.service.project.BranchService;
+import cn.seecoder.web.service.branch.BranchService;
 import cn.seecoder.web.service.project.ProjectService;
 import com.nju.edu.gitlab.vo.BranchVO;
 import com.spotify.docker.client.ProgressHandler;
@@ -27,7 +27,6 @@ import java.nio.file.Files;
 import java.nio.file.Path;
 import java.nio.file.Paths;
 import java.nio.file.StandardOpenOption;
-import java.util.Date;
 import java.util.List;
 
 @Slf4j
@@ -69,7 +68,7 @@ public class SonarJavaImageBuildHandler extends AbstractHandler {
         // convert url for local test
         UriComponentsBuilder builder = UriComponentsBuilder.fromHttpUrl(repoUrl);
         repoUrl = builder.scheme("https").host("seecoder-gitlab-gitlab.seec.seecoder.cn").path(".git/").toUriString();
-        BranchVO branch = branchService.getBranchById(projectId, branchOrHash);
+        BranchVO branch = branchService.getBranchByName(projectId, branchOrHash);
         String commitHash;
         boolean isBranch;
         if (branch == null) {

+ 1 - 1
web/src/main/java/cn/seecoder/web/model/po/commit/CommitPO.java

@@ -6,7 +6,7 @@ import lombok.Builder;
 import lombok.Data;
 import lombok.NoArgsConstructor;
 import org.springframework.beans.BeanUtils;
-import cn.seecoder.web.model.vo.GitWebHookVO;
+import cn.seecoder.web.model.vo.commit.GitWebHookVO;
 
 /**
  * @author PuHong Weng

+ 1 - 1
web/src/main/java/cn/seecoder/web/model/vo/GitWebHookVO.java → web/src/main/java/cn/seecoder/web/model/vo/commit/GitWebHookVO.java

@@ -1,4 +1,4 @@
-package cn.seecoder.web.model.vo;
+package cn.seecoder.web.model.vo.commit;
 
 import io.swagger.annotations.ApiModel;
 import lombok.Data;

+ 2 - 2
web/src/main/java/cn/seecoder/web/service/project/BranchService.java → web/src/main/java/cn/seecoder/web/service/branch/BranchService.java

@@ -1,4 +1,4 @@
-package cn.seecoder.web.service.project;
+package cn.seecoder.web.service.branch;
 
 import com.nju.edu.gitlab.vo.BranchVO;
 
@@ -7,5 +7,5 @@ import java.util.List;
 public interface BranchService {
     List<BranchVO> getAllBranches(Integer projectId);
 
-    BranchVO getBranchById(Integer projectId, String branchName);
+    BranchVO getBranchByName(Integer projectId, String branchName);
 }

+ 36 - 0
web/src/main/java/cn/seecoder/web/service/commit/CommitLinkService.java

@@ -0,0 +1,36 @@
+package cn.seecoder.web.service.commit;
+
+import cn.seecoder.web.model.enums.CommitRelatedEnum;
+import cn.seecoder.web.model.po.commit.CommitPO;
+import cn.seecoder.web.model.vo.commit.GitWebHookVO;
+import cn.seecoder.web.model.vo.commit.CommitVO;
+
+import java.util.List;
+
+public interface CommitLinkService {
+    void linkCommitByInfoFromGitlab(GitWebHookVO gitWebHookVO);
+
+    void saveLinkedCommit(CommitPO po);
+    /**
+     * 不同分支可能会push相同的commit,分析过的commit不应该再分析,这里是判断是否分析共没有
+     * @param id commit hash id
+     */
+    boolean isLinked(String id);
+
+    List<CommitVO> getTreeLinkedCommits(Integer treeId);
+
+    List<CommitVO> getBugLinkedCommits(Integer bugId);
+
+    List<CommitVO> getLinkedCommits(Integer projectId);
+
+    CommitPO getLinkedCommit(String hash);
+    /**
+     * link commit and tree node or bug
+     * @param projectId
+     * @param commitHash
+     * @param relatedType
+     * @param relatedId
+     * @return
+     */
+    boolean link(Integer projectId, String commitHash, CommitRelatedEnum relatedType, Integer relatedId);
+}

+ 28 - 0
web/src/main/java/cn/seecoder/web/service/commit/CommitQualityService.java

@@ -0,0 +1,28 @@
+package cn.seecoder.web.service.commit;
+
+import cn.seecoder.web.model.enums.CommitCheckResultEnum;
+import cn.seecoder.web.model.vo.commit.CommitQualityVO;
+import cn.seecoder.web.model.vo.hook.SonarResultHookVO;
+
+import java.util.Map;
+
+public interface CommitQualityService {
+
+    /**
+     * process the coming json data from sonarqube
+     * @param sonarResultHookVO
+     * @return
+     */
+    boolean processSonarResult(SonarResultHookVO sonarResultHookVO);
+
+    Map<String, CommitCheckResultEnum> getCommitsQualityMapByProjectId(Integer projectId);
+
+    CommitCheckResultEnum getQualityResultByCommit(String hash);
+    /**
+     * get commit quality by commit hash and project id
+     * @param projectId
+     * @param commitHash
+     * @return
+     */
+    CommitQualityVO getQualityByCommit(Integer projectId, String commitHash);
+}

+ 24 - 0
web/src/main/java/cn/seecoder/web/service/commit/CommitService.java

@@ -0,0 +1,24 @@
+package cn.seecoder.web.service.commit;
+
+import cn.seecoder.web.model.enums.CommitRelatedEnum;
+import cn.seecoder.web.model.po.commit.CommitPO;
+import cn.seecoder.web.model.vo.commit.CommitQualityVO;
+import cn.seecoder.web.model.vo.commit.CommitVO;
+import cn.seecoder.web.model.vo.hook.SonarResultHookVO;
+import com.nju.edu.gitlab.vo.DiffVO;
+
+import java.util.List;
+import java.util.Set;
+
+/**
+ * @author PuHong Weng
+ * @date 2021/3/21
+ * @description: 项目相关的 git commit 记录分析功能
+ */
+public interface CommitService {
+    List<CommitVO> getCommitsByBranchName(Integer projectId, String branchName);
+
+    CommitVO getCommitByHash(Integer projectId, String hash);
+
+    Set<DiffVO> getDiff(Integer projectId, String fromHash, String toHash);
+}

+ 3 - 3
web/src/main/java/cn/seecoder/web/service/impl/project/BranchServiceImpl.java → web/src/main/java/cn/seecoder/web/service/impl/branch/BranchServiceImpl.java

@@ -1,6 +1,6 @@
-package cn.seecoder.web.service.impl.project;
+package cn.seecoder.web.service.impl.branch;
 
-import cn.seecoder.web.service.project.BranchService;
+import cn.seecoder.web.service.branch.BranchService;
 import com.nju.edu.gitlab.SeecoderGitlabApi;
 import com.nju.edu.gitlab.SeecoderGitlabException;
 import com.nju.edu.gitlab.vo.BranchVO;
@@ -28,7 +28,7 @@ public class BranchServiceImpl implements BranchService {
     }
 
     @Override
-    public BranchVO getBranchById(Integer projectId, String branchName) {
+    public BranchVO getBranchByName(Integer projectId, String branchName) {
         for (BranchVO branchVO : this.getAllBranches(projectId)) {
             if (branchVO.getName().equals(branchName)) {
                 return branchVO;

+ 216 - 0
web/src/main/java/cn/seecoder/web/service/impl/commit/CommitLinkServiceImpl.java

@@ -0,0 +1,216 @@
+package cn.seecoder.web.service.impl.commit;
+
+import cn.seecoder.common.util.LogTrackingUtil;
+import cn.seecoder.common.util.OpType;
+import cn.seecoder.web.core.commit.CommitResolver;
+import cn.seecoder.web.core.commit.model.CommitRule;
+import cn.seecoder.web.dao.commit.CommitMapper;
+import cn.seecoder.web.dao.user.UserMapper;
+import cn.seecoder.web.model.enums.CommitRelatedEnum;
+import cn.seecoder.web.model.po.bug_list.BugListPO;
+import cn.seecoder.web.model.po.commit.CommitPO;
+import cn.seecoder.web.model.po.tree.TreeNodePO;
+import cn.seecoder.web.model.vo.commit.GitWebHookVO;
+import cn.seecoder.web.model.vo.commit.CommitVO;
+import cn.seecoder.web.service.bug_list.BugListService;
+import cn.seecoder.web.service.commit.CommitLinkService;
+import cn.seecoder.web.service.commit.CommitService;
+import cn.seecoder.web.service.tree.TreeNodeService;
+import com.alibaba.fastjson.JSONObject;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import java.util.List;
+import java.util.stream.Collectors;
+
+@Service
+@Slf4j
+public class CommitLinkServiceImpl implements CommitLinkService {
+    @Autowired
+    private CommitMapper commitMapper;
+    @Autowired
+    private TreeNodeService treeNodeService;
+    @Autowired
+    private BugListService bugListService;
+    @Autowired
+    private CommitService commitService;
+    @Autowired
+    private UserMapper userMapper;
+
+    @Override
+    public void linkCommitByInfoFromGitlab(GitWebHookVO gitWebHookVO) {
+
+//
+//        List<String> emails = new ArrayList<>();
+//        emails.add(gitWebHookVO.getUser_email());
+//        List<GitlabUserEmailDTO> users;
+//        try {
+//            users = seecoderGitlabApi.findUserByEmails(emails);
+//        } catch (SeecoderGitlabException e) {
+//            throw new ServiceException("统一代码服务出现访问错误,无法正确分析webhook信息");
+//        }
+//        Integer userId = users.size()!=0 ? users.get(0).getUserId() : null;
+
+        Integer projectId = gitWebHookVO.getProject_id();
+        for (GitWebHookVO.Commit commit: gitWebHookVO.getCommits()){
+            if (this.isLinked(commit.getId())){
+                //已经解析过了
+                log.info("Commits 已经解析过了, id: {}", commit.getId());
+                continue;
+            }
+            //ANA 日志需要打出用户的commit信息
+            JSONObject object = new JSONObject();
+            try{
+                object.put("commit_id",commit.getId());
+                object.put("user_id",userMapper.selectIdByEmail(commit.getAuthor().getEmail()));
+                object.put("project_id",projectId);
+                object.put("commit_time",commit.getTimestamp());
+                object.put("message",commit.getMessage());
+            }catch (Exception ignored){}
+
+
+            log.info("resolving commit id : {}, title : {}, message : {}", commit.getId(), commit.getTitle(), commit.getMessage());
+            //todo 注意目前分析的是 message
+            // 应该分析 title 还是 message 与学生的提交规范有关
+            CommitRule rule = CommitResolver.resolve(commit.getMessage());
+            if (rule == null){
+                log.info("Commits 不符合规范, id: {}", commit.getId());
+                //ANA
+                try {
+                    object.put("type","不合规范");
+                    String data = JSONObject.toJSONString(object);
+                    LogTrackingUtil.log(data, OpType.COMMIT);
+                } catch (Exception ignored) {}
+                continue;
+            }
+            switch (rule.getType()){
+                case FEAT:
+                    treeNodeService.updateNodeState(rule.getId(),rule.getState());
+                    this.saveLinkedCommit(new CommitPO(commit,projectId, CommitRelatedEnum.TREE_ID, rule.getId()));
+                    log.info("Commits 关联tree节点, id: {}", commit.getId());
+                    //ANA
+                    try {
+                        object.put("type","关联tree");
+                        String data = JSONObject.toJSONString(object);
+                        LogTrackingUtil.log(data, OpType.COMMIT);
+                    } catch (Exception ignored) {}
+                    break;
+                case FIX:
+                    bugListService.updateState(rule.getState(), rule.getId());
+                    this.saveLinkedCommit(new CommitPO(commit,projectId, CommitRelatedEnum.BUG_ID, rule.getId()));
+                    log.info("Commits 关联bug节点, id: {}", commit.getId());
+                    //ANA
+                    try {
+                        object.put("type","关联bug");
+                        String data = JSONObject.toJSONString(object);
+                        LogTrackingUtil.log(data, OpType.COMMIT);
+                    } catch (Exception ignored) {}
+                    break;
+                case UNKNOWN:
+                    break;
+            }
+        }
+    }
+
+    @Override
+    public void saveLinkedCommit(CommitPO po) {
+
+        //ANA 日志需要打出用户commit的信息
+        try{
+            JSONObject object = new JSONObject();
+            object.put("commit_id",po.getId());
+            object.put("user_id",userMapper.selectIdByUserName(po.getGitlabUsername()));
+            object.put("project_id",po.getProjectId());
+            object.put("commit_name",po.getGitlabUsername());
+            object.put("commit_time",po.getTimestamp());
+            object.put("message",po.getMessage());
+            object.put("type",po.getRelatedType());
+
+            String data = JSONObject.toJSONString(object);
+            LogTrackingUtil.log(data, OpType.COMMIT);
+        }catch (Exception e){}
+
+        commitMapper.insert(po);
+    }
+
+    @Override
+    public boolean isLinked(String id) {
+        return 1 == commitMapper.isExist(id);
+    }
+
+    @Override
+    public List<CommitVO> getTreeLinkedCommits(Integer treeId) {
+        return commitMapper.selectByRelatedIdAndType(treeId,CommitRelatedEnum.TREE_ID).stream()
+                .map(CommitVO::new)
+                .collect(Collectors.toList());
+    }
+
+    @Override
+    public List<CommitVO> getBugLinkedCommits(Integer bugId) {
+        return commitMapper.selectByRelatedIdAndType(bugId,CommitRelatedEnum.BUG_ID).stream()
+                .map(CommitVO::new)
+                .collect(Collectors.toList());
+    }
+
+    @Override
+    public CommitPO getLinkedCommit(String hash) {
+        return commitMapper.selectByCommitId(hash);
+    }
+
+    @Override
+    public List<CommitVO> getLinkedCommits(Integer projectId) {
+        return commitMapper.selectByProjectId(projectId).stream()
+                .map(CommitVO::new)
+                .collect(Collectors.toList());
+    }
+
+    @Override
+    public boolean link(Integer projectId, String commitHash, CommitRelatedEnum relatedType, Integer relatedId) {
+        if (relatedType == CommitRelatedEnum.NONE){
+            commitMapper.deleteByCommitId(commitHash);
+            return true;
+        }
+
+        // check if the related target exists
+        if (relatedType == CommitRelatedEnum.TREE_ID){
+            TreeNodePO node = treeNodeService.getNodeByNodeId(relatedId);
+            if (node == null){
+                return false;
+            } else if (! node.getProjectId().equals(projectId)) {
+                return false;
+            }
+        } else {
+            BugListPO node = bugListService.getBugById(relatedId);
+            if (node == null){
+                return false;
+            } else if (! node.getProjectId().equals(projectId)) {
+                return false;
+            }
+        }
+
+        // check if the commit is already exist, then update it. if not, insert a new one.
+        CommitPO commitPODB = commitMapper.selectByCommitId(commitHash);
+        if (commitPODB != null){
+            commitPODB.setRelatedType(relatedType);
+            commitPODB.setRelatedId(relatedId);
+            commitMapper.update(commitPODB);
+        } else {
+            CommitVO commit = commitService.getCommitByHash(projectId, commitHash);
+
+            CommitPO commitPO = new CommitPO();
+            commitPO.setId(commit.getId());
+            commitPO.setMessage(commit.getMessage());
+            commitPO.setTitle(commit.getTitle());
+            commitPO.setProjectId(projectId);
+            commitPO.setTimestamp(commit.getTimestamp());
+            commitPO.setGitlabUsername(commit.getGitlabUsername());
+            commitPO.setEmail(commit.getAuthorEmail());
+            commitPO.setRelatedType(relatedType);
+            commitPO.setRelatedId(relatedId);
+
+            this.saveLinkedCommit(commitPO);
+        }
+        return true;
+    }
+}

+ 126 - 0
web/src/main/java/cn/seecoder/web/service/impl/commit/CommitQualityServiceImpl.java

@@ -0,0 +1,126 @@
+package cn.seecoder.web.service.impl.commit;
+
+import cn.seecoder.api.ApplicationProperties;
+import cn.seecoder.web.dao.commit.CommitQualityMapper;
+import cn.seecoder.web.model.enums.CommitCheckResultEnum;
+import cn.seecoder.web.model.po.commit.CommitQualityPO;
+import cn.seecoder.web.model.vo.commit.CommitQualityVO;
+import cn.seecoder.web.model.vo.hook.SonarResultHookVO;
+import cn.seecoder.web.service.commit.CommitQualityService;
+import com.alibaba.fastjson.JSONArray;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import java.text.DateFormat;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.*;
+
+@Slf4j
+@Service
+public class CommitQualityServiceImpl implements CommitQualityService {
+    @Autowired
+    CommitQualityMapper commitQualityMapper;
+
+    @Autowired
+    private ApplicationProperties applicationProperties;
+
+    @Override
+    public boolean processSonarResult(SonarResultHookVO sonarResultHookVO) {
+        try {
+            SonarResultHookVO.Properties properties = sonarResultHookVO.getProperties();
+            String commitHash = properties.getCommitHash();
+            CommitQualityPO commitQualityPO = new CommitQualityPO();
+            commitQualityPO.setProjectId(properties.getProjectId());
+            commitQualityPO.setCommitHash(commitHash);
+            commitQualityPO.setCheckResult(sonarResultHookVO.getQualityGate().getStatus());
+
+            // convert time to java date
+            DateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss");
+            simpleDateFormat.setTimeZone(TimeZone.getTimeZone("UTC"));
+            Date date = simpleDateFormat.parse(sonarResultHookVO.getChangedAt());
+            commitQualityPO.setCheckTime(date);
+
+            // convert localhost url to available url
+            String url = sonarResultHookVO.getProject().getUrl();
+            // http://localhost:9000/dashboard?id\u003dsonart-4194-sonar-sonar-83700f2455cef5ca81ee0561d1a5509229ee0bcb
+            // to
+            // https://sonarqube-test.seec.seecoder.cn/dashboard?id=sonart-4194-sonar-sonar-83700f2455cef5ca81ee0561d1a5509229ee0bcb
+            String host = applicationProperties.getSonar().getHost();
+            url = url.replace("http://localhost:9000", host).replace("\\u003", "=");
+            commitQualityPO.setResultUrl(url);
+
+            commitQualityPO.setSonarProjectKey(sonarResultHookVO.getProject().getKey());
+
+            // set quality conditions json
+            String conditionsArrayJson = JSONArray.toJSONString(sonarResultHookVO.getQualityGate().getConditions());
+            commitQualityPO.setQualityConditionsJson(conditionsArrayJson);
+
+            // update to database
+            CommitQualityPO lastCommitQualityPO = commitQualityMapper.selectByCommitHash(commitHash);
+            if (lastCommitQualityPO != null) {
+                commitQualityPO.setId(lastCommitQualityPO.getId());
+                commitQualityMapper.update(commitQualityPO);
+            } else {
+                commitQualityMapper.insert(commitQualityPO);
+            }
+            return true;
+        } catch (NullPointerException e) {
+            log.error("传入的Sonar Result VO存在问题");
+            return false;
+        } catch (ParseException e) {
+            log.error("传入的时间格式不正确,期待格式:yyyy-MM-dd'T'HH:mm:ss");
+            return false;
+        }
+    }
+
+    @Override
+    public CommitQualityVO getQualityByCommit(Integer projectId, String commitHash) {
+        CommitQualityPO commitQualityPO = commitQualityMapper.selectByCommitHash(commitHash);
+        if (commitQualityPO != null) {
+            CommitQualityVO commitQualityVO = new CommitQualityVO();
+            commitQualityVO.setCommitHash(commitHash);
+            commitQualityVO.setCheckResult(convertCommitCheckResult(commitQualityPO.getCheckResult()));
+            commitQualityVO.setCheckTime(commitQualityPO.getCheckTime());
+            commitQualityVO.setResultUrl(commitQualityPO.getResultUrl());
+            List<CommitQualityVO.QualityCondition> qualityConditions = JSONArray.parseArray(commitQualityPO.getQualityConditionsJson(), CommitQualityVO.QualityCondition.class);
+            commitQualityVO.setQualityConditions(qualityConditions);
+            return commitQualityVO;
+        } else {
+            CommitQualityVO commitQualityVO = new CommitQualityVO();
+            commitQualityVO.setCheckResult(CommitCheckResultEnum.NONE);
+            return commitQualityVO;
+        }
+    }
+
+    @Override
+    public Map<String, CommitCheckResultEnum> getCommitsQualityMapByProjectId(Integer projectId) {
+        Map<String, CommitQualityPO> stringCommitQualityPOMap = commitQualityMapper.selectMapByProjectId(projectId);
+        Map<String, CommitCheckResultEnum> stringCommitCheckResultEnumHashMap = new HashMap<>();
+        for (Map.Entry<String, CommitQualityPO> entry :
+                stringCommitQualityPOMap.entrySet()) {
+            stringCommitCheckResultEnumHashMap.put(entry.getKey(), convertCommitCheckResult(entry.getValue().getCommitHash()));
+        }
+        return stringCommitCheckResultEnumHashMap;
+    }
+
+    @Override
+    public CommitCheckResultEnum getQualityResultByCommit(String hash) {
+        CommitQualityPO commitQualityPO = commitQualityMapper.selectByCommitHash(hash);
+        if (commitQualityPO != null) {
+            return convertCommitCheckResult(commitQualityPO.getCheckResult());
+        } else {
+            return CommitCheckResultEnum.NONE;
+        }
+    }
+
+    // convert String result to Enum result
+    private CommitCheckResultEnum convertCommitCheckResult(String rawResult) {
+        if (rawResult.equals("OK")) {
+            return CommitCheckResultEnum.PASS;
+        } else {
+            return CommitCheckResultEnum.FAIL;
+        }
+    }
+}

+ 124 - 0
web/src/main/java/cn/seecoder/web/service/impl/commit/CommitServiceImpl.java

@@ -0,0 +1,124 @@
+package cn.seecoder.web.service.impl.commit;
+
+import cn.seecoder.api.ApplicationProperties;
+import cn.seecoder.common.util.LogTrackingUtil;
+import cn.seecoder.common.util.OpType;
+import cn.seecoder.web.dao.commit.CommitQualityMapper;
+import cn.seecoder.web.dao.user.UserMapper;
+import cn.seecoder.web.model.enums.CommitCheckResultEnum;
+import cn.seecoder.web.model.enums.CommitRelatedEnum;
+import cn.seecoder.web.model.po.bug_list.BugListPO;
+import cn.seecoder.web.model.po.commit.CommitQualityPO;
+import cn.seecoder.web.model.po.tree.TreeNodePO;
+import cn.seecoder.web.model.vo.commit.CommitQualityVO;
+import cn.seecoder.web.model.vo.commit.CommitVO;
+import cn.seecoder.web.model.vo.hook.SonarResultHookVO;
+import cn.seecoder.web.service.bug_list.BugListService;
+import cn.seecoder.web.service.commit.CommitLinkService;
+import cn.seecoder.web.service.commit.CommitQualityService;
+import cn.seecoder.web.service.tree.TreeNodeService;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import com.nju.edu.gitlab.SeecoderGitlabApi;
+import com.nju.edu.gitlab.vo.DiffVO;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import cn.seecoder.web.dao.commit.CommitMapper;
+import cn.seecoder.web.model.po.commit.CommitPO;
+import cn.seecoder.web.service.commit.CommitService;
+
+import java.text.DateFormat;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.*;
+import java.util.stream.Collectors;
+
+/**
+ * @author PuHong Weng
+ * @date 2021/3/23
+ * @description:
+ */
+@Service
+@Slf4j
+public class CommitServiceImpl implements CommitService {
+
+    private final SeecoderGitlabApi seecoderGitlabApi;
+
+    @Autowired
+    public CommitServiceImpl(SeecoderGitlabApi seecoderGitlabApi) {
+        this.seecoderGitlabApi = seecoderGitlabApi;
+    }
+
+    @Autowired
+    private CommitLinkService commitLinkService;
+    @Autowired
+    private CommitQualityService commitQualityService;
+
+
+    @Override
+    public List<CommitVO> getCommitsByBranchName(Integer projectId, String BranchName) {
+        List<CommitVO> allCommits = new ArrayList<CommitVO>();
+        Map<String, CommitCheckResultEnum> commitsQualityMapByProjectId = commitQualityService.getCommitsQualityMapByProjectId(projectId);
+
+        try{
+            List<com.nju.edu.gitlab.vo.commit.CommitVO> commitsResponse = seecoderGitlabApi.getCommitsByBranch(projectId, BranchName);
+            for (com.nju.edu.gitlab.vo.commit.CommitVO commit : commitsResponse){
+                CommitVO commitVO = new CommitVO(commit);
+                String hash = commitVO.getId();
+                CommitPO commitPO = commitLinkService.getLinkedCommit(hash);
+                if (commitPO != null){
+                    commitVO.setRelatedType(commitPO.getRelatedType());
+                    commitVO.setRelatedId(commitPO.getRelatedId());
+                } else {
+                    commitVO.setRelatedType(CommitRelatedEnum.NONE);
+                }
+
+                // deal with check result
+                CommitCheckResultEnum commitCheckResultEnum = commitsQualityMapByProjectId.getOrDefault(hash, CommitCheckResultEnum.NONE);
+                commitVO.setCheckResult(commitCheckResultEnum);
+
+                allCommits.add(commitVO);
+            }
+
+        } catch (Exception e){
+            e.printStackTrace();
+            return new ArrayList<>();
+        }
+
+        return allCommits;
+    }
+
+    @Override
+    public CommitVO getCommitByHash(Integer projectId, String hash) {
+        try {
+            com.nju.edu.gitlab.vo.commit.CommitVO commit = seecoderGitlabApi.getCommitByHash(projectId, hash);
+            CommitVO commitVO = new CommitVO(commit);
+            CommitPO commitPO = commitLinkService.getLinkedCommit(hash);
+            if (commitPO != null){
+                System.out.println(commitPO.getId());
+                commitVO.setRelatedType(commitPO.getRelatedType());
+                commitVO.setRelatedId(commitPO.getRelatedId());
+            } else {
+                commitVO.setRelatedType(CommitRelatedEnum.NONE);
+            }
+
+            commitVO.setCheckResult(commitQualityService.getQualityResultByCommit(hash));
+
+            return commitVO;
+        } catch (Exception e){
+            e.printStackTrace();
+            return null;
+        }
+    }
+
+    @Override
+    public Set<DiffVO> getDiff(Integer projectId, String fromHash, String toHash) {
+        try{
+            return seecoderGitlabApi.compare(projectId, fromHash, toHash);
+        }catch (Exception e){
+            e.printStackTrace();
+        }
+        return new HashSet<>();
+    }
+}

+ 0 - 322
web/src/main/java/cn/seecoder/web/service/impl/project/CommitServiceImpl.java

@@ -1,322 +0,0 @@
-package cn.seecoder.web.service.impl.project;
-
-import cn.seecoder.api.ApplicationProperties;
-import cn.seecoder.common.util.LogTrackingUtil;
-import cn.seecoder.common.util.OpType;
-import cn.seecoder.common.util.SpringUtil;
-import cn.seecoder.web.dao.commit.CommitQualityMapper;
-import cn.seecoder.web.dao.user.UserMapper;
-import cn.seecoder.web.model.enums.CommitCheckResultEnum;
-import cn.seecoder.web.model.enums.CommitRelatedEnum;
-import cn.seecoder.web.model.po.bug_list.BugListPO;
-import cn.seecoder.web.model.po.commit.CommitQualityPO;
-import cn.seecoder.web.model.po.tree.TreeNodePO;
-import cn.seecoder.web.model.vo.commit.CommitQualityVO;
-import cn.seecoder.web.model.vo.commit.CommitVO;
-import cn.seecoder.web.model.vo.hook.SonarResultHookVO;
-import cn.seecoder.web.service.bug_list.BugListService;
-import cn.seecoder.web.service.tree.TreeNodeService;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.google.gson.JsonArray;
-import com.nju.edu.gitlab.SeecoderGitlabApi;
-import com.nju.edu.gitlab.vo.DiffVO;
-import lombok.extern.slf4j.Slf4j;
-import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.stereotype.Service;
-import cn.seecoder.web.dao.commit.CommitMapper;
-import cn.seecoder.web.model.po.commit.CommitPO;
-import cn.seecoder.web.service.project.CommitService;
-
-import java.text.DateFormat;
-import java.text.ParseException;
-import java.text.SimpleDateFormat;
-import java.util.*;
-import java.util.stream.Collectors;
-
-/**
- * @author PuHong Weng
- * @date 2021/3/23
- * @description:
- */
-@Service
-@Slf4j
-public class CommitServiceImpl implements CommitService {
-
-    private final CommitMapper commitMapper;
-    private final SeecoderGitlabApi seecoderGitlabApi;
-    private final TreeNodeService treeNodeService;
-    private final BugListService bugListService;
-
-    @Autowired
-    public CommitServiceImpl(CommitMapper commitMapper, SeecoderGitlabApi seecoderGitlabApi, TreeNodeService treeNodeService, BugListService bugListService) {
-        this.commitMapper = commitMapper;
-        this.seecoderGitlabApi = seecoderGitlabApi;
-        this.treeNodeService = treeNodeService;
-        this.bugListService = bugListService;
-    }
-
-    @Autowired
-    private UserMapper userMapper;
-    @Autowired
-    private CommitQualityMapper commitQualityMapper;
-    @Autowired
-    private ApplicationProperties applicationProperties;
-
-    @Override
-    public void save(CommitPO po) {
-
-        //ANA 日志需要打出用户commit的信息
-        try{
-            JSONObject object = new JSONObject();
-            object.put("commit_id",po.getId());
-            object.put("user_id",userMapper.selectIdByUserName(po.getGitlabUsername()));
-            object.put("project_id",po.getProjectId());
-            object.put("commit_name",po.getGitlabUsername());
-            object.put("commit_time",po.getTimestamp());
-            object.put("message",po.getMessage());
-            object.put("type",po.getRelatedType());
-
-            String data = JSONObject.toJSONString(object);
-            LogTrackingUtil.log(data, OpType.COMMIT);
-        }catch (Exception e){}
-
-        commitMapper.insert(po);
-    }
-
-    @Override
-    public List<CommitPO> listByProjectAndType(Integer projectId, CommitRelatedEnum type) {
-        return commitMapper.selectByProjectIdAndType(projectId,type);
-    }
-
-
-    @Override
-    public boolean isResolved(String id) {
-        return 1 == commitMapper.isExist(id);
-    }
-
-    @Override
-    public List<CommitVO> getTreeCommit(Integer treeId) {
-        return commitMapper.selectByRelatedIdAndType(treeId,CommitRelatedEnum.TREE_ID).stream()
-                .map(CommitVO::new)
-                .collect(Collectors.toList());
-    }
-
-    @Override
-    public List<CommitVO> getBugCommit(Integer bugId) {
-        return commitMapper.selectByRelatedIdAndType(bugId,CommitRelatedEnum.BUG_ID).stream()
-                .map(CommitVO::new)
-                .collect(Collectors.toList());
-    }
-
-    @Override
-    public List<CommitVO> getCommits(Integer projectId) {
-        return commitMapper.selectByProjectId(projectId).stream()
-                .map(CommitVO::new)
-                .collect(Collectors.toList());
-    }
-
-    @Override
-    public List<CommitVO> getCommitsByBranchName(Integer projectId, String BranchName) {
-        List<CommitVO> allCommits = new ArrayList<CommitVO>();
-        Map<String, CommitQualityPO> stringCommitQualityPOMap = commitQualityMapper.selectMapByProjectId(projectId);
-
-        try{
-            List<com.nju.edu.gitlab.vo.commit.CommitVO> commitsResponse = seecoderGitlabApi.getCommitsByBranch(projectId, BranchName);
-            for (com.nju.edu.gitlab.vo.commit.CommitVO commit : commitsResponse){
-                CommitVO commitVO = new CommitVO(commit);
-                String hash = commitVO.getId();
-                CommitPO commitPO = commitMapper.selectByCommitId(hash);
-                if (commitPO != null){
-//                System.out.println(commitPO.getId());
-                    commitVO.setRelatedType(commitPO.getRelatedType());
-                    commitVO.setRelatedId(commitPO.getRelatedId());
-                } else {
-//                System.out.println("hh");
-                    commitVO.setRelatedType(CommitRelatedEnum.NONE);
-                }
-
-                // deal with check result
-                CommitQualityPO commitQualityPO = stringCommitQualityPOMap.getOrDefault(hash, null);
-                if (commitQualityPO == null) {
-                    commitVO.setCheckResult(CommitCheckResultEnum.NONE);
-                } else {
-                    commitVO.setCheckResult(convertCommitCheckResult(commitQualityPO.getCheckResult()));
-                }
-
-                allCommits.add(commitVO);
-            }
-
-        } catch (Exception e){
-            e.printStackTrace();
-            return new ArrayList<>();
-        }
-
-        return allCommits;
-    }
-
-    @Override
-    public CommitVO getCommitByHash(Integer projectId, String hash) {
-        try {
-            com.nju.edu.gitlab.vo.commit.CommitVO commit = seecoderGitlabApi.getCommitByHash(projectId, hash);
-            CommitVO commitVO = new CommitVO(commit);
-            CommitPO commitPO = commitMapper.selectByCommitId(hash);
-            if (commitPO != null){
-                System.out.println(commitPO.getId());
-                commitVO.setRelatedType(commitPO.getRelatedType());
-                commitVO.setRelatedId(commitPO.getRelatedId());
-            } else {
-                commitVO.setRelatedType(CommitRelatedEnum.NONE);
-            }
-
-            CommitQualityPO commitQualityPO = commitQualityMapper.selectByCommitHash(hash);
-            if (commitQualityPO == null) {
-                commitVO.setCheckResult(CommitCheckResultEnum.NONE);
-            } else {
-                commitVO.setCheckResult(convertCommitCheckResult(commitQualityPO.getCheckResult()));
-            }
-
-            return commitVO;
-        } catch (Exception e){
-            e.printStackTrace();
-            return null;
-        }
-    }
-
-    @Override
-    public Set<DiffVO> getDiff(Integer projectId, String fromHash, String toHash) {
-        try{
-            Set<DiffVO> diff = seecoderGitlabApi.compare(projectId, fromHash, toHash);
-            return diff;
-        }catch (Exception e){
-            e.printStackTrace();
-        }
-        return new HashSet<>();
-    }
-
-    @Override
-    public boolean link(Integer projectId, String commitHash, CommitRelatedEnum relatedType, Integer relatedId) {
-        if (relatedType == CommitRelatedEnum.NONE){
-            commitMapper.deleteByCommitId(commitHash);
-            return true;
-        }
-
-        // check if the related target exists
-        if (relatedType == CommitRelatedEnum.TREE_ID){
-            TreeNodePO node = treeNodeService.getNodeByNodeId(relatedId);
-            if (node == null){
-                return false;
-            } else if (! node.getProjectId().equals(projectId)) {
-                return false;
-            }
-        } else {
-            BugListPO node = bugListService.getBugById(relatedId);
-            if (node == null){
-                return false;
-            } else if (! node.getProjectId().equals(projectId)) {
-                return false;
-            }
-        }
-
-        // check if the commit is already exist, then update it. if not, insert a new one.
-        CommitPO commitPODB = commitMapper.selectByCommitId(commitHash);
-        if (commitPODB != null){
-            commitPODB.setRelatedType(relatedType);
-            commitPODB.setRelatedId(relatedId);
-            commitMapper.update(commitPODB);
-        } else {
-            CommitVO commit = this.getCommitByHash(projectId, commitHash);
-
-            CommitPO commitPO = new CommitPO();
-            commitPO.setId(commit.getId());
-            commitPO.setMessage(commit.getMessage());
-            commitPO.setTitle(commit.getTitle());
-            commitPO.setProjectId(projectId);
-            commitPO.setTimestamp(commit.getTimestamp());
-            commitPO.setGitlabUsername(commit.getGitlabUsername());
-            commitPO.setEmail(commit.getAuthorEmail());
-            commitPO.setRelatedType(relatedType);
-            commitPO.setRelatedId(relatedId);
-
-            this.save(commitPO);
-        }
-        return true;
-    }
-
-    @Override
-    public boolean processSonarResult(SonarResultHookVO sonarResultHookVO) {
-        try {
-            SonarResultHookVO.Properties properties = sonarResultHookVO.getProperties();
-            String commitHash = properties.getCommitHash();
-            CommitQualityPO commitQualityPO = new CommitQualityPO();
-            commitQualityPO.setProjectId(properties.getProjectId());
-            commitQualityPO.setCommitHash(commitHash);
-            commitQualityPO.setCheckResult(sonarResultHookVO.getQualityGate().getStatus());
-
-            // convert time to java date
-            DateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss");
-            simpleDateFormat.setTimeZone(TimeZone.getTimeZone("UTC"));
-            Date date = simpleDateFormat.parse(sonarResultHookVO.getChangedAt());
-            commitQualityPO.setCheckTime(date);
-
-            // convert localhost url to available url
-            String url = sonarResultHookVO.getProject().getUrl();
-            // http://localhost:9000/dashboard?id\u003dsonart-4194-sonar-sonar-83700f2455cef5ca81ee0561d1a5509229ee0bcb
-            // to
-            // https://sonarqube-test.seec.seecoder.cn/dashboard?id=sonart-4194-sonar-sonar-83700f2455cef5ca81ee0561d1a5509229ee0bcb
-            String host = applicationProperties.getSonar().getHost();
-            url = url.replace("http://localhost:9000", host).replace("\\u003", "=");
-            commitQualityPO.setResultUrl(url);
-
-            commitQualityPO.setSonarProjectKey(sonarResultHookVO.getProject().getKey());
-
-            // set quality conditions json
-            String conditionsArrayJson = JSONArray.toJSONString(sonarResultHookVO.getQualityGate().getConditions());
-            commitQualityPO.setQualityConditionsJson(conditionsArrayJson);
-
-            // update to database
-            CommitQualityPO lastCommitQualityPO = commitQualityMapper.selectByCommitHash(commitHash);
-            if (lastCommitQualityPO != null) {
-                commitQualityPO.setId(lastCommitQualityPO.getId());
-                commitQualityMapper.update(commitQualityPO);
-            } else {
-                commitQualityMapper.insert(commitQualityPO);
-            }
-            return true;
-        } catch (NullPointerException e) {
-            log.error("传入的Sonar Result VO存在问题");
-            return false;
-        } catch (ParseException e) {
-            log.error("传入的时间格式不正确,期待格式:yyyy-MM-dd'T'HH:mm:ss");
-            return false;
-        }
-    }
-
-    @Override
-    public CommitQualityVO getQualityByCommit(Integer projectId, String commitHash) {
-        CommitQualityPO commitQualityPO = commitQualityMapper.selectByCommitHash(commitHash);
-        if (commitQualityPO != null) {
-            CommitQualityVO commitQualityVO = new CommitQualityVO();
-            commitQualityVO.setCommitHash(commitHash);
-            commitQualityVO.setCheckResult(convertCommitCheckResult(commitQualityPO.getCheckResult()));
-            commitQualityVO.setCheckTime(commitQualityPO.getCheckTime());
-            commitQualityVO.setResultUrl(commitQualityPO.getResultUrl());
-            List<CommitQualityVO.QualityCondition> qualityConditions = JSONArray.parseArray(commitQualityPO.getQualityConditionsJson(), CommitQualityVO.QualityCondition.class);
-            commitQualityVO.setQualityConditions(qualityConditions);
-            return commitQualityVO;
-        } else {
-            CommitQualityVO commitQualityVO = new CommitQualityVO();
-            commitQualityVO.setCheckResult(CommitCheckResultEnum.NONE);
-            return commitQualityVO;
-        }
-    }
-
-    // convert String result to Enum result
-    private CommitCheckResultEnum convertCommitCheckResult(String rawResult) {
-        if (rawResult.equals("OK")) {
-            return CommitCheckResultEnum.PASS;
-        } else {
-            return CommitCheckResultEnum.FAIL;
-        }
-    }
-}

+ 0 - 67
web/src/main/java/cn/seecoder/web/service/project/CommitService.java

@@ -1,67 +0,0 @@
-package cn.seecoder.web.service.project;
-
-import cn.seecoder.web.model.enums.CommitRelatedEnum;
-import cn.seecoder.web.model.po.commit.CommitPO;
-import cn.seecoder.web.model.vo.commit.CommitQualityVO;
-import cn.seecoder.web.model.vo.commit.CommitVO;
-import cn.seecoder.web.model.vo.hook.SonarResultHookVO;
-import com.nju.edu.gitlab.vo.DiffVO;
-
-import java.util.List;
-import java.util.Set;
-
-/**
- * @author PuHong Weng
- * @date 2021/3/21
- * @description: 项目相关的 git commit 记录分析功能
- */
-public interface CommitService {
-
-    void save(CommitPO po);
-
-    List<CommitPO> listByProjectAndType(Integer projectId, CommitRelatedEnum type);
-
-
-    /**
-     * 不同分支可能会push相同的commit,分析过的commit不应该再分析,这里是判断是否分析共没有
-     * @param id commit hash id
-     */
-    boolean isResolved(String id);
-
-    List<CommitVO> getTreeCommit(Integer treeId);
-
-    List<CommitVO> getBugCommit(Integer bugId);
-
-    List<CommitVO> getCommits(Integer projectId);
-
-    List<CommitVO> getCommitsByBranchName(Integer projectId, String branchName);
-
-    CommitVO getCommitByHash(Integer projectId, String hash);
-
-    Set<DiffVO> getDiff(Integer projectId, String fromHash, String toHash);
-
-    /**
-     * link commit and tree node or bug
-     * @param projectId
-     * @param commitHash
-     * @param relatedType
-     * @param relatedId
-     * @return
-     */
-    boolean link(Integer projectId, String commitHash, CommitRelatedEnum relatedType, Integer relatedId);
-
-    /**
-     * process the coming json data from sonarqube
-     * @param sonarResultHookVO
-     * @return
-     */
-    boolean processSonarResult(SonarResultHookVO sonarResultHookVO);
-
-    /**
-     * get commit quality by commit hash and project id
-     * @param projectId
-     * @param commitHash
-     * @return
-     */
-    CommitQualityVO getQualityByCommit(Integer projectId, String commitHash);
-}