Kaarsemaker.net


hosturl.py
3.75 KB

103 lines

Download

filtercache.py
query.py

Preview

 1 # Modified version of the {% url %} tag that allows you to specify a hostname
 2 # {% hosturl http://hostpath/path path.to.some_view arg1,arg2,name1=value1 %}
 3 
 4 from django import template
 5 from django.conf import settings
 6 
 7 register = template.Library()
 8 
 9 class HostURLNode(template.Node):
10     def __init__(self, hostpath, view_name, args, kwargs, asvar):
11         self.hostpath = hostpath
12         self.view_name = view_name
13         self.args = args
14         self.kwargs = kwargs
15         self.asvar = asvar
  1 # Modified version of the {% url %} tag that allows you to specify a hostname
  2 # {% hosturl http://hostpath/path path.to.some_view arg1,arg2,name1=value1 %}
  3 
  4 from django import template
  5 from django.conf import settings
  6 
  7 register = template.Library()
  8 
  9 class HostURLNode(template.Node):
 10     def __init__(self, hostpath, view_name, args, kwargs, asvar):
 11         self.hostpath = hostpath
 12         self.view_name = view_name
 13         self.args = args
 14         self.kwargs = kwargs
 15         self.asvar = asvar
 16         print self.view_name
 17 
 18     def render(self, context):
 19         from django.core.urlresolvers import reverse, NoReverseMatch
 20         args = [arg.resolve(context) for arg in self.args]
 21         kwargs = dict([(smart_str(k,'ascii'), v.resolve(context))
 22                        for k, v in self.kwargs.items()])
 23         
 24         
 25         # Try to look up the URL twice: once given the view name, and again
 26         # relative to what we guess is the "main" app. If they both fail, 
 27         # re-raise the NoReverseMatch unless we're using the 
 28         # {% hosturl ... as var %} construct in which cause return nothing.
 29         url = ''
 30         try:
 31             url = reverse(self.view_name, args=args, kwargs=kwargs)
 32         except NoReverseMatch:
 33             project_name = settings.SETTINGS_MODULE.split('.')[0]
 34             try:
 35                 url = reverse(project_name + '.' + self.view_name,
 36                               args=args, kwargs=kwargs)
 37             except NoReverseMatch:
 38                 if self.asvar is None:
 39                     raise
 40                     
 41         if self.asvar:
 42             context[self.asvar] = self.hostpath + url
 43             return ''
 44         else:
 45             return self.hostpath + url
 46 
 47 def hosturl(parser, token):
 48     """
 49     Returns an absolute URL matching given view with its parameters.
 50 
 51     This is a way to define links that aren't tied to a particular URL
 52     configuration::
 53 
 54         {% hosturl hostpath path.to.some_view arg1,arg2,name1=value1 %}
 55 
 56     The first argument is a path to a view. It can be an absolute python path
 57     or just ``app_name.view_name`` without the project name if the view is
 58     located inside the project.  Other arguments are comma-separated values
 59     that will be filled in place of positional and keyword arguments in the
 60     URL. All arguments for the URL should be present.
 61 
 62     For example if you have a view ``app_name.client`` taking client's id and
 63     the corresponding line in a URLconf looks like this::
 64 
 65         ('^client/(\d+)/$', 'app_name.client')
 66 
 67     and this app's URLconf is included into the project's URLconf under some
 68     path::
 69 
 70         ('^clients/', include('project_name.app_name.urls'))
 71 
 72     then in a template you can create a link for a certain client like this::
 73 
 74         {% hosturl http://other_server/path/to app_name.client client.id %}
 75 
 76     The URL will look like ``http://other_server/path/to/clients/client/123/``.
 77     """
 78     bits = token.contents.split(' ')
 79     if len(bits) < 3:
 80         raise TemplateSyntaxError("'%s' takes at least two arguments"
 81                                   " (hostpath and path to a view)" % bits[0])
 82     hostpath = bits[1]
 83     viewname = bits[2]
 84     args = []
 85     kwargs = {}
 86     asvar = None
 87         
 88     if len(bits) > 3:
 89         bits = iter(bits[3:])
 90         for bit in bits:
 91             if bit == 'as':
 92                 asvar = bits.next()
 93                 break
 94             else:
 95                 for arg in bit.split(","):
 96                     if '=' in arg:
 97                         k, v = arg.split('=', 1)
 98                         k = k.strip()
 99                         kwargs[k] = parser.compile_filter(v)
100                     elif arg:
101                         args.append(parser.compile_filter(arg))
102     return HostURLNode(hostpath, viewname, args, kwargs, asvar)
103 hosturl = register.tag(hosturl)

Show all