Skip to content

Commit

Permalink
Merge pull request #36 from tychoish/jira-service
Browse files Browse the repository at this point in the history
support for jira to complete #32
  • Loading branch information
ralphbean committed Jan 5, 2013
2 parents 7c9335b + 5d3e70a commit e51bed8
Show file tree
Hide file tree
Showing 4 changed files with 103 additions and 5 deletions.
19 changes: 16 additions & 3 deletions bugwarrior/README.rst
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
bugwarrior - Pull tickets from github, bitbucket, and trac into taskwarrior
===========================================================================
bugwarrior - Pull tickets from github, bitbucket, bugzilla, jira, and trac into taskwarrior
===========================================================================================

.. split here
Expand All @@ -14,6 +14,7 @@ It currently supports the following remote resources:
- `megaplan <http://www.megaplan.ru/>`_
- `teamlab <http://www.teamlab.com/>`_
- `redmine <http://www.redmine.org/>`_
- `jira <http://www.atlassian.com/software/jira/overview>`_

Configuring
-----------
Expand Down Expand Up @@ -93,7 +94,7 @@ Create a ``~/.bugwarriorrc`` file with the following contents.
default_priority = H

# Here's an example of a bugzilla target. This will scrape every ticket
# 1) that is not closed and 2) for which [email protected] is either the
# 1) that is not closed and 2) that [email protected] is either the
# owner or reporter or is cc'd on. Bugzilla instances can be quite different
# from one another so use this with caution and please report bugs so we can
# make bugwarrior support more robust!
Expand All @@ -115,6 +116,18 @@ Create a ``~/.bugwarriorrc`` file with the following contents.
default_priority = H
project_name = example

# Here's an example of a jira project. The ``jira-python`` module is
# a bit particular, and jira deployments, like Bugzilla, tend to be
# reasonably customized. So YMMV. The ``base_uri`` must not have a
# have a trailing slash. This will fetch comments and cases from
# jira assigned to ``username`` where the status is not closed or
# resolved.
[jira.project]
service = jira
jira.base_uri = https://jira.example.org
jira.username = ralph
jira.password = OMG_LULZ

# Here's an example of a teamlab target.
[my_teamlab]
service = teamlab
Expand Down
6 changes: 4 additions & 2 deletions bugwarrior/services/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,8 +40,8 @@ def description(self, title, url, number, cls="issue"):
'pull_request': 'PR',
}
# TODO -- get the '35' here from the config.
return "%s%s#%i - %s .. %s" % (
MARKUP, cls_markup[cls], number,
return "%s%s#%s - %s .. %s" % (
MARKUP, cls_markup[cls], str(number),
title[:35], self.shorten(url)
)

Expand Down Expand Up @@ -90,6 +90,7 @@ def get_owner(self, issue):
from bz import BugzillaService
from teamlab import TeamLabService
from redmine import RedMineService
from jira import JiraService


# Constant dict to be used all around town.
Expand All @@ -100,6 +101,7 @@ def get_owner(self, issue):
'bugzilla': BugzillaService,
'teamlab': TeamLabService,
'redmine': RedMineService,
'jira': JiraService,
}


Expand Down
82 changes: 82 additions & 0 deletions bugwarrior/services/jira.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
from __future__ import absolute_import

import time
from datetime import date

from twiggy import log
from jira.client import JIRA

from bugwarrior.services import IssueService
from bugwarrior.config import die

def get_priority(priority):
if priority is None:
return 'Major'
else:
return priority


class JiraService(IssueService):
# A map of jira priorities to taskwarrior priorities
priorities = {
'Trivial': 'L',
'Minor': 'L',
'Major': 'M',
'Critical': 'H',
'Blocker': 'H',
}

def __init__(self, *args, **kw):
super(JiraService, self).__init__(*args, **kw)
self.username = self.config.get(self.target, 'jira.username')
self.url = self.config.get(self.target, 'jira.base_uri')
self.query = 'assignee=' + self.username + ' AND status != closed and status != resolved'
self.jira = JIRA(options={'server': self.config.get(self.target, 'jira.base_uri')},
basic_auth=(self.username,
self.config.get(self.target, 'jira.password')))

@classmethod
def validate_config(cls, config, target):
for option in ['jira.username', 'jira.password', 'jira.base_uri']:
if not config.has_option(target, option):
die("[%s] has no '%s'" % (target, option))

IssueService.validate_config(config, target)

def get_owner(self, issue):
return True

def annotations(self, issue):

annotations = []

comments = self.jira.comments(issue)

if comments is []:
pass
else:
for comment in comments:
created = date.fromtimestamp(time.mktime(time.strptime(comment.created[0:10], '%Y-%m-%d')))

annotations.append(self.format_annotation(created, comment.author, comment.body))

return dict(annotations)

def issues(self):
cases = self.jira.search_issues(self.query, maxResults=-1)

log.debug(" Found {0} total.", len(cases))

return [dict(
description=self.description(
title=case.fields.summary,
url=self.url + '/browse/' + case.key,
number=case.key.rsplit('-', 1)[1], cls="issue",
),
project=case.key.rsplit('-', 1)[0],
priority=self.priorities.get(
get_priority(case.fields.priority),
self.default_priority,
),
**self.annotations(case.key)
) for case in cases]
1 change: 1 addition & 0 deletions setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@
"requests",
"offtrac",
"python-bugzilla",
"jira-python",
"taskw >= 0.4.2",
],
entry_points="""
Expand Down

0 comments on commit e51bed8

Please sign in to comment.