HPCC4J-574 Jirabot Improvements #71
Workflow file for this run
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
# JiraBot github action | |
# ===================== | |
# | |
name: jirabot | |
on: | |
pull_request_target: | |
types: [opened, reopened] | |
branches: | |
- "master" | |
- "candidate-*" | |
jobs: | |
jirabot: | |
runs-on: ubuntu-20.04 | |
steps: | |
- uses: "actions/setup-python@v5" | |
with: | |
python-version: "3.8" | |
- name: "Install dependencies" | |
run: | | |
set -xe | |
python -VV | |
python -m site | |
python -m pip install --upgrade pip setuptools wheel | |
python -m pip install --upgrade atlassian-python-api | |
python -m pip --version | |
- name: "Run" | |
env: | |
JIRABOT_USERNAME : ${{ secrets.JIRABOT_USERNAME }} | |
JIRABOT_PASSWORD : ${{ secrets.JIRABOT_PASSWORD }} | |
JIRA_URL : ${{ vars.JIRA_URL }} | |
PULL_REQUEST_NUMBER : ${{ github.event.pull_request.number }} | |
PULL_REQUEST_TITLE : ${{ github.event.pull_request.title }} | |
PULL_REQUEST_AUTHOR_NAME : ${{ github.event.pull_request.user.login }} | |
PULL_URL: ${{ github.event.pull_request.html_url }} | |
COMMENTS_URL: ${{ github.event.pull_request.comments_url }} | |
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
GHUB_JIRA_USER_MAP: ${{ vars.GHUB_JIRA_USER_MAP }} | |
JIRA_ISSUE_PROPERTY_MAP: ${{ vars.JIRA_ISSUE_PROPERTY_MAP }} | |
JIRA_ISSUE_TRANSITION_MAP: ${{ vars.JIRA_ISSUE_TRANSITION_MAP }} | |
run: | | |
import os | |
import re | |
import time | |
import sys | |
import json | |
from atlassian.jira import Jira | |
def updateIssue(jira, issue, prAuthor : str, transitionMap: dict, propertyMap: dict, pull_url: str) -> str: | |
result = '' | |
issueName = issue['key'] | |
issueFields = issue['fields'] | |
statusName = str(issueFields['status']['name']) | |
transition = transitionMap.get(statusName, None) | |
if transition == None: | |
print('Error: Unable to find transition for status: ' + statusName) | |
elif transition != '': | |
try: | |
jira.issue_transition(issueName, transition) | |
result += 'Workflow Transition: ' + transition + '\n' | |
except Exception as error: | |
transitions = jira.get_issue_transitions(issueName) | |
result += 'Error: Transition: "' + transition + '" failed with: "' + str(error) + '" Valid transitions=' + str(transitions) + '\n' | |
prFieldName = propertyMap.get('pullRequestFieldName', 'customfield_10010') | |
if prFieldName in issueFields: | |
currentPR = issueFields[prFieldName] | |
else: | |
print('Error: Unable to find pull request field with field name: ' + prFieldName) | |
currentPR = None | |
if currentPR is None: | |
jira.update_issue_field(issueName, {prFieldName: pull_url}) | |
result += 'Updated PR\n' | |
elif currentPR is not None and currentPR != pull_url: | |
result += 'Additional PR: ' + pull_url + '\n' | |
if prAuthor: | |
assignee = issueFields['assignee'] | |
if assignee is None: | |
assigneeId = '' | |
assigneeEmail = '' | |
else: | |
assigneeId = assignee['accountId'] | |
assigneeEmail = assignee["emailAddress"] | |
prAuthorId = prAuthor["accountId"] | |
prAuthorEmail = prAuthor["emailAddress"] | |
if assigneeId is None or assigneeId == '': | |
jira.assign_issue(issueName, prAuthorId) | |
result += 'Assigning user: ' + prAuthorEmail + '\n' | |
elif assigneeId != prAuthorId: | |
result += 'Changing assignee from: ' + assigneeEmail + ' to: ' + prAuthorEmail + '\n' | |
jira.assign_issue(issueName, prAuthorId) | |
return result | |
jirabot_user = os.environ['JIRABOT_USERNAME'] | |
jirabot_pass = os.environ['JIRABOT_PASSWORD'] | |
jira_url = os.environ['JIRA_URL'] | |
pr = os.environ['PULL_REQUEST_NUMBER'] | |
title = os.environ['PULL_REQUEST_TITLE'] | |
prAuthor = os.environ['PULL_REQUEST_AUTHOR_NAME'] | |
pull_url = os.environ['PULL_URL'] | |
github_token = os.environ['GITHUB_TOKEN'] | |
comments_url = os.environ['COMMENTS_URL'] | |
print("%s %s %s" % (title, prAuthor, comments_url)) | |
result = '' | |
issuem = re.search("(HPCC4J|JAPI)-[0-9]+", title) | |
if issuem: | |
nameCorrectionPattern = re.compile("hpcc4j", re.IGNORECASE) | |
issue_name = nameCorrectionPattern.sub("JAPI",issuem.group()) | |
userDict = json.loads(os.environ['GHUB_JIRA_USER_MAP']) | |
if not isinstance(userDict, dict): | |
userDict = {} | |
if prAuthor in userDict: | |
prAuthor = userDict.get(prAuthor) | |
print('Mapped Github user to Jira user: ' + prAuthor) | |
jira = Jira(url=jira_url, username= jirabot_user, password= jirabot_pass, cloud=True) | |
jiraUser = None | |
userSearchResults = jira.user_find_by_user_string(query=prAuthor) | |
if userSearchResults and len(userSearchResults) > 0: | |
jiraUser = userSearchResults[0] | |
else: | |
print('Error: Unable to find Jira user: ' + prAuthor + ' continuing without assigning') | |
if not jira.issue_exists(issue_name): | |
sys.exit('Error: Unable to find Jira issue: ' + issue_name) | |
else: | |
issue = jira.issue(issue_name) | |
result = 'Jirabot Action Result:\n' | |
transitionMap = json.loads(os.environ['JIRA_ISSUE_TRANSITION_MAP']) | |
if not isinstance(transitionMap, dict): | |
print('Error: JIRA_ISSUE_TRANSITION_MAP is not a valid JSON object, ignoring.') | |
transitionMap = {} | |
jiraIssuePropertyMap = json.loads(os.environ['JIRA_ISSUE_PROPERTY_MAP']) | |
if not isinstance(jiraIssuePropertyMap, dict): | |
print('Error: JIRA_ISSUE_PROPERTY_MAP is not a valid JSON object, ignoring.') | |
jiraIssuePropertyMap = {} | |
result += updateIssue(jira, issue, jiraUser, transitionMap, jiraIssuePropertyMap, pull_url) | |
jira.issue_add_comment(issue_name, result) | |
result = 'Jira Issue: ' + jira_url + '/browse/' + issue_name + '\n\n' + result | |
# Escape the result for JSON | |
result = json.dumps(result) | |
curlCommand = 'curl -X POST %s -H "Content-Type: application/json" -H "Authorization: token %s" --data \'{ "body": %s }\'' % ( comments_url, github_token, result ) | |
os.system(curlCommand) | |
else: | |
print('Unable to find Jira issue name in title') | |
print(result) | |
shell: python |