1

我正在尝试使用 drf-nested-routers 创建嵌套 url 模式,如下所示:

/projects/{project_pk}/join_request/{pk}

使用我当前的设置,我能够/projects成功导航,并查看超链接的 join_requests 列表:

[
    {
        "url": "http://127.0.0.1:8000/projects/1/",
        "join_requests": [
            "http://127.0.0.1:8000/projects/1/join_requests/1/",
            "http://127.0.0.1:8000/projects/1/join_requests/2/"
        ],
        "name": "Sample Project"
    }
]

但是,当我单击 join_request 时,出现以下错误:

ImproperlyConfigured at /projects/1/join_requests/1/
Could not resolve URL for hyperlinked relationship using view name "projectjoinrequest-detail". You may have failed to include the related model in your API, or incorrectly configured the `lookup_field` attribute on this field.

作为一个 DRF 初学者,经过大量研究后,我无法确定我哪里出错了。如果有人可以发布示例或建议我在哪里配置错误,我将不胜感激:

在models.py中,我有:

class Project(models.Model):
    name = models.TextField()  # what is the name of the project

class ProjectJoinRequest(models.Model):
    request = models.TextField()
    user = models.ForeignKey(User, on_delete=models.CASCADE, related_name="join_requests", blank=True, null=True)
    project = models.ForeignKey(Project, on_delete=models.CASCADE, related_name="join_requests", blank=True, null=True)

class User(AbstractUser):
    name = models.TextField()

在 serializers.py 中:

from rest_framework_nested.relations import NestedHyperlinkedRelatedField

class ProjectSerializer(serializers.HyperlinkedModelSerializer):

    join_requests = NestedHyperlinkedRelatedField(
        many=True,
        read_only=True,
        view_name='projectjoinrequest-detail',
        parent_lookup_kwargs={'project_pk': 'project__pk'}
    )

    class Meta:
        model = models.Project
        fields = ["join_requests", "name"]

class ProjectJoinRequestSerializer(serializers.HyperlinkedModelSerializer):
    class Meta:
        model = models.ProjectJoinRequest
        fields = "__all__"

在views.py中:

class ProjectViewSet(viewsets.ViewSet):
    serializer_class = serializers.ProjectSerializer
    queryset = models.Project.objects.all()

    def list(self, request):
        queryset = models.Project.objects.filter()
        serializer = serializers.ProjectSerializer(queryset, many=True, context={"request" : request})
        return Response(serializer.data)

    def retrieve(self, request, pk=None):
        queryset = models.Project.objects.filter()
        project = get_object_or_404(queryset, pk=pk)
        serializer = serializers.ProjectSerializer(project, context={"request": request})
        return Response(serializer.data)

class ProjectJoinRequestViewSet(viewsets.ViewSet):
    serializer_class = serializers.ProjectJoinRequestSerializer
    queryset = models.ProjectJoinRequest.objects.all()

    def list(self, request, project_pk=None):
        queryset = models.ProjectJoinRequest.objects.filter(project=project_pk)
        serializer = serializers.ProjectJoinRequestSerializer(queryset, many=True, context={'request': request})
        return Response(serializer.data)

    def retrieve(self, request, pk=None, project_pk=None):
        queryset = models.ProjectJoinRequest.objects.filter(pk=pk, project=project_pk)
        project_join_request = get_object_or_404(queryset, pk=pk)
        serializer = serializers.ProjectJoinRequestSerializer(project_join_request, context={'request': request})
        return Response(serializer.data)

和 urls.py:

router = routers.DefaultRouter()
router.register(r'projects', views.ProjectViewSet)
projects_router = routers.NestedSimpleRouter(router, r'projects', lookup='project')
projects_router.register(r'join_requests', views.ProjectJoinRequestViewSet)
urlpatterns = [
    url(r'^', include(router.urls)),
    url(r'^', include(projects_router.urls)),
]
4

0 回答 0