私のコードには、ユーザーのビューセットがあります。私が欲しいのは、ReadOnlyModelViewSetが正常に実行する読み取り操作(/ users/42および/ users /)のみを許可することです。
さらに、新しいユーザーを登録するために[〜#〜] post [〜#〜]にアクセスできる/ users/register URLが必要です。
class UserViewSet(viewsets.ReadOnlyModelViewSet):
queryset = User.objects.all()
serializer_class = UserSerializer
@list_route(methods=['post'])
def register(request):
serializer = UserSerializer(data=request.DATA)
if serializer.is_valid():
user = User.objects.create_user(
username = serializer.init_data['username'],
password = serializer.init_data['password'],
)
return Response(serializer.data, status=status.HTTP_201_CREATED)
else:
return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
いくつかの質問:
これは正しいやり方でしょうか?
list_routeまたはdetail_routeデコレータに配置した場合、メソッドに特定のsignatureはありますか? detail_routeの例では、メソッドのシグネチャは常に同じであるためです。method_name(self、request、pk = None):
ありがとう!
あなたのコードはほぼ正しいです、あなたはちょうど登録メソッドに正しい署名を欠いています:
def register(self, request):
これは、 ドキュメント によると正しい署名です。さらに tests は、ルーティングに追加のパラメーターを渡すことは不可能であり、pkは常に@detail_route
なので、次のものが必要です。
@detail_route
def register(self, request, pk=None):
詳細ルートと
@list_route
def register(self, request):
リストルート用。
ただし、ModelViewSetが内部で行うように、組み込みの ViewSetMixinsを利用することをお勧めします :
from rest_framework import exceptions, mixins
class UserViewSet(mixins.CreateModelMixin,
mixins.RetrieveModelMixin,
mixins.ListModelMixin,
GenericViewSet):
queryset = User.objects.all()
serializer_class = UserSerializer
def create(self, request):
serializer = UserSerializer(data=request.DATA)
if serializer.is_valid():
user = User.objects.create_user(
username = serializer.init_data['username'],
password = serializer.init_data['password'],
)
return Response(serializer.data, status=status.HTTP_201_CREATED)
else:
return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
一般的なユーザーのサインアップについては、現在プロジェクトで作業している Django-registration-restframework もご覧ください。
個人的には、プロジェクトのModelViewSetに依存しており、適切に承認されたユーザーのみが特定のアクションを実行できることを確認しています。これを行うには、モデル全体の 権限 または Djangoガーディアン と組み合わせて使用できます)オブジェクト固有の権限。
特にREST APIを使用すると、最終的には、特定のユーザーがすべてのリクエストを細かく管理する必要なく、特定のオブジェクトに対してのみアクションを実行できるようになります。オブジェクトレベルの権限は、ここで使用します。
detail_routeおよびdetail_listは、@ actionを使用する代わりに、DRF 3.0では非推奨になります。
from rest_framework.decorators import action
@action(methods=['POST'], detail=True)
def sale(self):
...
このメソッドがそのエンドポイントによって表されるモデルの単一のインスタンスを説明する場合は、detail = Trueを使用し、そのモデルのクエリセットを表す必要がある場合はFalseを使用します。