Skip to content

Commit

Permalink
Merge pull request #415 from gratipay/renderers-more-data
Browse files Browse the repository at this point in the history
Give more data to renderers
  • Loading branch information
pjz committed Feb 16, 2015
2 parents a48f305 + 9c9fb67 commit bd0934f
Show file tree
Hide file tree
Showing 3 changed files with 49 additions and 8 deletions.
20 changes: 13 additions & 7 deletions aspen/renderers/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,12 +29,14 @@
configuration an Aspen configuration object
Instances of each Renderer subclass are callables that take three arguments and
return a function (confused yet?). The three arguments are:
Instances of each Renderer subclass are callables that take five arguments and
return a function (confused yet?). The five arguments are:
factory the Factory creating this object
filepath the filesystem path of the resource in question
raw the bytestring of the page of the resource in question
media_type the media type of the page
offset the line number at which the page starts
Each Renderer instance is a callable that takes a context dictionary and
Expand Down Expand Up @@ -86,14 +88,16 @@ class CheeseFactory(Factory):

class Renderer(object):

def __init__(self, factory, filepath, raw):
"""Takes a Factory and two bytestrings.
def __init__(self, factory, filepath, raw, media_type, offset):
"""Takes a Factory, three bytestrings, and an int.
"""
self._filepath = filepath
self._factory = factory
self._changes_reload = factory._changes_reload
self.meta = self._factory.meta
self.raw = raw
self.media_type = media_type
self.offset = offset
self.compiled = self.compile(self._filepath, self.raw)

def __call__(self, context):
Expand Down Expand Up @@ -122,6 +126,8 @@ def render_content(self, context):
self.compiled the result of self.compile (generally a template in
compiled object form)
self.meta the result of Factory.compile_meta
self.media_type the media type of the page
self.offset the line number at which the page starts
"""
return self.raw # pass-through
Expand All @@ -136,11 +142,11 @@ def __init__(self, configuration):
self._changes_reload = configuration.changes_reload
self.meta = self.compile_meta(configuration)

def __call__(self, filepath, raw):
"""Given two bytestrings, return a callable.
def __call__(self, filepath, raw, media_type, offset):
"""Given three bytestrings and an int, return a callable.
"""
self._update_meta()
return self.Renderer(self, filepath, raw)
return self.Renderer(self, filepath, raw, media_type, offset)

def _update_meta(self):
if self._changes_reload:
Expand Down
2 changes: 1 addition & 1 deletion aspen/resources/simplate.py
Original file line number Diff line number Diff line change
Expand Up @@ -141,7 +141,7 @@ def compile_page(self, page):
_parse_specline = self._bound_parse_specline \
if self.is_bound else self._unbound_parse_specline
make_renderer, media_type = _parse_specline(page.header)
renderer = make_renderer(self.fs, page.content)
renderer = make_renderer(self.fs, page.content, media_type, page.offset)
if media_type in self.renderers:
raise SyntaxError("Two content pages defined for %s." % media_type)

Expand Down
35 changes: 35 additions & 0 deletions tests/test_renderers.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
from __future__ import absolute_import
from __future__ import division
from __future__ import print_function
from __future__ import unicode_literals

from aspen import json
from aspen.renderers import Factory, Renderer


def test_a_custom_renderer(harness):
class TestRenderer(Renderer):

def compile(self, *a):
return self.raw.upper()

def render_content(self, context):
d = dict((k, v) for k, v in self.__dict__.items() if k[0] != '_')
return json.dumps(d)

class TestFactory(Factory):
Renderer = TestRenderer

def compile_meta(self, configuration):
return 'foobar'

website = harness.client.website
website.renderer_factories['lorem'] = TestFactory(website)

r = harness.simple("[---]\n[---] text/html via lorem\nLorem ipsum")
d = json.loads(r.body)
assert d['meta'] == 'foobar'
assert d['raw'] == 'Lorem ipsum'
assert d['media_type'] == 'text/html'
assert d['offset'] == 2
assert d['compiled'] == 'LOREM IPSUM'

0 comments on commit bd0934f

Please sign in to comment.