Я хочу создать версию моего API, но не могу заставить работать функцию реверса.
Я следую схеме управления версиями пространства имен, предложенной на веб-сайте DRF: изменение пространства имен
Iу меня есть одно приложение под названием аутентификация и внутри папки аутентификации у меня есть:
authentication/
|
-- models.py, apps.py, admin.py
-- api_v1/
|
-- views.py
-- serializers.py
-- urls.py
В моем основном urls.py я определил
urlpatterns = [
url(r'admin/', admin.site.urls),
url(r'^api/v1/',include
('my_project.apps.authentication.api_v1.urls',namespace='v1'),
('my_project.apps.posts.api_v1.urls',namespace='v1')
),
url(r'^$', lambda _: redirect('http://localhost:8888/')),
]
Это аутентификация/api_v1/urls.py
from rest_framework.routers import DefaultRouter
from authentication.api_v1.views import UserViewSet
app_name = 'authentication'
router = DefaultRouter()
router.register(r'users', UserViewSet, base_name='authentication-user')
urlpatterns = router.urls
И когда я выполняю
./manage.py show_urls
/api/v1/users/ authentication.api_v1.views.UserViewSet v1:authentication-user-list
/api/v1/users/<pk>/ authentication.api_v1.views.UserViewSet v1:authentication-user-detail
Когда я пытаюсь вернуться, например, из оболочки, у меня появляется следующая ошибка:
> reverse('v1:authentication-user-detail', kwargs={'pk': '5'})
NoReverseMatch: Reverse for 'authentication-user-detail' not found. 'authentication-user-detail' is not a valid view function or pattern name.
> reverse('authentication:v1:posts-job-detail', kwargs={'pk': '5'})
NoReverseMatch: 'v1' is not a registered namespace inside 'authentication'
> reverse('v1:authentication:posts-job-detail', kwargs={'pk': '5'})
NoReverseMatch: 'authentication' is not a registered namespace inside 'v1'
НО, если я не добавлю namespace = 'v1' в URL-адреса приложения, например:
url(r'^api/v1/',include('my_project.apps.authentication.api_v1.urls')
Тогда обратные функции будут работать
> reverse('authentication:authentication-user-detail', kwargs={'pk':5})
> '/api/v1/users/5/'
Я думаю, что янеправильно называю реверс или, может быть, какая-то конфигурация?Потому что, если я вызываю API, например, через почтальона, конечная точка работает нормально.
ОБНОВЛЕНИЕ:
Я думаю, что проблема в том, что у меня одинаковое пространство имен для двух записей вмой главный urls.py я опоздаю.Я думаю, что решение состоит в том, чтобы иметь только одну запись в моих основных URL-адресах и переместить все остальные в другой файл.
ОБНОВЛЕНИЕ 2
Я думаю (я не уверенесли это правильно) я заставляю это работать так.В моем основном urls.py
api_v1 =[
url(r'^api/v1/',
include('my_project.apps.agreements.api_v1.urls')),
url(r'^api/v1/',
include('my_project.apps.authentication.api_v1.urls')) ]
urlpatterns = [
url(r'', include((api_v1,'v1'), namespace="v1")),
]
Если вместо этого в шаблоны URL я включаю вот так:
urlpatterns = [
url(r'', include(api_v1, namespace="v1")),
]
У меня появляется следующая ошибка: 'Указание пространства имен в include ()без предоставления app_name 'django.core.exceptions.ImproperlyConfigured: указание пространства имен в include () без предоставления app_name не поддерживается.Установите атрибут app_name во включенном модуле или передайте 2-кортеж, содержащий список шаблонов и app_name вместо этого.
Дело в том, что v1 в качестве второго аргумента, "app_name", фактически егоне имя приложения, я просто поместил его там, чтобы не было ошибки ....
Также теперь, наоборот, я должен сделать это так (работает):
reverse('v1:authentication:authentication-user-detail', kwargs={'pk': '5'})
'/api/v1/users/5/'
И не так, как я хотел, это:
reverse('v1:authentication-user-detail' . .
ОБНОВЛЕНИЕ 3
Для последней проблемы я решил ее, комментируя app_name внутри файла url из конкретного приложения,Так было бы
# app_name = 'authentication'
router = DefaultRouter()
router.register(r'users', UserViewSet, base_name='authentication-user')