Django Rest Framework GET request with params - django

I'm trying to make a get request with params (srcFilename) in Django Rest Framework. I'm pretty confused about where to add the "req.query.srcFilename" (as it would be in javascript) in django. I read I have to add the complete url with the params in "<>" as shown in the code below, but it wont find the url.
views.py:
#api_view(['GET'])
def api_generate_signed_url(request, srcFilename):
print(f'srcFilename: {srcFilename}')
bucket = storage_client.bucket(bucket_name)
blob = bucket.blob(srcFilename)
if request.method == 'GET':
url = blob.generate_signed_url(
version="v4",
# This URL is valid for 15 minutes
expiration=datetime.timedelta(minutes=15),
# Allow GET requests using this URL.
method="GET",
)
print(f"Generated GET signed URL: {url}")
return Response(url)
urls.py:
from django.urls import include, path
from rest_framework import routers
from .views import api_generate_signed_url
router = routers.DefaultRouter()
urlpatterns = [
path('', include(router.urls)),
path('api-auth/', include('rest_framework.urls', namespace='rest_framework')),
path(r'signedurl?srcFilename=<srcFilename>', api_generate_signed_url),
]
When trying this in Postman I get the following error:
The current path, signedurl, didn't match any of these.
Postman screenshot

You have to change your path as below...
path('signedurl', api_generate_signed_url),
No need to write ?srcFilename=<srcFilename>. Just remove it.
Then in your view access your request parameters through the QueryDict request.query_params.get('srcFilename').

Related

Show 'POST' method API in urls.py and browser url list

