2016-06-01 7 views
0

私はdjango authテーブルのUserモデルを拡張し、同じものに対して残りのAPIを実装していました。django restフレームワークでネストされたシリアライザを実装する方法は?

GET/POSTリクエストを実装する方法がわかりません。

マイmodels.pyコードは次のとおりです。

class UserProfile(models.Model): 
    """User profile model for information about user.""" 

    users = models.OneToOneField(User) 
    phone_regex = RegexValidator(regex=r'^\+?1?\d{9,15}$', message="Phone number must be entered in the format: '+999999999'") 
    phone_number = models.CharField(max_length=100, validators=[phone_regex], blank=True) 
    created_timestamp = models.DateTimeField(auto_now_add=True, null=True) 
    updated_timestamp = models.DateTimeField(auto_now=True, null=True) 

マイserializers.pyコードは次のとおりです。

class UserSerializer(serializers.ModelSerializer): 
    """Serializer for users.""" 

    class Meta: 
     model = User 


class UserProfileSerializer(serializers.ModelSerializer): 
    """Serializer for user profiles.""" 

    users = UserSerializer(many=True) 

    class Meta: 
     model = UserProfile 

    def create(self, validated_data): 
     users_data = validated_data.pop('users') 
     print 'yes' 
     print users_data 
     user_profile = UserProfile.objects.create(**validated_data) 
     for user_data in users_data: 
      user_data, created = User.objects.get_or_create(first_name=user_data['first_name'], last_name=user_data['last_name'], 
     username=user_data['username'], password=user_data['password'], email=user_data['email'], is_active=['is_active']) 
     user_profile.users.add(user_data) 
    return user_profile 

マイv1.pyコードは次のとおりです。

class UserProfileList(APIView): 
    """Get and post user profiles data.""" 

    def get(self, request, format=None): 
     """Get users.""" 
     user_profiles = UserProfile.objects.all() 
     serialized_user_profiles = UserProfileSerializer(user_profiles, many=True) 
     return Response(serialized_user_profiles.data) 

    def post(self, request, format=None): 
     """Post users.""" 
     serializer = UserSerializer(data=request.data) 
     if serializer.is_valid(): 
      serializer.save() 
     return Response(serializer.data, status=status.HTTP_201_CREATED) 
    return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST) 

私はこの問題を考えますv1.pyファイルにあります。私はGETとPOST要求をしたい、私はJSONデータを送信するPOST要求のために。誰かがその実装で私を助けることができますか?実際には、POSTリクエストを行い、UserモデルとUserProfileモデルの両方にデータを格納するための単一のエンドポイントが必要です。

答えて

1

上記のコードを

models.py

class UserProfile(models.Model): 
    user = models.OneToOneField(User) 
    phone_number = models.CharField(max_length=100, validators=[ 
    RegexValidator(regex=r'^\+?1?\d{9,15}$', message="Phone number must be entered in the format: '+999999999'") 
    ], blank=True, null=True) 
    created_timestamp = models.DateTimeField(auto_now_add=True, null=True) 
    updated_timestamp = models.DateTimeField(auto_now=True, null=True) 

Serializers.py

class UserSerializer(serializers.ModelSerializer): 
    class Meta: 
     model = User 

class UserProfileSerializer(serializers.ModelSerializer): 
    user = UserSerializer(required=True) 
    class Meta: 
     model = UserProfile 

    def create(self, validated_data): 
     user_data = validated_data.pop('user', None) 
     user = User.objects.create_user(**user_data) 
     return UserProfile.objects.create(user=user, **validated_data) 

    def update(self, instance, validated_data): 
     user_dict = validated_data.pop('user', None) 
     if user_dict: 
      user_obj = instance.user 
      for key, value in user_dict.iteritems(): 
       setattr(user_obj, key, value) 
      user_obj.save() 
      validated_data["user"] = user_obj 
     for key, value in validated_data.iteritems(): 
      setattr(instance, key, value) 
     instance.save() 
     return instance 

ビューセットを変更します。PY

from rest_framework import mixins 
from rest_framework import viewsets 

class MyUserViewSet(mixins.UpdateModelMixin, 
        mixins.CreateModelMixin, 
        mixins.ListModelMixin, 
        viewsets.GenericViewSet): 

    authentication_classes = (TokenAuthentication, SessionAuthentication) 
    permission_classes = (AllowAny,) 
    serializer_class = UserProfileSerializer 
    queryset = UserProfile.objects.all() 

