Skip to content

Commit

Permalink
2375 add jinja2 render functionality
Browse files Browse the repository at this point in the history
  • Loading branch information
tobes committed May 24, 2012
1 parent 7fc29e1 commit 53cc673
Show file tree
Hide file tree
Showing 3 changed files with 69 additions and 1 deletion.
11 changes: 11 additions & 0 deletions ckan/config/environment.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,10 @@
from paste.deploy.converters import asbool
import sqlalchemy
from pylons import config
from pylons.i18n import _, N_
from genshi.template import TemplateLoader
from genshi.filters.i18n import Translator
from jinja2 import Environment, PackageLoader

import ckan.config.routing as routing
import ckan.model as model
Expand Down Expand Up @@ -167,6 +169,7 @@ def find_controller(self, controller):
if extra_template_paths:
# must be first for them to override defaults
template_paths = extra_template_paths.split(',') + template_paths
config['pylons.app_globals'].template_paths = template_paths

# Translator (i18n)
translator = Translator(pylons.translator)
Expand All @@ -182,6 +185,14 @@ def template_loaded(template):
config['pylons.app_globals'].genshi_loader = TemplateLoader(
template_paths, auto_reload=True, callback=template_loaded)

# Create Jinja2 environment
env = config['pylons.app_globals'].jinja_env = Environment(
loader=PackageLoader('ckan', 'templates'),
extensions=['jinja2.ext.i18n']
)
env.install_gettext_callables(_, N_, newstyle=False)
config['pylons.app_globals'].jinja_env = env

# CONFIGURATION OPTIONS HERE (note: all config options will override
# any Pylons config options)

Expand Down
19 changes: 18 additions & 1 deletion ckan/lib/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,16 +14,18 @@
from pylons.controllers.util import abort as _abort
from pylons.controllers.util import redirect_to, redirect
from pylons.decorators import jsonify, validate
from pylons.i18n import _, ungettext, N_, gettext
from pylons.i18n import _, ungettext, N_, gettext, ngettext
from pylons.templating import cached_template, pylons_globals
from genshi.template import MarkupTemplate
from genshi.template.base import TemplateSyntaxError
from genshi.template.text import NewTextTemplate
from webhelpers.html import literal

import ckan.exceptions
import ckan
import ckan.authz as authz
from ckan.lib import i18n
import lib.render
import ckan.lib.helpers as h
from ckan.plugins import PluginImplementations, IGenshiStreamFilter
from ckan.lib.helpers import json
Expand Down Expand Up @@ -69,6 +71,12 @@ def render_text(template_name, extra_vars=None, cache_force=None):
method='text',
loader_class=NewTextTemplate)

def render_jinja2(template_name, extra_vars):
env = config['pylons.app_globals'].jinja_env
template = env.get_template(template_name)
return template.render(**extra_vars)


def render(template_name, extra_vars=None, cache_key=None, cache_type=None,
cache_expire=None, method='xhtml', loader_class=MarkupTemplate,
cache_force = None):
Expand All @@ -86,8 +94,17 @@ def render_template():
# we remove it so any bad templates crash and burn
del globs['url']

template_path, template_type = lib.render.template_info(template_name)

# Jinja2 templates
if template_type == 'jinja2':
# TODO should we raise error if genshi filters??
return render_jinja2(template_name, globs)

# Genshi templates
template = globs['app_globals'].genshi_loader.load(template_name,
cls=loader_class)

stream = template.generate(**globs)

for item in PluginImplementations(IGenshiStreamFilter):
Expand Down
40 changes: 40 additions & 0 deletions ckan/lib/render.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
import os
import re

from pylons import config

_template_info_cache = {}

def find_template(template_name):
''' looks through the possible template paths to find a template
returns the full path is it exists. '''
template_paths = config['pylons.app_globals'].template_paths
for path in template_paths:
if os.path.exists(os.path.join(path, template_name)):
return os.path.join(path, template_name)

def template_type(template_path):
''' returns best guess for template type
returns 'jinja2', 'genshi', 'genshi-text' '''
if template_path.endswith('.txt'):
return 'genshi-text'
f = open(template_path, 'r')
source = f.read()
if re.search('\{\[|\%', source):
return 'jinja2'
return 'genshi'

def template_info(template_name):
''' Returns the path and type for a template '''

if template_name in _template_info_cache:
t_data = _template_info_cache[template_name]
return t_data['template_type'], t_data['template_type']

template_path = find_template(template_name)
t_type = template_type(template_path)

t_data = {'template_path' : template_path,
'template_type' : t_type,}
_template_info_cache[template_name] = t_data
return template_path, t_type

0 comments on commit 53cc673

Please sign in to comment.