CQM可视化开发

    相信大家对代码质量规范已经不陌生,一般大公司都会进行代码质量检查,用来管理N多项目的质量,如果达不到要求,那么不好意思,请去搞搞代码,从今往后就成为领导重点管理对象。
    在质量管理当中,我负责去管理整个团队的CQM问题,由此走上代码规范的道路。
    从管理手段来讲,开个会,提醒大家要按照公司的规范,根据工具(SonarLint等),提交代码前,用工具check一下,有问题及时修改。宣传后大家的反响不大,而且问题越来越多,大家明显不自觉,
都认为这个没什么用啦,浪费时间,不形成习惯。大家都知道,不形成习惯的规范,就像制度摆在这里木有人执行,可悲的管理者。
    对于我来说,也觉得很难执行,有时候我只能呵呵一下,但还是要想办法管理起来,由此想通过可视化界面展现起来,让所有都看到,CQM问题不控制,会越来越多的不规范代码横空出世,下面讲讲如何
建立CQM可视化界面,
    1、思考Sonar的结果如何才能获取到?
    Sonar编译后,会记录历史记录,Sonar提供http访问接口,返回json报文格式,可获取到你想要的结果,这下有点小兴奋,有渠道获取了。
    访问URL:http://ip:port/api/resources?resource=${project_key}&&metrics=${metrics_key}
    返回格式:[{"id":793214,"uuid":"1234","key":"com.myjob","name":"CRM_JOB","scope":"PRJ","qualifier":"TRK","date":"2016-11-25T19:18:35+0800","creationDate":"2016-04-25T10:26:12+0800","lname":"CRM_JOB","version":"1.0","description":"","msr":[{"key":"critical_violations","val":0.0,"frmt_val":"0"}]}]
    开始编码:
    public  Map reqeustIde(String resource, String metrics){
        final HttpConnectionManagerParams params = new HttpConnectionManagerParams();
        params.setConnectionTimeout(AbstractQuery.DEFAULT_TIMEOUT_MILLISECONDS);
        params.setSoTimeout(AbstractQuery.DEFAULT_TIMEOUT_MILLISECONDS);
        params.setDefaultMaxConnectionsPerHost(4);
        params.setMaxTotalConnections(40);

        final MultiThreadedHttpConnectionManager connectionManager = new MultiThreadedHttpConnectionManager();
        connectionManager.setParams(params);
        HttpClient httpClient = new HttpClient(connectionManager);
        httpClient.getParams().setAuthenticationPreemptive(true);
        Credentials defaultcreds = new UsernamePasswordCredentials("abcdefg", "123456");
        httpClient.getState().setCredentials(AuthScope.ANY, defaultcreds);
        final PostMethod post = new PostMethod("http://localhost:8080/api/resources?resource=" + resource + "&metrics=" + metrics);
        try {
            httpClient.executeMethod(post);
            String jsonStr = post.getResponseBodyAsString();
            System.out.println(jsonStr);
            ObjectMapper mapper = new ObjectMapper();
            return mapper.readValue(jsonStr.substring(1, jsonStr.length() - 1), Map.class);
        } catch (HttpException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
        return new HashMap();
    }
    2、如何把这些信息转换成模型呢?
    模型考虑维度:
    ①编译的分支项目,就是要扫描的编译项目
    ②扫描的issuess类型
    ③扫描Sonar后的结果记录,定时扫描,如果已经扫描过就不记录
    ④分支项目的临界值,保证这个值不能被超过,如果超过则告警
    经过我慎重思考,产出一下模型:
    create table tb_project(
        id bigint UNSIGNED not null auto_increment comment '主键标识',
        project_name varchar(100) not null default '' comment '编译项目名称',
        project_key varchar(100) not null default '' comment '项目key',
        create_time timestamp NOT NULL DEFAULT '1980-01-01 00:00:00' COMMENT '记录创建时间',
        last_update_time timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '记录最后修改时间',
        PRIMARY KEY (`id`)
    );


    create table tb_type(
        id bigint UNSIGNED not null auto_increment comment '主键标识',
        type_name varchar(100) not null default '' comment '扫描类型中文名称',
        type_key varchar(100) not null default '' comment '扫描key',
        create_time timestamp NOT NULL DEFAULT '1980-01-01 00:00:00' COMMENT '记录创建时间',
        last_update_time timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '记录最后修改时间',
        PRIMARY KEY (`id`)
    );

    create table tb_scan_critical_value(
        id bigint UNSIGNED not null auto_increment comment '主键标识',
        project_key varchar(100) not null default '' comment '项目key',
        type_key varchar(100) not null default '' comment '扫描key',
        critical_val  bigint(20) not null default 0 comment '临界值',
        current_val  bigint(20) not null default 0 comment '当前值',
        create_time timestamp NOT NULL DEFAULT '1980-01-01 00:00:00' COMMENT '记录创建时间',
        last_update_time timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '记录最后修改时间',
        PRIMARY KEY (`id`)
    );

    create table tb_scan_record(
        id bigint UNSIGNED not null auto_increment comment '主键标识',
        project_name varchar(100) not null default '' comment '编译项目名称',
        project_key varchar(100) not null default '' comment '项目key',
        uuid varchar(100) not null default '' comment '项目uuid',
        version varchar(100) not null default '' comment '版本号,以时间维度',
        key_date varchar(50) not null default '' comment '',
        key_creationdate varchar(50) not null default '' comment '',
        lname varchar(100) not null default '' comment '',
        description varchar(200) not null default '' comment '描述',
        type_key varchar(100) not null default '' comment '扫描key',
        type_val bigint(20) not null default 0 comment '扫描值',
        PRIMARY KEY (`id`)
    );
    3、action请求处理逻辑思考
    有以下步骤:
    ①查询需要扫描的内容
    select a.project_key,b.type_key from tb_project a , tb_type b
    ②查出重复的信息
    select distinct project_key,version from tb_scan_record where project_key ='${project_key}' and version ='${version}'
    ③把扫描结果插入到结果表中:tb_scan_record
    ④:插入临界值表:tb_scan_critical_value,如果已经存在则更新critical_val、current_val值,如果critical_val>current_val,则临界值以后以current_val为准,这里控制会越来越小。
    ⑤统计结果输出
    select project_name,project_key,sum(critical_val) as total_critical_val,sum(current_val)  as total_current_val from (
                select a.project_name,b.project_key,b.critical_val,b.current_val  
                 from tb_project a,tb_scan_critical_value b where a.project_key = b.project_key  order by  a.project_key) c   group by project_name,project_key
    ⑥查询类型的输出:
    select a.project_name,b.project_key,b.critical_val as critical_val,b.type_key,b.current_val as current_val from tb_project a,tb_scan_critical_value b where a.project_key = b.project_key order by project_key
    4、编写图形界面

    Jsp页面:
 <%@page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>CQM可视化界面</title>
<script language="JavaScript">
function myrefresh()
{
       window.location.reload();
}
setTimeout('myrefresh()',60000 * 10 ); //指定1秒刷新一次
</script>
</head>
<body>
    <table cellpadding="1" cellspacing="0" width="100%" style="border-width: 1px;font-size:55px;" >
        <tr align="center">
            <td>CQM可视化界面</td>
        </tr>
    </table>
    <table cellpadding="1" cellspacing="0" width="100%" style="border-width: 1px;font-size:55px;" >
    <c:forEach  items="${totalPageMap}" var="totalObj">
        <tr>
            <c:if test="${totalObj.status== 'fail'}">
                <td style="background-color: red">
                    ${totalObj.project_name}【临界值:${totalObj.total_critical_val}当前值:${totalObj.total_current_val}】
                </td>
            </c:if>
            <c:if test="${totalObj.status== 'succeed'}">
                <td style="background-color: green">
                    ${totalObj.project_name}【临界值:${totalObj.total_critical_val}当前值:${totalObj.total_current_val}】
                </td>
            </c:if>
        </tr>
    </c:forEach>
    </table>
    <table cellpadding="1" cellspacing="0" width="100%" style="border-width: 1px;font-size:18px;" >
        <tr style="background-color: green">
            <td>项目</td>
            <td>等级类型</td>
            <td>临界值</td>
            <td>当前值</td>
        </tr>
        <c:forEach  items="${pageMap}" var="obj">
            <c:if test="${obj.status == 'fail'}">
                <tr style="background-color: red">
                    <td >
                        ${obj.project_name}
                    </td>
                    <td >
                        ${obj.type_key}
                    </td>
                    <td >
                        ${obj.critical_val}
                    </td>
                    <td >
                        ${obj.current_val}
                    </td>
                </tr>
            </c:if>
            <c:if test="${obj.status== 'succeed'}">
                <tr style="background-color: green">
                    <td >
                        ${obj.project_name}
                    </td>
                    <td >
                        ${obj.type_key}
                    </td>
                    <td >
                        ${obj.critical_val}
                    </td>
                    <td >
                        ${obj.current_val}
                    </td>
                </tr>    
            </c:if>
        </c:forEach>
    </table>
</body>
</html>
    
   作者:godsfer

转载于:https://my.oschina.net/u/2292306/blog/797041

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值