paul@21 | 1 | # -*- coding: iso-8859-1 -*- |
paul@21 | 2 | """ |
paul@21 | 3 | MoinMoin - ReadMessage Action |
paul@21 | 4 | |
paul@21 | 5 | @copyright: 2012, 2013 by Paul Boddie <paul@boddie.org.uk> |
paul@21 | 6 | @license: GNU GPL (v2 or later), see COPYING.txt for details. |
paul@21 | 7 | """ |
paul@21 | 8 | |
paul@21 | 9 | from MoinMoin.action import ActionBase |
paul@21 | 10 | from MoinSupport import * |
paul@73 | 11 | from ItemSupport import ItemStore |
paul@21 | 12 | from email.parser import Parser |
paul@21 | 13 | |
paul@21 | 14 | Dependencies = [] |
paul@21 | 15 | |
paul@21 | 16 | class ReadMessage(ActionBase, ActionSupport): |
paul@21 | 17 | |
paul@21 | 18 | "An action that can read a stored message component." |
paul@21 | 19 | |
paul@21 | 20 | def __init__(self, pagename, request): |
paul@21 | 21 | |
paul@21 | 22 | """ |
paul@21 | 23 | On the page with the given 'pagename', use the given 'request' to access |
paul@21 | 24 | message components. |
paul@21 | 25 | """ |
paul@21 | 26 | |
paul@21 | 27 | ActionBase.__init__(self, pagename, request) |
paul@21 | 28 | self.store = ItemStore(self.page, "messages", "message-locks") |
paul@21 | 29 | |
paul@21 | 30 | def get_form_html(self, buttons_html): |
paul@21 | 31 | |
paul@21 | 32 | "Present an interface for accessing a message component." |
paul@21 | 33 | |
paul@21 | 34 | _ = self._ |
paul@21 | 35 | request = self.request |
paul@21 | 36 | form = self.get_form() |
paul@21 | 37 | |
paul@21 | 38 | message = form.get("message", [""])[0] |
paul@21 | 39 | part = form.get("part", [""])[0] |
paul@21 | 40 | |
paul@21 | 41 | # Fill in the fields and labels. |
paul@21 | 42 | |
paul@21 | 43 | d = { |
paul@21 | 44 | "buttons_html" : buttons_html, |
paul@21 | 45 | "message_label" : _("Message number"), |
paul@21 | 46 | "message_default" : escattr(message), |
paul@21 | 47 | "part_label" : _("Part identifier"), |
paul@21 | 48 | "part_default" : escattr(part), |
paul@21 | 49 | } |
paul@21 | 50 | |
paul@21 | 51 | # Prepare the output HTML. |
paul@21 | 52 | |
paul@21 | 53 | html = ''' |
paul@21 | 54 | <table> |
paul@21 | 55 | <tr> |
paul@21 | 56 | <td class="label"><label>%(message_label)s</label></td> |
paul@21 | 57 | <td> |
paul@21 | 58 | <input name="message" type="text" value="%(message_default)s" /> |
paul@21 | 59 | </td> |
paul@21 | 60 | </tr> |
paul@21 | 61 | <tr> |
paul@21 | 62 | <td class="label"><label>%(part_label)s</label></td> |
paul@21 | 63 | <td> |
paul@21 | 64 | <input name="part" type="text" value="%(part_default)s" /> |
paul@21 | 65 | </td> |
paul@21 | 66 | </tr> |
paul@21 | 67 | <tr> |
paul@21 | 68 | <td></td> |
paul@21 | 69 | <td class="buttons"> |
paul@21 | 70 | %(buttons_html)s |
paul@21 | 71 | </td> |
paul@21 | 72 | </tr> |
paul@21 | 73 | </table>''' % d |
paul@21 | 74 | |
paul@21 | 75 | return html |
paul@21 | 76 | |
paul@21 | 77 | def do_action(self): |
paul@21 | 78 | |
paul@21 | 79 | "Attempt to send the message." |
paul@21 | 80 | |
paul@21 | 81 | _ = self._ |
paul@21 | 82 | request = self.request |
paul@21 | 83 | form = self.get_form() |
paul@21 | 84 | |
paul@21 | 85 | message_number = form.get("message", [None])[0] |
paul@21 | 86 | part_identifier = form.get("part", [None])[0] |
paul@21 | 87 | |
paul@21 | 88 | if not message_number: |
paul@21 | 89 | return 0, _("A message number must be given.") |
paul@21 | 90 | |
paul@21 | 91 | if not part_identifier: |
paul@21 | 92 | return 0, _("A part identifier must be given.") |
paul@21 | 93 | |
paul@21 | 94 | # Obtain the message. |
paul@21 | 95 | |
paul@21 | 96 | try: |
paul@21 | 97 | message_text = self.store[int(message_number)] |
paul@21 | 98 | except (IndexError, ValueError): |
paul@21 | 99 | return 0, _("No such message is stored on this page.") |
paul@21 | 100 | |
paul@21 | 101 | # Visit the message parts, looking for the indicated component. |
paul@21 | 102 | |
paul@99 | 103 | message = Parser().parsestr(message_text) |
paul@21 | 104 | |
paul@21 | 105 | if message.is_multipart(): |
paul@21 | 106 | for part in message.get_payload(): |
paul@21 | 107 | |
paul@21 | 108 | # For the selected component, return the content as a response |
paul@21 | 109 | # to the current request. |
paul@21 | 110 | |
paul@21 | 111 | if part.get("Content-ID") == part_identifier: |
paul@21 | 112 | charset = part.get_content_charset() |
paul@21 | 113 | headers = [ |
paul@21 | 114 | "Content-Type: %s%s" % ( |
paul@21 | 115 | part.get_content_type(), |
paul@21 | 116 | charset and ("; charset=%s" % charset) or "" |
paul@21 | 117 | ) |
paul@21 | 118 | ] |
paul@21 | 119 | get_send_headers(request)(headers) |
paul@21 | 120 | request.write(part.get_payload(decode=True)) |
paul@21 | 121 | return 1, None |
paul@21 | 122 | |
paul@21 | 123 | return 0, _("No such component in the indicated message.") |
paul@21 | 124 | |
paul@21 | 125 | def render_success(self, msg, msgtype=None): |
paul@21 | 126 | |
paul@21 | 127 | """ |
paul@21 | 128 | Render neither 'msg' nor 'msgtype' since a resource has already been |
paul@21 | 129 | produced. |
paul@21 | 130 | NOTE: msgtype is optional because MoinMoin 1.5.x does not support it. |
paul@21 | 131 | """ |
paul@21 | 132 | |
paul@21 | 133 | pass |
paul@21 | 134 | |
paul@21 | 135 | # Action function. |
paul@21 | 136 | |
paul@21 | 137 | def execute(pagename, request): |
paul@21 | 138 | ReadMessage(pagename, request).render() |
paul@21 | 139 | |
paul@21 | 140 | # vim: tabstop=4 expandtab shiftwidth=4 |