0

我正在使用 Django v1.7dev 和 Django Rest Framework v2.3

我扩展了用户类如下:

class UserProfile(models.Model):
   user = models.OneToOneField(User)
   gang = models.ForeignKey('Gang', related_name='gangsters')

   def __unicode__(self):
       return self.user.username

User.profile = property(lambda u: UserProfile.objects.get_or_create(user=u)[0])

我还创建了一个用户序列化程序端点(当我发送 GET 请求时它不显示密码,但在我发送帖子时接受它,目的是使用它进行注册:

class UserSerializer(serializers.ModelSerializer):

class Meta:
    model = User
    fields = ('id', 'username', 'password', 'email')


def restore_object(self, attrs, instance=None):
    user = super(UserSerializer, self).restore_object(attrs, instance)
    user.set_password(attrs['password'])
    return user

def to_native(self, obj):
    ret = super(UserSerializer, self).to_native(obj)
    del ret['password']
    return ret

我很想扩展序列化程序以包含 gang 参数。类似的东西

gang = serializers.Field(source='profile.gang')

但可写而不是只读,因此当我注册用户时,我也可以插入帮派,可能以原子方式。在这种情况下,最好的方法是什么?我尝试过使用其他字段类型,但直到现在都没有成功。目前我正在发送两个单独的帖子(一个用于用户,一个用于用户配置文件,但我敢打赌有更好的方法......)

4

2 回答 2

0

这是我最终采用的解决方案,基于 Carlton 的链接问题(但有一些更改,因为用户需要为登录进行身份验证,但在注册期间无法进行身份验证:

class UserAuthView(APIView):

#Login. Returns the current user.
def get(self, request, *args, **kwargs):
    # Only UserProfileSerializer is required to serialize data
    if (request.user.is_authenticated()):
        serializer = UserProfileSerializer(
                instance=request.user.profile)
        return Response(serializer.data, status=status.HTTP_200_OK)

    return Response(status=status.HTTP_401_UNAUTHORIZED)


#Register new user.
def post(self, request, format=None):
    user_serializer = UserSerializer(data=request.DATA)
    errors = dict()
    if user_serializer.is_valid():
        user =user_serializer.save()
        data = request.DATA.copy()
        data['user'] = User.objects.latest('id').id
        user_profile_serializer = UserProfileSerializer(data=data)

        if user_profile_serializer.is_valid():
            user_profile_serializer.save()
            return Response(user_profile_serializer.data, status=status.HTTP_201_CREATED)

        errors.update(user_profile_serializer.errors)
        return Response(errors, status=status.HTTP_400_BAD_REQUEST)


    errors.update(user_serializer.errors)
    return Response(errors, status=status.HTTP_400_BAD_REQUEST)
于 2013-11-01T11:02:09.820 回答
0

您可以采用两种通用方法:更新相关字段post_save()或使用两个序列化程序,并在处理请求之前要求两者都有效。

查看此问题以获取有关两者的更多详细信息

于 2013-10-24T08:18:02.360 回答