Skip to content
This repository was archived by the owner on Nov 19, 2024. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions plugin/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -154,6 +154,7 @@
<dependency>
<groupId>io.jenkins.plugins</groupId>
<artifactId>echarts-api</artifactId>
<version>5.4.0-4</version>
</dependency>
<dependency>
<groupId>io.jenkins.plugins</groupId>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@
import edu.hm.hafner.echarts.BuildResult;
import edu.hm.hafner.echarts.ChartModelConfiguration;
import edu.hm.hafner.echarts.JacksonFacade;
import edu.hm.hafner.echarts.Palette;
import edu.hm.hafner.echarts.line.LineSeries;
import edu.hm.hafner.echarts.line.LineSeries.FilledMode;
import edu.hm.hafner.echarts.line.LineSeries.StackedMode;
Expand All @@ -12,6 +11,7 @@

import io.jenkins.plugins.coverage.metrics.model.CoverageStatistics;
import io.jenkins.plugins.coverage.metrics.model.Messages;
import io.jenkins.plugins.echarts.JenkinsPalette;

/**
* Builds the Java side model for a trend chart showing the line and branch coverage of a project. The number of builds
Expand All @@ -23,6 +23,9 @@
* @see JacksonFacade
*/
public class CoverageTrendChart {
private static final String LINE_COVERAGE_COLOR = JenkinsPalette.GREEN.normal();
private static final String BRANCH_COVERAGE_COLOR = JenkinsPalette.GREEN.dark();

/**
* Creates the chart for the specified results.
*
Expand All @@ -42,7 +45,7 @@ public LinesChartModel create(final Iterable<BuildResult<CoverageStatistics>> re
LinesChartModel model = new LinesChartModel(dataSet);
if (dataSet.isNotEmpty()) {
LineSeries lineSeries = new LineSeries(Messages.Metric_LINE(),
Palette.GREEN.getNormal(), StackedMode.SEPARATE_LINES, FilledMode.FILLED,
LINE_COVERAGE_COLOR, StackedMode.SEPARATE_LINES, FilledMode.FILLED,
dataSet.getSeries(CoverageSeriesBuilder.LINE_COVERAGE));
model.addSeries(lineSeries);
model.useContinuousRangeAxis();
Expand All @@ -59,7 +62,7 @@ private static void addSecondSeries(final LinesDataSet dataSet, final LinesChart
final String name, final String seriesId) {
if (dataSet.containsSeries(seriesId)) {
LineSeries branchSeries = new LineSeries(name,
Palette.GREEN.getHover(), StackedMode.SEPARATE_LINES, FilledMode.FILLED,
BRANCH_COVERAGE_COLOR, StackedMode.SEPARATE_LINES, FilledMode.FILLED,
dataSet.getSeries(seriesId));

model.addSeries(branchSeries);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,9 @@ public String getId() {
public TableConfiguration getTableConfiguration() {
TableConfiguration tableConfiguration = new TableConfiguration();
tableConfiguration.responsive();
tableConfiguration.select(SelectStyle.SINGLE);
if (getId().contains("inline")) {
tableConfiguration.select(SelectStyle.SINGLE);
}
renderer.configureTable(tableConfiguration);
return tableConfiguration;
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
.coverage-cell-outer {
border: 1px solid var(--medium-grey);
border: 1px solid var(--dark-grey);
border-radius: 10px;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

<bs:page it="${it}">

<link rel="stylesheet" href="${resURL}/plugin/code-coverage-api/css/style.css"/>
<link rel="stylesheet" href="${resURL}/plugin/code-coverage-api/css/view-model.css"/>

<div class="row py-3 flex-nowrap">

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,10 @@
<st:adjunct includes="io.jenkins.plugins.echarts"/>
<st:adjunct includes="io.jenkins.plugins.data-tables-select"/>

<link rel="stylesheet" href="${resURL}/plugin/code-coverage-api/css/custom-style.css"/>
<link rel="stylesheet" href="${resURL}/plugin/code-coverage-api/css/style.css"/>
<link rel="stylesheet" href="${resURL}/plugin/font-awesome-api/css/jenkins-style.css"/>
<link rel="stylesheet" href="${resURL}/plugin/code-coverage-api/css/view-model.css"/>

<script type="text/javascript" src="${resURL}/plugin/code-coverage-api/js/view-model.js"/>
<script type="text/javascript" src="${resURL}/plugin/code-coverage-api/js/colors.js"/>

<j:set var="formatter" value="${it.formatter}"/>

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,8 @@
<st:adjunct includes="io.jenkins.plugins.echarts"/>
<st:adjunct includes="io.jenkins.plugins.data-tables-select"/>

<link rel="stylesheet" href="${resURL}/plugin/code-coverage-api/css/custom-style.css"/>
<link rel="stylesheet" href="${resURL}/plugin/code-coverage-api/css/style.css"/>
<link rel="stylesheet" href="${resURL}/plugin/font-awesome-api/css/jenkins-style.css"/>
<link rel="stylesheet" href="${resURL}/plugin/code-coverage-api/css/style.css"/>

<script type="text/javascript" src="${resURL}/plugin/code-coverage-api/js/charts.js"/>
<script type="text/javascript" src="${resURL}/plugin/code-coverage-api/js/colors.js"/>
Expand Down
14 changes: 0 additions & 14 deletions plugin/src/main/webapp/css/column-style.css

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -93,3 +93,73 @@
#coverage-table td {
vertical-align: middle;
}

table.source {
border-spacing: 0;
border-collapse: collapse;
border: 1px solid #bbb;
width: 100%;
}

table.source td {
border-spacing: 0;
border-collapse: collapse;
border: 0 solid #bbb;
padding-left: 0.2em;
padding-right: 0.2em;
font-family: monospace;
}

table.source .text {
margin-top: -1px;
}

table.source td.line {
text-align: right;
border-width: 0 1px 0 0;
}

table.source td.hits {
text-align: right;
border-width: 0px 1px 0px 0px;
}

table.source th {
padding-left: 0.5em;
font-weight: bold;
font-family: serif;
background-color: #f0f0f0;
border-width: 1px 1px 1px 1px;
text-align: left;
}

table.source tr.coverFull {
background-color: var(--green);
color: var(--white);
font-weight: bold;
}

table.source tr.coverPart {
background-color: var(--orange);
color: var(--text-color);
font-weight: bold;
}

table.source tr.coverPart td.hits, table.source tr.coverNone td.hits {
font-weight: bold;
}

table.source tr.coverNone {
background-color: var(--red);
color: var(--white);
font-weight: bold;
}

table.source tr.noCover {
background-color: var(--background-color);
color: var(--text-color);
}

table.source tr.coverSkip {
background-color: #b4b4b4;
}
55 changes: 23 additions & 32 deletions plugin/src/main/webapp/js/view-model.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,17 @@
/* global jQuery3, viewProxy, echartsJenkinsApi, bootstrap5 */

getJenkinsColors = function (colors) {
// TODO: also handle HSL colors and parse them to hex in order to use dark mode colors
const colorHexMapping = new Map;
colors.forEach(function (jenkinsId) {
const colorHex = getComputedStyle(document.body).getPropertyValue(jenkinsId);
if (colorHex.match(/^#[a-fA-F0-9]{6}$/) !== null) {
colorHexMapping.set(jenkinsId, colorHex);
}
})
return colorHexMapping;
};

const CoverageChartGenerator = function ($) {
var selectedTreeNode;

Expand All @@ -14,41 +26,18 @@ const CoverageChartGenerator = function ($) {
}
});
};

