2014-04-12 16 views
13

Ich verfolge this tutorial aber diese Probleme, denen ich nicht beheben kann:Django Rest Framework Benutzerregistrierung?

  1. Nach Benutzer registrieren, kann ich nicht mit dem Benutzer zu dem api melden Sie sich an, da das Kennwort nicht „Invalid Passwortformat oder unbekannt gehasht Hashalgorithmus. " in Admin
  2. kann ich keine Beiträge zu 'api/Konten' oder das Formular in der browseable api sehen, wenn ich nicht in den api angemeldet bin

Mein Code:

from django.contrib.auth.models import User 
from rest_framework import serializers 

class UserSerializer(serializers.ModelSerializer): 
    class Meta: 
     model = User 
     fields = ('password', 'first_name', 'last_name', 'email') 
     write_only_fields = ('password',) 

    def restore_object(self, attrs, instance=None): 
     # call set_password on user object. Without this 
     # the password will be stored in plain text. 
     user = super(UserSerializer, self).restore_object(attrs, instance) 
     user.set_password(attrs['password']) #somehow not hashing 
     return user 
+1

In DRF 3.0, 'write_only_fields = ('Passwort',)' geändert, um 'extra_kwargs = { 'Passwort': { 'WRITE_ONLY': True} }} –

+1

Eine andere gute Lösung: http://stackoverflow.com/questions/27468552/changing-serializer-fields-on-the-fly/#answer-27471503 –

Antwort

1

Bitte beachten Sie, dass set_password() speichert das Objekt NICHT und seit Sie den Super als erstes aufgerufen haben, ist Ihr Objekt bereits mit einem rohen Passwort gespeichert.

Verwenden Sie einfach post_save(), um das Passwort zu speichern.

def post_save(self, obj, created=False): 
    """ 
    On creation, replace the raw password with a hashed version. 
    """ 
    if created: 
     obj.set_password(obj.password) 
     obj.save() 
+0

Dies funktioniert möglicherweise nicht in DRF 3.0.2 – wsgeorge

+3

Dies funktioniert nicht Arbeit in DRF 3.x. – Divick

13

Ich versuchte die akzeptierte Antwort in DRF 3.0.2 und es hat nicht funktioniert. Das Passwort wurde nicht gehackt.

Stattdessen überschreiben die create-Methode in Ihrem Modell Serializer

def create(self, validated_data): 
     user = User(email=validated_data['email'], username=validated_data['username']) 
     user.set_password(validated_data['password']) 
     user.save() 
     return user 

Dieses Hashes das Passwort, wenn Sie einen Benutzer mit dem Rest Rahmen schaffen, nicht post_save

+2

Es könnte einfacher sein, Benutzer.objects.create_user (** valided_data) zu verwenden, um den Benutzer (mit Hash-Passwort) zu erstellen, anstatt es in zwei Zeilen zu tun, – aensm

-1

Wir können ein Signal in Benutzer schreiben zu lösen Dies.

def create_hash(sender, instance=None, *args, **kwargs): 
passwd = instance.password 
instance.set_password(passwd) 


pre_save.connect(create_hash, sender=User) 
2

Ich habe wsgeorge 's Lösung verwendet, um mein eigenes zu bauen. Ein leeres User Objekt erstellt wird, nur so kann ich .set_password() verwenden:

def create(self, validated_data): 
    user = User() 
    user.set_password(validated_data['password']) 
    validated_data['password'] = user.password 
    return super(UserSerializer, self).create(validated_data) 

Anders als bei seiner Antwort, ich speichere nicht den Benutzer selbst. Ich überlasse das der Elternklasse, die super aufruft.

6

Ein weiterer Ansatz für die DRF 3.X:

from django.contrib.auth import get_user_model 
from django.contrib.auth.hashers import make_password 

    def create(self, validated_data):  
     if validated_data.get('password'): 
      validated_data['password'] = make_password(
       validated_data['password'] 
      ) 

     user = get_user_model().objects.create(**validated_data) 

     return user 
+0

Sie sind perfekt –

Verwandte Themen