禅道数据的统计【源代码在文末】

项目管理工具很多,我们公司一直用禅道做bug管理,随便把项目管理也搞到禅道上,从需求建立--立项--分任务--执行任务--完成,用的是开源版本,所以少了很多报表,用过一段时间专业版,统计报表数据也不怎么好用,报表都不是自己想要的。

所以自己用python搞了一套统计:

 

 

 简单模块:

1.各种报表分个类,比如bug的,周报,日报,项目统计等

2.common,处理table,发邮件,链接数据库等

3.sql_script,存放数据库脚本的

贴几个项目代码【需要的拿去用】:

## sql内部用的,数据量不大,没怎么优化,怎么方便怎么写

#BUG每天分布情况


SELECT
    z.`部门组`,
    z.`被指派`,
    CONCAT(
        z.提交人,
        '(',
        t.realname,
        ')'
    ) 提交人,
    z.`项目名称`,
    z.`Bug标题`,
    z.Bug状态,
    z.提交时间
FROM
    (
        SELECT
            d.`name` 部门组,
            CONCAT(
                a.assignedTo,
                '(',
                u.realname,
                ')'
            ) 被指派,
            a.openedBy 提交人,
            a.`name` 项目名称,
            CONCAT(a.id, '--', a.title) Bug标题,
            CASE
        WHEN a.`status` = 'resolved' THEN
            '已解决'
        WHEN a.`status` = 'active' THEN
            '激活'
        WHEN a.`status` = 'closed' THEN
            '已关闭'
        END Bug状态,
        a.openedDate 提交时间
    FROM
        (
            SELECT
                b.id,
                p.`name`,
                b.title,
                b.`status`,
                b.openedBy,
                b.openedDate,
                CASE
            WHEN LENGTH(b.resolvedBy) > 0 THEN
                b.resolvedBy
            ELSE
                b.assignedTo
            END assignedTo,
            b.resolvedBy
        FROM
            zt_bug AS b,
            zt_project AS p
        WHERE
            b.openedDate >= CURDATE() # DATE_SUB(CURDATE(), INTERVAL 7 DAY)
        AND b.project NOT IN ('107')
        AND b.project = p.id
        AND b.deleted = '0'
        ) AS a,
        zt_user AS u,
        zt_dept AS d
    WHERE
        a.assignedTo = u.account
    AND u.dept = d.id
    ) AS z,
    zt_user AS t
WHERE
    z.`提交人` = t.account
ORDER BY
    部门组 ASC,
    被指派 ASC,
    Bug状态 ASC
# -*- coding: UTF-8 -*-
# 表列合并算法

import numpy as np


# 统计相同的列的值及个数
def find_same_column(l, end=0, exc=''):
    """
    :param l: 需要计算的列表
    :param end: 需要合并的列数(前end列合并),默认为0列计算
    :param exc: 列需要排除合并的值,默认为所有值都不合并
    :return al: 返回计算好的列表
    """
    al = []
    for i in range(len(l)):
        # if end == 0:
        #     end = 100000
        stop = end
        if exc == '':
            exc = '!@#$%^&*'
        logo = str(exc)
        last = ''
        num = 1
        part = []
        for x in range(len(l[i])):
            # 只合并列数范围
            if i < stop:
                # 列值和标识值相同则不合并
                if str(l[i][x]) != str(logo):
                    # 找相同的列值,相等则计数+1
                    if l[i][x] == last:
                        num += 1
                        # 如果列表循环完则append计数
                        if x + 1 == len(l[i]):
                            part.append(str(num))
                    # 如果列值不同则更新last值并重置计数位
                    else:
                        # 上一个列表的num没有append,这里append
                        # 如果是列表第一个则不更新,如果列表上一个值与标识相同也不更新
                        if x != 0 and str(l[i][x-1]) != str(logo):
                            part.append(str(num))
                        last = l[i][x]
                        part.append(last)
                        num = 1
                        # 如果列表循环完append计数
                        if x+1 == len(l[i]):
                            part.append(str(num))
                # 列表值与标识为相同不合并,直接append
                else:
                    # 还是要判断是否append num
                    if x != 0 and str(l[i][x-1]) != str(logo):
                        part.append(str(num))
                    part.append(l[i][x])
                    part.append(str(1))
            else:
                part.append(l[i][x])
                part.append(str(1))
        al.append(part)
    return al


# 处理td标签
def deal_td(l):
    """
    :param l:  需要处理td标签的列表
    :return al: 返回处理好的列表
    """
    al = []
    for i in range(len(l)):
        part = []
        for x in range(0, len(l[i]), 2):
            if x == len(l[i]):
                break
            t_value = str(l[i][x])
            t_sum = int(l[i][x+1])
            if t_sum >= 2:
                for num in range(t_sum):
                    if num == 0:
                        part.append('<td rowspan="%s">' % str(t_sum) + t_value + '</td>')
                    else:
                        part.append('')
            else:
                part.append('<td>' + t_value + '</td>')

        al.append(part)
    return al


# 处理tr标签
def deal_tr(l):
    """
    :param l: 需要处理tr的列表
    :return: 返回处理好的tr字符串
    """
    # 倒置列表
    td = np.tile(l, 1).T.tolist()
    tr = ''
    for i in td:
        l_tr = ''
        for x in range(len(i)):
            l_tr += i[x]
            s_tr = '<tr>' + l_tr + '</tr>' + '\n'
        tr += s_tr
    return tr
# coding = utf-8
# 禅道项目度量--每日bug激活统计


import sys
import datetime
from common import common_mail_test as mail
from common import common_read_sql as read_sql
from common import common_mysql_config as mysql


