Django REST Framework: Could not resolve URL for hyperlinked relationship using view name

匿名 (未验证) 提交于 2019-12-03 08:59:04

问题:

I've extensively researched this fairly common issue, but none of the fixes worked for me. I'm building a Django project in REST framework and want to use hyperlinked relations. The User can have many Cars and Routes, which are independent. A Route is a collection of Positions.

These are my serializers:

class CarSerializer(serializers.HyperlinkedModelSerializer):     user = serializers.Field(source='user.username')     class Meta:         model = Car         fields = ('url', 'make', 'year', 'car_model', 'user')  class PositionSerializer(serializers.HyperlinkedModelSerializer):     class Meta:         model = Position         fields = ('url', 'drive_route', 'timestamp', 'latitude', 'longitude', 'altitude','speed','heading', 'accuracy', 'altitude_accuracy')  class DrivingRouteSerializer(serializers.HyperlinkedModelSerializer):     position = serializers.HyperlinkedRelatedField(view_name='position', many=True)     user = serializers.Field(source='user.username')     class Meta:         model = DrivingRoute         fields = ('url', 'id', 'route', 'position', 'user')  class UserSerializer(serializers.HyperlinkedModelSerializer):     routes = serializers.HyperlinkedRelatedField(view_name='routes-detail', many=True)     car = serializers.HyperlinkedRelatedField(view_name='car-detail', many=True)     class Meta:         model = User         fields = ('url', 'username', 'routes', 'car') 

And here are the views:

class CarViewSet(viewsets.ModelViewSet):     queryset = Car.objects.all()     serializer_class = CarSerializer     permission_classes = (permissions.IsAuthenticatedOrReadOnly,)     def pre_save(self, obj):         obj.user = self.request.user  class DrivingRouteViewSet(viewsets.ModelViewSet):     queryset = DrivingRoute.objects.all()     serializer_class = DrivingRouteSerializer     permission_classes = (permissions.IsAuthenticatedOrReadOnly,)     def pre_save(self, obj):         obj.user = self.request.user  class PositionViewSet(viewsets.ModelViewSet):     queryset = Position.objects.all()     serializer_class = PositionSerializer  class UserViewSet(viewsets.ReadOnlyModelViewSet):     queryset = User.objects.all()     serializer_class = UserSerializer 

And, for what it's worth, the URLs. I am using the Default Router, just as in the Django REST Framwork tutorial.

router = DefaultRouter() router.register(r'car', views.CarViewSet) router.register(r'routes', views.DrivingRouteViewSet) router.register(r'position', views.PositionViewSet) router.register(r'users', views.UserViewSet) 

Overall, this is almost exactly the same as in the tutorial. Loading the 'routes', 'car', and 'position' URLS works fine, but the 'users' URL throws the error "Could not resolve URL for hyperlinked relationship using view name 'routes-detail'."

回答1:

The view_name should typically be [route]-detail for routers, where [route] is the name of the model you registered the ViewSet under.

In your case, the view_name should be position-detail, not just position. You are also using routes-detail instead of drivingroutes-detail, which is using the long name because your model is DrivingRoute and not Route. You can override this by setting a base_name (third parameter) when using register on the router.

router = DefaultRouter() router.register(r'car', views.CarViewSet) router.register(r'routes', views.DrivingRouteViewSet, "routes") router.register(r'position', views.PositionViewSet) router.register(r'users', views.UserViewSet) 


回答2:

You have the following views:

  • car-list
  • car-detail
  • drivingroute-list
  • drivingroute-detail
  • position-list
  • position-detail
  • user-list
  • user-detail

If we take for example the following route:

router.register(r'car', views.CarViewSet) 

It means that it is accessible under http://yourapi.com/car/ for car-list and under http://yourapi.com/car/1/ for car-detail (where 1 is the id).

The view names get built out of the class name minus suffix ViewSet plus list or detail.

Change your code according to these rules and please try again.

Cheers!



易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!