Attachment 'findandreplace0.1Beta.py'

Download

   1 # -*- coding: iso-8859-1 -*-
   2 """
   3     MoinMoin - findandreplace action
   4 
   5     @copyright: 2006 Richard Flieger
   6     @contact: < e DASH mail AT rf DASH mmx DOT de >
   7     @license: GNU GPL, see COPYING for details.
   8     
   9     Description:
  10         This action allows users to search words and
  11         sentenses on the current wiki-page and replace
  12         the results by another text.
  13         
  14     Feathers:
  15         * regulare expressions
  16         * wildcard character
  17         * fixed strings
  18         * show results
  19         * show context
  20         * highlight in page
  21         * show raw-text
  22         * toggle highlightning
  23         * replace selected
  24         * replace all
  25         * preview
  26         * custumend comment
  27         * trivial change or not
  28         * language support
  29     
  30     History:
  31         2007/03/11 0.1b: Beta, dirty hack
  32         
  33 """
  34 
  35 from MoinMoin.Page import Page
  36 from MoinMoin import PageEditor
  37 from MoinMoin.widget.dialog import Dialog
  38 from re import *
  39 import re
  40 import shutil
  41 import time
  42 
  43 class FindAndReplaceAction:
  44 
  45     def __init__(self, request, referrer):
  46         self.request = request
  47         self.referrer = referrer
  48         self._ = request.getText
  49 
  50     def render( self ):
  51         
  52         self.form = self.request.form
  53         
  54         self.currentusername = self.request.page.page_name
  55         
  56         if not self.request.user.may.read(self.currentusername) or self.form.has_key(u'cancel_button'):
  57             query = {'action': 'show'}
  58             url = Page(self.request, self.referrer).url(self.request, query, 0)
  59             self.request.http_redirect(url)
  60         
  61         self.find = self.form.get('find', [None] )[0]
  62         self.replace = self.form.get('replace', [""] )[0]
  63         self.methode = self.form.get('methode', ["text"])[0]
  64         self.casesensitive = self.form.get( 'casesensitive', [0])[0]
  65         self.word = self.form.get('word', [None])[0]
  66         self.context = self.form.get('context', [0])[0]
  67         self.selected = self.form.get('selected', [])
  68         self.comment = self.form.get('comment', [""] )[0]
  69         self.highlight = self.form.get( 'highlight',[""] )[0]
  70         self.multiline = self.form.get( "multiline", [""])[0]
  71         self.searchonly = self.form.get( "searchonly", [""])[0]
  72         self.trivial = self.form.get( "trivial", [0] )[0]
  73         self.showraw = self.form.get( "showraw", [0] )[0]
  74         
  75         if not self.request.user.may.write(self.currentusername):
  76             self.showraw = 0
  77         self.contextsize = 20
  78         
  79         if not self.context:
  80             self.contextsize = 0
  81             
  82         self.userhelp = self._("""
  83 = Help =
  84  
  85 == Regulare expressions ==
  86 
  87  alternation:: A vertical bar separates alternatives. For example, "gray|grey", which could be shortened to the equivalent "gr(a|e)y", can match "gray" or "grey".
  88  grouping:: Parentheses are used to define the scope and precedence of the operators. For example, "gray|grey" and "gr(a|e)y" are different patterns, but they both describe the set containing gray and grey.
  89  quantification:: [[BR]]A quantifier after a character or group specifies how often that preceding expression is allowed to occur. The most common quantifiers are ?, *, and +:[[BR]]'''?''' The question mark indicates there is 0 or 1 of the previous expression. For example, "colou?r" matches both color and colour.[[BR]]'''*''' The asterisk indicates there are 0, 1 or any number of the previous expression. For example, "go*gle" matches ggle, gogle, google, gooogle, etc.[[BR]]'''+''' The plus sign indicates that there is at least 1 of the previous expression. For example, "go+gle" matches gogle, google, gooogle, etc. (but not ggle).
  90 
  91 ''for detailt look at: [http://en.wikipedia.org/wiki/Regular_Expressions Wikipedia]''
  92 == Wildcard character ==
  93  The asterisk (*) usually substitutes as a wildcard character for any zero or more characters, and the question mark (?) usually substitutes as a wildcard character for any one character
  94 
  95 ''for detailt look at: [http://en.wikipedia.org/wiki/Wildcard_character Wikipedia]''
  96 """)
  97         
  98         self.lang_dict = {
  99                           ##Headlines
 100                           u"title_searchtext_text" : self._('''Search Text'''),
 101                           u"title_findandreplace_text" : self._( '''find and replace''' ),
 102                           
 103                           ##Menu Text
 104                           u"text_raw_text" : self._('''Raw'''),
 105                           u"text_method_text" : self._('''Methode:'''),
 106                           u"text_option_text" : self._('''Options:'''),
 107                           u"text_context_text" : self._('''Display context of search results'''),
 108                           u"text_search_text" : self._( '''Find what''' ),
 109                           u"text_replace_text" : self._( '''Replace with''' ),
 110                           u"text_text_text" : self._( '''Fixed string''' ),
 111                           u"text_word_text" : self._( '''Whole words''' ),
 112                           u"text_wildcards_text" : self._( '''Wildcard character''' ),
 113                           u"text_casesensitive_text" : self._( '''Case-sensitive''' ),
 114                           u"text_regularexpression_text" : self._( '''Regular expressions'''),
 115                           u"text_Wrap search_text" : self._('''Wrap search'''),
 116                           u"text_comment_text" : self._('''Comment'''),
 117                           u"text_multiline_text" : self._('''Multiline'''),
 118                           u"text_searchonly_text" : self._('''Search only'''),
 119                           u"text_notsaved_text" : self._('''Your changes are not saved!'''),
 120                           u"text_saved_text" : self._('''Thank you for your changes. Your attention to detail is appreciated.'''),
 121                           u"text_trivial_text" : self._('''Trivial change'''),
 122                           u"text_langcomment_text" : self._('''"%s" replaced by "%s"'''),
 123                           u"text_showraw_text" : self._('''Show raw Text'''),
 124 
 125                           u"text_match_text" : self._('''%(matchcount)d %(matches)s for "%(title)s"'''),
 126                           
 127                           ##Buttons
 128                           u"highlight_button" : self._( '''Highlight on/off''' ),
 129                           u"search_button" : self._( '''Search''' ),
 130                           u"cancel_button" : self._( '''Cancel''' ),
 131                           u"preview_button" : self._( '''Preview''' ),
 132                           u"replaceall_button" : self._( '''Replace all''' ),
 133                           u"replaceselected_button" : self._( '''Replace selected''' ),
 134                           u"help_button" : self._('''help'''),
 135                           u"about_button" : self._('''about''' )
 136                           }
 137         
 138         self.regex_dict = { u'%3F' : u'?',
 139                       }
 140         
 141         self.wildcard_dict = { u'''?''' : u'''.''',
 142                           u'''*''' : u'''.*?''' }
 143         
 144         self.normal_dict = { ##u'''\\''' : u'''\\\\''',
 145                         u'''.''' : u'''\\.''',
 146                         u'''*''' : u'''\\*''',
 147                         u'''[''' : u'''\\[''',
 148                         u''']''' : u'''\\]''',
 149                         u'''(''' : u'''\\(''',
 150                         u''')''' : u'''\\)''' }
 151         
 152         if self.form.has_key(u"help_button" ):
 153             self.generateHelpMessage()
 154             
 155         if self.form.has_key(u"about_button" ):
 156             self.generateAboutMessage()
 157 
 158         ##Search Action
 159         if not self.find and not self.replace:
 160             msg = self.generateSearchDialog()
 161             page = Page(self.request, self.referrer )
 162             page.send_page(self.request, msg=msg )
 163             return ''
 164 
 165         if self.form.has_key(u"highlight_button") or self.form.has_key(u"search_button") or self.form.has_key(u"selected_button") or self.form.has_key(u"preview_button") or self.form.has_key(u"all_button"):
 166             
 167             if self.request.user.may.read(self.currentusername):
 168                 self.getFindRegex()
 169                 
 170                 if self.form.has_key(u"highlight_button") or self.form.has_key(u"search_button"):
 171                 
 172                     oldtext = self.getPageText( self.referrer)
 173                     results = self.findallResults( oldtext )
 174                     if not results:    
 175                         msg = self.generateNoResultMessage()
 176                         page = Page(self.request, self.referrer )
 177                         page.send_page(self.request, msg=msg )
 178                         return ''
 179                     else:
 180                         p = Page(self.request, self.referrer)
 181                         rev = p.get_real_rev()
 182                         msg = self.generateReplaceDialog( rev, results )
 183                         
 184                         page = Page(self.request, self.referrer )
 185                         page.send_page(self.request, msg=msg )
 186                         return u""
 187     
 188                 if not self.comment:
 189                     self.comment = (u'''%(text_langcomment_text)s''' % self.lang_dict) % ( self.find, self.replace )
 190                 
 191                 p = Page(self.request, self.referrer)
 192                 newrev = p.get_real_rev()
 193                 
 194                 rev = int(self.form.get( u"rev", 0 )[0])
 195                 
 196                 if rev == newrev:
 197                     self.oldtext = self.getPageText(self.referrer)
 198                 else:
 199                     query = {'action': 'findandreplace'}
 200                     url = Page(self.request, self.referrer).url(self.request, query, 0)
 201                     self.request.http_redirect(url)
 202                 
 203                 newtext = 0
 204                 
 205                 if self.form.has_key( u"all_button" ):
 206                     newtext = self.replaceAll()
 207                 
 208                 elif self.form.has_key( u"selected_button" ):
 209                     if self.selected:
 210                         newtext = self.replaceSelected()                    
 211                 else:
 212                     return 0
 213     
 214                 if newtext == 0 or newtext == self.oldtext: 
 215                     query = {'action': 'show'}
 216                     url = Page(self.request, self.referrer).url(self.request, query, 0)
 217                     self.request.http_redirect(url)
 218                 
 219             page = PageEditor.PageEditor(self.request, self.referrer, do_editor_backup=0)  
 220             newtext = page.normalizeText(newtext)           
 221             p = Page(self.request, self.referrer)
 222             print rev
 223             rev = int(newrev )
 224             print rev
 225             try:
 226                 page.saveText(newtext, rev, comment=self.comment, trivial=self.trivial)
 227                 msg = "%(text_saved_text)s" % self.lang_dict
 228             except:
 229                 msg = "%(text_notsaved_text)s" % self.lang_dict
 230             page = Page(self.request, self.referrer )
 231             page.send_page(self.request, msg=msg )
 232     
 233         return ''
 234     
 235     def getFindRegex(self):
 236 
 237         self.findregex = self.find
 238         if self.methode == "regex":
 239             for entry in self.regex_dict:
 240                 self.findregex = self.findregex.replace( entry, self.regex_dict[entry] )
 241                 
 242         elif self.methode == "wildcards":
 243             for entry in self.wildcard_dict:
 244                 self.findregex = self.findregex.replace( entry, self.wildcard_dict[entry] )
 245                 
 246         else:
 247             for entry in self.normal_dict:
 248                 self.findregex = self.findregex.replace( entry, self.normal_dict[entry] )
 249         if self.word == "1":
 250             self.findregex = u'\\b%s\\b' % self.findregex
 251             
 252         if not self.casesensitive:
 253             ignorcase = "i"
 254         else:
 255             ignorcase = ""
 256             
 257         if self.multiline:
 258             multiline = u"sm"
 259         else:
 260             multiline = u""
 261         
 262         if multiline or ignorcase:
 263             pattern = u"(?%(m)s%(i)s)" % {u"i" : ignorcase,
 264                                              u"m" : multiline }
 265         else:
 266             pattern = ""
 267             
 268         self.findregex = u"%(p)s%(f)s" % { u"p" : pattern, u"f" : self.findregex}
 269     
 270     def getPageText(self, pagename ):
 271         oldtext = PageEditor.PageEditor(self.request, pagename , do_editor_backup=0)
 272         return oldtext.get_raw_body()
 273     
 274     def replaceSelected(self):
 275         pattern = re.compile( self.findregex)
 276         resultlist = pattern.findall( self.oldtext)#, self.casesensitive )
 277         index = 0
 278         newtext = self.oldtext
 279         pos1 = newtext.find(resultlist[0])
 280         for result in resultlist:
 281             pos2 = newtext[pos1:].find(result)
 282             pos2 = pos1 + len(result)
 283             if str(index) in self.selected:               
 284                 newtext = newtext[:pos1] + self.replace + newtext[pos2:]
 285             pos1 = pos2 + newtext[pos2:].find(result)
 286             index += 1
 287         return newtext
 288     
 289     def replaceAll(self):
 290         newtext=re.sub(self.findregex, self.form.get(u"replace",[u""])[0], self.oldtext )
 291         return newtext  
 292       
 293     def parsText( regex, source ):
 294         variable = re.search( regex, source )
 295         regex = regex.replace('\+|\.', '.')
 296         if variable != None:
 297             variable = variable.group( 1 )
 298             value = variable.decode("iso-8859-1")
 299         else:
 300             value = u"N/A"
 301         return value
 302     
 303     def findallResults(self, text ):
 304         pattern = re.compile( self.findregex)#, self.casesensitive )
 305         resultList = pattern.findall( text)
 306         pos = 0
 307         newresultList = []
 308         for result in resultList:
 309             pos = text.find(result,pos)
 310             if pos > self.contextsize:
 311                 pos1 = pos - self.contextsize
 312             else:
 313                 pos1 = 0
 314             pos2 = pos + len(result) + self.contextsize
 315             newresultList.append( (text[pos1:pos], result,text[pos+len(result):pos2]) ) 
 316             pos += len(result) +1
 317         return newresultList
 318         
 319     def generateReplaceDialog( self, rev, list ):
 320         html =[]
 321         if len(list) > 1:
 322             matches = self._("""matches""")
 323         else:
 324             matches = self._("""match""")
 325         html.append(( u'<b>"%(text_match_text)s</b><br><br>' % self.lang_dict) % { u"title" : self.find, u"matchcount" : len( list ), u"matches" : matches } )
 326         html.append(u'<form method="post" action="">')
 327         index = 0
 328         for entry in list:
 329             html.append('''<p>''')
 330             if not self.searchonly:
 331                 html.append( u'<input type="checkbox" name="selected" value="%(index)s">' % { u"index" : index } )
 332             html.append( u'...%s<strong class="highlight">%s</strong>%s ...</p>' % ( entry[0], entry[1], entry[2] ) )
 333             index += 1
 334             
 335             
 336         if self.showraw:
 337             pagetext = self.getPageText(self.referrer)
 338             html.append("""<b>%(text_raw_text)s</b></br>""" % self.lang_dict)
 339             html.append("""<pre>\n%s\n</pre>""" % pagetext )
 340             
 341         if not self.searchonly:
 342             html.append( '''<p>%(text_replace_text)s''' % self.lang_dict )
 343             html.append( '''<input type="text" name="replace" size="20" value="%(replace)s"></p>''' % { u"replace" : self.replace })
 344         
 345         print self.trivial
 346         if self.trivial:
 347             trivialchecked = u"checked=checked"
 348             
 349         else:
 350             trivialchecked = u""
 351         
 352         html.append( '''%(text_comment_text)s <input type="text" size="20" name="comment" value="%(comment)s">
 353         %(text_trivial_text)s <input type="checkbox" name="trivial" value="1" %(trivialchecked)s>''' % { 
 354                                                                                       u"trivialchecked" : trivialchecked,
 355                                                                                       u"comment" : self.comment,
 356                                                                                       u"text_comment_text" : self.lang_dict[u"text_comment_text"],
 357                                                                                       u"text_trivial_text" : self.lang_dict[u"text_trivial_text"]  } )
 358         
 359         html.append( '''<input type="hidden" name="replace" value="%(replace)s"> 
 360         <input type="hidden" name="rev" value="%(rev)d">
 361         <input type="hidden" name="find" value="%(find)s">
 362         <input type="hidden" name="word" value="%(word)s"> 
 363         <input type="hidden" name="methode" value="%(methode)s">
 364         <input type="hidden" name="highlight" value="%(findregex)s">
 365         <input type="hidden" name="showraw" value="%(showraw)s">
 366         <input type="hidden" name="multiline" value="%(multiline)s">
 367         <input type="hidden" name="searchonly" value="%(searchonly)s">
 368         </p>''' % {             u"replace" : self.replace,
 369                                 u"rev" : rev,
 370                                 u"find" : self.find,
 371                                 u"word" : self.word,
 372                                 u"methode" : self.methode,
 373                                 u"context" : self.context,
 374                                 u"findregex" : self.highlight,
 375                                 u"multiline" : self.multiline,
 376                                 u"searchonly" : self.searchonly,
 377                                 u"showraw" : self.showraw,
 378                                 } )
 379         html.append('''<p>''')
 380         
 381         if not self.searchonly:
 382             html.append( '''<input type="hidden" name="action" value="findandreplace">
 383             <input type="submit" name="preview_button" value="%(preview_button)s">''' % self.lang_dict)
 384             
 385             html.append( '''<input type="submit" name="selected_button" value="%(replaceselected_button)s">
 386             <input type="submit" name="all_button" value="%(replaceall_button)s">''' % self.lang_dict )
 387             
 388         html.append( '''<input type="submit" name="cancel_button" value="%(cancel_button)s"></p>
 389             ''' % self.lang_dict)
 390         
 391         html.append( '''</div></form>''')
 392         
 393         if not self.highlight:
 394             self.highlight = self.findregex
 395         else:
 396             self.highlight = u""        
 397         
 398         html.append( '''<form method="post" action="">
 399         <input type="hidden" name="replace" value="%(replace)s"> 
 400         <input type="hidden" name="rev" value="%(rev)d">
 401         <input type="hidden" name="find" value="%(find)s">
 402         <input type="hidden" name="word" value="%(word)s"> 
 403         <input type="hidden" name="methode" value="%(methode)s">
 404         <input type="hidden" name="highlight" value="%(findregex)s">
 405         <input type="hidden" name="comment" value="%(comment)s">
 406         <input type="hidden" name="multiline" value="%(multiline)s">
 407         <input type="hidden" name="searchonly" value="%(searchonly)s">
 408         <input type="hidden" name="showraw" value="%(showraw)s">
 409         </p>''' % {             u"replace" : self.replace,
 410                                 u"rev" : rev,
 411                                 u"find" : self.find,
 412                                 u"word" : self.word,
 413                                 u"methode" : self.methode,
 414                                 u"comment" : self.comment,
 415                                 u"context" : self.context,
 416                                 u"findregex" : self.highlight,
 417                                 u"multiline" : self.multiline,
 418                                 u"searchonly" : self.searchonly,
 419                                 u"showraw" : self.showraw
 420                                 } )
 421         if self.trivial:
 422             html.append( """<input type="hidden" name="trivial" value="1">"""  )
 423                          
 424         if self.casesensitive:
 425             html.append( '''<input type="hidden" name="casesensitive" value="%(casesensitive)s">''' % {u"casesensitive" : self.casesensitive,}   )
 426         
 427         if self.context:
 428             html.append( '''<input type="hidden" name="context" value="%(context)s">''' % {u"context" : self.context, } )
 429         
 430         html.append( '''<input type="hidden" name="action" value="findandreplace">
 431         <input type="submit" name="highlight_button" value="%(highlight_button)s"></form>
 432         ''' % self.lang_dict)
 433         return Dialog (self.request, content=u"\n".join( html ) )
 434     
 435     def generateNoResultMessage( self ):
 436         return self._(u'''Nothing found for "%s"!''') %(self.find)
 437     
 438     def generateSearchDialog(self):
 439         
 440         html =  u'''<b>%(title_findandreplace_text)s</b><br/>
 441             %(title_searchtext_text)s<br/>
 442             <form method="get" action=""><div>
 443             <input type="hidden" name="action" value="findandreplace">
 444             <table border=0px>
 445             <tr>
 446             <td align="right" valign="middle">
 447                 %(text_search_text)s: <input type="text" name="find" size="20"><br/>
 448                 %(text_replace_text)s: <input type="text" name="replace" size="20"><br/>
 449                 %(text_comment_text)s: <input type="text" name="comment" size="20">
 450             </td>
 451              <td align="left" valign="middle">
 452              <p>%(text_option_text)s</p>
 453              <input type="checkbox" name="word" value="1">
 454              %(text_word_text)s<br/>
 455               <input type="checkbox" name="multiline" value="1">
 456              %(text_multiline_text)s<br/>
 457              <input type="checkbox" name="casesensitive" value="1">
 458              %(text_casesensitive_text)s<br/>
 459              <input type="checkbox" name="context" value="1">
 460              %(text_context_text)s<br/>
 461              <input type="checkbox" name="showraw" value="1">
 462              %(text_showraw_text)s<br/>
 463              <input type="checkbox" name="trivial" value="1">
 464              %(text_trivial_text)s<br/>
 465              </td>
 466              <td>
 467              <p>%(text_method_text)s</p>
 468              <input type="radio" name="methode" value="none" checked="checked">
 469              %(text_text_text)s<br/>
 470              <input type="radio" name="methode" value="wildcards">
 471              %(text_wildcards_text)s<br/>
 472              <input type="radio" name="methode" value="regex">
 473              %(text_regularexpression_text)s<br/>
 474              </td>
 475              </tr>
 476              <tr>
 477              <td valign="bottom">
 478              <p><input type="checkbox" name="searchonly" value="1"> %(text_searchonly_text)s</p>
 479              <input type="submit" name="search_button" value="%(search_button)s">
 480              <input type="submit" name="cancel_button" value="%(cancel_button)s">
 481              
 482              <input type="submit" name="help_button" value="%(help_button)s">
 483              <input type="submit" name="about_button" value="%(about_button)s">
 484              </td>
 485              </tr>
 486              </table>
 487             </div></form><br>
 488             ''' % self.lang_dict
 489         
 490         return Dialog (self.request, content=html)
 491     
 492     def generateHelpMessage(self):
 493         msg = self.userhelp
 494         page = Page(self.request, self.referrer )
 495         page.send_page(self.request, msg=msg )
 496         
 497     def generateAboutMessage(self):
 498         msg = "<pre>%s</pre>" % __doc__
 499         page = Page(self.request, self.referrer )
 500         page.send_page(self.request, msg=msg )
 501 
 502         
 503 def execute( pagename, request ):
 504     return FindAndReplaceAction( request, pagename ).render()

