-
Notifications
You must be signed in to change notification settings - Fork 49
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
PORT-5598 | Jira integration - support sprints | Change priority to name #804
Open
lordsarcastic
wants to merge
85
commits into
main
Choose a base branch
from
port-5598
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
+1,408
−203
Open
Changes from 64 commits
Commits
Show all changes
85 commits
Select commit
Hold shift + click to select a range
a3d6380
Implemeneted support for sprints
lordsarcastic 2a2811c
Changed priority in issue to be name
lordsarcastic 2d3f527
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 7121711
Implemented support for sprint states and issues source
lordsarcastic be33aef
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 0367e78
Fix type cast attribute overlap error
lordsarcastic 9307d15
Formatted port-app-config
lordsarcastic b9abc49
Added new mapping for board url
lordsarcastic 75a090a
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 67966a1
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 6b6cb82
Fixed issues on jira integration
lordsarcastic 58f9984
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 1fe260f
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic ec6c1a0
Implemented processing for all webhook events
lordsarcastic 320caa2
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 32d82d3
Fix unclosed pagination for sprint
lordsarcastic 1a6a376
Fix bugs in webhook
lordsarcastic 90f4071
Fixed bug in deleting entities
lordsarcastic db696f1
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 5df8c3d
Merge branch 'main' into port-5598
mk-armah ff31969
Fix Nonetype error
lordsarcastic 41e7fcc
Bumped application version
lordsarcastic a447370
Update changelog
lordsarcastic 69458cc
Merge branch 'port-5598' of github.com:port-labs/ocean into port-5598
lordsarcastic 91b406d
Remove sourcing issues from boards
lordsarcastic 4362377
Ran formatting
lordsarcastic df881df
Chore: Removed boards entirely
lordsarcastic 88899ba
Implemeneted support for sprints
lordsarcastic ac6d419
Changed priority in issue to be name
lordsarcastic 0be072f
Implemented support for sprint states and issues source
lordsarcastic d9d4f72
Fix type cast attribute overlap error
lordsarcastic 8560691
Formatted port-app-config
lordsarcastic b19e8b7
Added new mapping for board url
lordsarcastic d4b0242
Fixed issues on jira integration
lordsarcastic a616d5b
Implemented processing for all webhook events
lordsarcastic f72fd3e
Fix unclosed pagination for sprint
lordsarcastic 1158543
Fix bugs in webhook
lordsarcastic d2fa837
Fixed bug in deleting entities
lordsarcastic d761c9e
[Integration][Pagerduty] Fix incident default mapping and blueprint …
Tankilevitch fd9cf23
PORT-9572 Update the default JQL provided by the JIRA integration (#868)
MPTG94 e97e3ab
[AWS] Bug fix global resources not synced for all accounts (#845)
shalev007 59cdfa6
[Integration][AWS] throw error if no permissions on region (#889)
shalev007 012474c
Remove sourcing issues from boards
lordsarcastic b755efa
Ran formatting
lordsarcastic 52cd217
Chore: Removed boards entirely
lordsarcastic 6a5a123
Merge branch 'port-5598' of github.com:port-labs/ocean into port-5598
lordsarcastic fd1731d
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic f14d717
Merge branch 'main' into port-5598
PeyGis 6aa8f99
Fix: Fixed ingesting issues with sprint
lordsarcastic 028eb1a
Fix: Single quote causing mapping to not be applied
lordsarcastic 266256a
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 5eb0eb2
Chore: Made ingestion faster
lordsarcastic 04de891
Fix: Lint issues
lordsarcastic 6742a22
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 4423064
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic c9e5345
Added changelog information
lordsarcastic 4fca62a
Bumped version
lordsarcastic 264faa7
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 64ecbd1
Chore: bumped version
lordsarcastic ebe15f9
Chore: Removed sprints from integration
lordsarcastic c74edb7
Fix: Bug on params for issues
lordsarcastic 444d177
Fix: Bug on params for issues
lordsarcastic 80b388b
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic a572710
Merge branch 'main' into port-5598
PeyGis d4f36f6
Fix: Changelog, blueprints and method name
lordsarcastic 4f8ca50
Merge branch 'main' into port-5598
PeyGis 4602bd1
Implemented tests for Jira
lordsarcastic bb26949
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 1eaf4fb
Merge branch 'main' into port-5598
PeyGis bd6c269
Fixed bug in tests
lordsarcastic 8b6acc5
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic ec3727f
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 8c9c29a
Bumped integration version and ocean dependency
lordsarcastic 34acfc9
Updated changelog
lordsarcastic 8e34aa1
Fix: Lint errors
lordsarcastic 19f49bb
Fix: Uncomment items in spec.yaml file
lordsarcastic 1879b0b
Fix: commented code
lordsarcastic 52d6a8c
Chore: Adjusted fixtures data
lordsarcastic bdf93d1
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic f1f8495
Bumped version
lordsarcastic f6668e6
Chore: Fix lint and lock file
lordsarcastic bae8656
Chore: Reverted changelog changes
lordsarcastic 8d663f6
Chore: Updated changelog
lordsarcastic 9ae1adc
Merge remote-tracking branch 'origin/main' into port-5598
lordsarcastic 4dd0f85
Bumped integration version due to merge
lordsarcastic File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,154 @@ | ||
import typing | ||
from typing import Any, AsyncGenerator | ||
|
||
import httpx | ||
from httpx import BasicAuth, Timeout | ||
from loguru import logger | ||
from port_ocean.context.ocean import ocean | ||
from port_ocean.utils import http_async_client | ||
|
||
PAGE_SIZE = 50 | ||
WEBHOOK_NAME = "Port-Ocean-Events-Webhook" | ||
REQUEST_TIMEOUT = 120 | ||
|
||
|
||
CREATE_UPDATE_WEBHOOK_EVENTS = [ | ||
"jira:issue_created", | ||
"jira:issue_updated", | ||
"project_created", | ||
"project_updated", | ||
"project_restored_deleted", | ||
"project_restored_archived", | ||
] | ||
|
||
DELETE_WEBHOOK_EVENTS = [ | ||
"jira:issue_deleted", | ||
"project_deleted", | ||
"project_soft_deleted", | ||
"project_archived", | ||
] | ||
|
||
WEBHOOK_EVENTS = [ | ||
*CREATE_UPDATE_WEBHOOK_EVENTS, | ||
*DELETE_WEBHOOK_EVENTS, | ||
] | ||
|
||
|
||
class JiraClient: | ||
def __init__(self, jira_url: str, jira_email: str, jira_token: str) -> None: | ||
self.jira_url = jira_url | ||
self.agile_url = f"{self.jira_url}/rest/agile/1.0" | ||
self.jira_rest_url = f"{self.jira_url}/rest" | ||
self.detail_base_url = f"{self.jira_rest_url}/api/3" | ||
|
||
self.jira_api_auth = BasicAuth(jira_email, jira_token) | ||
self.webhooks_url = f"{self.jira_rest_url}/webhooks/1.0/webhook" | ||
|
||
self.client = http_async_client | ||
self.client.auth = self.jira_api_auth | ||
self.client.timeout = Timeout(REQUEST_TIMEOUT) | ||
|
||
@staticmethod | ||
def _generate_base_req_params( | ||
maxResults: int = 50, startAt: int = 0 | ||
) -> dict[str, Any]: | ||
return { | ||
"maxResults": maxResults, | ||
"startAt": startAt, | ||
} | ||
|
||
async def _make_paginated_request( | ||
self, | ||
url: str, | ||
params: dict[str, Any] = {}, | ||
is_last_function: typing.Callable[ | ||
[dict[str, Any]], bool | ||
] = lambda response: response["isLast"], | ||
) -> AsyncGenerator[dict[str, list[dict[str, Any]]], None]: | ||
params = {**self._generate_base_req_params(), **params} | ||
is_last = False | ||
logger.info(f"Making paginated request to {url} with params: {params}") | ||
while not is_last: | ||
try: | ||
response = await self.client.get(url, params=params) | ||
response.raise_for_status() | ||
response_data = response.json() | ||
yield response_data | ||
is_last = is_last_function(response_data) | ||
start = response_data["startAt"] + response_data["maxResults"] | ||
params = {**params, "startAt": start} | ||
logger.info(f"Next page startAt: {start}") | ||
except httpx.HTTPStatusError as e: | ||
|
||
logger.error( | ||
f"HTTP error with status code: {e.response.status_code}" | ||
f" and response text: {e.response.text}" | ||
) | ||
raise | ||
except httpx.HTTPError as e: | ||
logger.error(f"HTTP occurred while fetching Jira data {e}") | ||
raise | ||
logger.info("Finished paginated request") | ||
return | ||
|
||
async def get_projects(self) -> AsyncGenerator[list[dict[str, Any]], None]: | ||
lordsarcastic marked this conversation as resolved.
Show resolved
Hide resolved
|
||
async for projects in self._make_paginated_request( | ||
f"{self.detail_base_url}/project/search" | ||
): | ||
yield projects["values"] | ||
|
||
async def get_all_issues( | ||
self, | ||
params: dict[str, Any] = {}, | ||
) -> AsyncGenerator[list[dict[str, Any]], None]: | ||
async for issues in self._make_paginated_request( | ||
f"{self.detail_base_url}/search", | ||
params=params, | ||
is_last_function=lambda response: response["startAt"] | ||
+ response["maxResults"] | ||
>= response["total"], | ||
): | ||
yield issues["issues"] | ||
|
||
async def _get_single_item(self, url: str) -> dict[str, Any]: | ||
try: | ||
response = await self.client.get(url) | ||
response.raise_for_status() | ||
return response.json() | ||
except httpx.HTTPStatusError as e: | ||
logger.error( | ||
f"HTTP error on {url}: {e.response.status_code} - {e.response.text}" | ||
) | ||
raise | ||
except httpx.HTTPError as e: | ||
logger.error(f"HTTP occurred while fetching Jira data {e}") | ||
raise | ||
|
||
async def get_single_project(self, project: str) -> dict[str, Any]: | ||
return await self._get_single_item(f"{self.detail_base_url}/project/{project}") | ||
|
||
async def get_single_issue(self, issue: str) -> dict[str, Any]: | ||
return await self._get_single_item(f"{self.agile_url}/issue/{issue}") | ||
|
||
async def create_events_webhook(self, app_host: str) -> None: | ||
webhook_target_app_host = f"{app_host}/integration/webhook" | ||
webhook_check_response = await self.client.get(f"{self.webhooks_url}") | ||
webhook_check_response.raise_for_status() | ||
webhook_check = webhook_check_response.json() | ||
|
||
for webhook in webhook_check: | ||
if webhook["url"] == webhook_target_app_host: | ||
logger.info("Ocean real time reporting webhook already exists") | ||
return | ||
|
||
body = { | ||
"name": f"{ocean.config.integration.identifier}-{WEBHOOK_NAME}", | ||
"url": webhook_target_app_host, | ||
"events": WEBHOOK_EVENTS, | ||
} | ||
|
||
webhook_create_response = await self.client.post( | ||
f"{self.webhooks_url}", json=body | ||
) | ||
webhook_create_response.raise_for_status() | ||
logger.info("Ocean real time reporting webhook created") |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Empty file.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am thinking maybe we should add a property with sprint, where the description of the property will point the user to the docs?