webapp template inheritance problem

193 views
Skip to first unread message

MHblue

unread,
Oct 9, 2008, 7:34:38 PM10/9/08
to Google App Engine
Hi there,
I have a simple request handler that is supposed to take a URL and map
it to template files where/when they exist [see #1, below] and it
works *except* where I have a template inside a folder (/templates/
folder/thisone.html) that inherits from a template in its parent /
templates/ folder (/templates/base.html).

So when I navigate to myurl.com/folder/thisone.html (which starts with
{% extends 'base.html' %} or {% extends '../base.html' %}) I see the
results shown in [#2].

Navigating to myurl.com/folder/atemplate.html does work if it is not
tryiing to extend 'base.html'.

Any ideas?

Thanks,

Matt

[#1] request handler
class MainPage(webapp.RequestHandler):
def get(self):
if self.request.path == "/":
thistemplate = "index.html"
else:
thistemplate = self.request.path
template_values = []
template_path = 'templates' + thistemplate
path = os.path.join(os.path.dirname(__file__), template_path)
try:
self.response.out.write(template.render(path, template_values))
except:
self.response.out.write('Page does not exist... sorry! <br />
Your path: '+str(self.request.path)+'<br />Template path:
'+str(template_path))

[#2] results of navigating to myurl.com/folder/thisone.html

Page does not exist... sorry! path: /folder/thisone.html
Template path: templates/folder/thisone.html

MHblue

unread,
Oct 9, 2008, 11:11:34 PM10/9/08
to Google App Engine
OK I took the "try... except" out to see errors.

Here's what's happening.

My folder / template structure:
/templates/base.html
/templates/section.html <-- inherits from base.html {% extends
"base.html" %}
/templates/section/item.html <-- inherits from section.html {%
extends "../section.html" }%

item.html "finds" section.html just fine.

But section.html can't find base.html unless I change it to {% extends
"../base.html" %} ... despite the fact that it is located in the same
directory.

MHblue

unread,
Oct 9, 2008, 11:57:20 PM10/9/08
to Google App Engine
After talking to some people on #django it seems that with Django,
template searches always begin with the template_dirs, which would
include /templates/ and further, relative template paths do not work.

However, for me on GAE, {% extend 'base.html' %} does not work if the
template is not in the same folder as 'base.html' -- so somehow the
template-searching is not working as it does in Django.

I can't find any documentation or information on this. Does anyone
know how I can specify / look at how GAE's webapp/templating system
works? How do I set the equivalent of TEMPLATE_DIRS given that I am
not using Django?

Bill

unread,
Oct 10, 2008, 4:12:55 AM10/10/08
to Google App Engine
I copied the template code from google.appengine.ext.webapp and
modified it to allow a template directory hierarchy under render() and
load(). So my template.py has something like this:

def render(template_path, template_dict, debug=False,
template_dirs=()):
"""Renders the template at the given path with the given dict of
values.

Example usage:
render("templates/index.html", {"name": "Bret", "values": [1, 2,
3]})

Args:
template_path: path to a Django template
template_dict: dictionary of values to apply to the template
"""
t = load(template_path, debug, template_dirs)
return t.render(Context(template_dict))


template_cache = {}
def load(path, debug=False, template_dirs=()):
"""Loads the Django template from the given path.

It is better to use this function than to construct a Template using
the
class below because Django requires you to load the template with a
method
if you want imports and extends to work in the template.
"""
abspath = os.path.abspath(path)

if not debug:
template = template_cache.get(abspath, None)
else:
template = None

if not template:
directory, file_name = os.path.split(abspath)
new_settings = {
'TEMPLATE_DIRS': (directory,) + template_dirs,
'TEMPLATE_DEBUG': debug,
'DEBUG': debug,
}
old_settings = _swap_settings(new_settings)
try:
template = django.template.loader.get_template(file_name)
finally:
_swap_settings(old_settings)

if not debug:
template_cache[abspath] = template

def wrap_render(context, orig_render=template.render):
URLNode = django.template.defaulttags.URLNode
save_urlnode_render = URLNode.render
old_settings = _swap_settings(new_settings)
try:
URLNode.render = _urlnode_render_replacement
return orig_render(context)
finally:
_swap_settings(old_settings)
URLNode.render = save_urlnode_render

template.render = wrap_render

return template

----

I have a view.py that constructs a template_dirs tuple so I can have a
base.html at a root directory and more specific templates for modules
in subdirectories.

Hope that helps,
Bill
Reply all
Reply to author
Forward
0 new messages