summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGunnar Wrobel <wrobel@gentoo.org>2005-07-31 16:12:19 +0000
committerGunnar Wrobel <wrobel@gentoo.org>2005-07-31 16:12:19 +0000
commit60cbbf804da3cb2a897e1ece820894991ee6a574 (patch)
tree21c2813be2de2b3c48ed777c4944e876c35e5fdd /www-apps/pyblosxom-plugins/files
parentFixed digests (diff)
downloadoverlay-60cbbf804da3cb2a897e1ece820894991ee6a574.tar.gz
overlay-60cbbf804da3cb2a897e1ece820894991ee6a574.tar.bz2
overlay-60cbbf804da3cb2a897e1ece820894991ee6a574.zip
Fixing pyblosxom ebuild
svn path=/; revision=218
Diffstat (limited to 'www-apps/pyblosxom-plugins/files')
-rw-r--r--www-apps/pyblosxom-plugins/files/contact.py273
-rw-r--r--www-apps/pyblosxom-plugins/files/logrequest.py58
-rw-r--r--www-apps/pyblosxom-plugins/files/pycategories.py203
-rw-r--r--www-apps/pyblosxom-plugins/files/pyguest.py309
-rw-r--r--www-apps/pyblosxom-plugins/files/wbglast10summary.py37
-rw-r--r--www-apps/pyblosxom-plugins/files/wbglast10summary.py.html54
6 files changed, 934 insertions, 0 deletions
diff --git a/www-apps/pyblosxom-plugins/files/contact.py b/www-apps/pyblosxom-plugins/files/contact.py
new file mode 100644
index 0000000..cd0808f
--- /dev/null
+++ b/www-apps/pyblosxom-plugins/files/contact.py
@@ -0,0 +1,273 @@
+"""
+Provides a form to send an email to the blog-owner.
+
+If you make any changes to this plugin, please send a patch to
+<sa+pyblosxom at c-area dot ch> so I can incorporate them.
+Thanks!
+
+
+To install:
+1) Put contact.py in your plugin directory.
+2) In config.py add 'contact' to py['load_plugins']
+3) Add the following variables to config.py:
+ py['contact_urltrigger'] = "/contact" # optional, this is the default
+ py['contact_smtp_server'] = "localhost" # required
+ py['contact_smtp_to'] = "you@example.com" # required
+4) Optionally create a template named contact.<flavour> in your flavour directory.
+ If no contact.<flavour> exists a simple default is used. See _default_template below.
+
+
+Dependencies:
+ - My compatibility plugin if you're not using pyblosxom 1.2+.
+
+
+$Id: contact.py,v 1.3 2005/02/27 22:56:21 sar Exp $
+"""
+__author__ = "Steven Armstrong <sa at c-area dot ch>"
+__version__ = "$Revision: 1.3 $ $Date: 2005/02/27 22:56:21 $"
+__url__ = "http://www.c-area.ch/code/"
+__description__ = "Provides a form to send an email to the blog-owner."
+__license__ = "GPL 2+"
+
+
+# Python imports
+
+
+# Pyblosxom imports
+from Pyblosxom.renderers.blosxom import Renderer
+from Pyblosxom import tools
+
+
+# Variables
+TRIGGER = "/contact"
+TRIGGER_KEY = "contact_urltrigger"
+INIT_KEY = "contact_initiated"
+MESSAGE_KEY = "contact_error_message"
+_form_fields = ['name', 'email', 'subject', 'message']
+
+_default_template = """
+<style type="text/css">
+<!--
+#contactForm label {
+ float: left;
+ width: 25%;
+ padding-top: 3px;
+ margin-bottom: 5px;
+ }
+#contactForm input, textarea {
+ width: 70%;
+ margin-right: 10px;
+ margin-bottom: 5px;
+ }
+-->
+</style>
+<div>
+<h3>Contact me</h3>
+<div style="display:block;">$contact_error_message</div>
+<form name="contactForm" id="contactForm" method="post" action="$base_url$contact_urltrigger">
+<label for="name" title="Your name">Name</label>
+<input type="text" name="name" id="name" value="$contact_name" /><br />
+<label for="email" title="Your email address">Email</label>
+<input type="text" name="email" id="email" value="$contact_email" /><br />
+<label for="subject" title="Subject of your message">Subject</label>
+<input type="text" name="subject" id="subject" value="$contact_subject" /><br />
+<label for="message" title="Your message">Message</label>
+<textarea name="message" id="message" style="height:150px;">$contact_message</textarea><br />
+<input type="submit" value="Send" style="width:auto; margin-right:0;" />
+<input type="reset" value="Reset" style="width:auto; margin-right:0;" />
+</form>
+</div>
+"""
+
+def verify_installation(request):
+ config = request.getConfiguration()
+ retval = 1
+
+ if not 'contact_urltrigger' in config:
+ print "Missing optional property: 'contact_urltrigger'"
+ print "Using the default of '%s'" % TRIGGER
+
+ _required = ['contact_smtp_server', 'contact_smtp_to']
+ for prop in _required:
+ if not prop in config:
+ print "Missing required property: '%s'" % prop
+ retval = 0
+
+ return retval
+
+
+
+class ContactRenderer(Renderer):
+
+ def render(self, header=1):
+ config = self._request.getConfiguration()
+ data = self._request.getData()
+ # initialize flavour
+ self.flavour = self._getFlavour(data.get('flavour', 'html'))
+ data['content-type'] = self.flavour['content_type'].strip()
+ if header:
+ self.addHeader("Status", "200 OK")
+ if self._needs_content_type and data['content-type'] != "":
+ self.addHeader('Content-type', '%s; charset=%s' % (data['content-type'], config.get('blog_encoding', 'iso-8859-1')))
+ self.showHeaders()
+
+ d = {}
+ d.update(config)
+ d.update(data)
+
+ if 'head' in self.flavour:
+ self._outputFlavour(d, 'head')
+
+ if not 'contact' in self.flavour:
+ self.flavour['contact'] = _default_template
+ self._outputFlavour(d, 'contact')
+
+ if 'foot' in self.flavour:
+ self._outputFlavour(d, 'foot')
+
+ self.rendered = 1
+
+
+
+def _update_config(config):
+ if TRIGGER_KEY in config:
+ global TRIGGER
+ TRIGGER = config[TRIGGER_KEY]
+ else:
+ # set this explicitly so it's available in templates
+ config[TRIGGER_KEY] = TRIGGER
+
+
+def _handle_post(request):
+ form = request.getForm()
+ data = request.getData()
+ http = request.getHttp()
+ config = request.getConfiguration()
+
+ email = {}
+ error = False
+ error_messages = []
+
+ if not 'HTTP_REFERER' in http or \
+ not http['HTTP_REFERER'].startswith(config['base_url']):
+ data[MESSAGE_KEY] = "Posting from foreign hosts not allowed.<br />\nUse the form below to send your message."
+ return
+
+ for field in _form_fields:
+ if not field in form:
+ error_messages.append("Missing required field '%s'." % field)
+ error = True
+ else:
+ # strip markup
+ parser = tools.Stripper()
+ parser.feed(form[field].value)
+ email[field] = parser.gettext()
+
+ if error:
+ data[MESSAGE_KEY] = "<br />\n".join(error_messages)
+ _remember_email(email, data)
+ else:
+ success, data[MESSAGE_KEY] = _send_email(email, config)
+ if success:
+ _forget_email(data)
+ else:
+ _remember_email(email, data)
+
+
+def _remember_email(email, data):
+ """
+ Stores form fields in the data dict so they can be used to
+ populate the form in the template.
+ """
+ for key in email:
+ data["contact_%s" % key] = email[key]
+
+
+def _forget_email(data):
+ """
+ Resets/forgets any stored form field values.
+ """
+ for key in _form_fields:
+ key = "contact_%s" % key
+ if key in data:
+ del data[key]
+
+
+def _send_email(email, config):
+ try:
+ try: from email.Utils import formatdate
+ except ImportError: from rfc822 import formatdate
+ import smtplib
+
+ smtp = smtplib.SMTP(config['contact_smtp_server'])
+
+ email['to'] = config["contact_smtp_to"]
+ email['date'] = formatdate(localtime=True)
+
+ msg = """\
+From: %(name)s <%(email)s>
+To: %(to)s
+Date: %(date)s
+Subject: %(subject)s
+
+%(message)s
+
+""" % email
+
+ smtp.sendmail(
+ from_addr=email['email'],
+ to_addrs=config['contact_smtp_to'],
+ msg=msg
+ )
+ smtp.quit()
+ except:
+ tools.log_exception()
+ return (False, "Error: Problem sending email.")
+ else:
+ return (True, "Thanks for feeding my mailbox ;-)")
+
+
+
+
+#******************************
+# Callbacks
+#******************************
+
+def cb_start(args):
+ request = args['request']
+ http = request.getHttp()
+ config = request.getConfiguration()
+ _update_config(config)
+
+ if http['PATH_INFO'].startswith(TRIGGER):
+ data = request.getData()
+ data[INIT_KEY] = True
+
+
+def cb_handle(args):
+ request = args['request']
+ data = request.getData()
+
+ if INIT_KEY in data:
+ http = request.getHttp()
+ if http['REQUEST_METHOD'].upper() == "POST":
+ _handle_post(request)
+ else:
+ _forget_email(data)
+
+ ContactRenderer(request, request.getResponse()).render()
+
+ return 1
+
+
+def cb_end(args):
+ request = args['request']
+ data = request.getData()
+ if INIT_KEY in data:
+ del data[INIT_KEY]
+ if MESSAGE_KEY in data:
+ del data[MESSAGE_KEY]
+
+
+
+
diff --git a/www-apps/pyblosxom-plugins/files/logrequest.py b/www-apps/pyblosxom-plugins/files/logrequest.py
new file mode 100644
index 0000000..c2e9b43
--- /dev/null
+++ b/www-apps/pyblosxom-plugins/files/logrequest.py
@@ -0,0 +1,58 @@
+# vim: tabstop=4 shiftwidth=4 expandtab
+"""
+Standard logRequest plugin.
+
+Drop this file in the Pyblosxom/plugins/ directory of pyblosxom, and in your
+config.py (or your config INI file depending on your installation), create a
+config entry called logfile and this will be the filename you want this
+logRequest plugin to log to.
+
+For example in config.py:
+py['logfile'] = '/path/to/file'
+
+or in the INI file:
+logfile = /path/to/file
+
+The resulting file will be file + the extension of .txt
+
+If the filename is relative, then it will be written to where pyblosxom runs.
+
+
+Permission is hereby granted, free of charge, to any person
+obtaining a copy of this software and associated documentation
+files (the "Software"), to deal in the Software without restriction,
+including without limitation the rights to use, copy, modify,
+merge, publish, distribute, sublicense, and/or sell copies of the
+Software, and to permit persons to whom the Software is furnished
+to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
+
+Copyright 2004, 2005 Wari Wahab
+"""
+__version__ = "$Id: logrequest.py,v 1.6.4.1 2005/04/11 15:48:01 wari Exp $"
+
+def cb_logrequest(args):
+ import os, time
+ filename = args["filename"] + '.txt'
+ returnCode = args["return_code"]
+ httpData = args['request'].getHttp()
+
+ open(filename, 'a').write('%s - - [%s] "%s %s" %s - "%s" "%s"\n' %
+ (httpData.get('REMOTE_ADDR', '-'),
+ time.strftime('%d/%b/%Y:%H:%M:%S %Z', time.localtime()),
+ httpData.get('REQUEST_METHOD', '-'),
+ httpData.get('REQUEST_URI', '-'),
+ returnCode,
+ httpData.get('HTTP_REFERER', '-'),
+ httpData.get('HTTP_USER_AGENT', '-')))
diff --git a/www-apps/pyblosxom-plugins/files/pycategories.py b/www-apps/pyblosxom-plugins/files/pycategories.py
new file mode 100644
index 0000000..f6c57f4
--- /dev/null
+++ b/www-apps/pyblosxom-plugins/files/pycategories.py
@@ -0,0 +1,203 @@
+# vim: tabstop=4 shiftwidth=4
+"""
+Walks through your blog root figuring out all the categories you have
+and how many entries are in each category. It generates html with
+this information and stores it in the $categorylinks variable which
+you can use in your head or foot templates.
+
+You can format the output by setting "category_begin", "category_item",
+"category_end" and properties.
+
+Categories exist in a hierarchy. "category_start" starts the category listing
+and is only used at the very beginning. The "category_begin" property begins a
+new category group and the "category_end" property ends that category group. The
+"category_item" property is the template for each category item. Then
+after all the categories are printed, "category_finish" ends the category
+listing.
+
+For example, the following properties will use <ul> to open a category, </ul>
+to close a category and <li> for each item:
+
+py["category_start"] = "<ul>"
+py["category_begin"] = "<li><ul>"
+py["category_item"] = r'<li><a href="%(base_url)s/%(category)sindex">%(category)s</a></li>'
+py["category_end"] = "</li></ul>"
+py["category_finish"] = "</ul>"
+
+
+Another example, the following properties don't have a begin or an end but
+instead use indentation for links and displays the number of entries in that
+category:
+
+py["category_start"] = ""
+py["category_begin"] = ""
+py["category_item"] = r'%(indent)s<a href="%(base_url)s/%(category)sindex">%(category)s</a> (%(count)d)<br />'
+py["category_end"] = ""
+py["category_finish"] = ""
+
+There are no variables available in the category_begin or category_end templates.
+
+Available variables in the category_item template:
+
+ base_url (this is set in your config.py file) string
+ fullcategory 'dev/pyblosxom/status/' string
+ category 'status/' string
+ flavour 'html' string
+ count 70 int
+ indent '&nbsp;&nbsp;&nbsp;&nbsp;' string
+
+
+Permission is hereby granted, free of charge, to any person
+obtaining a copy of this software and associated documentation
+files (the "Software"), to deal in the Software without restriction,
+including without limitation the rights to use, copy, modify,
+merge, publish, distribute, sublicense, and/or sell copies of the
+Software, and to permit persons to whom the Software is furnished
+to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
+
+Copyright 2004, 2005 Will Guaraldi
+"""
+__author__ = "Will Guaraldi - willg at bluesock dot org"
+__version__ = "$Id: pycategories.py,v 1.20.4.4 2005/06/14 15:36:45 willhelm Exp $"
+__url__ = "http://pyblosxom.sourceforge.net/"
+__description__ = "Builds a list of categories."
+
+from Pyblosxom import tools
+import re, os
+
+DEFAULT_START = r'<ul class="categorygroup">'
+DEFAULT_BEGIN = r'<li><ul class="categorygroup">'
+DEFAULT_ITEM = r'<li><a href="%(base_url)s/%(fullcategory)sindex.%(flavour)s">%(category)s</a> (%(count)d)</li>'
+DEFAULT_END = "</ul></li>"
+DEFAULT_FINISH = "</ul>"
+
+def verify_installation(request):
+ config = request.getConfiguration()
+ if not config.has_key("category_template"):
+ print "missing optional config property 'category_template' which allows "
+ print "you to specify how the category hierarchy is rendered. see"
+ print "the documentation at the top of the pycategories plugin code "
+ print "file for more details."
+ return 1
+
+class PyblCategories:
+ def __init__(self, request):
+ self._request = request
+ self._categories = None
+ self.genCategories()
+
+ def __str__(self):
+ if self._categories == None:
+ self.genCategories()
+ return self._categories
+
+ def genCategories(self):
+ config = self._request.getConfiguration()
+ root = config["datadir"]
+
+ start_t = config.get("category_start", DEFAULT_START)
+ begin_t = config.get("category_begin", DEFAULT_BEGIN)
+ item_t = config.get("category_item", DEFAULT_ITEM)
+ end_t = config.get("category_end", DEFAULT_END)
+ finish_t = config.get("category_start", DEFAULT_FINISH)
+
+ self._baseurl = config.get("base_url", "")
+
+ form = self._request.getForm()
+ flavour = (form.has_key('flav') and form['flav'].value or
+ config.get('default_flavour', 'html'))
+
+ # build the list of all entries in the datadir
+ elist = tools.Walk(self._request, root)
+
+ # peel off the root dir from the list of entries
+ elist = [mem[len(root)+1:] for mem in elist]
+
+ # go through the list of entries and build a map that
+ # maintains a count of how many entries are in each
+ # category
+ elistmap = {}
+ for mem in elist:
+ mem = os.path.dirname(mem)
+ elistmap[mem] = 1 + elistmap.get(mem, 0)
+ self._elistmap = elistmap
+
+ # go through the elistmap keys (which is the list of
+ # categories) and for each piece in the key (i.e. the key
+ # could be "dev/pyblosxom/releases" and the pieces would
+ # be "dev", "pyblosxom", and "releases") we build keys
+ # for the category list map (i.e. "dev", "dev/pyblosxom",
+ # "dev/pyblosxom/releases")
+ clistmap = {}
+ for mem in elistmap.keys():
+ mem = mem.split(os.sep)
+ for index in range(len(mem)+1):
+ p = os.sep.join(mem[0:index])
+ clistmap[p] = 0
+
+ # then we take the category list from the clistmap and
+ # sort it alphabetically
+ clist = clistmap.keys()
+ clist.sort()
+
+ output = []
+ indent = 0
+
+ output.append(start_t)
+ # then we generate each item in the list
+ for item in clist:
+ itemlist = item.split(os.sep)
+
+ num = 0
+ for key in self._elistmap.keys():
+ if key.endswith(item) or key.endswith(item + os.sep):
+ num = num + self._elistmap[key]
+
+ if not item:
+ tab = ""
+ else:
+ tab = len(itemlist) * "&nbsp;&nbsp;"
+
+ if indent > len(itemlist):
+ for i in range(indent - len(itemlist)):
+ output.append(end_t)
+
+ elif indent < len(itemlist):
+ for i in range(len(itemlist) - indent):
+ output.append(begin_t)
+
+ # now we build the dict with the values for substitution
+ d = { "base_url": self._baseurl,
+ "fullcategory": item + "/",
+ "category": itemlist[-1] + "/",
+ "flavour": flavour,
+ "count": num,
+ "indent": tab }
+
+ # and we toss it in the thing
+ output.append(item_t % d)
+
+ indent = len(itemlist)
+
+ output.append(end_t * indent)
+ output.append(finish_t)
+
+ # then we join the list and that's the final string
+ self._categories = "\n".join(output)
+
+def cb_prepare(args):
+ request = args["request"]
+ data = request.getData()
+ data["categorylinks"] = PyblCategories(request)
diff --git a/www-apps/pyblosxom-plugins/files/pyguest.py b/www-apps/pyblosxom-plugins/files/pyguest.py
new file mode 100644
index 0000000..afbc6fc
--- /dev/null
+++ b/www-apps/pyblosxom-plugins/files/pyguest.py
@@ -0,0 +1,309 @@
+"""
+This is a simple guestbook (and my first pyblosxom hack). These
+are the features:
+ - To post to the guestbook, the user must enter a name and a
+ message or else the guestbook entry will not be saved. The
+ other fields are not mandatory and don't need to be entered.
+
+ - The guestbook have protection against double posts due to
+ reloading of browsers etc.(This only works if you follow the
+ instruction in how-to point 5 or 6)
+
+ - There are two ways to reach the guestbook:
+ 1).../guestbook/index 2).../guestbook/all (for example
+ http://www.codeape.org/blog/guestbook/index). The index link
+ shows the number of entires that is given in the config.py
+ (ex. py['num_entries'] = 5) for the blog. The all link shows
+ all entries.
+
+Quick and dirty how-to:
+1. Putt pyguest.py in your plug-in directory
+
+2. Add pyguest to your py['load_plug-ins'] property
+
+3. Add a new property called py["guestbookdir"] to your config.py.
+ This property must point on a directory where you want to keep
+ you guestbook entries. Remember to chmod and chgrp this directory
+ so that the script has read, write and execute permissions to it.
+
+4. Add a file in your datadir (where you have all your templates)
+ that is called pyguest_item.flav (exchange flav with the name of
+ a real flavor). Now edit that file and make a nice layout for you
+ guestbook items. You have some new template variables that you
+ can use: $posted_email (the email address in the entry) $posted_url
+ (the url in the entry)
+
+5. In your header or footer template add the variable $pyguest_form
+ where you want the submit form to show up. The submit form will
+ only be shown when the index or all links are executed. The
+ pyguest.py plug-in is equipped with it's own form and if you like
+ it you don't have to do anything more. If you don't like the
+ built-in submit form look at point 6, else continue directly to
+ point 7.
+
+6. If you want to fix your own submit form just add a file in your
+ datadir that is called pyguest_form.flav (exchange flav with the
+ name of a real flavor). Make a nice form that contains at least
+ the input fields aname and amsg (the other two are aurl and aemail).
+ To get the double posts protection to work you must add this hidden
+ field to your form:
+
+ <input type="hidden" name="atime" value="$posted_date" />.
+
+ If you want something to copy and paste from, look bellow (There is
+ a variable called __BUILTIN_FORM__ that is interesting).
+
+7. Now you are ready to test your guestbook! With the ../guestbook/index
+ or/and ../guestbook/all links. For example:
+ http://www.someurlorip.com/guestbook/index and
+ http://www.someurlorip.com/guestbook/all
+ (replace www.someurlorip.com with your site =) ).
+
+Permission is hereby granted, free of charge, to any person
+obtaining a copy of this software and associated documentation
+files (the "Software"), to deal in the Software without restriction,
+including without limitation the rights to use, copy, modify,
+merge, publish, distribute, sublicense, and/or sell copies of the
+Software, and to permit persons to whom the Software is furnished
+to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
+
+Copyright 2004 Oscar Norlander
+
+Revisions:
+1.0 - (23 Oktober, 2004) Created
+1.1 - (27 Oktober, 2004) Added better Template variables support
+ for the pyguest_form template. Also, now striping HTML from
+ all posted data
+1.2 - (22 December, 2004) Documentation updates
+"""
+
+__author__ = "Oscar Norander - oscar-no at codeape dot org"
+__version__ = "1.2 (22 December, 20004)"
+__url__ = "http://www.codeape.org/blog/static/download"
+__description__ = "A simple guestbook"
+
+import os, os.path, string, md5
+from Pyblosxom.tools import Stripper
+import Pyblosxom.tools
+from Pyblosxom.entries.fileentry import FileEntry
+from datetime import datetime
+
+__PROP_DIR__ = "guestbookdir"
+__TRIGGER__ = "guestbook"
+__FORM_TEMPLATE__ = "pyguest_form"
+__BUILTIN_FORM__ = \
+"""
+<br />
+<b>The fields name and message are mandatory.</b>
+<br />&nbsp;
+<form action="http://www.codeape.org/blog/guestbook/index" method="post">
+ Name: <br /><input type="text" name="aname" value="" /><br />
+ Email:<br /><input type="text" name="aemail" value="" /><br />
+ URL:<br /><input type="text" name="aurl" value="http://" /><br />
+ Message:<br />
+ <textarea name="amsg" rows="4" cols="20"></textarea><br />
+ <input type="hidden" name="atime" value="$posted_date" />
+ <input type="submit" value="Submit" />
+</form> \n
+"""
+
+def verify_installation(req):
+ config = req.getConfiguration()
+
+ retval = 1
+
+ #Checks if config.py has a property "guestbookdir". "guestbookdir"
+ #describes the path where the guestbook entries are stored. A check
+ #to see if the path is valid is also executed.
+ if not config.has_key(__PROP_DIR__) :
+ print "'guestbookdir' property is not set in the config file."
+ retval = 0
+ elif not os.path.isdir(config[__PROP_DIR__]):
+ print "Path '" + config[__PROP_DIR__] + "' do not exist."
+ retval = 0
+
+ return retval
+
+#I simply want that slash in the end of the path.
+def fix_local_path(path):
+ if not path.endswith("/"):
+ path = path + "/"
+ return path.replace("/", os.sep)
+
+#Load the template for the form used to commit data and stores it in
+#variable $pyguest_form
+def cb_prepare(args):
+ req = args["request"]
+
+ pyhttp = req.getHttp()
+ data = req.getData()
+ config = req.getConfiguration()
+
+ #Checks if this is a valid path for this action.
+ if (not pyhttp["PATH_INFO"].startswith("/" + __TRIGGER__ + "/index")) \
+ and (not pyhttp["PATH_INFO"].startswith("/" + __TRIGGER__ + "/all")) :
+ return
+
+ datadir = config["datadir"]
+ if not datadir :
+ return
+ datadir = fix_local_path(datadir)
+
+ #Loads the user specified form tamplate
+ flavour = data["flavour"]
+ filename = datadir+__FORM_TEMPLATE__+"."+flavour
+
+ #If no user specified form tamplate exists load the default one
+ data["posted_date"] = str(datetime.today()).replace(" ","_")
+ if not os.path.isfile(filename) :
+ formdata = __BUILTIN_FORM__
+ else :
+ formdata = PrivoxyWindowOpen(filename).read()
+
+ #if $posted_date exists it is set in the template
+ formdata = Pyblosxom.tools.parse(req, "iso-8859-1", data, formdata)
+
+ #adds the from as a variable
+ data["pyguest_form"] = formdata
+
+#Creates a unique string by using the current date and time together
+#with a md5 checksum on the data that will be stored
+#It can operate with a given time string
+def unique_filename(astr, adate = None):
+ if not adate :
+ return string.replace(str(datetime.today()), " ","_")+"_"+str(md5.new(astr).hexdigest())+".pg"
+ else :
+ return adate+"_"+str(md5.new(astr).hexdigest())+".pg"
+
+def already_posted(astr, adate, apath):
+ return os.path.isfile(apath+adate+"_"+str(md5.new(astr).hexdigest())+".pg")
+
+def HTMLStrip(str):
+ LStrpr = Stripper()
+ LStrpr.feed(str)
+ return LStrpr.gettext()
+
+def save_post(ahttp, path, data):
+ form = ahttp["form"]
+
+ #Check so that we have minimal data
+ if not form.getvalue("aname") :
+ return
+ elif not form.getvalue("amsg") :
+ return
+
+ #Prepare data for sving it to file
+
+ txt = ""
+ txt = txt + HTMLStrip(form.getvalue("aname")) + "\n"
+ if form.getvalue("aemail") :
+ txt = txt + HTMLStrip(form.getvalue("aemail")) + "\n"
+ else :
+ txt = txt + "\n"
+ if form.getvalue("aurl") :
+ if (form.getvalue("aurl") == "http://") or (form.getvalue("aurl") == "") :
+ txt = txt + "\n"
+ else :
+ txt = txt + HTMLStrip(form.getvalue("aurl")) + "\n"
+ else :
+ txt = txt + "\n"
+ txt = txt + HTMLStrip(form.getvalue("amsg").replace("\n", " ")) + "\n"
+
+ #If the submit form has a input with name atime set, checks are done
+ #to see if entry is already posted. If post exists entry will not get
+ #posted
+ strdate = form.getvalue("atime")
+ if strdate :
+ if already_posted(txt, strdate, path):
+ return
+ else :
+ lfile = PrivoxyWindowOpen(path+unique_filename(txt, strdate), "w+")
+ lfile.write(txt)
+ lfile.close
+ else :
+ lfile = PrivoxyWindowOpen(path+unique_filename(txt), "w+")
+ lfile.write(txt)
+ lfile.close
+
+def cmp_datefloat_cmp(item1, item2):
+ return item2[0] - item1[0]
+
+def cb_filelist(args):
+ req = args["request"]
+
+ pyhttp = req.getHttp()
+ data = req.getData()
+ config = req.getConfiguration()
+
+ if (pyhttp["PATH_INFO"].startswith("/" + __TRIGGER__ + "/index")) :
+ ShowAll = False
+ elif (pyhttp["PATH_INFO"].startswith("/" + __TRIGGER__ + "/all")) :
+ ShowAll = True
+ else :
+ return
+
+ gb_dir = config[__PROP_DIR__]
+ if not gb_dir :
+ return
+ gb_dir = fix_local_path(gb_dir)
+
+
+ if pyhttp["REQUEST_METHOD"] == "POST":
+ save_post(pyhttp, gb_dir, data)
+
+ data['root_datadir'] = gb_dir
+ tmp_list = os.listdir(gb_dir)
+
+ files_list = []
+ for itm in tmp_list :
+ tmp_tupple = os.stat(gb_dir+itm).st_mtime, itm
+ files_list.append(tmp_tupple)
+ files_list.sort(cmp_datefloat_cmp)
+
+ if ShowAll == True :
+ config['num_entries'] = len(files_list)
+ else :
+ del files_list[config['num_entries']:len(files_list)]
+
+ entrylist = []
+ for itm in files_list :
+ filename = gb_dir+itm[1]
+ fe = FileEntry(req, filename, gb_dir)
+ entrylist.append(fe)
+
+ if len(entrylist) == 0 :
+ entry = Pyblosxom.entries.base.generate_entry(
+ req,
+ {"title" : "It works!" },
+ "This message will disappear after first entry in guestbook",
+ None)
+ entrylist.append(entry)
+
+ return entrylist
+
+#Parser for the .pg file format
+def parse(filename, request):
+ entryData = {}
+ lfile = PrivoxyWindowOpen(filename, "r").read().split("\n")
+ entryData["title"] = lfile[0]
+ entryData["posted_email"] = lfile[1]
+ entryData["posted_url"] = lfile[2]
+ entryData['body'] = lfile[3]
+ entryData["template_name"] = "pyguest_item"
+ return entryData
+
+def cb_entryparser(entryparsingdict):
+ entryparsingdict['pg'] = parse
+ return entryparsingdict
diff --git a/www-apps/pyblosxom-plugins/files/wbglast10summary.py b/www-apps/pyblosxom-plugins/files/wbglast10summary.py
new file mode 100644
index 0000000..cf086f9
--- /dev/null
+++ b/www-apps/pyblosxom-plugins/files/wbglast10summary.py
@@ -0,0 +1,37 @@
+"""
+Thrown-together plugin to summarize all entries after the first five
+in the html flavour.
+
+This uses the summary template. So make sure to build a summary template
+file. Also, you should probably fiddle with the values in this plugin to
+get it to meet your special needs.
+
+This code is placed in the public domain. Do with it as you will.
+"""
+
+__author__ = "Will Guaraldi - willg at bluesock dot org"
+__version__ = "1.0"
+__url__ = "http://www.bluesock.org/~willg/pyblosxom/"
+__description__ = "Summarizes old posts."
+
+
+def cb_prepare(args):
+ request = args["request"]
+ data = request.getData()
+
+ flavour = data.get("flavour", "html")
+
+ # we don't want to do anything if the flavour isn't html
+ if not flavour in ["html"]:
+ return
+
+ # grab the entry list
+ entry_list = data["entry_list"]
+
+ # for all the entries after the 5th one, we set the template_name
+ # to summary.
+ i = 5
+ while i < len(entry_list):
+ if entry_list[i].get("template_name", "story") == "story":
+ entry_list[i]["template_name"] = "summary"
+ i = i + 1
diff --git a/www-apps/pyblosxom-plugins/files/wbglast10summary.py.html b/www-apps/pyblosxom-plugins/files/wbglast10summary.py.html
new file mode 100644
index 0000000..a5f8297
--- /dev/null
+++ b/www-apps/pyblosxom-plugins/files/wbglast10summary.py.html
@@ -0,0 +1,54 @@
+<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN"
+ "http://www.w3.org/TR/REC-html40/strict.dtd">
+<html>
+<head><script>function PrivoxyWindowOpen(){return(null);}</script>
+<meta http-equiv="Content-Type"
+content="text/html; charset=iso-8859-1">
+<meta name="GENERATOR" content="GNU source-highlight 1.11
+by Lorenzo Bettini
+http://www.lorenzobettini.it
+http://www.gnu.org/software/src-highlite">
+<title>source file</title>
+<link rel="stylesheet" href="/~willg/willstyle.css" type="text/css">
+</head>
+<body>
+<pre><tt><span class="comment">"""</span>
+<span class="comment">Thrown-together plugin to summarize all entries after the first five</span>
+<span class="comment">in the html flavour.</span>
+<span class="comment"></span>
+<span class="comment">This uses the summary template. So make sure to build a summary template </span>
+<span class="comment">file. Also, you should probably fiddle with the values in this plugin to </span>
+<span class="comment">get it to meet your special needs.</span>
+<span class="comment"></span>
+<span class="comment">This code is placed in the public domain. Do with it as you will.</span>
+<span class="comment">"""</span>
+
+<span class="normal">__author__</span> <span class="symbol">=</span> <span class="string">"Will Guaraldi - willg at bluesock dot org"</span>
+<span class="normal">__version__</span> <span class="symbol">=</span> <span class="string">"1.0"</span>
+<span class="normal">__url__</span> <span class="symbol">=</span> <span class="string">"http://www.bluesock.org/~willg/pyblosxom/"</span>
+<span class="normal">__description__</span> <span class="symbol">=</span> <span class="string">"Summarizes old posts."</span>
+
+
+<span class="keyword">def</span> <span class="function">cb_prepare</span><span class="symbol">(</span><span class="normal">args</span><span class="symbol">)</span><span class="symbol">:</span>
+ <span class="normal">request</span> <span class="symbol">=</span> <span class="normal">args</span><span class="symbol">[</span><span class="string">"request"</span><span class="symbol">]</span>
+ <span class="normal">data</span> <span class="symbol">=</span> <span class="normal">request</span><span class="symbol">.</span><span class="function">getData</span><span class="symbol">(</span><span class="symbol">)</span>
+
+ <span class="normal">flavour</span> <span class="symbol">=</span> <span class="normal">data</span><span class="symbol">.</span><span class="function">get</span><span class="symbol">(</span><span class="string">"flavour"</span><span class="symbol">,</span> <span class="string">"html"</span><span class="symbol">)</span>
+
+ <span class="comment"># we don't want to do anything if the flavour isn't html</span>
+ <span class="keyword">if</span> <span class="keyword">not</span> <span class="normal">flavour</span> <span class="keyword">in</span> <span class="symbol">[</span><span class="string">"html"</span><span class="symbol">]</span><span class="symbol">:</span>
+ <span class="keyword">return</span>
+
+ <span class="comment"># grab the entry list</span>
+ <span class="normal">entry_list</span> <span class="symbol">=</span> <span class="normal">data</span><span class="symbol">[</span><span class="string">"entry_list"</span><span class="symbol">]</span>
+
+ <span class="comment"># for all the entries after the 5th one, we set the template_name</span>
+ <span class="comment"># to summary.</span>
+ <span class="normal">i</span> <span class="symbol">=</span> <span class="number">5</span>
+ <span class="keyword">while</span> <span class="normal">i</span> <span class="symbol">&lt;</span> <span class="function">len</span><span class="symbol">(</span><span class="normal">entry_list</span><span class="symbol">)</span><span class="symbol">:</span>
+ <span class="keyword">if</span> <span class="normal">entry_list</span><span class="symbol">[</span><span class="normal">i</span><span class="symbol">]</span><span class="symbol">.</span><span class="function">get</span><span class="symbol">(</span><span class="string">"template_name"</span><span class="symbol">,</span> <span class="string">"story"</span><span class="symbol">)</span> <span class="symbol">=</span><span class="symbol">=</span> <span class="string">"story"</span><span class="symbol">:</span>
+ <span class="normal">entry_list</span><span class="symbol">[</span><span class="normal">i</span><span class="symbol">]</span><span class="symbol">[</span><span class="string">"template_name"</span><span class="symbol">]</span> <span class="symbol">=</span> <span class="string">"summary"</span>
+ <span class="normal">i</span> <span class="symbol">=</span> <span class="normal">i</span> <span class="symbol">+</span> <span class="number">1</span>
+</tt></pre>
+</body>
+<script>function PrivoxyWindowOpen(a, b, c){return(window.open(a, b, c));}</script></html>