function getTextColor() {
return getComputedStyle(document.body).getPropertyValue('--text-color') || '#333';
}

/**
* Searches for a Jenkins color by a color id.
*
* @param jenkinsColors The available Jenkins colors
* @param id The color id
* @param defaultValue The default value if the id does not exist
* @param alpha The alpha value between [0;255]
* @returns {string} the hex code of the Jenkins color or, if not existent, the default value
*/
function getJenkinsColorById(jenkinsColors, id, defaultValue, alpha) {
const alphaHex = alpha.toString(16);
if (jenkinsColors.has(id)) {
const color = jenkinsColors.get(id);
if (color.match(/^#[a-fA-F0-9]{6}$/) !== null) {
return color + alphaHex;
}
}
return defaultValue + alphaHex;
}

function createOverview(overview, id, jenkinsColors) {
const missedColor = getJenkinsColorById(jenkinsColors, "--red", "#ff4d65", 120);
const coveredColor = getJenkinsColorById(jenkinsColors, "--green", "#4bdf7c", 120);
function createOverview(overview, id) {
const missedColor = echartsJenkinsApi.resolveJenkinsColor("--red");
const missedText = echartsJenkinsApi.resolveJenkinsColor("--white");
const coveredColor = echartsJenkinsApi.resolveJenkinsColor("--green");
const coveredText = echartsJenkinsApi.resolveJenkinsColor("--white");

const summaryChartDiv = $('#' + id);
summaryChartDiv.height(overview.metrics.length * 31 + 150 + 'px');
const summaryChart = echarts.init(summaryChartDiv[0]);
summaryChartDiv[0].echart = summaryChart;

const textColor = getTextColor();
const textColor = echartsJenkinsApi.getTextColor();

const summaryOption = {
tooltip: {
Expand Down Expand Up @@ -143,7 +132,8 @@ const CoverageChartGenerator = function ($) {
label: {
show: true,
position: 'insideLeft',
color: 'black',
color: coveredText,
fontWeight: 'bold',
formatter: function (obj) {
return overview.covered[obj.dataIndex];
}
Expand All @@ -162,7 +152,8 @@ const CoverageChartGenerator = function ($) {
label: {
show: true,
position: 'insideRight',
color: 'black',
color: missedText,
fontWeight: 'bold',
formatter: function (obj) {
return overview.missed[obj.dataIndex];
}
Expand Down Expand Up @@ -359,7 +350,7 @@ const CoverageChartGenerator = function ($) {
renderTrendChart();

viewProxy.getOverview(function (t) {
createOverview(t.responseObject(), 'coverage-overview', jenkinsColors);
createOverview(t.responseObject(), 'coverage-overview');
});

$('.tree-chart').each(function () {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,10 +15,12 @@
import edu.hm.hafner.echarts.ChartModelConfiguration.AxisType;
import edu.hm.hafner.echarts.line.LinesChartModel;
import edu.hm.hafner.echarts.line.LinesDataSet;
import edu.hm.hafner.util.ResourceTest;
import edu.hm.hafner.util.VisibleForTesting;

import io.jenkins.plugins.coverage.metrics.model.CoverageStatistics;

import static net.javacrumbs.jsonunit.assertj.JsonAssertions.*;
import static org.assertj.core.api.Assertions.*;
import static org.mockito.Mockito.*;

Expand All @@ -27,7 +29,7 @@
*
* @author Ullrich Hafner
*/
class CoverageSeriesBuilderTest {
class CoverageSeriesBuilderTest extends ResourceTest {

Check notice

Code scanning / CodeQL

Unused classes and interfaces

Unused class: CoverageSeriesBuilderTest is not referenced within this codebase. If not used as an external API it should be removed.
@Test
void shouldHaveEmptyDataSetForEmptyIterator() {
CoverageSeriesBuilder builder = new CoverageSeriesBuilder();
Expand Down Expand Up @@ -99,6 +101,37 @@ void shouldHaveTwoValuesForSingleBuild() {
assertThat(dataSet.getSeries(CoverageSeriesBuilder.BRANCH_COVERAGE)).containsExactly(75.0);
}

@Test
void shouldHaveTwoValuesForTwoBuilds() {
CoverageSeriesBuilder builder = new CoverageSeriesBuilder();

BuildResult<CoverageStatistics> first = createResult(1,
new CoverageBuilder().setMetric(Metric.LINE).setCovered(1).setMissed(1).build(),
new CoverageBuilder().setMetric(Metric.BRANCH).setCovered(3).setMissed(1).build());
BuildResult<CoverageStatistics> second = createResult(2,
new CoverageBuilder().setMetric(Metric.LINE).setCovered(1).setMissed(3).build(),
new CoverageBuilder().setMetric(Metric.BRANCH).setCovered(1).setMissed(3).build());

LinesDataSet dataSet = builder.createDataSet(createConfiguration(), List.of(first, second));

assertThat(dataSet.getDomainAxisSize()).isEqualTo(2);
assertThat(dataSet.getDomainAxisLabels()).containsExactly("#1", "#2");

assertThat(dataSet.getDataSetIds()).containsExactlyInAnyOrder(
CoverageSeriesBuilder.LINE_COVERAGE,
CoverageSeriesBuilder.BRANCH_COVERAGE);

assertThat(dataSet.getSeries(CoverageSeriesBuilder.LINE_COVERAGE))
.containsExactly(50.0, 25.0);
assertThat(dataSet.getSeries(CoverageSeriesBuilder.BRANCH_COVERAGE))
.containsExactly(75.0, 25.0);

CoverageTrendChart trendChart = new CoverageTrendChart();
var model = trendChart.create(List.of(first, second), createConfiguration());

assertThatJson(model).isEqualTo(toString("chart.json"));
}

private ChartModelConfiguration createConfiguration() {
ChartModelConfiguration configuration = mock(ChartModelConfiguration.class);
when(configuration.getAxisType()).thenReturn(AxisType.BUILD);
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
{
"domainAxisLabels": [
"#1", "#2"
],
"buildNumbers": [
1, 2
],
"series": [
{
"name": "Line Coverage",
"type": "line",
"symbol": "circle",
"data": [
50.0, 25.0
],
"itemStyle": {
"color": "--green",
"borderColor": "#ffffff",
"borderWidth": 0
},
"stack": "",
"areaStyle": {
"normal": true
}
},
{
"name": "Branch Coverage",
"type": "line",
"symbol": "circle",
"data": [
75.0, 25.0
],
"itemStyle": {
"color": "--dark-green",
"borderColor": "#ffffff",
"borderWidth": 0
},
"stack": "",
"areaStyle": {
"normal": true
}
}
],
"domainAxisItemName": "Build",
"integerRangeAxis": false,
"rangeMax": 100.0,
"rangeMin": 25.0
}