KidServletFactory.py :  » Web-Frameworks » Webware » Webware-1.0.2 » KidKit » Python Open Source

Home
Python Open Source
1.3.1.2 Python
2.Ajax
3.Aspect Oriented
4.Blog
5.Build
6.Business Application
7.Chart Report
8.Content Management Systems
9.Cryptographic
10.Database
11.Development
12.Editor
13.Email
14.ERP
15.Game 2D 3D
16.GIS
17.GUI
18.IDE
19.Installer
20.IRC
21.Issue Tracker
22.Language Interface
23.Log
24.Math
25.Media Sound Audio
26.Mobile
27.Network
28.Parser
29.PDF
30.Project Management
31.RSS
32.Search
33.Security
34.Template Engines
35.Test
36.UML
37.USB Serial
38.Web Frameworks
39.Web Server
40.Web Services
41.Web Unit
42.Wiki
43.Windows
44.XML
Python Open Source » Web Frameworks » Webware 
Webware » Webware 1.0.2 » KidKit » KidServletFactory.py
"""Servlet factory for Kid templates.

This allows you to run Kid template files directly from within Webware.
Compiled templates are cached either along with the templates or in the
KidKit subdirectory of the WebKit Cache directory.

Note that the Kid package itself is not part of Webware; you need to install
it separately (see http://www.kid-templating.org for more information).


CREDITS:

* Kid has been developed by Ryan Tomayko (rtomayko<at>gmail.com).
* KidKit was contributed by Winston Wolff (winstonw<at>stratolab.com).
  Based on the Cheetah servlet factory. No caching, fixed servlet hook.
* Improved version contributed by Christoph Zwerschke (cito<at>online.de).
  Based on the PSP servlet factory. Supports caching and servlet hooks.

"""

import os
from glob import glob
from WebKit.ServletFactory import ServletFactory
from WebKit.Servlet import Servlet
from WebKit.Page import Page

defaultHook = Page.respond # the default hook for Kid servlets
defaultOutput = 'html' # the default Kid output method
defaultFormat = 'default' # the default Kid output format
defaultExtensions = ['.kid'] # the default extensions for Kid templates

from kid import load_template,output_methods
try: # output formatting exists in newer Kid versions only
  from kid.format import output_formats
except ImportError:
  output_formats = None
from kid.compiler import KidFile


def kidClass(module):
  """Return a WebKit servlet class for a Kid template module."""

  try:
    hook = module.hook
  except AttributeError:
    hook = defaultHook
  assert type(hook) == type(defaultHook)
  ServletClass = hook.im_class
  assert issubclass(ServletClass, Servlet)
  writeMethod = hook.__name__
  try:
    output = module.output
  except AttributeError:
    output = defaultOutput
  assert output in output_methods
  if output_formats is None:
    format = None
  else:
    try:
      format = module.format
    except AttributeError:
      format = defaultFormat
    assert format in output_formats

  class KidServlet(ServletClass):
    """The base class for a Kid servlet."""

    _module = module
    _template = module.Template()
    _output = output
    _format = format

    def writeTemplate(self, *args, **kwargs):
      self._template.servlet = self
      response = self._response
      fragment = response.size() > 0
      if format is None:
        self._template.write(self._response,
          fragment=fragment, output=output)
      else:
        self._template.write(self._response,
          fragment=fragment, output=output, format=format)

  setattr(KidServlet, writeMethod, KidServlet.writeTemplate)
  return KidServlet


class KidServletFactory(ServletFactory):
  """Servlet factory for Kid templates."""

  def __init__(self, application):
    ServletFactory.__init__(self, application)
    setting = application.setting
    global defaultOutput # the default Kid output method
    defaultOutput = setting('KidOutputMethod', defaultOutput)
    global defaultFormat # the default Kid output format
    defaultFormat = setting('KidOutputFormat', defaultFormat)
    global defaultExtensions # the default Kid template extensions
    self._extensions = setting('ExtensionsForKid', defaultExtensions)
    defaultExtensions = self._extensions
    self._cacheTemplates = setting('CacheKidTemplates', True)
    self._useCache = setting('UseKidKitCache', False)
    if self._useCache:
      self._cacheSource = setting('CacheKidSource', True)
      self._clearCache = setting('ClearKidCacheOnStart', False)
      self._cacheDir = os.path.join(application._cacheDir, 'KidKit')
      if self._clearCache:
        self.clearFileCache()
    else:
      self._cacheSource = self._clearCache = False
      self._cacheDir = None
    t = ['_'] * 256
    from string import digits,letters
    for c in digits + letters:
      t[ord(c)] = c
    self._classNameTrans = ''.join(t)

  def uniqueness(self):
    return 'file'

  def extensions(self):
    return self._extensions

  def flushCache(self):
    """Clean out the cache of classes in memory and on disk."""
    ServletFactory.flushCache(self)
    if self._clearCache:
      self.clearFileCache()

  def clearFileCache(self):
    """Clear class files stored on disk."""
    files = glob(os.path.join(self._cacheDir, '*.*'))
    map(os.remove, files)

  def computeClassName(self, pagename):
    """Generate a (hopefully) unique class/file name for each Kid file.

    Argument: pagename: the path to the Kid template file
    Returns: a unique name for the class generated fom this Kid file

    """
    # Compute class name by taking the path and substituting
    # underscores for all non-alphanumeric characters:
    return os.path.splitdrive(pagename)[1].translate(self._classNameTrans)

  def loadClass(self, transaction, path):
    """Load servlet class for the given Kid template."""
    classname = self.computeClassName(path)
    if self._cacheTemplates and self._useCache:
      # Cache the compiled templates separately:
      mtime = os.path.getmtime(path)
      classfile = os.path.join(self._cacheDir, classname + ".py")
      if not self._cacheSource:
        classfile += __debug__ and 'c' or 'o'
      if not os.path.exists(classfile) \
          or os.path.getmtime(classfile) != mtime:
        kidFile = KidFile(path)
        if self._cacheSource:
          kidFile.dump_source(classfile)
        else:
          kidFile.dump_code(classfile)
        # Set the modification time of the compiled file
        # to be the same as the source file;
        # that's how we'll know if it needs to be recompiled:
        os.utime(classfile, (os.path.getatime(classfile), mtime))
      module = self.importAsPackage(transaction, classfile)
    else:
      # Let Kid care about the caching:
      module = load_template(path, cache=self._cacheTemplates)
    # Setting __orig_file__ here is already too late,
    module.__orig_file__ = path
    # so we need to tell ImportSpy explicitely about the file:
    self._imp.watchFile(path)
    theClass = kidClass(module)
    theClass._orig_file = path
    theClass.__name__ = self.computeClassName(path)
    return theClass
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.