Skip to content

Commit

Permalink
feat(test): updates paginated issues test to simpler approach
Browse files Browse the repository at this point in the history
Fixes lint
  • Loading branch information
shariff-6 committed Dec 13, 2024
1 parent 0c8a9dd commit d35f2a6
Show file tree
Hide file tree
Showing 2 changed files with 73 additions and 55 deletions.
31 changes: 25 additions & 6 deletions integrations/jira/jira/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,11 @@ async def _get_paginated_data(
if extract_key:
items = response_data.get(extract_key, [])
else:
items = response_data if isinstance(response_data, list) else [response_data]
items = (
response_data
if isinstance(response_data, list)
else [response_data]
)

if not items:
break
Expand Down Expand Up @@ -125,8 +129,15 @@ async def _get_cursor_paginated_data(

response_data = await self._send_api_request(method, url, params=params)

items = (response_data.get(extract_key, []) if extract_key
else ([response_data] if isinstance(response_data, dict) else response_data))
items = (
response_data.get(extract_key, [])
if extract_key
else (
[response_data]
if isinstance(response_data, dict)
else response_data
)
)

if not items:
break
Expand All @@ -139,6 +150,7 @@ async def _get_cursor_paginated_data(

if not has_next_page:
break

@staticmethod
def _generate_base_req_params(
maxResults: int = 0, startAt: int = 0
Expand All @@ -147,6 +159,7 @@ def _generate_base_req_params(
"maxResults": maxResults,
"startAt": startAt,
}

async def _get_webhooks(self) -> List[Dict[str, Any]]:
return await self._send_api_request("GET", url=self.webhooks_url)

Expand All @@ -155,7 +168,9 @@ async def create_events_webhook(self, app_host: str) -> None:
webhooks = await self._get_webhooks()

for webhook in webhooks:
if webhook.get("url") == webhook_target_app_host: # Use .get() to safely access dictionary
if (
webhook.get("url") == webhook_target_app_host
):
logger.info("Ocean real time reporting webhook already exists")
return

Expand Down Expand Up @@ -209,7 +224,9 @@ async def get_paginated_users(self) -> AsyncGenerator[List[Dict[str, Any]], None
async for users in self._get_paginated_data(f"{self.api_url}/users/search"):
yield users

async def get_paginated_teams(self, org_id: str) -> AsyncGenerator[List[Dict[str, Any]], None]:
async def get_paginated_teams(
self, org_id: str
) -> AsyncGenerator[List[Dict[str, Any]], None]:
logger.info("Getting teams from Jira")

base_url = f"https://admin.atlassian.com/gateway/api/public/teams/v1/org/{org_id}/teams"
Expand Down Expand Up @@ -271,7 +288,9 @@ async def get_user_team_mapping(self, org_id: str) -> Dict[str, str]:
logger.info(f"Created mapping for {len(user_team_mapping)} users")
return user_team_mapping

async def enrich_users_with_teams(self, users: List[Dict[str, Any]], org_id: str) -> List[Dict[str, Any]]:
async def enrich_users_with_teams(
self, users: List[Dict[str, Any]], org_id: str
) -> List[Dict[str, Any]]:
users_to_process = [user for user in users if "teamId" not in user]

if not users_to_process:
Expand Down
97 changes: 48 additions & 49 deletions integrations/jira/tests/test_client.py
Original file line number Diff line number Diff line change
Expand Up @@ -134,36 +134,54 @@ async def test_get_single_issue(mock_jira_client: JiraClient) -> None:
assert result == issue_data


# @pytest.mark.asyncio
# async def test_get_paginated_issues_with_event(mock_jira_client: JiraClient) -> None:
# """
# Test get_paginated_issues with an event-based resource_config.
# """
# # Mock JiraResourceConfig
# mock_config = JiraResourceConfig(
# selector=JiraResourceConfig.Selector(query="TEST", jql="project = TEST")
# )

# # Patch the global `event.resource_config` in the event module
# async with event_context("test_event") as test_event:
# with patch("event.resource_config", mock_config):
# # Prepare mock JiraClient
# mock_jira_client.api_url = "https://jira.example.com"

# # Mock the paginated data generator
# async def mock_paginated_data(*args: Any, **kwargs: Any) -> AsyncGenerator[List[Dict[str, Any]], None]:
# yield [{"key": "TEST-1"}, {"key": "TEST-2"}]

# mock_jira_client._get_paginated_data = mock_paginated_data

# # Call the method
# issues = []
# async for issue_batch in mock_jira_client.get_paginated_issues():
# issues.extend(issue_batch)

# # Assertions
# assert len(issues) == 2
# assert issues == [{"key": "TEST-1"}, {"key": "TEST-2"}]
@pytest.mark.asyncio
async def test_get_paginated_issues(mock_jira_client: JiraClient) -> None:
"""Test get_paginated_issues with JQL filtering"""

# Mock response data
issues_data = {"issues": [{"key": "TEST-1"}, {"key": "TEST-2"}], "total": 2}

# Mock config for JQL
mock_config = MagicMock()
mock_config.selector.jql = "project = TEST"

# Mock the port app config needed for event_context
mock_port_app_config = MagicMock()

async with event_context(
"test_event",
trigger_type="manual",
attributes={},
) as test_event:
# Set the port app config on the event context
test_event._port_app_config = mock_port_app_config

# Import and use resource_context
from port_ocean.context.resource import resource_context

async with resource_context(mock_config):
with patch.object(
mock_jira_client, "_send_api_request", new_callable=AsyncMock
) as mock_request:
mock_request.side_effect = [issues_data, {"issues": []}]

issues = []
async for issue_batch in mock_jira_client.get_paginated_issues():
issues.extend(issue_batch)

assert len(issues) == 2
assert issues == issues_data["issues"]

# Verify JQL was passed correctly
mock_request.assert_called_with(
"GET",
f"{mock_jira_client.api_url}/search",
params={
"jql": "project = TEST",
"maxResults": PAGE_SIZE,
"startAt": 0,
},
)


@pytest.mark.asyncio
Expand Down Expand Up @@ -329,22 +347,3 @@ async def test_create_events_webhook(mock_jira_client: JiraClient) -> None:

await mock_jira_client.create_events_webhook(app_host)
mock_request.assert_called_once() # Only checks for existence


@pytest.mark.asyncio
async def test_cursor_pagination_first_page_empty(mock_jira_client: JiraClient) -> None:
with patch.object(
mock_jira_client, "_send_api_request", new_callable=AsyncMock
) as mock_request:
mock_request.return_value = {
"results": [], # Add the expected key with empty results
"pageInfo": {"hasNextPage": False},
}
results: List[Dict[str, Any]] = []
async for batch in mock_jira_client._get_cursor_paginated_data(
"test_url",
"GET",
extract_key="results", # Specify the extract_key as used in the real client
):
results.extend(batch)
assert len(results) == 0

0 comments on commit d35f2a6

Please sign in to comment.