1 # -*- coding: iso-8859-1 -*- 2 """ 3 MoinMoin - EventAggregatorNewEvent Action 4 5 @copyright: 2008, 2009, 2010 by Paul Boddie <paul@boddie.org.uk> 6 @copyright: 2000-2004 Juergen Hermann <jh@web.de>, 7 2003-2008 MoinMoin:ThomasWaldmann, 8 2004-2006 MoinMoin:AlexanderSchremmer, 9 2007 MoinMoin:ReimarBauer. 10 @license: GNU GPL (v2 or later), see COPYING.txt for details. 11 """ 12 13 from MoinMoin.action import ActionBase 14 from MoinMoin.Page import Page 15 from MoinMoin.PageEditor import PageEditor 16 import EventAggregatorSupport 17 import calendar 18 import re 19 20 Dependencies = ['pages'] 21 22 # Action class and supporting functions. 23 24 class EventAggregatorNewEvent(ActionBase): 25 26 "An event creation dialogue requesting various parameters." 27 28 def _get_selected(self, value, input_value): 29 return input_value is not None and value == input_value and 'selected="selected"' or '' 30 31 def _get_selected_for_list(self, value, input_values): 32 return value in input_values and 'selected="selected"' or '' 33 34 def _get_input(self, form, name, default): 35 return int(form.get(name, [None])[0] or default) 36 37 def get_form_html(self, buttons_html): 38 _ = self._ 39 request = self.request 40 form = request.form 41 42 # Handle advanced and basic forms. 43 44 show_advanced = form.get("advanced") and not form.get("basic") 45 46 # Prepare the category list. 47 48 category_list = [] 49 category_pagenames = form.get("category", []) 50 51 for category_name, category_pagename in \ 52 EventAggregatorSupport.getCategoryMapping( 53 EventAggregatorSupport.getCategories(request), 54 request): 55 56 selected = self._get_selected_for_list(category_pagename, category_pagenames) 57 58 # In the advanced view, populate a menu. 59 60 if show_advanced: 61 category_list.append('<option value="%s" %s>%s</option>' % (category_pagename, selected, category_name)) 62 63 # In the basic view, use hidden fields. 64 65 elif selected: 66 category_list.append('<input value="%s" name="category" type="hidden" />' % category_pagename) 67 68 # Initialise month lists. 69 70 start_month_list = [] 71 start_month_list.append('<option value=""></option>') 72 end_month_list = [] 73 end_month_list.append('<option value=""></option>') 74 75 start_month = self._get_input(form, "start-month", 0) 76 end_month = self._get_input(form, "end-month", 0) 77 78 # Prepare month lists, selecting specified months. 79 80 for month in range(1, 13): 81 month_label = _(EventAggregatorSupport.getMonthLabel(month)) 82 selected = self._get_selected(month, start_month) 83 start_month_list.append('<option value="%02d" %s>%s</option>' % (month, selected, month_label)) 84 selected = self._get_selected(month, end_month) 85 end_month_list.append('<option value="%02d" %s>%s</option>' % (month, selected, month_label)) 86 87 # Permitting configuration of the template name. 88 89 template_default = getattr(request.cfg, "event_aggregator_new_event_template", "EventTemplate") 90 91 d = { 92 "buttons_html" : buttons_html, 93 "category_label" : _("Categories"), 94 "category_list" : "\n".join(category_list), 95 "start_month_list" : "\n".join(start_month_list), 96 "end_month_list" : "\n".join(end_month_list), 97 "start_label" : _("Start date (day, month, year)"), 98 "start_day_default" : form.get("start-day", [""])[0], 99 "start_year_default" : form.get("start-year", [""])[0] or EventAggregatorSupport.getCurrentYear(), 100 "end_label" : _("End date (day, month, year) - if different"), 101 "end_day_default" : form.get("end-day", [""])[0], 102 "end_year_default" : form.get("end-year", [""])[0], 103 "title_label" : _("Event title/summary"), 104 "title_default" : form.get("title", [""])[0], 105 "description_label" : _("Event description"), 106 "description_default" : form.get("description", [""])[0], 107 "template_label" : _("Event template"), 108 "template_default" : form.get("template", [""])[0] or template_default, 109 "parent_label" : _("Parent page"), 110 "parent_default" : form.get("parent", [""])[0], 111 "advanced_label" : _("Show advanced options"), 112 "basic_label" : _("Show basic options"), 113 } 114 115 # Prepare the output HTML. 116 117 html = ''' 118 <table> 119 <tr> 120 <td class="label"><label>%(title_label)s</label></td> 121 <td> 122 <input name="title" type="text" size="40" value="%(title_default)s" /> 123 </td> 124 </tr> 125 <tr> 126 <td class="label"><label>%(start_label)s</label></td> 127 <td> 128 <input name="start-day" type="text" value="%(start_day_default)s" size="2" /> 129 <select name="start-month"> 130 %(start_month_list)s 131 </select> 132 <input name="start-year" type="text" value="%(start_year_default)s" size="4" /> 133 </td> 134 </tr> 135 <tr> 136 <td class="label"><label>%(end_label)s</label></td> 137 <td> 138 <input name="end-day" type="text" value="%(end_day_default)s" size="2" /> 139 <select name="end-month"> 140 %(end_month_list)s 141 </select> 142 <input name="end-year" type="text" value="%(end_year_default)s" size="4" /> 143 </td> 144 </tr> 145 <tr> 146 <td class="label"><label>%(description_label)s</label></td> 147 <td> 148 <input name="description" type="text" size="40" value="%(description_default)s" /> 149 </td> 150 </tr>''' % d 151 152 if show_advanced: 153 html += ''' 154 <tr> 155 <td></td> 156 <td> 157 <input name="basic" type="submit" value="%(basic_label)s" /> 158 <input name="advanced" type="hidden" value="true" /> 159 </td> 160 </tr> 161 <tr> 162 <td class="label"><label>%(category_label)s</label></td> 163 <td class="content"> 164 <select multiple="multiple" name="category"> 165 %(category_list)s 166 </select> 167 </td> 168 </tr> 169 <tr> 170 <td class="label"><label>%(template_label)s</label></td> 171 <td> 172 <input name="template" type="text" size="40" value="%(template_default)s" /> 173 </td> 174 </tr> 175 <tr> 176 <td class="label"><label>%(parent_label)s</label></td> 177 <td> 178 <input name="parent" type="text" size="40" value="%(parent_default)s" /> 179 </td> 180 </tr> 181 <tr> 182 <td></td> 183 <td class="buttons"> 184 %(buttons_html)s 185 </td> 186 </tr> 187 </table>''' % d 188 else: 189 html += ''' 190 <tr> 191 <td></td> 192 <td> 193 <input name="advanced" type="submit" value="%(advanced_label)s" /> 194 %(category_list)s 195 <input name="parent" type="hidden" value="%(parent_default)s" /> 196 <input name="template" type="hidden" value="%(template_default)s" /> 197 </td> 198 </tr> 199 <tr> 200 <td></td> 201 <td class="buttons"> 202 %(buttons_html)s 203 </td> 204 </tr> 205 </table>''' % d 206 207 return html 208 209 def do_action(self): 210 211 "Create the new event." 212 213 _ = self._ 214 form = self.request.form 215 216 # If no title exists in the request, an error message is returned. 217 218 title = form.get("title", [None])[0] 219 template = form.get("template", [None])[0] 220 221 if not title: 222 return 0, _("No event title specified.") 223 224 if not template: 225 return 0, _("No page template specified.") 226 227 return self.create_event(self.request) 228 229 def render_success(self, msg, msgtype=None): 230 231 """ 232 Render neither 'msg' nor 'msgtype' since redirection should occur 233 instead. 234 NOTE: msgtype is optional because MoinMoin 1.5.x does not support it. 235 """ 236 237 pass 238 239 def create_event(self, request): 240 241 "Create an event page using the 'request'." 242 243 _ = request.getText 244 form = request.form 245 246 category_pagenames = form.get("category", []) 247 description = form.get("description", [None])[0] 248 249 try: 250 title = form["title"][0] 251 template = form["template"][0] 252 parent = form["parent"][0] 253 254 start_day = self._get_input(form, "start-day", 0) 255 start_month = self._get_input(form, "start-month", 0) 256 start_year = self._get_input(form, "start-year", 0) 257 end_day = self._get_input(form, "end-day", start_day) 258 end_month = self._get_input(form, "end-month", start_month) 259 end_year = self._get_input(form, "end-year", start_year) 260 261 start_year, start_month, start_day = self.constrain_date(start_year, start_month, start_day) 262 end_year, end_month, end_day = self.constrain_date(end_year, end_month, end_day) 263 264 except (TypeError, ValueError): 265 return 0, _("Days and years must be numbers yielding a valid date!") 266 267 except (KeyError, IndexError): 268 return 0, _("Event title or template missing.") 269 270 start_date = self.make_date_string(start_year, start_month, start_day) 271 end_date = self.make_date_string(end_year, end_month, end_day) 272 273 # Copy the template. 274 275 page = PageEditor(request, template) 276 277 if not page.exists(): 278 return 0, _("Event template not available.") 279 280 event_page = EventAggregatorSupport.EventPage(page) 281 282 # Use any parent page information. 283 284 if parent: 285 full_title = "%s/%s" % (parent.rstrip("/"), title) 286 else: 287 full_title = title 288 289 # Load the new page and replace the event details in the body. 290 291 new_page = PageEditor(request, full_title) 292 293 if new_page.exists(): 294 return 0, _("The specified page already exists. Please choose another name.") 295 296 new_event_page = EventAggregatorSupport.EventPage(new_page) 297 new_event_page.copyPage(event_page) 298 299 if new_event_page.getFormat() == "wiki": 300 event_details = { 301 "start" : start_date, "end" : end_date, 302 "title" : title, "summary" : title, 303 "description" : description 304 } 305 new_event = EventAggregatorSupport.Event(new_event_page, event_details) 306 new_event_page.setEvents([new_event]) 307 new_event_page.setCategoryMembership(category_pagenames) 308 new_event_page.saveChanges() 309 310 # Redirect and return success. 311 312 query = {'action' : 'edit'} 313 request.http_redirect(new_page.url(request, query)) 314 return 1, None 315 316 def make_date_string(self, year, month, day): 317 return "%s-%s-%s" % ( 318 year and ("%04d" % year) or "YYYY", 319 month and ("%02d" % month) or "MM", 320 day and ("%02d" % day) or "DD" 321 ) 322 323 def constrain_date(self, year, month, day): 324 if year and month and day: 325 wd, last_day = calendar.monthrange(year, month) 326 day = max(min(day, last_day), 1) 327 return year, month, day 328 329 # Action function. 330 331 def execute(pagename, request): 332 EventAggregatorNewEvent(pagename, request).render() 333 334 # vim: tabstop=4 expandtab shiftwidth=4