Attached Files

To refer to attachments on a page, use attachment:filename, as shown below in the list of files. Do NOT use the URL of the [get] link, since this is subject to change and can break easily.
  • [get | view] (2011-04-14 07:28:03, 4.7 KB) [[attachment:CreateNewPage.py]]
  • [get | view] (2011-04-14 07:26:24, 4.2 KB) [[attachment:CreateNewPage1.6.py]]
  • [get | view] (2006-09-10 21:29:29, 40.4 KB) [[attachment:CreatePdfDocument2_0_3.py]]
  • [get | view] (2006-09-12 06:05:06, 40.5 KB) [[attachment:CreatePdfDocument2_0_4.py]]
  • [get | view] (2006-09-12 12:00:09, 40.6 KB) [[attachment:CreatePdfDocument2_0_5.py]]
  • [get | view] (2006-11-14 21:56:11, 43.5 KB) [[attachment:CreatePdfDocument2_0_6.py]]
  • [get | view] (2006-11-15 17:00:47, 43.8 KB) [[attachment:CreatePdfDocument2_0_7.py]]
  • [get | view] (2006-11-16 22:06:18, 43.8 KB) [[attachment:CreatePdfDocument2_0_8.py]]
  • [get | view] (2006-12-17 15:54:21, 43.6 KB) [[attachment:CreatePdfDocument2_0_9.py]]
  • [get | view] (2007-08-20 09:10:23, 67.2 KB) [[attachment:CreatePdfDocument2_1_0.py]]
  • [get | view] (2007-08-21 07:39:49, 67.1 KB) [[attachment:CreatePdfDocument2_1_1.py]]
  • [get | view] (2007-09-11 19:16:37, 67.3 KB) [[attachment:CreatePdfDocument2_1_2.py]]
  • [get | view] (2007-09-18 20:17:58, 68.1 KB) [[attachment:CreatePdfDocument2_1_3.py]]
  • [get | view] (2007-09-21 13:32:54, 71.1 KB) [[attachment:CreatePdfDocument2_1_4.py]]
  • [get | view] (2007-09-23 20:56:30, 73.4 KB) [[attachment:CreatePdfDocument2_1_5.py]]
  • [get | view] (2007-09-25 20:54:48, 74.5 KB) [[attachment:CreatePdfDocument2_2_0.py]]
  • [get | view] (2008-06-23 21:08:49, 77.0 KB) [[attachment:CreatePdfDocument2_3_0.py]]
  • [get | view] (2008-06-26 19:25:07, 81.0 KB) [[attachment:CreatePdfDocument2_3_1.py]]
  • [get | view] (2008-07-06 05:50:38, 83.1 KB) [[attachment:CreatePdfDocument2_3_2.py]]
  • [get | view] (2008-07-09 17:42:02, 83.3 KB) [[attachment:CreatePdfDocument2_3_3.py]]
  • [get | view] (2008-09-07 11:11:01, 83.5 KB) [[attachment:CreatePdfDocument2_3_4.py]]
  • [get | view] (2009-01-11 15:53:09, 84.3 KB) [[attachment:CreatePdfDocument2_3_5.py]]
  • [get | view] (2009-02-16 06:52:06, 84.2 KB) [[attachment:CreatePdfDocument2_3_6.py]]
  • [get | view] (2010-01-29 11:53:21, 82.8 KB) [[attachment:CreatePdfDocument2_4_0.py]]
  • [get | view] (2010-01-31 14:10:03, 84.6 KB) [[attachment:CreatePdfDocument2_4_1.py]]
  • [get | view] (2010-09-18 16:23:23, 85.6 KB) [[attachment:CreatePdfDocument2_4_2.py]]
  • [get | view] (2006-06-16 20:56:53, 4.9 KB) [[attachment:FlashManager.py-1.5.3-1]]
  • [get | view] (2003-12-07 18:15:53, 3.9 KB) [[attachment:HTML2MoinMoin.py]]
  • [get | view] (2005-10-16 08:24:35, 4.9 KB) [[attachment:HelpOn-1.3.5-4.py]]
  • [get | view] (2006-02-03 19:21:04, 4.9 KB) [[attachment:HelpOn-1.5.1-5.py]]
  • [get | view] (2006-07-04 10:45:22, 4.8 KB) [[attachment:HelpOn-1.5.4-6.py]]
  • [get | view] (2006-07-04 22:39:14, 4.8 KB) [[attachment:HelpOn-1.6.0-7.py]]
  • [get | view] (2006-07-06 13:50:17, 4.0 KB) [[attachment:HelpOn-1.6.0-8.py]]
  • [get | view] (2008-01-10 17:43:24, 4.8 KB) [[attachment:HelpOn-1.6.0-9.py]]
  • [get | view] (2008-08-19 14:44:54, 5.0 KB) [[attachment:HelpOn-1.7.1-10.py]]
  • [get | view] (2005-02-20 18:28:34, 10.8 KB) [[attachment:IRSS.py]]
  • [get | view] (2005-03-09 22:46:23, 2.9 KB) [[attachment:ImportHtml-1.2.py]]
  • [get | view] (2003-12-07 18:15:53, 2.8 KB) [[attachment:ImportHtml.py]]
  • [get | view] (2003-12-07 18:15:53, 1.8 KB) [[attachment:IrcChat.py]]
  • [get | view] (2008-06-09 11:27:20, 4.4 KB) [[attachment:MoinCrypt.py]]
  • [get | view] (2010-11-29 12:08:27, 7.5 KB) [[attachment:PageActions.py]]
  • [get | view] (2006-08-07 15:12:19, 0.5 KB) [[attachment:PermanentLink.py]]
  • [get | view] (2003-12-07 18:15:53, 6.3 KB) [[attachment:PhoneDial.py]]
  • [get | view] (2005-04-17 14:21:47, 3.6 KB) [[attachment:RecommendPage-1.3.4-1.py]]
  • [get | view] (2005-04-19 18:21:52, 5.5 KB) [[attachment:RecommendPage-1.3.4-2.py]]
  • [get | view] (2005-05-02 19:53:09, 5.6 KB) [[attachment:RecommendPage-1.3.4-3.py]]
  • [get | view] (2005-09-03 07:33:35, 6.3 KB) [[attachment:RecommendPage-1.3.4-4.py]]
  • [get | view] (2005-09-05 17:44:03, 6.9 KB) [[attachment:RecommendPage-1.3.5-5.py]]
  • [get | view] (2005-09-07 16:42:26, 7.5 KB) [[attachment:RecommendPage-1.3.5-6.py]]
  • [get | view] (2005-09-08 16:06:28, 7.7 KB) [[attachment:RecommendPage-1.3.5-7.py]]
  • [get | view] (2005-11-01 11:31:51, 9.0 KB) [[attachment:RecommendPage-1.3.5-8.py]]
  • [get | view] (2006-02-03 19:40:51, 8.3 KB) [[attachment:RecommendPage-1.5.1-9.py]]
  • [get | view] (2008-01-11 09:14:35, 6.8 KB) [[attachment:RecommendPage-1.6.0-10.py]]
  • [get | view] (2008-08-19 14:44:59, 6.9 KB) [[attachment:RecommendPage-1.7.1-11.py]]
  • [get | view] (2008-06-09 11:27:40, 1.7 KB) [[attachment:ShowActions.py]]
  • [get | view] (2008-06-09 10:34:02, 5.3 KB) [[attachment:ShowDecrypted.py]]
  • [get | view] (2005-03-30 21:17:28, 7.7 KB) [[attachment:Slideshow.py]]
  • [get | view] (2004-02-02 20:48:31, 2.0 KB) [[attachment:SubscribeUser.py]]
  • [get | view] (2007-01-26 17:08:30, 2.2 KB) [[attachment:Subscribers-1.6.0.py]]
  • [get | view] (2003-12-07 18:15:53, 1.8 KB) [[attachment:Subscribers.py]]
  • [get | view] (2006-03-18 23:16:51, 0.8 KB) [[attachment:UserPreferences.py]]
  • [get | view] (2004-01-05 09:56:25, 8.1 KB) [[attachment:VisualSiteMap.py]]
  • [get | view] (2015-08-30 21:04:23, 11.1 KB) [[attachment:VisualSiteMap_1.10.py]]
  • [get | view] (2004-10-08 10:59:16, 9.3 KB) [[attachment:VisualSiteMap_1.2.py]]
  • [get | view] (2005-03-16 01:30:09, 9.8 KB) [[attachment:VisualSiteMap_1.3.py]]
  • [get | view] (2014-08-19 01:34:10, 10.8 KB) [[attachment:VisualSiteMap_1.9.py]]
  • [get | view] (2007-08-18 18:52:55, 1.0 KB) [[attachment:backlink.py]]
  • [get | view] (2007-03-15 05:53:49, 23.5 KB) [[attachment:findandreplace0.1Beta.py]]
  • [get | view] (2005-03-27 20:32:10, 3.6 KB) [[attachment:gallery2image-1.3.3-1.py]]
  • [get | view] (2005-08-03 20:14:56, 4.0 KB) [[attachment:gallery2image-1.3.3-2.py]]
  • [get | view] (2005-11-13 18:10:26, 20.7 KB) [[attachment:gallery2image-1.3.5-10.py]]
  • [get | view] (2005-11-25 22:03:50, 20.8 KB) [[attachment:gallery2image-1.3.5-11.py]]
  • [get | view] (2005-08-08 17:23:43, 8.4 KB) [[attachment:gallery2image-1.3.5-4.py]]
  • [get | view] (2005-08-13 15:15:45, 13.7 KB) [[attachment:gallery2image-1.3.5-5.py]]
  • [get | view] (2005-08-31 22:05:22, 15.5 KB) [[attachment:gallery2image-1.3.5-6.py]]
  • [get | view] (2005-10-29 20:23:50, 15.9 KB) [[attachment:gallery2image-1.3.5-8.py]]
  • [get | view] (2005-11-01 11:31:24, 17.6 KB) [[attachment:gallery2image-1.3.5-9.py]]
  • [get | view] (2006-01-27 20:52:32, 20.9 KB) [[attachment:gallery2image-1.5.1-12.py]]
  • [get | view] (2006-08-06 09:01:01, 22.1 KB) [[attachment:gallery2image-1.5.4-13.py]]
  • [get | view] (2006-08-11 18:21:40, 22.2 KB) [[attachment:gallery2image-1.5.4-14.py]]
  • [get | view] (2006-11-16 20:23:27, 22.6 KB) [[attachment:gallery2image-1.5.6-16.py]]
  • [get | view] (2006-08-11 18:30:22, 22.2 KB) [[attachment:gallery2image-1.6.0-15.py]]
  • [get | view] (2008-02-06 10:13:45, 22.3 KB) [[attachment:gallery2image-1.6.0-16.py]]
  • [get | view] (2008-05-20 15:51:09, 22.4 KB) [[attachment:gallery2image-1.6.3-17.py]]
  • [get | view] (2006-09-06 06:19:48, 1.3 KB) [[attachment:getmmap.py]]
  • [get | view] (2004-07-18 09:48:00, 1.5 KB) [[attachment:localnames.py]]
  • [get | view] (2005-03-25 15:02:31, 2.6 KB) [[attachment:newpageonly.py]]
  • [get | view] (2005-03-30 09:02:00, 3.5 KB) [[attachment:newpageonly_20050330.py]]
  • [get | view] (2006-06-06 19:12:27, 9.7 KB) [[attachment:pdf.py]]
  • [get | view] (2006-08-30 10:51:51, 36.0 KB) [[attachment:pdf2_0_0.py]]
  • [get | view] (2006-08-30 13:57:36, 36.5 KB) [[attachment:pdf2_0_1.py]]
  • [get | view] (2006-02-04 04:25:29, 1.0 KB) [[attachment:sisterindex.py]]
  • [get | view] (2004-10-28 07:33:10, 0.7 KB) [[attachment:xml.py]]
 All files | Selected Files: delete move to page copy to page

You are not allowed to attach a file to this page.