Restricting display of links/buttons
There was a recent thread discussing about restricting display of links based on permission to access the target link. I am just trying to consolidate the informations discussed in that thread and share my thoughts on the best practices. If you have any suggestions please add a comment here.
The question was, "How to restrict some links to display only for principals with access to the link target ?"
It could be links,buttons or any other part of the web page. Ideally it is better to use a content provider (eg:- viewlet) to generate the links/buttons where you need to restrict display based on permissions. You can use the API provided in zope.security module to perform security related operations. We will go through an example without using viewlet. However, the same idea should work with viewlet also.
He is a template file:
This is the view class:
The zope.security.canAccess function would be sufficient in most of the cases to check whether a user has permission to access the attribute of an object. In the above example, if __setitem__ attribute is accessible, user can add new objects to that container object. Here I assume that, if write access is given inside the container, we can display that links. If the logic is different to show the links, see whether you can convert that logic into an attribute acess logic. A bit advanced example is given by Ilshad in another reply. There he checks for the access to the render method of views.The zope.security.canWrite function can be used to check whether an attribute can be set or not. I think usage of this method will be less compared to canAccess.
There is a third function called zope.security.checkPermission, which can used to check for a particular permission explicitly. In normal cases this function will not be required as it is very specific to a particular permission checking. It is not a good idea to use permission names directly from views, if you come across anything like this, it might be a code smell.