On Mon, May 18, 2015 at 12:23 PM Amirouche Boubekki < [email protected]> wrote:
> On Mon, May 18, 2015 at 12:12 PM Amirouche Boubekki < > [email protected]> wrote: > >> I would like to implement similar functionality to Django template's >>>> custom tags in Jinja. >>>> >>>> In Django templates, to have a server-side function return a string >>>> >>> The example you give below returns a dictionary. Not a string. >> > I got it, you return the context of the template argument of /inclusin_tag/. meh. I did not read the decorator the first time. > >> >>> and have it inserted to a template, you can do something as this: >>>> >>> from django import template >>>> >>>> register = template.Library() >>>> @register.inclusion_tag('app/gallery.html')def get_gallery(active=None): >>>> ### do complex server side things, etc. >>>> >>>> context_dict = { >>>> ... >>>> } >>>> return context_dict >>>> >>>> I don't fully understand the purpose of the function /get_gallery/. You >> are updating the context of the template? Your are returning a variable >> that ca be used with a /for/ and /with/ tags? >> > I get it. > >> >>> Now, calling this is as simple as >>>> >>>> {% load app_tags %}{% get_gallery 'home' %} >>>> >>>> This seems clear enough for me. >>>> >>> You have nested|recursive concept/defintions: [view-code.py]-->[template-code.py] --> [filter-code.py] --> [filter-template-code] - - - > [filter-code] You can do otherwise, by returning quickly back every time in the template and do the gluing there, instead, of nesting calls and signatures. You rephrase is with: ``` {% for section in sections %} {{ render(get_gallery(section), 'html') | safe }} {% endfor %} ``` That said, i prefer to use methods: ``` {% for section in sections %} {{ section.gallery.render.html() }} {% endfor %} ``` More or less.. Anyway.. > Now my question: even after reading through all parts of the Jinja2 >>>> documentation, I do not see how a similar functionality should be >>>> implemented in Jinja. I've seen that Jinja supports macros, calls, imports, >>>> custom tests, custom filters, but I cannot see anything related to defining >>>> custom tags with arbitrary server-side Python code. >>>> >>> The main feature is that you can not replace context variable function >> with filters or the otherway around :))) #CognitveLoad >> >> Two concepts I know of: >> >> - filters, like /{live|love}/ this one will turn the content of the >> variable /live/ to something computed in python function named in the >> context /love/. filters can not be used as context variables. >> >> - context function that returns a context or string or else; maybe the >> context is updated. Anyway you can use assignements >> <http://jinja.pocoo.org/docs/dev/templates/#assignments> instead of >> django's with. >> >> >>> The closest I've seen is custom filters, but that has a weird syntax >>>> when used for tag-like purposes: to call tag(param1, param2), you'd >>>> need to write param1|tag(param2). Also, I don't see how it can be used >>>> for parameter-less functions. >>>> >>> not if you put the function in the context just like /user/, /message/, >> pass procedure as a variable of the template context. >> >> >>> There is also the whole extension support, but that seems overly >>>> complicated with the simplest example >>>> <http://jinja.pocoo.org/docs/dev/extensions/#example-extension> taking >>>> up 56 lines of code in the doc. >>>> >>>> Can you explain how do you solve this problem, both in standalone >>>> Jinja2 environment (think static site generation) >>>> >>> I attached the make.py of my blog. There is a function called "jinja" >> it's commented what i does. and I also attach the index.jinja and >> base.jinja they must live in ./_templates. I never use this engine to do >> jinja alone. If you can't make it work hit me. Here is the jinja code: >> >> edit: uncomment to make use of the fact that filters and context dict are merged. > ```asc11 >> *-{{ "007"|love(42) }}* >> {% for ognoin in live(1985, 12, 31, bof="0x12ee7df") %} >> [[{{ ognoin }}]] >> {{ live(132)|love(4096) }} >> {% endfor %} >> >> {% for fish in love(1337) %} >> {{ "off" }} #} >> {% endfor %} #} >> ``` >> > rendering is at: http://www.hyperdev.fr/#main >> > edit: copy+paste output of the mino-template: *-['a', 'b', 'c', 'abc', '007', (42,), {}]* [[a]] ['a', 'b', 'c', 'abc', ['a', 'b', 'c', 'abc', 132, (), {}], (4096,), {}] [[b]] ['a', 'b', 'c', 'abc', ['a', 'b', 'c', 'abc', 132, (), {}], (4096,), {}] [[c]] ['a', 'b', 'c', 'abc', ['a', 'b', 'c', 'abc', 132, (), {}], (4096,), {}] [[abc]] ['a', 'b', 'c', 'abc', ['a', 'b', 'c', 'abc', 132, (), {}], (4096,), {}] [[1985]] ['a', 'b', 'c', 'abc', ['a', 'b', 'c', 'abc', 132, (), {}], (4096,), {}] [[(12, 31)]] ['a', 'b', 'c', 'abc', ['a', 'b', 'c', 'abc', 132, (), {}], (4096,), {}] [[{'bof': '0x12ee7df'}]] ['a', 'b', 'c', 'abc', ['a', 'b', 'c', 'abc', 132, (), {}], (4096,), {}] > >> The context is populated by jinja function: >> >> ``` >> def jinja(template, **context): >> """Render template /template/ found in /.//_templates// directory. >> >> wrapper around /Jinja.render/ where do add filter or improve >> context.""" >> path = str(Path('./_templates').resolve()) >> >> # to be used as a filter and context function >> def love(abc, *args, **kwargs): >> return ['a', 'b', 'c', 'abc', abc, args, kwargs] >> >> return Jinja.render( >> # the relative path of the directory we want >> # to render to, relative to /path/. >> template, >> # the root path where to look for templates >> # both the above /template/ but also other >> # template references in templates. >> path, >> # filter are text transformers. Some kind of html tags. >> # use functions in context to create Djano-like tags >> # aka. tags that be both manipulated the conte >> filters=dict(love=love), >> # every keyword except filters are made >> # available in the template context. The keyword >> # contexte variable is dubbed with the key of the >> # keyword argument. >> # Here /love/ is stored as /live/. >> live=love, >> # what was passed as context is forwarded as-is >> **context >> ) >> ``` >> >> Jinja.render is a *generic* frontend to jinja that allows to only use one >> class. You init with base settings and then use this jinja instance >> (usually several times). Here jinja **/function/** is only a shortcut *in >> the context of /make.py/*. >> >> Anyway, /love/ is a filter, /live/ is a function variable. /live/ does >> everything you need. >> >> and under the new Django versions (1.8+)? >>>> >>> Not time for this this time.. >> >> NB: look up the code I render epub and pdf ^_^ >> > > I updated the make.py:jinja to make filters available as context function. > and remove the comment block in the jinja file. See attached files. > -- You received this message because you are subscribed to the Google Groups "pocoo-libs" group. To unsubscribe from this group and stop receiving emails from it, send an email to [email protected]. To post to this group, send email to [email protected]. Visit this group at http://groups.google.com/group/pocoo-libs. For more options, visit https://groups.google.com/d/optout.
