I have a Device model in django and I would like to be able to authenticate it.
class Device(models.Model):
device_key = models.CharField(max_length=100)
udid = models.CharField(max_length=100, unique=True)
To be more specific, given the above Device model, I would like to be able to achieve something similar to TokenAuthentication (http://django-rest-framework.org/api-guide/authentication.html#tokenauthentication).
Sending a request to a login URL with the device_key and udid should return a token, which identifies the Device model, and can be used for further requests.
Note:
Devices are NOT Users. I already use the User model for different purposes.
This question is basically similar to asking how do I authenticate a custom user model in django, which does not have a decent answer either (Django custom User model authentication)
Is there a "django" way to do this?
Related
I have a model called Lead which represents my possible future_customer.
In order to update a boolean field called is_approved in this model, I'm sending an email to the Lead's email ID along with a URL and this URL will take you to a page in my website where it asks for Approval.
How do I deal with permissions in Django Rest framework views? There is no django user associated with Lead model and I cannot use any authentication related classes.
Obscured url along with AllowAny permission is good enough?
What generally happens in a normal scenario for validation of emails is that they generate a unique token for the corresponding email. Then they when the user clicks on the email. He is taken to a page where there could be form submit which takes to a POST page or just validates directly.
The only security is that the unique id is just unique and there is a very rare chance for someone generate those id's via brute-force. That's the only security. You can add a expire also that makes the link valid only for few days.
You find the corresponding email associated with the same and update is_approved field accordingly.
Your model and view should look something like this.
class Lead(models.Model):
email = models.EmailField()
unique_id = models.CharField(default=uuid.uuid4)
is_approved = models.BooleanField(default=False)
def get_absolute_url(self):
return reverse('lead_verification', kwargs={'unique_id': self.unique_id})
class LeadVerificationView(APIView):
def post(self, unique_id):
lead = Lead.objects.get(unique_id=unique_id)
lead.is_approved = True
lead.save()
I using django from last 4-5 months and recently started learning django-rest-framework and I'm confused about proper authentication system,
Actually I am trying to build an application mostly using REST API because my
client can be both browser and Android,
so I need an authentication system in which user can sign up using both django
built-in auth(django.contrib.auth.model.User) as well as third-party social
authentication(Google, Facebook, etc..).
Now, I'm confused about how do I create my database, because when ever i'll create
a table/model lets say a 'Book', then this model would need a foreign key to the user model and here user can be both 'django.contrib.auth.model.User' and a user signed-up using third party auth,
So how I will refer to User in foreign key Field of my models?
And I have also decided to customize django's buit-in auth because i want
user to login using their email not username.
class Book(models.Model):
title = models.CharField(...)
author = models.ForeignKey(?) ? Here, how do i refer to both
'django.contrib...User' and users signed-up
using thrid-party auth.
Let me elaborate on your question.
First of all: You're lucky. There's an (almost) out of the box version for your problem.
For social and normal authentication and registration, including email verification etc. you can rely on django-allauth:
https://github.com/pennersr/django-allauth
django-restauth provides a restful platform built on top of all-auth, so that you don't even have to start building your auth rest api from scratch:
https://github.com/Tivix/django-rest-auth
When it comes to your db schema, there are a few options. You could go ahead and build your own authentication system, which, in my opinion, is overkill.
Rather more, I would implement a profile model, which has a OneToOne relationship to the User model from django.contrib.auth.models.User as described in this chapter of the Django docs.
Your models (of course in separated apps) would look like this:
from django.contrib.auth.models import User
from django.db import models
#other imports
class UserProfile(models.Model):
user = models.OneToOneField(User, related_name='profile')
books_read = models.IntegerField(default=0)
books_recommended = models.IntegerField(default=0)
class Book(models.Model):
title = models.CharField(...)
author = models.ForeignKey('UserProfile', related_name='books')
Another question you will run into is how to update and/or display those nested relations in your serializers.
This FAQ article from the django-restauth docs and this chapter of the official django-rest_framework docs will get you jumpstarted.
Best,
D
My case is related to a purchase, the customer who buys something and the seller who sold it.
Models.py
from django.contrib.auth.models import User
class buy(models.Model):
customer = models.ForeignKey(User)
seller = models.ForeignKey(User)
I am aware that the above code is wrong, I write it that way so the question is understood.
I take the django.contrib authentication system, to avoid having to make another authentication system for clients and one for sellers, I want django code reuse.
A solution had thought of creating another data model to sellers or customers, but in my view and in the login I'm using django.contrib, then I would still use this system authentication would like to know if there is any way or if I ultimately that create another authentication system?
I'm just guessing, if you have a Product model that has a user field in which case he's the actual seller, why don't you use seller = models.ForeignKey(Product, to_field='user')
I just included python social auth and added Facebook login. I have a Profile model where I save some user data like "description" and "username".
class Profile(models.Model):
username = models.CharField(max_length=75)
user_des = models.CharField(max_length=250, blank=True, null=True)
...
How do I relate the user's Facebook account to the existing model, and where do I save that relation?
Looking at the social auth docs I found that you can specify custom user models using this in your settings.py:
SOCIAL_AUTH_USER_MODEL = 'myapp.CustomUser'
In your case it will be:
SOCIAL_AUTH_USER_MODEL = 'myapp.Profile'
The docs I found this on are here:
http://django-social-auth.readthedocs.org/en/latest/configuration.html#custom-user-model
They also include documentation of ORMs here:
http://django-social-auth.readthedocs.org/en/latest/configuration.html#orms
edit:
By default social-auth uses the
django.contrib.auth.User
model to save users, the documentation can be found here:
https://docs.djangoproject.com/en/dev/ref/contrib/auth/
For my needs builtin model User is not enough... So I have my own model UserProfile and I want make authentication on site through this model (UserProfile does not inherit from User model and not related to it at all).
My Model:
class UserProfile(models.Model):
password = models.CharField(max_length = 40)
email = models.EmailField(max_length = 72, unique = True)
## Add this so that you can use request.user.is_authenticated
def is_authenticated(self):
return True
But builtin authentication uses model User.
So I want to understand how can I change that, so authentication use my model UserProfile with all auth features???
A good tutorial would be great!
(Step by step in views, models and authentication)
PS: I know I can store extra data in other model but I don't want that
Here's an even more extreme example but illustrates that what you want to do can be done. The author not only replaces the User model which the authentication backend uses but also uses SQLAlchemy instead of the Django ORM. http://tomforb.es/using-a-custom-sqlalchemy-users-model-with-django
The main point is that you need to write your backend authenticate and get_user methods to retrieve your custom User model. If you want to also support permissions you would need to write has_perm.
I used this article and it worked good enough for me, hope it can be useful for you.
Sultan