Limit access on website's parts (Django) - django

I have the website where I need to limit users access to the website's parts. To keep it simple let's say while website is in beta - I want only registered users can see the website and all the parts. But later I will want to remove those limits.
What I can do - do this login in the template level. Like in all the templates I can have {% if user.is_authenticated %} and then just show some message if not.
Second thing which is in my minds - I can define middleware which will check if the user is logged in and if not - redirect him to the login page.
I see bad thing about the template solution, because after I will release the website out of beta, I will need to modify a lot of templates...
What else I can choose here?
Thanks!

You must tag all methods or classes involved with the login_required decorator. If you're using generic views, set login_required=True when defining them in urls.py.

Related

Adding Wagtail to an existing Django app

I'm quite new to Django and Wagtail, and I'm having some difficulty with what I think is a very basic use.
How do I allow Wagtail to edit an existing view's template, while serving that template using Django's serving mechanism?
Assume I have an app (HomePage) created to serve the site's main index (/). I have the HomePage's views set up to render template and certain elements dynamically. Now I want that template to be editable via Wagtail's CMS interface. Something as simple as an image on the frontpage, or a headline.
The closest I've gotten so far has been to follow the Wagtail beginner's tutorial to override the base HomePage class in my app's models.py. That only made my pages available via the /pages/ URL.
Thank you for any help.
Since your site's home page is not a Page object in the Wagtail sense, I'd suggest looking at Wagtail's facilities for managing non-page content - snippets and ModelAdmin would be possible candidates, but I reckon the site settings module would be the best fit.
A Setting model gives you a set of fields which can be configured for display in the Wagtail admin using a 'panels' definition, just like you'd get for a page model - with the important property that only one settings record exists per site. You can retrieve this record within your homepage view or template as shown in the docs, and output it on your template as desired.
One way do that, is to let Wagtail serve your homepage. You will need to change your project's url configuration accordingly, to make wagtail's urls serve the root of your site.
Then, you can pack your dynamic content into a custom template_tag and include in your homepage html template.

Where is account login template under mezzanine?

I'm trying to look for the login page. I've created a folder registeration/login.html under templates, but it doesn't read my updated file at all.
Secondly, there's a button that says login but takes me to accounts/login page, how do I just forward the url to accounts/login then? and where do i customize the login page? I've tried creating an accounts/loginunder templates, that doesn't work.
urls.py
url('^', include('django.contrib.auth.urls')),
It is always a good idea to check out the source code of the framework when you're looking for the answer. In django.contrib.auth.views.LoginView default template is:
template_name = 'registration/login.html'
{% url 'login' %}
Use to retrieve pages from template (html)
I realize this is very late, but will hopefully be helpful for others facing similar issue.
This is the Mezzanine source code for login page which Mezzanine renders by default.
So, you can do something like
python manage.py collecttemplates -t accounts/account_login.html
to copy the above file to your app template directory, and modify the copied file as per your needs.
Bonus: You can find other account related templates (like sign up, password reset, etc.) here.

Single-page login in Django app

I'm currently using out-of-the-box django.contrib.auth to handle authentication in my Django app. This means that the user starts at a log in page and is redirected to the app on successful login. I would like to make my app single-page, including this login process, where a redirect doesn't happen, but maybe a "hot" template switch-out or some fancy client-side div magic (that still remains secure). My Google searching turned up pretty short, the closest solution dealing with putting a log in form on every page.
Any direction or ideas here would be much appreciated. I would obviously prefer to work within the existing confines of django.contrib.auth if possible, but I'm open to all solutions.
I'm not sure I understand your question completely. I think you want to have a single page. If so, put logic in your template that checks to see if the user is authenticated. If not, display a login form that POSTS to the appropriate django.contrib.auth view. You can supply an argument to this view to have it redirect back to your page. When you come back, the user will be authenticated, so you won't display the login form.
Have a look at Django-Easy-Pjax https://pypi.python.org/pypi/django-easy-pjax - it works like a charm and is well documented. Everything you like is being made with AJAX requests: links, forms using GET and forms using POST.
Essentially you only need to add a data-pjax="#id_of_the_container_where_the_result_goes" attribute in your a and form tags.
And the great thing about it: It updates the title and location bar of your browser.
One caveat: If you want to upload files in some form, this is not supported by Easy-Pjax, so you might want to use some workaround jQuery library for that.

partly caching a view method

I am using Memcached (with python-memcached binding) with one of my django projects. The scenario is that on the homepage i have:
A Top Bar : (This contains the links to login / User name with a link to the profile)
A Search Form
Few Blocks Of Results
Currently, I am using the cache_page() decorator to cache the whole page as follows:
#cache_page(3600)
def home(request):
# View Code Goes Here
and the above is working as expected. But as the homepage is a publicly accessible page i am facing a problem with one scenario where:
An anonymous user request the home page(the page get's cached if it
is not already).
Now the user logs in and is redirected to the homepage.
The cached homepage loads (Topbar still shows a login link instead of the logged in user's Name and profile link as the page was cached before the user logged in.)
Question:
Is there a way either on template level or on view level, that lets us specify a block we DO NOT want to cache while using cache_page() decorator ?
Please Note: I am aware that we can use {% cache %} template tag or cache.set for each block in the above scenario. But i am specifically looking for a solution where we can use the cache_page() decorator and still be able to specify a block that i do not want cached in a particular view or a template
use CACHE_MIDDLEWARE_ANONYMOUS_ONLY
yet it sounds as a middleware option, it affects #cache_page as well

Rendering an existing site invite only in Django

For a project I'm working on, we're still undecided whether the site will launch on an invite-only basis, or be open to the general public immediately. Notwithstanding the management of invites, how would one go about to render a public site invite-only in Django?
One way I can come up with is adding #login_required to all views, but that seems to be too labour intensive... In other words, is there a way to restrict the use of the site to those who have login credentials in one swoop?
Thanks in advance!
Have you looked at the privatebeta application (PyPI, GitHub)? It seems like that does what you are looking for. Otherwise you can at least have a look at their middleware component to base your code on.
Perhaps you could use signals to catch people that are not logged in:
http://docs.djangoproject.com/en/dev/ref/signals/#django.core.signals.request_started
Or you could fiddle with the urlpatterns somehow, so that the urlpatterns list only contains the required login stuff when you're not logged in. That would work, right?