How can I efficiently restrict a non-CMS page view to a user group in wagtail with 'permissions_required' hook? - wagtail

I have an app within my wagtail site which uses several pages constructed in views.py (here because they contain complex-ish processing of forms and data and do not need any CMS functionality). One of these views, I want to restrict to users of a specific group.
For other pages, I use a #logon required mixin, which works fine. I can write some code which uses something like def has_group(user, group_name):
return user.groups.filter(name=group_name).exists(), but this seems messy when wagtail has a nice built in permissions model. Therefore, I am trying to use the following hook in wagtail_hook.py:
from django.contrib.auth.models import Permission
from wagtail.core import hooks
#hooks.register('register_permissions')
def view_committee_page():
return Permission.objects.filter(codename="view_committee_page")
This isn't showing up in wagtail admin under group object permissions as I believe it should.
My understanding is only based on the odd example I've found using Wagtail v1.X. The documentation is vague on this specific hook: https://docs.wagtail.io/en/v2.5.1/reference/hooks.html#register-permissions
The only modification I've made to the examples I've seen (eg. here: Wagtail set additional permissions for MyPage ) is to update wagtail.wagtailcore to wagtail.core as per 2.0 release notes.
I know my wagtail_hooks.py file is being picked up correctly as I have another hook in there working as expected.
Am I missing something? Is there a more up to date way to solve this problem?

How about creating your own function with the decorator:
#hooks.register('before_serve_page')
in watail_hooks.py there is a function called check_view_restrictions() so you could do something similar to this?

You would also need to set the permissions on your Page model.
from wagtail.core.models import Page
class MyPage(Page):
class Meta:
permissions = (("page_view_only", "Can view my pages"),)
Then use the hook in wagtail_hooks.py
from django.contrib.auth.models import Permission
from wagtail.core import hooks
#hooks.register('register_permissions')
def page_view_only():
return Permission.objects.filter(codename="page_view_only")
There should be a new permission available in the admin Group settings.

Related

Is it possible to customize Wagtail's auth forms?

This page shows how to customize templates: https://docs.wagtail.io/en/stable/advanced_topics/customisation/admin_templates.html
But I want to customize the forms instead. I'm trying to add reCaptcha to all of them.
Is this possible?
Wagtail provides a Django setting called WAGTAILADMIN_USER_LOGIN_FORM which allows a custom form to be declared for the login form.
Wagtail does not provide a setting for the password reset workflow though unfortunately.
settings/base.py
WAGTAILADMIN_USER_LOGIN_FORM = 'app.forms.CustomLoginForm'
forms.py
from django import forms
from wagtail.admin.forms.auth import LoginForm
class CustomLoginForm(LoginForm):
captcha = forms.CharField(required=True)
A reminder that there is a way to work with custom User models in Wagtail which may also suit your customisation needed.

Wagtail Form static fields & superuser-only page

I did not found any answer to this. So is there a way in Wagtail to have an AbstractEmailForm without AbstractFormField (for example, can I hard code them into AbstractEmailForm? I know that AbstractEmailField has some variables that Django requires). I just need to have a contact form only with email field, I dont need to set fields dynamically.
And the second question: How do I set permission for that form page so that only superuser can edit the form page?(And the translated version too? There are a lot of answers to this, but I don't actually understand how to do it with AbstractEmailForm).
Thanks a lot!
If you're hard-coding your form fields, then the Wagtail forms module doesn't really give you anything that you don't already get from Django's forms framework, and so you're better off using Django forms directly. The serve method on a Wagtail page is equivalent to a Django view function, so any form-processing logic that would normally go into a view function can be placed in serve.
There's an example of this here (but written for Wagtail 1.x, so imports will need adjusting): https://github.com/gasman/wagtail-form-example/commits/master

CakePHP bake generating auth component user actions

I'm sure there is a relatively simple answer. I am trying to use CakePHP 2.0 to bake an application from the command line, and i would like cake to create the basic AuthComponent methods for my user model. the database table for users is named users, which includes the two necessary fields for auth, username and password.
I've been able to include AuthComponent in my usersController from bake, but have been unsuccessful at getting it to generate basic usersController actions for auth, such as login() and logout().
How can I do this? generating this skeleton code will help save a lot of time.
Thanks in advance!!!!
default bake templates are only for CRUD (create=add, read=index,view update=edit, delete=delete), not for the rest. but it is fairly simple to customize your templates according to your needs.
Although login/logout are one-time-needed methods and don't make any sense to be baked. Its easier and faster to just manually "make" them. For login use the add template as basis, logout doesnt need any view.

cakephp plugin model/controller cache issue with main model/controller

I have a plugin with user model, profile model and an user controller, in this user model is associated with profile model. In my main model folder (under app), I have user model and user controller(here I have not associated with profile). Sometimes I'm getting errors saying that user model is not associated with profile model. Also sometimes I'm getting the error - "missing action logout in users controller". I have given the logout action in the app/controller/userscontroller but that method is not available in myplugin/usercontroller. Im using cakephp2.0.. How can I solve this issue ? How cakephp is setting the cache for models and controllers ? I don't want to completely disable the cache.
I've had trouble with this as well. Basically it comes down to the fact that Cake doesn't support controllers with the same class name. So a controller named UsersController on plugin and app level will cause trouble with caching and some components (the Auth component, for example).
Support for identical classnames in various levels of a Cake application will come in Cake 3.0 which will require PHP 5.3, which in turn supports namespaces, a feature needed for correctly handling duplicate class names.
With no word on when Cake 3.0 will be released as the 2.0 branch is just out of beta, I refactored my plugin by prepending the plugin name to my controllers, views and models.
So UserModel became PluginUserModel and UsersController became PluginUsersController. It's a bit of a hassle, because you have to update all the views and variables which use the model's name.
My original question contains some links to the Cake bug tracker where similar questions were raised, should you be interested in some background,

CakePHP - Only display a link if user (ARO) has permission for page?

I'm using CakePHP's ACL component to manage permissions for my app. I have about three different "Roles", with different access levels. I am using the HTML helper throughout, to create links to different pages. I would like links to only display if the user has permission to access the page.
The obvious but cumbersome approach, I guess, would be to set variables to the view containing permissions and show links based on these variables.
I was wondering if there is a better way - perhaps a helper that extends the HTML helper to provide a method that checks permissions first?
Thanks.
I wouldn't recommend to use a helper which has this sort of functionality.
This is because this helper would have to do the checking on every link you use on that page. This would slow down your application.
So I think the best approach is your approach. Set the permission on login and display your links accordingly.
We are using this in our application, too, and it works very good and fast.

Resources