Django休息框架没有索引Api Root中的自定义CBV

时间:2015-12-17 01:24:38

标签: django-rest-framework

在Django-rest-framework中我有一个简单的CBV

class LocationList(APIView):
    """
    List all locations (id and name)
    """
    def get(self, request, format=None):
        # Make connection to SQL server db
        dbargs = dict(
            DRIVER='{FreeTDS}',
            SERVER=django_settings.DB_HOST,
            PORT=django_settings.DB_PORT,
            DATABASE=django_settings.DB_NAME,
            UID=django_settings.DB_USER,
            PWD=django_settings.DB_PWD,
        )

        cnxn = pyodbc.connect(**dbargs)    
        # Query db
        curs = cnxn.cursor()
        select_locations_cmd = 'SELECT list_id, cast(list_name as text) FROM location_lists;'
        curs = curs.execute(select_locations_cmd)

        # Serialize
        sdata = [dict(list_id=lid, list_name=lname) for lid, lname in curs.fetchall()]

        # Close cnxn
        cnxn.close()

        return Response(sdata)

正如您所看到的,它只是查询外部数据库,手动序列化结果并将其返回到django-rest-framework Response对象中。

urls.py我有

router = routers.DefaultRouter()
router.register(r'someothermodel', SomeOtherModelViewSet)


urlpatterns = [url(r'^', include(router.urls)),
               url(r'^locationlists/$', LocationList.as_view(), name="weather-location-lists"),

               ]

这很好用,但我关心的是当我访问根API网址时,它只显示someothermodel的端点,该端点是通过路由器注册的并使用了标准的ViewSet。它根本不列出locationlists端点。 我可以访问浏览器中的/locationlists端点(或者在没有问题的情况下发出GET请求),但它没有编入索引

如何在根目录下对其进行索引?所以它和

一起出现
Api Root
HTTP 200 OK
Allow: GET, HEAD, OPTIONS
Content-Type: application/json
Vary: Accept

{
    "someothertask": "http://127.0.0.1:8000/someothertask/",
}

2 个答案:

答案 0 :(得分:1)

您所指的页面由路由器供电,在您的情况下LocationList未通过路由器注册。因此它不会出现在端点列表中。

@Linovia指出,路由器只处理视图集。通过一些更改,这很容易实现:

# views.py
from rest_framework.viewsets import ViewSet

class LocationList(ViewSet):

    def list(self, request, format=None):  # get -> list
        ...

# urls.py
router = routers.DefaultRouter()
router.register(r'someothermodel', SomeOtherModelViewSet)
router.register(r'locationlists', LocationList, base_name='weather-location')

urlpatterns = [
    url(r'^', include(router.urls)),
]

您现在应该看到:

{
    "someothertask": "http://127.0.0.1:8000/someothertask/",
    "locationlists": "http://127.0.0.1:8000/locationlists/",
}

值得注意的是,您的视图的反向名称现已从weather-location-lists更改为weather-location-list,但希望这可能是对可能使用过的地方的微小更改。

答案 1 :(得分:0)

路由器仅适用于ViewSet