from django.template import Library, Node, TemplateSyntaxError register = Library() def parse_args_kwargs_and_as_var(parser, bits): args = [] kwargs = {} as_var = None bits = iter(bits) for bit in bits: if bit == 'as': as_var = bits.next() break else: for arg in bit.split(","): if '=' in arg: k, v = arg.split('=', 1) k = k.strip() kwargs[k] = parser.compile_filter(v) elif arg: args.append(parser.compile_filter(arg)) return args, kwargs, as_var def get_args_and_kwargs(args, kwargs, context): out_args = [arg.resolve(context) for arg in args] out_kwargs = dict([(smart_str(k,'ascii'), v.resolve(context)) for k, v in kwargs.items()]) return out_args, out_kwargs class SomeObject(object): def __init__(self, *args, **kwargs): self.args = args self.kwargs = kwargs class GetWithArgsAndKwargs(Node): def __init__(self, args, kwargs, as_var): self.args = args self.kwargs = kwargs self.as_var = as_var def render(self, context): args, kwargs = get_args_and_kwargs(self.args, self.kwargs, context) # call something with the args or kwargs here some_object = SomeObject(*args, **kwargs) context[self.as_var] = some_object return '' def get_with_args_and_kwargs(parser, token): bits = token.contents.split(' ') if len(bits) < 1: raise TemplateSyntaxError("'%s' takes at least one argument" % bits[0]) if len(bits) > 1: args, kwargs, as_var = parse_args_kwargs_and_as_var(parser, bits[1:]) return GetWithArgsAndKwargs(args, kwargs, as_var) register.tag(get_with_args_and_kwargs)