# 数据获取
def deal_mysql(f):
    """
    数据获取与处理
    :param f:
    :return:
    """
    cursor = mysql.db.cursor()
    sql = read_sql.read_sql(f)
    cursor.execute(sql)
    results = cursor.fetchall()
    cursor.close()
    mysql.db.close()
    # tuple类型转换为list类型
    li = list(results)
    """
    把id相同的数据的放入pl列表,再把列表放入al列表
    """
    al = []
    pl = []
    for i in range(len(li)):
        if i == 0:
            pl.append(li[i])
        # 如果和列表里的名字相同,继续append
        if li[i][0] == li[i - 1][0]:
            pl.append(li[i])
        # 如果不相同,没有到末尾,把当前列表加入al列表,并清空pl列表/i-1 >0 排除i=0情况
        if li[i][0] != li[i - 1][0] and i - 1 > 0 and len(pl) != 0:
            al.append(pl)
            pl = []

        if i != len(li) - 1:
            # 如果和之前的不同,和之后的也不同,且不是末尾:
            if li[i][0] != li[i - 1][0] and i - 1 > 0 and li[i][0] != li[i + 1][0]:
                pl.append(li[i])
                al.append(pl)
                pl = []
            # 如果和之前的不同,和之后的相同,且不是末尾:
            if li[i][0] != li[i - 1][0] and i - 1 > 0 and li[i][0] == li[i + 1][0]:
                pl.append(li[i])

        # 如果是末尾
        if i == len(li) - 1:
            # pl.append(li[i])  # 后来发现重复插入最后一条数据  先注释
            al.append(pl)
    # 只取满足日期的数据
    el = []
    for i in al:
        for x in i:
            if str(x[3]).split(' ')[0] == str(datetime.datetime.now()).split(' ')[0]:
                el.append(i)
                break
    return el


# 处理html
def deal_html(tl):
    """
    生成html
    :param tl:
    :return:
    """
    subject = 'BUG激活统计'
    head = """
        <head>
        <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
        <title>BUG被激活</title>
        <body>
        <div id="container">
         <center>
        <strong>汇总时间: """ + str(datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')) + """</strong>
        <p><strong>备注:BUG被激活次数大于等于3次</strong></p>
        <div id="content">
         <table border="1" cellpadding="2" style="border-collapse:collapse;margin-top:10px">
         <tr>
           <td colspan="5" align="center" height="35px"><font size="5"><strong>BUG激活情况</strong></font></td> 
         </tr>
    """
    ht = ''
    for i in tl:

        zj = ''
        beg = ''
        a = ''
        b = ''
        c = ''
        title = """
                <tr>
                   <td colspan="5" width="120" align="left"><font size="3" height="30px" ><strong>BUG标题:</strong>
                   <a href="http://chandao.thecover.cn/zentao/bug-view-%s.html">%s</a></font></td>
                </tr>
                """ % (i[0][0], i[0][4])
        for x in range(len(i)):
            ti = """
                  <tr>
                    <td rowspan="%s" width="80" align="center"><font size="3"><strong>ID</strong></font></td>
                    <td width="100" align="center"><font size="3"><strong>操作人</strong></font></td>
                    <td width="100" align="center"><font size="3"><strong>解决类型</strong></font></td>
                    <td width="180" align="center"><font size="3"><strong>操作时间</strong></font></td>
                    <td width="700" align="left"><font size="3"><strong>备注</strong></font></td>
                  </tr> 
                """
            if x == 0:
                beg = """
                       <tr>
                         <td rowspan="%s" width="80" align="center"><font size="3">%s</font></td>
                         <td width="100" align="center"><font size="3">%s</font></td>
                         <td width="100" align="center"><font size="3">%s</font></td>
                         <td width="180" align="center"><font size="3">%s</font></td>
                         <td width="700" align="left"><font size="3">%s</font></td>
                       </tr> 
                    """ % (len(i), i[x][0], i[x][1], i[x][2], i[x][3], i[x][5])
            else:
                a = """<tr><td width="100" align="center"><font size="3">%s</font></td>""" % i[x][1]
                if i[x][2] == 'activated':
                    b = """<td width="100" align="center"><font size="3" color="red">%s</font></td>""" % i[x][2]
                else:
                    b = """<td width="100" align="center"><font size="3">%s</font></td>""" % i[x][2]
                c = """
                    <td width="180" align="center"><font size="3">%s</font></td>
                    <td width="700" align="left"><font size="3">%s</font></td>
                    </tr> 
                    """ % (i[x][3], i[x][5])

            zj += a + b + c

            ho = """
                <tr>
                   <td colspan="5" width="120" align="right" ><font size="3" color="white">.</font></td>
                 </tr>
                """
        ht += title + ti + beg + zj + ho

    end = """
            </table>
            <p><font size="3" ><center>--------------------<strong><a href="http://chandao.thecover.cn/">汇总数据源于禅道系统</a>
            </strong>--------------------</center></font>
            </center>
            </div>
            </div>
            </div>
            </body>
            </html>
        """
    html = head + ht + end
    return subject, html


mysql_l = deal_mysql(sys._getframe())
if len(mysql_l) > 0:
    s, h = deal_html(mysql_l)
    try:
        if mail.cs_mail_send(s, h):
            print('Send success')
        else:
            print('Send failure')
    except Exception as e:
        raise e
else:
    print("NO Data !")

 

统计展示:

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

配置jenkins定时跑任务执行

 

源代码下载地址:

 

https://download.csdn.net/download/tengdakuaijie1/12272565

 

posted @ 2019-11-04 15:08  drewgg  阅读(1478)  评论(6编辑  收藏