diff --git a/tcms/settings/common.py b/tcms/settings/common.py index a263fa3449..17037fc8a1 100644 --- a/tcms/settings/common.py +++ b/tcms/settings/common.py @@ -107,6 +107,7 @@ (_('Breakdown'), reverse_lazy('testing-breakdown')), (_('Status matrix'), reverse_lazy('testing-status-matrix')), (_('Execution trends'), reverse_lazy('testing-execution-trends')), + (_('TestCase health'), reverse_lazy('test-case-health')), ]), ('More coming soon', 'http://kiwitcms.org/blog/kiwi-tcms-team/2019/03/03/legacy-reports-become-telemetry/'), diff --git a/tcms/telemetry/static/telemetry/js/testing/test-case-health.js b/tcms/telemetry/static/telemetry/js/testing/test-case-health.js new file mode 100644 index 0000000000..84840f3fe6 --- /dev/null +++ b/tcms/telemetry/static/telemetry/js/testing/test-case-health.js @@ -0,0 +1,94 @@ +$(document).ready(() => { + loadInitialProduct(); + loadInitialTestPlans(); + + document.getElementById('id_product').onchange = () => { + update_version_select_from_product(); + update_build_select_from_product(true); + updateTestPlanSelectFromProduct(drawPage); + }; + + document.getElementById('id_version').onchange = drawPage; + document.getElementById('id_build').onchange = drawPage; + document.getElementById('id_test_plan').onchange = drawPage; + + $('#id_after').on('dp.change', drawPage); + $('#id_before').on('dp.change', drawPage); + + drawPage(); +}) + +function drawPage() { + const query = {}; + + const productId = $('#id_product').val(); + if (productId) { + query['case__plan__product'] = productId; + } + + const versionId = $('#id_version').val(); + if (versionId) { + query['case__plan__product_version'] = versionId; + } + + const buildId = $('#id_build').val(); + if (buildId) { + query['build_id'] = buildId; + } + + const testPlanId = $('#id_test_plan').val(); + if (testPlanId) { + query['case__plan__plan_id'] = testPlanId; + } + + const dateBefore = $('#id_before'); + if (dateBefore.val()) { + query['close_date__lte'] = dateBefore.data('DateTimePicker').date().format('YYYY-MM-DD 23:59:59'); + } + + const dateAfter = $('#id_after'); + if (dateAfter.val()) { + query['close_date__gte'] = dateAfter.data('DateTimePicker').date().format('YYYY-MM-DD 00:00:00'); + } + + jsonRPC("Testing.test_case_health", query, data => { + drawTable('#test-case-health-table', data); + }) +} + +function drawTable(selector, data) { + $(`${selector} > tbody`).remove() + + $(selector).DataTable({ + data: data, + columns: [ + { + data: null, + render: renderTestCaseColumn + }, + { + data: null, + render: renderFailedExecutionsColumn + }, + { + data: null, + render: renderPercentColumn + }, + ], + paging: false, + ordering: false, + dom: "t" + }); +} + +function renderTestCaseColumn(data) { + return `TC-${data.case_id}: ${data.case_summary}`; +} + +function renderFailedExecutionsColumn(data) { + return `${data.count.fail} of ${data.count.all}`; +} + +function renderPercentColumn(data) { + return Number.parseFloat(data.count.fail / data.count.all * 100).toFixed(1); +} diff --git a/tcms/telemetry/templates/telemetry/testing/test-case-health.html b/tcms/telemetry/templates/telemetry/testing/test-case-health.html new file mode 100644 index 0000000000..399e3afb56 --- /dev/null +++ b/tcms/telemetry/templates/telemetry/testing/test-case-health.html @@ -0,0 +1,100 @@ +{% extends "base.html" %} +{% load i18n %} +{% load static %} + +{% block title %}{% trans "TestCase Health" %}{% endblock %} + +{% block contents %} +
{% trans "Most frequently failing test cases" %} | +||
---|---|---|
{% trans "Test Case" %} | +{% trans "Failed executions" %} | +{% trans "% of failed executions" %} | +