home *** CD-ROM | disk | FTP | other *** search
/ Mac Easy 2010 May / Mac Life Ubuntu.iso / casper / filesystem.squashfs / usr / share / pyshared / launchpadbugs / text_bug.py < prev    next >
Encoding:
Python Source  |  2008-08-05  |  9.9 KB  |  293 lines

  1. """
  2. TODO:
  3.  * check .private/.security: this seems to be wrong/maybe it  does not work
  4.  * remove these ugly dict-element vs. object-attribute things
  5. """
  6.  
  7. from bugbase import Bug as BugBase
  8. import email
  9. import cStringIO as StringIO
  10. import re
  11. import ConfigParser
  12.  
  13. from lptime import LPTime
  14. from lphelper import user, product
  15. from tasksbase import LPTasks, LPTask
  16. from attachmentsbase import LPAttachments, LPAttachment
  17. from commentsbase import LPComments, LPComment
  18.         
  19. class Task(LPTask):
  20.     def __init__(self, task_dict):
  21.                 
  22.         #print task_dict
  23.         task_dict["affects"], task_dict["targeted_to"] = product.parse_text_product(task_dict["task"])
  24.         for i in ("reporter", "assignee"):
  25.             task_dict[i] = user.parse_text_user(task_dict[i])
  26.         for i in ("date-created", "date-confirmed", "date-assigned",
  27.                   "date-inprogress", "date-closed", "date-left-new",
  28.                   "date-incomplete", "date-triaged", "date-fix-committed",
  29.                   "date-fix-released"):
  30.             if task_dict.has_key(i):
  31.                 task_dict[i] = LPTime(task_dict[i])
  32.             else:
  33.                 task_dict[i] = None
  34.         task_dict["remote"] = task_dict.get("watch", None)
  35.         #print task_dict
  36.         LPTask.__init__(self, task_dict)
  37.                     
  38.     def get_date_created(self):
  39.         return self._date_created
  40.     
  41.     def get_date_confirmed(self):
  42.         return self._date_confirmed
  43.     
  44.     def get_date_assigned(self):
  45.         return self._date_assigned
  46.     
  47.     def get_date_inprogress(self):
  48.         return self._date_inprogress
  49.     
  50.     def get_date_closed(self):
  51.         return self._date_closed
  52.         
  53.     def get_date_left_new(self):
  54.         return self._date_left_new
  55.         
  56.     def get_date_incomplete(self):
  57.         return self._date_incomplete
  58.  
  59.     def get_date_triaged(self):
  60.         return self._date_triaged
  61.  
  62.     def get_date_fix_committed(self):
  63.         return self._date_fix_committed
  64.  
  65.     def get_date_fix_released(self):
  66.         return self._date_fix_released
  67.     
  68.     def get_user(self):
  69.         return self._user
  70.  
  71.     def get_component(self):
  72.         return self._component
  73.         
  74.         
  75. class BugReport(object): 
  76.     def __init__(self, bug_dict, connection=None):
  77.         self.__data = bug_dict
  78.         for i in ("tags", "duplicates"):
  79.             self.__data[i] = self.__data[i].split()
  80.         self.__data["bugnumber"] = int(bug_dict["bug"])
  81.         del self.__data["bug"]
  82.         self.__data["reporter"] = user.parse_text_user(self.__data["reporter"])
  83.         self.__data["subscribers"] = [user.parse_text_user(u) for u in self.__data["subscribers"].split("\n") if u]
  84.         
  85.         self.__data["description"] = ""
  86.         for i in ("date-reported", "date-updated"):
  87.             self.__data[i] = LPTime(self.__data[i])
  88.         a = list()
  89.         for i in [i for i in self.__data["attachments"].split("\n") if i]:
  90.             try:
  91.                 url, contenttype = i.split(" ", 1)
  92.             except ValueError:
  93.                 if not i.startswith("http://"):
  94.                     continue
  95.                 else:
  96.                     raise
  97.             contenttype = contenttype.split(";")[0]
  98.             a.append(Attachment(url, contenttype, connection, self.__data["bugnumber"]))
  99.         self.__data["attachments"] = Attachments(a)
  100.         
  101.     def _add_description(self, description):
  102.         self.__data["description"] = description
  103.         
  104.     def __getattr__(self, name):
  105.         try:
  106.             return self.__data[name.replace("_", "-")]
  107.         except KeyError:
  108.             if name in ["bugnumber", "title", "reporter", "duplicate_of", "duplicates", "subscribers",
  109.                         "assignee", "private", "security", "tags", "date_reported", "date_updated",
  110.                         "description", "attachments"]:
  111.                 return None
  112.             else:
  113.                 raise AttributeError
  114.         
  115. class Comments(LPComments):
  116.     def __init__(self):
  117.         LPComments.__init__(self)
  118.         
  119. class Comment(LPComment):
  120.     
  121.     def __init__(self, nr, author, date, comment):
  122.         LPComment.__init__(self,text=comment)
  123.         self.set_attr(nr=nr, user=user.parse_text_user(author[0]), date=LPTime(date[0]))
  124.  
  125.  
  126. class Attachments(LPAttachments):
  127.     def __init__(self, a_set):
  128.         LPAttachments.__init__(self, attachments=a_set, parsed=True)
  129.         
  130.     def add(self, attachment):
  131.         raise NotImplementedError, "It is impossible to add attachments in the text-mode"
  132.         
  133.     def remove(self, key=None, func=None):
  134.         raise NotImplementedError, "It is impossible to remove attachments in the text-mode"
  135.  
  136. class Attachment(LPAttachment):
  137.     def __init__(self, url, contenttype, connection, bugnumber=None):
  138.         LPAttachment.__init__(self, connection, url=url, contenttype=contenttype)
  139.         self.__bugnumber = bugnumber
  140.                     
  141.     def get_sourcepackage(self):
  142.         if self.is_up:
  143.             return "unknown_sourcepackage"
  144.             
  145.     def get_bugnumber(self):
  146.         if self.is_up:
  147.             return self.__bugnumber
  148.         
  149.         
  150.  
  151. class TextPage(object):
  152.     def __init__(self, url, connection):
  153.         self.parsed = False
  154.         self.__url = url + "/+text"
  155.         self.__connection = connection
  156.         self.__data = {}
  157.         
  158.     def __getitem__(self, key):
  159.         if not self.parsed:
  160.             self.parse()
  161.         return self.__data.get(key, [])
  162.         
  163.     def parse(self):
  164.         text = self.__connection.get(self.__url).text
  165.         parts = text.split("\n\n")
  166.         tmp_task = LPTasks({"url": self.__url})
  167.         self.__data["comments"] = Comments()
  168.         current_task_tupel = LPTasks.current_from_url(self.__url)
  169.         while parts:
  170.             #~ print "LEN", len(parts)
  171.             if parts[0].startswith("bug:"):
  172.                 x = parts.pop(0)
  173.                 x = "[bug]\n" + x
  174.                 #~ print "BUG"
  175.                 data = ConfigParser.ConfigParser()
  176.                 data.readfp(StringIO.StringIO(x))
  177.                 self.__data["bug"] = BugReport(dict(data.items("bug")), connection=self.__connection)
  178.             elif parts[0].startswith("task:"):
  179.                 x = parts.pop(0)
  180.                 x = "[task]\n" + x
  181.                 #~ print "TASK"
  182.                 data = ConfigParser.ConfigParser()
  183.                 data.readfp(StringIO.StringIO(x))
  184.                 task_obj = Task(dict(data.items("task")))
  185.                 if task_obj.is_current(current_task_tupel):
  186.                     tmp_task._current = len(tmp_task)
  187.                 tmp_task.append(task_obj)
  188.                 continue
  189.             elif parts[0].startswith("Content-Type:"):
  190.                 l = "\n\n".join(parts)
  191.                 comments_msg = email.message_from_string(l)
  192.                 messages = comments_msg.get_payload()
  193.                 description = messages.pop(0)
  194.                 self.__data["bug"]._add_description(description.get_payload(decode=True))
  195.                 for i, msg in enumerate(messages):
  196.                     self.__data["comments"].append(Comment(i+1, msg.get_all("Author"), msg.get_all("Date"), msg.get_payload(decode=True)))
  197.                 parts = False
  198.                 continue
  199.             else:
  200.                 raise RuntimeError
  201.         if tmp_task._current is None and len(tmp_task) == 1:
  202.             # "only one task, this must be current"
  203.             tmp_task._current = 0
  204.         self.__data["task"] = tmp_task
  205.         self.parsed = True
  206.                     
  207.  
  208.  
  209. class Bug(BugBase):
  210.     def __init__(self, bug=None, url=None, connection=None):
  211.             
  212.         BugBase.__init__(self, bug, url, connection)
  213.         self.__textpage = TextPage(self.url, self.__connection)
  214.         
  215.     def get_url(self):
  216.         return self.url
  217.     
  218.     def get_bugnumber(self):
  219.         assert self.bugnumber == self.__textpage["bug"].bugnumber[0]
  220.         return self.__textpage["bug"].bugnumber[0]
  221.         
  222.     def get_reporter(self):
  223.         return self.__textpage["bug"].reporter
  224.         
  225.     def get_title(self):
  226.         return self.__textpage["bug"].title
  227.         
  228.     def get_subscriptions(self):
  229.         return set(self.__textpage["bug"].subscribers)
  230.         
  231.     def get_duplicate(self):
  232.         try: return self.__textpage["bug"].duplicate_of[0]
  233.         except: return None
  234.         
  235.     def get_duplicates(self):
  236.         # the 'or []'-statement ensures that this always returns a list and not 'None'
  237.         return set(self.__textpage["bug"].duplicates or [])
  238.         
  239.     def get_infotable(self):
  240.         return self.__textpage["task"]
  241.         
  242.     def get_info(self):
  243.         return self.__textpage["task"].current
  244.         
  245.     def get_status(self):
  246.         return self.__textpage["task"].current.status
  247.         
  248.     def get_importance(self):
  249.         return self.__textpage["task"].current.importance
  250.         
  251.     def get_target(self):
  252.         return self.__textpage["task"].current.target
  253.         
  254.     def get_milestone(self):
  255.         return self.__textpage["task"].current.milestone
  256.         
  257.     def get_assignee(self):
  258.         return self.__textpage["task"].current.assignee
  259.         
  260.     def get_sourcepackage(self):
  261.         return self.__textpage["task"].current.sourcepackage
  262.         
  263.     def get_affects(self):
  264.         return self.__textpage["task"].current.affects
  265.  
  266.     def get_private(self):
  267.         return bool(self.__textpage["bug"].private)
  268.  
  269.     def get_security(self):
  270.         return bool(self.__textpage["bug"].security)
  271.  
  272.     def get_tags(self):
  273.         return self.__textpage["bug"].tags
  274.         
  275.     def get_attachments(self):
  276.         return self.__textpage["bug"].attachments
  277.  
  278.     def get_date(self):
  279.         return self.__textpage["bug"].date_reported
  280.  
  281.     def get_date_updated(self):
  282.         return self.__textpage["bug"].date_updated
  283.         
  284.     def get_comments(self):
  285.         return self.__textpage["comments"]
  286.         
  287.     def get_description(self):
  288.         return self.__textpage["bug"].description or ""
  289.     get_description_raw = get_description
  290.         
  291.     def get_text(self):
  292.         return "%s\n%s" %(self.description,"\n".join([c.text for c in self.comments]))
  293.