Can i avoid the creation of the Django auth.model.User table when using "other authentication sources"? - django

As the Django documentation says about Other authentication sources, in order to authenticate against another source, you must implement your own authentication backend. Also, They explain that:
The Django admin system is tightly coupled to the Django User object described at the beginning of this document. For now, the best way to deal with this is to create a Django User object for each user that exists for your backend (e.g., in your LDAP directory, your external SQL database, etc.)
As i'm not going to use the admin system (i'm assuming they are referencing the admin application) can i avoid that table replication?
I was thinking of implementing the authenticate and get_user methods as the doc says but that implies the instantiation of the User class, so the next question would be: can the auth.models.User class be instantiated without having the actual Django User table?

The short answer to your question is - yes, it can. Simply set the managed property to False on the User model.

You should map the user from the external authentication into the auth.User object.

Remove django.contrib.auth from the INSTALLED_APPS setting.

Is there a particular reason you don't want the table to be created? If you write (or use a pre-existing) LDAP authentication backend, the User objects will be stored in the table, but they won't have any password information stored, and you can easily update fields like email address and name during the authentication process, so you won't create a disconnect between information stored in LDAP and managed in the Django table (i.e., you can continue updating auth information from LDAP, and don't have to worry about also updating it in the Django DB).

There's no way to avoid the table and still have any sort authentication. The "alternative" authentication methods still make use of the auth_user table, they just authenticate via another means.

Related

Django app has multiple database and multiple user

I have written one Django cloud based app. This app will have multiple user and for them multiple database, so that their data should be separate and they can save only to same database.
1) How can we implement it
2) How to automatically one user from login page to assign the database to write on it.
I don't have a complete answer, since you do not give a lot of detail. But here are a couple ots that f hinDjango supports custom database router implementations. A database router is a class that helps django decide which database to use for a particular model. Unfortunately I don't think this mechanism is granular enough for your needs. You can also specify the database to use in your code by using using(name) queryset method and save(using=name) form of save() method for instances. Of course this also means that some features of Django are going to be unvailable to you, since you cannot always expect to have a user. Look at the docs here for more info
https://docs.djangoproject.com/en/dev/topics/db/multi-db/

Why does django need a database for custom authentication backends?

I implemented a django custom authentication backend. My authenticate() returns a user object like this return User(username=username, password=password), but I never store the User object to a database.
Why do do the django docs recommend creating a database with user objects? (https://docs.djangoproject.com/en/1.4/topics/auth/#writing-an-authentication-backend - "...the best way to deal with this is to create a Django User object for each user that exists for your backend...")
If I try calling login(), there's a call made to the database. If logins are stored in sessions, why is a database necessary? (Using cached sessions)
The reason why you specifically need to save the User object is that it's common for apps to create database level relationships between objects and users (in order to persist the relationship across multiple requests).
A simple example would be the activity log in django.contrib.admin. It displays recent behaviour that users have performed. This only works when the user object is saved to the database.
Quite a few apps have a foreign key to auth.User; if you don't have that table populated then you don't get to use those apps.

Is data in Django’s request.POST object sanitised, at least enough for direct use in an ORM query?

I’m building a web forum using Django, including the built-in authentication module.
I’m using the built-in UserCreationForm to register users. However, as I‘ve decided to use e-mail addresses as the sole way to identify users, I’m generating a username for users before registering them.
To account for users who have already registered, before I generate a username, I check that a user doesn’t exist with the supplied e-mail address.
Is it safe to use the supplied e-mail address, directly from request.POST, in a query to the Django ORM, without doing any sanitisation on it? I can’t see anything in the documentation about data in request.POST being sanitised, but the ORM protects against SQL injection. Are there other potential attacks that I’m missing?
request.POST itself is not sanitized, but the Django ORM automatically sanitizes anything your throw at it, so yes, it's safe to simply pass it right to the ORM. Just be careful with using raw or extra.

Alternative Django Authenication

Need to integrate Django with an existing authentication system. That system has it's own database, API, login/logout,edit profile web pages and cookie.
(I may have to add a few additional profile fields stored/updated locally)
What's the proper approach to substitute the out-of-the-box authentication in Django?
The proper approach to substitute authentication from django's out-of-the-box to your own is to substitute your classes in the AUTHENTICATION_BACKENDS tuple in settings.py as described in http://docs.djangoproject.com/en/dev/topics/auth/#specifying-authentication-backends. This is incredibly useful for just the issue you're describing.
A good example of an authentication backend done this way is django-cas. This uses CAS to authenticate in a django application. You can use this as your template and just write hooks into your own authentication system identically.
HTH
I've created a custom authentication backend when I've had to do something similar to what you have to do. See: http://docs.djangoproject.com/en/dev/topics/auth/#writing-an-authentication-backend
In the authenticate function you call your api to authenticate the user, and then map them to a django.contrib.auth.model.User object on some primary key, like username for example. If the primary key is something other than username I usually create a mapping object, or put it into the profile object for the project.
This depends on how you want to handle the problem. If you don't need to keep the existing system running, your best bet is to import their data into the django project.
If the authentication system must stay in tact, you might have to write a wrapper for django.auth. I've done this in the past using SQLAlchemy http://www.sqlalchemy.org to integrate to the external database.
It might be helpful to take a look at the Django 1.2 multi-db support http://djangoadvent.com/1.2/multiple-database-support
In either case I'd try to get the user information into django.auth rather than to write your own authentication system.

Different authentication backend for the django admin

What would be the best solution to use a different authentication backend for the Django admin site?
See the documentation, which contains this quote:
The Django admin system is tightly
coupled to the Django User object
described at the beginning of this
document. For now, the best way to
deal with this is to create a Django
User object for each user that exists
for your backend (e.g., in your LDAP
directory, your external SQL database,
etc.) You can either write a script to
do this in advance, or your
authenticate method can do it the
first time a user logs in.