Django authentication and Ajax - URLs that require login

I want to add some Ajax-niceness to my Django-coded website.

In my Django code, I use the @login_required decorator from django.contrib.auth.decorators to mark which view requires authentication. The default behavior when a not authenticated user clicks it is to redirect him/her to login page, and then pass the target page.

What I saw on some sites, and really liked, is that when user clicks a link leading to a place restricted to logged-only users, instead of getting redirected to a login page, he/she gets a popup window (via JavaScript) asking him/her to log in or register. There's no redirection part, so no need for a user to use the "back" key if he/she decides he/she really doesn't like the website enough to waste the time registering.

So, the qestion is: how would you manage the task of automatically marking some links as "restricted" so JavaScript can handle their onclick event and display a "please log in" popup?


Asked by: Alissa738 | Posted: 01-10-2021






Answer 1

I am facing the same issue, and, like you, I would like a simple decorator to wrap around a Django ajax view in order to handle authentication in the same way that I have other views. One approach that seems promising to me is to use such a decorator in conjunction with JavaScript that looks for a certain value in the response.

Here is first revised draft of the decorator:

from functools import wraps

def ajax_login_required(view_func):
    @wraps(view_func)
    def wrapper(request, *args, **kwargs):
        if request.user.is_authenticated():
            return view_func(request, *args, **kwargs)
        json = simplejson.dumps({ 'not_authenticated': True })
        return HttpResponse(json, mimetype='application/json')
    return wrapper

Here is the view:

@ajax_login_required
def ajax_update_module(request, module_slug, action):
    # Etc ...
    return HttpResponse(json, mimetype='application/json')

And here is the JavaScript (jQuery):

$.post('/restricted-url/', data, function(json) {
    if (json.not_authenticated) {
        alert('Not authorized.');  // Or something in a message DIV
        return;
    }
    // Etc ...
});

EDIT: I've attempted to use functools.wraps, as suggested. I have not actually used this decorator in working code, so beware of possible bugs.

Answered by: Kelvin560 | Posted: 02-11-2021



Answer 2

Sounds like a page template possibility.

  1. You could pass a LINK_VIA (or something) that you provide as onClick="return popup(this, 'arg')" or None. Each link would be <A HREF="link" {{LINK_VIA}}>some text</a>.

    • For anonymous sessions, LINK_VIA has a value.
    • For logged in sessions, LINK_VIA is None
  2. You could use an {% if %} statement around your <A HREF=...> tags. This seems wordy.

  3. You could write your own custom tag with for {% link_via %}. I'm not familiar enough with this, but you can provide the link and text as strings and your tag can generate one of two kinds of links.

Answered by: Roman123 | Posted: 02-11-2021



Answer 3

I would agree with S.Lott

Make a check in the template, if the user is logged in, just put the link as usual, if not, put something like

<a href="{{link}}" onclick="return login_popup()"> 

where login_popup would return false if the user says cancel.

This could be probably be done much easier in Jinja2 through its macros.

If the template doesn't know which urls require the user to login, you probably need to re-consider your design.

If you must, I guess you can do the same thing that the django url dispatcher does to discover the view function.
see: django.core.urlresolvers

once you've grabbed the view function you can check if it's decorated with @login_required.

This would be done in a custom tag probably.
If you use Jinja2, you won't need the tag, just implement the function and expose it to the Environment, it's simple but you'll have to do a bit of reading on the API of Jinja2)

Answered by: Vivian330 | Posted: 02-11-2021



Answer 4

Built off of Eric Walker's solution, but for Django 2.0

# Standard Imports
import functools
import django.http

def ajax_login_required(view_func):
    @functools.wraps(view_func)
    def wrapper(request, *args, **kwargs):
        if request.user.is_authenticated:
            return view_func(request, *args, **kwargs)

        return django.http.JsonResponse('Unauthorized', status=401, safe=False)

    return wrapper

Answered by: Ryan287 | Posted: 02-11-2021



Answer 5

Here is proposed version of the decorator with wrap.__doc__ , wrap.__name__

from functools import wraps

def ajax_login_required(function):
    def wrap(request, *args, **kwargs):
        if request.user.is_authenticated():
            return function(request, *args, **kwargs)
        json = simplejson.dumps({ 'not_authenticated': True })
        return HttpResponse(json, mimetype='application/json')  
    wrap.__doc__ = function.__doc__
    wrap.__name__ = function.__name__
    return wrap

Answered by: Freddie411 | Posted: 02-11-2021



Similar questions

python - Scraping Javascript driven web pages with PyQt4 - how to access pages that need authentication?

I have to scrape a very, very simple page on our company's intranet in order to automate one of our internal processes (returning a function's output as successful or not). I found the following example: import sys from PyQt4.QtGui import * from PyQt4.QtCore import * from PyQt4.QtWebKit import * class Render(QWebPage): def __init__(self, url): self.app = QApplication(sys.argv) QWebPage.__...


python - Get HTML source, including result of javascript and authentication

I am building a web scraper and need to get the html page source as it actually appears on the page. However, I only get a limited html source, one that does not include the needed info. I think that I am either seeing it pre javascript loaded or else maybe I'm not getting the full info because I don't have the right authentication?? My result is the same as "view source" in Chrome when what I want is what Chrome's 'inspe...


javascript - twisted websocket chatserver openid authentication

i have a python chatserver that uses twisted and autobahn websockets for connection. factory = MessageServerFactory("ws://localhost:9000", debug=debug, debugCodePaths=debug) factory.protocol = MessageServerProtocol factory.setProtocolOptions(allowHixie76=True) listenWS(factory) this is the server import logging from autobahn.websocket import WebSocketServerFactory, WebSocke...


