Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to get request parameters from an encoded URL in Django?

I am using Django Rest Framework.

The API receives GET requests with json objects encoded into the URL. For example:

/endpoint?%7B%0D%0A++%22foo%22%3A%5B%22bar%22%2C%22baz%22%5D%0D%0A%7D

Where the decoded parameters are

{
  "foo":["bar","baz"]
}

I can't find anything in the documentation for Django or DRF pointing to how the framework can handle this so that I get a QueryDict with the json objects in it by doing something like:

request.query_params # Should yield a dict -> {foo=[bar,baz]}

How can I decode JSON encoded URLs in Django Rest Framework?

Note that my actual parameters are much more complex. Using POST is not an because the caller relies heavily on caching and bookmarking

like image 571
ritratt Avatar asked Oct 14 '25 14:10

ritratt


2 Answers

The Django request.GET object, and the request.query_params alias that Django REST adds, can only parse application/x-www-form-urlencoded query strings, the type encoded by using a HTML form. This format can only encode key-value pairs. There is no standard for encoding JSON into a query string, partly because URLs have a rather limited amount of space.

If you must use JSON in a query string, it'd be much easier for you if you prefixed the JSON data with a key name, so you can at least have Django handle the URL percent encoding for you.

E.g.

/endpoint?json=%7B%0D%0A++%22foo%22%3A%5B%22bar%22%2C%22baz%22%5D%0D%0A%7D

can be accessed and decoded with:

import json

json_string = request.query_params['json']
data = json.loads(json_string)

If you can't add the json= prefix, you need to decode the URL percent encoding yourself with urllib.parse.unquote_plus(), from the request.META['QUERY_STRING'] value:

from urllib.parse import unquote_plus
import json

json_string = unquote_plus(request.META['QUERY_STRING'])
data = json.loads(json_string)
like image 194
Martijn Pieters Avatar answered Oct 17 '25 08:10

Martijn Pieters


urllib ought to do it:

from urllib.parse import unquote
url = "endpoint?%7B%0D%0A++%22foo%22%3A%5B%22bar%22%2C%22baz%22%5D%0D%0A%7D"
url = unquote(url)
print(url)

The above almost works, but the encoding might be incorrect, not sure:

endpoint?{
++"foo":["bar","baz"]
}
like image 27
Richard Dunn Avatar answered Oct 17 '25 07:10

Richard Dunn



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!