Currently I got create a new API with method('POST')
how I can set it in the urls.py
so that when I runserver, at the browser able to found this API
view.py
#transaction.atomic
#api_view(['POST'])
def posting_simain_api(request,):
print("Start Time"+ str(panda.panda_toda
urls.py
from django.urls import include, path, include
from rest_framework import routers
from . import views
router = routers.DefaultRouter()
router.register(r'ts_TsSimain', views.TsSimainViewSet)
router.register(r'ts_TsSimain_parent', views.TsSimainViewSet_parent)
urlpatterns = [
path('', include(router.urls)),
path('posting_simain_api', views.posting_simain_api, name='posting_simain_api'),
path('api-auth/', include('rest_framework.urls', namespace='rest_framework'))
]
Question is
how I going to show this API in this list?
enter image description here
I want to show the API in the list here, so that Frontend Developer able to know what API are ready

How to reverse path for custom user when testing Django Rest Framework

I'm building a Django 3 app using a Custom User. I'm trying to test the Custom User, but I can't get the url using reverse. I'm using Django Rest Framework. I'm using Django Rest Auth.
myapp.api.urls.py:
app_name = 'myApp'
from django.urls import include, path, re_path
urlpatterns = [
...
path('users/', include('users.urls'), name='UsersURLS'),
]
myapp.users.urls.py
from django.urls import include, path
from . import api
app_name = 'users' # namespace for reverse
urlpatterns = [
path('', api.UserListView.as_view(), name='UsersPath'),
]
myapp.users.api.py
class UserListView(generics.ListCreateAPIView):
queryset = models.CustomUser.objects.all()
serializer_class = serializers.UserSerializer
authentication_classes = (TokenAuthentication,)
And in test_users_api.py:
from users.api import UserListView
user_detail_url = reverse('myApp:UsersURLS-list')
...
def test_user_detail(self):
self.client.force_authenticate(user=self.user)
response = self.client.post(user_detail_url, {'pk': self.user.id }, format='json')
Whatever I try for the reverse, I get an error that is it not a valid view or function name. So far I have tried:
reverse('myApp:UsersURLS-list')
reverse('users:UsersPath-list')
reverse(UserListView)
reverse('UsersPath')
I'd be grateful for any idea what I'm doing wrong, and how to get the reverse URL. I have it working for the rest of my endpoints which use router, but I can't see what's needed for my Custom User, which I set up following a tutorial and it works fine otherwise.
I found an answer in the rest-auth source code, at venv36/lib/python3.6/site-packages/rest_auth/tests/test_api.py, and mixins.py in the same folder. I don't know why my attempts to reverse fail, but this works:
user_detail_url = reverse('rest_user_details')
All names for reverse can be found in the mixins.py file.

404 Error while accessing API with tastypie

Just started with TastyPie to expose the data. Trying to tie together resources using tastypie.Api for urls.py.
But I get this error when I try to access them through localhost:api/**resource.
my api.py:
from tastypie.resources import ModelResource
from idg.models.molecule_dictionary import MoleculeDictionary
class MoleculeDictionaryResource(ModelResource):
class Meta:
queryset = MoleculeDictionary.objects.all()
# resource_name = 'moleculedictionary'
my url.py:
from django.conf.urls import url, include, patterns
from idg.api import MoleculeDictionaryResource
from django.contrib import admin
from tastypie.api import Api
from . import views
dictionary_resource = MoleculeDictionaryResource()
# private_api = Api(api_name='private')
# private_api.register(MoleculeDictionaryResource(), canonical=True)
urlpatterns = [
url(r'^$', views.index, name='index'),
# url(r'^exports/', include('data_exports.urls', namespace='data_exports')),
url(r'^api/', include(dictionary_resource.urls)),
]
Error:
Page not found (404)
Request Method: GET
Request URL: http://127.0.0.1:8000/api/moleculedictionary/?format=json
Using the URLconf defined in django_root.urls, Django tried these URL patterns, in this order:
^__debug__/
xadmin/
^idg/
^comments/
^admin/
The current URL, api/moleculedictionary/, didn't match any of these.
You're seeing this error because you have DEBUG = True in your Django settings file. Change that to False, and Django will display a standard 404 page.
Any suggestions ? I am not sure where I made a mistake. I have followed the tutorial (https://django-tastypie.readthedocs.org/en/latest/tutorial.html)
Uncomment line
resource_name = 'moleculedictionary'
in Your api.py file.
Try this:
private_api = Api(api_name='v1')
private_api.register(MoleculeDictionaryResource(), canonical=True)
url(r'^api/', include(private_api.urls)),
Then you should be able to access it with /api/v1/

Not able to add url in Django router

I am not able to add workers URL which is pointing to a method in views.py. In below urls.py configuration, I had created a DefaultRouter, and registered 6 URLs. First 5 are working good(They are Class Based Views), however the last URL(workers, which is method based view) is not working. This URL is not matched with any of the URLs listed in url.conf. Error message I am getting 'Using the URLconf defined in maidFactory.urls, Django tried these URL patterns, in this order:. . . . . . .The current URL, workers/, didn't match any of these.'
router = routers.DefaultRouter()
router.register(r'users', views.UserViewSet)
router.register(r'groups', views.GroupViewSet)
router.register(r'slots', views.SlotViewSet)
router.register(r'city', views.CityViewSet)
router.register(r'location',views.LocationViewSet,base_name='locationMy')
router.register(r'workers',views.WorkerViewSet,base_name='getWorkersBySlotAndLocation')
# Wire up our API using automatic URL routing.
# Additionally, we include login URLs for the browsable API.
urlpatterns = [
url(r'^', include(router.urls)),
#url(r'^', include('maidFactory.api.urls')),
url(r'^admin/', include(admin.site.urls)),
url(r'^auth/', include('rest_framework_social_oauth2.urls')),
url(r'^api-auth/', include('rest_framework.urls', namespace='rest_framework'))]
My method based view is as follows:
def WorkerViewSet(request):
cursor = connection.cursor()
#cursor.execute("UPDATE bar SET foo = 1 WHERE baz = %s", [self.baz])
cursor.execute("select p.wid,p.fname, a.description from workerProfile as p, workerAccount as a where a.isactive=1 and a.wid=p.wid")
row = cursor.fetchone()
return HttpResponse(row)
Your WorkerViewSet is not a actual DRF ViewSet but a Django function-based view returning Django HttpResponse.
You should convert it to a proper DRF viewset and then register your router with this viewset.
Another option is to add this as a url in urlpatterns in your urls file and it should work perfectly.
urlpatterns = [
url(r'^my/url/path/$', my_views.WorkerViewSet), # This will work
....
]

DRF Browsable API only shows one Router

Essentially, depending on the order in which I add my routes to my urlpatterns the browsable API will only show one router at a time. Here's my code:
urls.py:
from django.conf.urls import url, include
from rest_framework import routers
from .views import PlantViewSet
# url router
router = routers.DefaultRouter()
router.register(r'plants', PlantViewSet, base_name='Plants')
djoser_urls = [url(r'^', include('djoser.urls')), ]
urlpatterns = [
url(r'^api-auth/', include('rest_framework.urls', namespace='rest_framework')),
url(r'^docs/', include('rest_framework_swagger.urls')),
# url(r'^', include(router.urls)),
# url(r'^', include('djoser.urls')),
] + djoser_urls + router.urls
This only displays the djoser urls:
However simply reversing the order in which I add the urls:
urls.py:
from django.conf.urls import url, include
from rest_framework import routers
from .views import PlantViewSet
# url router
router = routers.DefaultRouter()
router.register(r'plants', PlantViewSet, base_name='Plants')
djoser_urls = [url(r'^', include('djoser.urls')), ]
urlpatterns = [
url(r'^api-auth/', include('rest_framework.urls', namespace='rest_framework')),
url(r'^docs/', include('rest_framework_swagger.urls')),
# url(r'^', include(router.urls)),
# url(r'^', include('djoser.urls')),
] + router.urls + djoser_urls
This only displays the router urls!
The same thing happens when I just use the include() lines I've commented out, whichever comes first in the list is the only router that gets displayed. Furthermore, no matter which router gets picked up the api-auth/ and docs/ urls are never shown. Is there anyway to get a unified api root without having to create my own custom view?
This doesn't have anything to do with Django REST framework, it happens because of how Django deals with duplicate urls.
You are trying to have a single url be handled by two different views: The DRF router index and the djoser root view. Django will only display the first view matching the search pattern that it finds, which is generally the first urls that are included in the url patterns.
Django REST framework will also not detect multiple routers that are available and group them together on the same page, which is sounds like you are hoping to see. Even if it could, djoser doesn't use a router so there is no way that DRF could actually know to include it.
Is there anyway to get a unified api root without having to create my own custom view?
So to answer the main question: No it is not possible for Django REST framework to automatically group these views together. You are going to need to create your own customer view to handle this.