python - TastyPie authentication for pure javascript site

I'm using Django TastyPie for my API. I have a completely separate HTML application that my user views and will see basic read only info from the Django API. My question is what authentication method should I use in this situation. The HTML application is technically me not the user and they don't login. The app is not Django but pure javascript, hiding a key or anything else is pointless.


jquery - how to do authentication of rest api from javascript, if javascript is on third party site?

I have a javascript placed on third party site and this js makes API calls to my server. JS is publicly available and third party cannot save credentials in JS. I want to authenticate API calls before sharing JSON and also want to rate limit. Any one has ideas on how can i authenticate API?


javascript - How to combine Tornado authentication and AngularJS?

I am using the authentication system provided as an example in the tornado documentation. When I want to combine it with AngularJS - AngularJS complains about a Cross-Origin Request. How can I combine Tornado's authentication system and AngularJS? Authentication Handlers class BaseHandler(tornado.web.RequestHandler): def get_current_user(self): user_json = self....


python - How to handle javascript content and redirects after successful weblogin SSO authentication?

I am writing a python script that downloads class content(mp4, pdf) from my school website. My school uses Weblogin SSO authentication to access any of their protected urls. I was able to authenticate my credentials using the first part of the script below: #1. Authenticate login_url = "https://weblogin.MY_SCHOOL.edu/login" payload = {'login':'my_loging','password':'my_pass'} target_url = "https://M...


authentication - Python login into a website with javascript form

I'm attempting to log into my school's website using Requests, but it doesn't get past the log in page and doesn't return the stuff in the password protected pages. All it does is return the HTML of the login page. Twill would not work as this page requires javascript. . The HTML login stuff is &lt;!--box content--&gt; &lt;div id="noscript" class="feedback-alert"&gt; To sign in to PowerSchool, you must us...


javascript - Django authentication : CSRF Failed

Sometimes I can't login to my application. The authentication is handled by Django API. But sometimes it returns a 403 error with this value in the result object : responseText: "{"detail":"CSRF Failed: CSRF token missing or incorrect."}" And yet in my application, I have : angular.module('app') .config(function(ezLayoutProvider, $httpProvider) { ezL...


javascript - Django generic authentication in views

How can I avoid needing to have this piece of code in every view function : if request.user.is_authenticated(): return HttpResponse("OK") else: return HttpResponse("Load_Login_Form") But instead execute it everytime/before an url/view is "called"?


Python Authentication API

I'm looking for a python library that will help me to create an authentication method for a desktop app I'm writing. I have found several method in web framework such as django or turbogears. I just want a kind of username-password association stored into a local file. I can write it by myself, but I'm really it already exists and will be a better solution (I'm not very fluent with encryption).


Can I implement a web user authentication system in python without POST?

My university doesn't support the POST cgi method (I know, it's crazy), and I was hoping to be able to have a system where a user can have a username and password and log in securely. Is this even possible? If it's not, how would you do it with POST? Just out of curiosity. Cheers!


authentication - Authenticating against active directory using python + ldap

How do I authenticate against AD using Python + LDAP. I'm currently using the python-ldap library and all it is producing is tears. I can't even bind to perform a simple query: import sys import ldap Server = "ldap://my-ldap-server" DN, Secret, un = sys.argv[1:4] Base = "dc=mydomain,dc=co,dc=uk" Scope = ldap.SCOPE_SUBTREE Filter = "(&amp;(objectClass=user)(sAMAccountName="+un+"))" Attrs = ["displ...


python - User Authentication in Django

is there any way of making sure that, one user is logged in only once? I would like to avoid two different persons logging into the system with the same login/password. I guess I could do it myself by checking in the django_session table before logging in the user, but I rather prefer using the framework, if there is already such functionality. Cheers, Thanks for the responses!


authentication - In Python, how might one log in, answer a web form via HTTP POST (not url-encoded), and fetch a returned XML file?

I am basically trying to export a configuration file, once a week. While the product in question allows you to log in manually via a web client, enter some information, and get an XML file back when you submit, there's no facility for automating this. I can get away with using Python 2.5 (have used for a while) or 2.6 (unfamiliar) to do this. I think I need to have some way to authenticate against the pr...


Python - downloading a file over HTTP with progress bar and basic authentication

I'm using urllib.urlretrieve to download a file, and implementing a download progress bar using the reporthook parameter. Since urlretrieve doesn't directly support authentication, I came up with import urllib def urlretrieve_with_basic_auth(url, filename=None, reporthook=None, data=None, username="", password=""): class OpenerWith...


authentication - What's the best way to specify a proxy with username and password for an **https** connection in python?

I read somewhere that currently urllib2 doesn't support authenticated https connection. My proxy uses a basic authentication only, but how to open an https based webpage through it . Please help me. Thanks.


python - Using AD as authentication for Django

I'm working on a Django-based application in a corporate environment and would like to use the existing Active Directory system for authentication of users (so they don't get yet another login/password combo). I would also like to continue to use Django's user authorization / permission system to manage user capabilities. Does anyone have a good example of this?


python - Google Data API authentication

I am trying to get my Django app (NOT using Google app engine) retrieve data from Google Contacts using Google Contacts Data API. Going through authentication documentation as well as Data API Python client docs ...


json - Authentication Required - Problems Establishing AIM OSCAR Session using Python

I'm writing a simple python script that will interface with the AIM servers using the OSCAR protocol. It includes a somewhat complex handshake protocol. You essentially have to send a GET request to a specific URL, receive XML or JSON encoded reply, extract a special session token and secret key, then generate a response using the token and the key. ...






Still can't find your answer? Check out these communities...



PySlackers | Full Stack Python | NHS Python | Pythonist Cafe | Hacker Earth | Discord Python



top