How to render a template page by calling its method from TAL portlet(@@manage-portlets)

StackOverflow https://stackoverflow.com/questions/18485058

  •  26-06-2022
  •  | 
  •  

Question

How do I call a method which is in the filesystem from a TAL Portlet (made available by collective.portlet.tal)?

This is how I did it: I defined a new BrowserView (createPictMenu.py in my case) and then registered it as the renderer for a new portlet component:

class AddressTAL(BrowserView)

    def my_address()
        address_bar = ViewTemplatePageFile('templates/address_left.pt') # this 
         is the page template I want for my new portlet.

And in configure.zcml:

<plone:portlet
    name="collective.portlet.tal.TALPortlet"
    interface="collective.portlet.tal.talportlet.ITALPortlet"
    assignment="collective.portlet.tal.talportlet.Assignment"
    view_permission="zope2.View"
    edit_permission="cmf.ManagePortal"
    renderer=".browser.createPictMenu.AddressTAL"
    addview="collective.portlet.tal.talportlet.AddForm"
    editview="collective.portlet.tal.talportlet.EditForm"
    />

Then I went to localhost:8080/myproject/@@manage-portlets and selected the TAL Portlet option from the Add Portlet dropdown list. I informed title as address and for description I inserted the snippet below to call address_tal():

<span tal:define="global li view/myaddress">
    <span tal:replace="structure li" /> 
</span> 

Unfortunately, it didn't work. Please help.

Was it helpful?

Solution

You should have registered your class AddressTAL with a browser:view directive, not a plone:portlet one. Like this:

<configure
    xmlns="http://namespaces.zope.org/zope"
    xmlns:browser="http://namespaces.zope.org/browser">

  <browser:page
      name="address-view"
      class=".browser.createPictMenu.AddressTAL"
      for="*"
      permission="zope2.View"
      />

</configure>

And then call it with:

<div tal:define="my_address python:context.restrictedTraverse('@@address-view').my_address()" >
    Your method returns <span tal:content="my_address" />
</div>

Or:

<div tal:define="address_view context/@@address-view" >
    Your method returns <span tal:content="address_view/my_address" />
</div>

OTHER TIPS

It's of very little information or matter that the method is on the file system. That's where it should be. Having it in the ZODB is possible but a bad idea.

But there are many types of methods, and how you call them from TAL differs.

You can have what in the ZMI is called "Script (Python) methods" that are accessed through portal_skins, you can have methods on content objects and you can have methods on views. These are all callable from TAL.

For methods that are neither of these, you will have to create a method of the above type that you can call, which in turn then calls the method you want to call. For a portlet the obvious place to create that method is by adding a method on the Renderer, which is a type of view, and which you can call from the portlets template.

In your case, the method you want to call is a method on the renderer already. That means you just call it.

<p tal:content="view/myaddress" />

Note that you have forgotten the self parameter in the definition. Also, please follow PEP8.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top