Skip to content

Commit

Permalink
wip unit tests
Browse files Browse the repository at this point in the history
  • Loading branch information
TunahanGuler committed Jan 22, 2025
1 parent b4595f2 commit 0d52b14
Show file tree
Hide file tree
Showing 4 changed files with 134 additions and 8 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,11 @@ class BitbucketMergeRequests(BitbucketProjectBase):

async def _api_url(self) -> URL:
"""Override to return the merge requests API."""
return await self._bitbucket_api_url("pull-requests")
url = str(await super()._api_url())
project = f"{self._parameter('owner')}/repos/{self._parameter('repository')}"
api_url = URL(f"{url}/rest/api/1.0/projects/{project}" + (f"/pull-requests?limit={self.PAGE_SIZE}"))
return URL(api_url)


async def _landing_url(self, responses: SourceResponses) -> URL:
"""Extend to add the project merge requests."""
Expand All @@ -24,16 +28,16 @@ async def _landing_url(self, responses: SourceResponses) -> URL:

async def _get_source_responses(self, *urls: URL) -> SourceResponses:
"""Extend to use Bitbucket pagination, if necessary."""
nr_merge_requests_to_skip = 0
responses = await super()._get_source_responses(*urls)
while len((await responses[-1].json())["values"]) == self.PAGE_SIZE:
nr_merge_requests_to_skip += self.PAGE_SIZE
while not (await responses[-1].json())["isLastPage"]:
nr_merge_requests_to_skip = (await responses[-1].json())["nextPageStart"]
responses.extend(await super()._get_source_responses(URL(f"{urls[0]}&start={nr_merge_requests_to_skip}")))
return responses

async def _parse_entities(self, responses: SourceResponses) -> Entities:
"""Override to parse the merge requests from the responses."""
merge_requests = []
pdb.set_trace()
for response in responses:
merge_requests.extend((await response.json())["values"])
landing_url = (await self._landing_url(responses))
Expand All @@ -49,7 +53,7 @@ def _create_entity(self, merge_request, landing_url: str) -> Entity:
return Entity(
key=merge_request["id"],
title=merge_request["title"],
target_branch=merge_request["toRef"],
target_branch=merge_request["toRef"]["id"],
url=f"{landing_url}/{merge_request['id']}",
state=merge_request["state"],
created=merge_request.get("createdDate"),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,13 @@ class BitbucketTestCase(SourceCollectorTestCase):
def setUp(self):
"""Extend to add generic test fixtures."""
super().setUp()
self.set_source_parameter("branch", "branch")
self.set_source_parameter("owner", "owner")
self.set_source_parameter("repository", "repository")

class BitbucketBranchesTestCase(BitbucketTestCase):
"""Base class for Bitbucket branches collectors."""

def setUp(self):
"""Extend to add branches test fixtures."""
super().setUp()
self.set_source_parameter("branch", "branch")
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,10 @@

from dateutil.tz import tzutc

from .base import BitbucketTestCase
from .base import BitbucketBranchesTestCase


class BitbucketInactiveBranchesTest(BitbucketTestCase):
class BitbucketInactiveBranchesTest(BitbucketBranchesTestCase):
"""Unit tests for the inactive branches metric."""

METRIC_TYPE = "inactive_branches"
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,115 @@
"""Unit tests for the Bitbucket merge requests collector."""
import pdb
from unittest.mock import AsyncMock

from source_collectors import BitbucketMergeRequests

from .base import BitbucketTestCase


class BitbucketMergeRequestsTest(BitbucketTestCase):
"""Unit tests for the merge requests metric."""

METRIC_TYPE = "merge_requests"

def setUp(self):
"""Extend to set up the metric under test."""
super().setUp()
self.landing_url = "https://bitbucket/projects/owner/repos/repository/pull-requests"

@staticmethod
def create_merge_request(
number: int,
approved: bool = False,
state: str = "OPEN",
branch: str = "main",
) -> dict[str, str | int | list[dict[str, int]]]:
"""Create a merge request fixture."""
return {
"id": number,
"title": f"Pull request {number}",
"toRef": {"id": f"refs/heads/{branch}"},
"state": state,
"createdDate": 1612890611,
"reviewers": [{"approved": True}, {"approved": approved}],
}

def create_entity(self, number: int):
"""Create an Bitbucket merge request entity."""
return {
"key": str(number),
"title": f"Pull request {number}",
"target_branch": "refs/heads/main",
"state": "OPEN",
"url": f"{self.landing_url}/{number}",
"created": 1612890611,
"closed": None,
"upvotes": "1",
"downvotes": "1",
}

def create_mr_json(self,
mr,
has_next_page: bool = False,
):
"""Create an entity."""
return {"size": len(mr), "limit": 25, "isLastPage": True, "start": 0, "values": mr, "hasNextPage": has_next_page}

async def test_merge_requests(self):
"""Test that the number of merge requests can be measured."""
self.set_source_parameter("merge_request_state", ["open"])
self.set_source_parameter("upvotes", "2") # Require at least two upvotes
self.set_source_parameter("target_branches_to_include", ["refs/heads/main"])
bitbucket_json = self.create_mr_json([
self.create_merge_request(1),
self.create_merge_request(2, state="DECLINED"),
self.create_merge_request(3, approved=True),
self.create_merge_request(4, branch="dev"),
])
response = await self.collect(get_request_json_return_value=bitbucket_json)
self.assert_measurement(
response,
value="1",
total="4",
entities=[self.create_entity(1)],
landing_url=self.landing_url,
)

# async def test_pagination(self):
# """Test that pagination works."""
# BitbucketMergeRequests.PAGE_SIZE = 1
# bitbucket_json = [
# { "isLastPage": False, "nextPageStart": 1, "values": [self.create_merge_request(1)]},
# { "isLastPage": False, "nextPageStart": 2, "values": [self.create_merge_request(2)]},
# { "isLastPage": True, "values": [self.create_merge_request(3)]},
# ]
# response = await self.collect(get_request_json_side_effect=bitbucket_json)
# pdb.set_trace()
# self.assert_measurement(
# response,
# value="2",
# total="2",
# entities=[self.create_entity(1), self.create_entity(2)],
# landing_url=self.landing_url,
# )

async def test_pagination(self):
"""Test that pagination works."""
merge_requests_json1 = self.create_mr_json([self.create_merge_request(1)], has_next_page=True)
merge_requests_json2 = self.create_mr_json([self.create_merge_request(2)])
# merge_request_fields_response = AsyncMock()
merge_requests_page1 = AsyncMock()
merge_requests_page2 = AsyncMock()
execute = AsyncMock(side_effect=[merge_requests_page1, merge_requests_page2])
# merge_request_fields_response.json = AsyncMock(return_value=self.merge_request_fields_json())
merge_requests_page1.json = AsyncMock(return_value=merge_requests_json1)
merge_requests_page2.json = AsyncMock(return_value=merge_requests_json2)
entities = [self.create_entity(1), self.create_entity(2)]
# response = await self.collect_merge_requests(execute)
# pdb.set_trace()
# self.assert_measurement(response, value="2", total="2", entities=entities, landing_url=self.landing_url)

# links = {"next": {"url": "https://harbor/next_page"}}
response = await self.collect(get_request_json_side_effect=[merge_requests_json1, merge_requests_json2])
# pdb.set_trace()
self.assert_measurement(response, value="2", entities=entities)

0 comments on commit 0d52b14

Please sign in to comment.