Skip to content

Commit

Permalink
add test for report
Browse files Browse the repository at this point in the history
  • Loading branch information
joelee2012 committed Aug 18, 2023
1 parent 31a98a9 commit 4198565
Show file tree
Hide file tree
Showing 5 changed files with 134 additions and 15 deletions.
2 changes: 1 addition & 1 deletion HISTORY.md
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ Release History
1.7 (2021-10-09)
-----------------
- `Jenkins.get_job` can accept job url now
- Support to retrive coverage which was generated by [JaCoCo](https://plugins.jenkins.io/jacoco/) and [Code Coverage API](https://plugins.jenkins.io/code-coverage-api/)
- Support to retrieve coverage which was generated by [JaCoCo](https://plugins.jenkins.io/jacoco/) and [Code Coverage API](https://plugins.jenkins.io/code-coverage-api/)

1.6 (2021-08-01)
-----------------
Expand Down
18 changes: 9 additions & 9 deletions api4jenkins/build.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
from .item import AsyncItem, Item
from .mix import (ActionsMixIn, AsyncActionsMixIn, AsyncDeletionMixIn,
AsyncDescriptionMixIn, DeletionMixIn, DescriptionMixIn)
from .report import CoverageReport, CoverageResult, CoverageTrends, TestReport
from .report import AsyncCoverageReport, AsyncCoverageResult, AsyncCoverageTrends, AsyncTestReport, CoverageReport, CoverageResult, CoverageTrends, TestReport


class Build(Item, DescriptionMixIn, DeletionMixIn, ActionsMixIn):
Expand Down Expand Up @@ -148,22 +148,22 @@ async def get_job(self):
return await self.jenkins.get_job(job_name)

async def get_test_report(self):
tr = TestReport(self.jenkins, f'{self.url}testReport/')
return tr if tr.exists() else None
tr = AsyncTestReport(self.jenkins, f'{self.url}testReport/')
return tr if await tr.exists() else None

async def get_coverage_report(self):
'''Access coverage report generated by `JaCoCo <https://plugins.jenkins.io/jacoco/>`_'''
cr = CoverageReport(self.jenkins, f'{self.url}jacoco/')
return cr if cr.exists() else None
cr = AsyncCoverageReport(self.jenkins, f'{self.url}jacoco/')
return cr if await cr.exists() else None

async def get_coverage_result(self):
'''Access coverage result generated by `Code Coverage API <https://plugins.jenkins.io/code-coverage-api/>`_'''
cr = CoverageResult(self.jenkins, f'{self.url}coverage/result/')
return cr if cr.exists() else None
cr = AsyncCoverageResult(self.jenkins, f'{self.url}coverage/result/')
return cr if await cr.exists() else None

Check warning on line 162 in api4jenkins/build.py

View check run for this annotation

Codecov / codecov/patch

api4jenkins/build.py#L161-L162

Added lines #L161 - L162 were not covered by tests

async def get_coverage_trends(self):
ct = CoverageTrends(self.jenkins, f'{self.url}coverage/trend/')
return ct if ct.exists() else None
ct = AsyncCoverageTrends(self.jenkins, f'{self.url}coverage/trend/')
return ct if await ct.exists() else None

Check warning on line 166 in api4jenkins/build.py

View check run for this annotation

Codecov / codecov/patch

api4jenkins/build.py#L165-L166

Added lines #L165 - L166 were not covered by tests


class AsyncWorkflowRun(AsyncBuild):
Expand Down
75 changes: 74 additions & 1 deletion api4jenkins/report.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
# encoding: utf-8
from .item import Item, camel, snake
from .item import AsyncItem, Item, camel, snake


class GetMixIn:
Expand Down Expand Up @@ -111,3 +111,76 @@ class CoverageTrend(ResultBase):
def __iter__(self):
for element in self.raw['elements']:
yield CoverageElement(element)


# async class

class AsyncGetMixIn:

async def get(self, name):
async for item in self:
if item.name == name:
return item


class AsyncTestReport(AsyncItem, AsyncGetMixIn):

async def __aiter__(self):
data = await self.api_json()
for suite in data['suites']:
yield TestSuite(suite)

@property
async def suites(self):
async for suite in self:
yield suite


class AsyncCoverageReport(AsyncItem, AsyncGetMixIn):
'''Access coverage report generated by `JaCoCo <https://plugins.jenkins.io/jacoco/>`_'''

report_types = ['branchCoverage', 'classCoverage', 'complexityScore',
'instructionCoverage', 'lineCoverage', 'methodCoverage']

async def __getattr__(self, name):
attr = camel(name)
if attr not in self.report_types:
raise AttributeError(
f"'CoverageReport' object has no attribute '{name}'")
return await self.get(attr)

async def __aiter__(self):
data = await self.api_json()
for k, v in data.items():
if k not in ['_class', 'previousResult']:
v['name'] = k
yield Coverage(v)

async def trends(self, count=2):
def _resolve(data):
if data['previousResult']:
yield from _resolve(data['previousResult'])
for k, v in data.items():
if k not in ['_class', 'previousResult']:
v['name'] = k
yield Coverage(v)
data = await self.api_json(depth=count)
for c in _resolve(data):
yield c

Check warning on line 169 in api4jenkins/report.py

View check run for this annotation

Codecov / codecov/patch

api4jenkins/report.py#L160-L169

Added lines #L160 - L169 were not covered by tests


class AsyncCoverageResult(AsyncItem, AsyncGetMixIn):
'''Access coverage result generated by `Code Coverage API <https://plugins.jenkins.io/code-coverage-api/>`_'''

async def __aiter__(self):
data = await self.api_json(depth=1)
for element in data['results']['elements']:
yield CoverageElement(element)

Check warning on line 178 in api4jenkins/report.py

View check run for this annotation

Codecov / codecov/patch

api4jenkins/report.py#L176-L178

Added lines #L176 - L178 were not covered by tests


class AsyncCoverageTrends(AsyncItem, AsyncGetMixIn):
async def __aiter__(self):
data = await self.api_json(depth=1)
for trend in data['trends']:
trend['name'] = trend['buildName']
yield CoverageTrend(trend)

Check warning on line 186 in api4jenkins/report.py

View check run for this annotation

Codecov / codecov/patch

api4jenkins/report.py#L183-L186

Added lines #L183 - L186 were not covered by tests
8 changes: 4 additions & 4 deletions tests/unit/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
from api4jenkins.node import Node, Nodes, AsyncNode, AsyncNodes
from api4jenkins.plugin import PluginsManager, AsyncPluginsManager
from api4jenkins.queue import Queue, QueueItem, AsyncQueue, AsyncQueueItem
from api4jenkins.report import CoverageReport, CoverageResult, TestReport
from api4jenkins.report import AsyncCoverageReport, AsyncCoverageResult, AsyncTestReport, CoverageReport, CoverageResult, TestReport
from api4jenkins.view import AllView, AsyncAllView

DATA = Path(__file__).with_name('tests_data')
Expand Down Expand Up @@ -42,11 +42,11 @@ def _api_json(self, tree='', depth=0):
return load_json('node/node.json')
elif isinstance(self, AllView):
return load_json('view/allview.json')
elif isinstance(self, TestReport):
elif isinstance(self, (TestReport, AsyncTestReport)):
return load_json('report/test_report.json')
elif isinstance(self, CoverageReport):
elif isinstance(self, (CoverageReport, AsyncCoverageReport)):
return load_json('report/coverage_report.json')
elif isinstance(self, CoverageResult):
elif isinstance(self, (CoverageResult, AsyncCoverageResult)):
return load_json('report/coverage_result.json')
elif isinstance(self, (QueueItem, AsyncQueueItem)):
return load_json('queue/waitingitem.json')
Expand Down
46 changes: 46 additions & 0 deletions tests/unit/test_report.py
Original file line number Diff line number Diff line change
Expand Up @@ -72,3 +72,49 @@ def test_get(self, build):
cr = build.get_coverage_result()
assert cr.get('Report').ratio == 100
assert cr.get('Line').ratio == 83.83372


@pytest.fixture
async def async_suite(async_test_report):
return await async_test_report.get('pytest')


@pytest.fixture
async def async_case(async_suite):
return await async_suite.get('test_exists')


@pytest.fixture
async def async_coverage_report(async_build):
return await async_build.get_coverage_report()


@pytest.fixture
async def async_test_report(async_build):
return await async_build.get_test_report()


class TestAsyncTestReport:

async def test_attributes(self, async_test_report):
assert await async_test_report.fail_count == 2
assert await async_test_report.pass_count == 37

async def test_iterate(self, async_test_report):
assert len([s async for s in async_test_report]) == 1
assert len([s async for s in async_test_report.suites]) == 1


class TestAsyncCoverageReport:

async def test_attributes(self, async_coverage_report):
assert (await async_coverage_report.branch_coverage).covered == 244
assert (await async_coverage_report.method_coverage).covered == 320

async def test_get(self, async_coverage_report):
assert (await async_coverage_report.get('branchCoverage')).covered == 244
assert (await async_coverage_report.get('methodCoverage')).covered == 320

async def test_wrong_attribute(self, async_coverage_report):
with pytest.raises(AttributeError):
await async_coverage_report.xxxxx

0 comments on commit 4198565

Please sign in to comment.