Mix View и ViewSet в просматриваемом файле api_root

У меня есть просматриваемый API:

restaurant_router = DefaultRouter()
restaurant_router.register(r'rooms', RoomsViewSet)
restaurant_router.register(r'printers', PrintersViewSet)
restaurant_router.register(r'shifts', ShiftsViewSet)

urlpatterns = patterns('',
    url(r'^$', api_root),
    url(r'^restaurant/$',
        RestaurantView.as_view(),
        name='api_restaurants_restaurant'),
    url(r'^restaurant/', include(restaurant_router.urls)),
)

В api_root я могу ссылаться на именованный маршрут:

@api_view(('GET',))
def api_root(request, format=None):
    return Response({
        'restaurant': reverse('api_restaurants_restaurant', request=request, format=format),
    })

Или я могу использовать API для просмотра, созданный с помощью DefaultRouter, как описано в документации:

Класс DefaultRouter, который мы используем, также автоматически создает API root для нас, поэтому теперь мы можем удалить метод api_root из нашего просмотра.

Что мне делать, если я хочу смешивать ViewSet и обычные представления и показывать все в одном корне API? DefaultRouter содержит только ViewSet, который он контролирует.

Ответ 1

Вы можете определять свои представления как ViewSets только одним методом. Таким образом, вы можете зарегистрировать его в маршрутизаторе, и он будет в одном пространстве с ViewSets.

http://www.django-rest-framework.org/api-guide/viewsets/

Ответ 2

Не похоже, что существует простой способ сделать это с помощью DefaultRouter, вам придется создать собственный маршрутизатор. Если это утешает логику DefaultRouter для создания представления APIRoot, достаточно просто, и вы, вероятно, можете легко свернуть свой собственный аналогичный маршрутизатор на основе класса DefaultRouter (например, изменить реализацию класса ApiRoot для извлечения дополнительных URL-адресов для включения, вы можете сделать это количество способов, например, передать их в конструктор маршрутизатора):

https://github.com/tomchristie/django-rest-framework/blob/86470b7813d891890241149928d4679a3d2c92f6/rest_framework/routers.py#L263

Ответ 3

Из http://www.django-rest-framework.org/api-guide/viewsets/:

Класс ViewSet - это просто тип представления на основе класса, который не предоставляет никаких обработчиков методов, таких как .get() или .post(), и вместо этого предоставляет такие действия, как .list() и .create()

Это означает, что мы можем расширить ваши ViewSets:

def other_rooms_view(request):
    return Response(...)


class RoomsViewSet(ViewSet):
    ...

    def list(self, request):
        return other_rooms_view(request)

restaurant_router = DefaultRouter()
restaurant_router.register(r'rooms', RoomsViewSet)