フォローrouters

routers.pyこのリンク

from rest_framework import routers 
router = routers.SimpleRouter() 
router.register('users', MyUserViewSet) 

urls.py私が使用している

from .routers import router 
urlpatterns = patterns(
    url(r'^api/v1/', include(router.urls)), 
) 
+0

'URL(R '^ V1 /ユーザー/ $ '、csrf_exempt(userregistration.v1.MyUserViewSet.as_view({' get ':' queryset '})))、 'urls.pyファイルで' 'QuerySet'オブジェクトが呼び出せません。 – Ankit

+0

getパラメータに 'queryset'をマッピングしていれば、mapp {" get ":" list "}する必要があります。このリンクに従ってくださいhttp://www.django-rest-framework.org/api-guide/routers/#example –

+0

私はしようとしましたが、「MyUserViewSet」オブジェクトに属性「list」がありません。 – Ankit

0

BaseBaseUserをサブクラス化することでUserモデルを拡張することをお勧めします。これには、BaseUserManagerのサブクラス化も必要です。そうすれば、シリアライザを1つのクラスにするだけでシリアライザを単純化することができます。また、BaseUserManagerのサブクラス化も必要です。

カスタムユーザーは、必要な数のカスタムフィールドを持つことができます。デフォルトのユーザーモデルと一対一の関係を作成するよりも、ユーザーモデルをこのように拡張する方が一般に簡単です。それはあなたにいくつかの論理と時間を節約します。

あなたがここで詳細を読むことができます: https://docs.djangoproject.com/ja/1.9/topics/auth/customizing/#specifying-a-custom-user-model

は、ここでは、サブクラスBaseUserManagerを行うだろうかの例です:

class MyUserManager(BaseUserManager): 
    def create_user(self, email=None, password=None, dateofbirth=None, username=None): 
     user = self.model(
      email=MyUserManager.normalize_email(email),  
      dateofbirth=dateofbirth, 
      username=username 
     ) 

     user.set_password(password) 
     user.save(using=self._db) 
     return user 

    def create_superuser(self, username, dateofbirth, email, password): 
     user = self.create_user(email=email, 
        password=password, 
        username=username, 
        dateofbirth=dateofbirth, 
       ) 
     user.is_superuser = True 
     user.save(using=self._db) 
     return user 

ここでサブクラス化AbstractBaseUserの例です:

このため
class MyUser(AbstractBaseUser): 

    email = models.EmailField(
     verbose_name='email address', 
     max_length=255, 
     unique=True 
    ) 

    dateofbirth = models.CharField(max_length=30, blank=True) 

    is_active = models.BooleanField(default=True) 
    is_superuser = models.BooleanField(default=False) 

    USERNAME_FIELD = 'email' 

    objects = MyUserManager() 

    def get_full_name(self): 
     return self.email 

    def get_short_name(self): 
     return self.email 

    def __unicode__(self): 
     return self.email 

    def has_perm(self, perm, obj=None): 
     return True 

    def has_module_perms(self, app_label): 
     return True 

    @property 
    def is_staff(self): 
     return self.is_superuser 

あなたがあなたのsettings.pyにauthユーザモデルを設定して、あなたのdjangoアプリがあなたが私たちであることを知らせる必要がありますカスタム・ユーザー・モデルINGの:ここで

AUTH_USER_MODEL = 'myapp.MyUser' 

することは簡単な部分です - シリアライザ:あなたはそれでいる間

class MyUserSerializer(serializers.ModelSerializer): 
    password = serializers.CharField(write_only=True, required=True) 

    class Meta: 
     model = MyUser 
     fields = (
      'email', 
      'password', 
      'dateofbirth', 
      'username', 
     ) 

    def create(self, validated_data): 
     password = validated_data.pop("password", None) 
     email = validated_data.pop("email", None) 
     username = validated_data.pop("username", None) 
     user = MyUser.objects.create_user(email=email, password=password, username=username, gender=gender, dateofbirth=dateofbirth) 
     MyUser.objects.filter(id=user.id).update(**validated_data) 
     return user 

は、APIView忘れると使用はるかに簡単ビューセット:

class MyUserViewSet(viewsets.ModelViewSet): 
    authentication_classes = (TokenAuthentication, SessionAuthentication) 
    permission_classes = (AllowAny,) 
    serializer_class = MyUserSerializer 

これだけでGET、POST、PUT、DELETEリクエストがすべて処理されます。

関連する問題