Hi,
I lied - I do have one more for today LOL
Debugging just now, I found that I had to add the charset to the
content type for it to work - was getting an exception from the core
when it tried to access the unicode body of the response. So here's
what I've got currently:
# -*- coding: utf-8 -*-
"""Extensions to TurboGears functionality"""
from tg import response
from tg.render import _get_tg_vars
from turbojson import jsonify
def render_jsonp(template_name, template_vars, **kwargs):
request_callback = template_vars.get('tg', None) and
template_vars['tg'].get('inputs', None) \
and template_vars['tg']['inputs'].get('jsoncallback', None)
callback = request_callback or template_name or
kwargs.pop('jsoncallback', None) or 'jsoncallback'
for key in _get_tg_vars():
del template_vars[key]
response.headers['Content-Type'] = 'text/javascript;
charset=utf-8'
return '%s(%s)' % (callback, jsonify.encode(template_vars))
... looking at your last version, I'm probably being overly cautious
in my obtaining of the jsoncallback value from the template_args
hehehe
In my attempts to solve this problem, I'd also tried to write a custom
decorator to do this ... but didn't get that to work for a variety of
reasons - some certainly due to the fact that I don't yet understand
TurboGears fully enough! ;) At any rate, here's the code I ended up
with (including some commented out stuff, and as mentioned: it doesn't
work LOL):
# -*- coding: utf-8 -*-
"""Decorators extending default TurboGears behaviour"""
from tg import expose
import pdb
class jsonp(object):
def __init__(self, callback_method_name = 'jsoncallback'):
self.callback_method_name = callback_method_name
def __call__(self, func):
#func.decoration.hooks['before_render'].append(self.before_render)
#func.decoration.hooks['after_render'].append(self.after_render)
self.func = func
def wrapper_wrapper(*args, **kwargs):
return self.wrapper(*args, **kwargs)
#pdb.set_trace()
if hasattr(func, 'decoration'):
wrapper_wrapper.decoration = func.decoration
#wrapper_wrapper.decoration.controller = wrapper_wrapper
delattr(func, 'decoration')
return wrapper_wrapper
def wrapper(self, *args, **kwargs):
result = self.func(*args, **kwargs)
if kwargs.has_key(self.callback_method_name):
result = "%s(%s)" % (kwargs[self.callback_method_name],
result)
return result
def before_render(self, *args, **kwargs):
if len(args) >= 2 and
args[1].has_key(self.callback_method_name):
self.callback_method = args[1][self.callback_method_name]
else:
self.callback_method = None
def after_render(self, response):
pdb.set_trace()
if self.callback_method:
response = "%s(%s)" % (self.callback_method, response)
return response
... as you can see, my intention was to be able to specify the name of
the callback parameter in the decorator (e.g.
jsonp('mycallbackparam')), then harvest the callback value from the
request when the method is called, and then use it subsequently after
the data has been rendered - that's when I found out, that the
after_render hook isn't able to alter non-mutable response values :(
Cheers,
C
On Oct 24, 2:11 pm, Christoph Zwerschke <[email protected]> wrote:
> Am 24.10.2010 13:48 schrieb [email protected]:
>
> > The last line, I think, should read:
>
> > return '%s(%s)' % (callback, json_encode(template_vars))
>
> Of course you're right with both remarks. It should be this:
>
> def render_jsonp(template_name, template_vars, **kwargs):
> callback = (template_vars['tg']['inputs'].get('callback')
> or template_name or 'callback')
> for key in _get_tg_vars():
> del template_vars[key]
> response.headers['Content-Type'] = 'text/javascript'
> return '%s(%s)' % (callback, json_encode(template_vars))
>
> Somewhat unpleasant here is that the JSONP controller now always has to
> declare a callback or **kwargs parameter.
>
> I guess we could solve this by creating an appropriate jsonp decorator
> as replacement for the expose decorator. This could pop the callback
> name from the query parameters and ignore the templ_context.
>
> -- Christoph
--
You received this message because you are subscribed to the Google Groups
"TurboGears" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to
[email protected].
For more options, visit this group at
http://groups.google.com/group/turbogears?hl=en.