Python POST ordered params - python

I have a web service that accepts passed in params using http POST but in a specific order, eg (name,password,data). I have tried to use httplib but all the Python http POST libraries seem to take a dictionary, which is an unordered data structure. Any thoughts on how to http POST params in order for Python?
Thanks!

Why would you need a specific order in the POST parameters in the first place? As far as I know there are no requirements that POST parameter order is preserved by web servers.
Every language I have used, has used a dictionary type object to hold these parameters as they are inherently key/value pairs.

Related

REST API url design

I have a REST API that has a database with table with two columns, product_id and server_id, that it serves product_ids to specific servers which request the data(based on the server_id from table).
Let's say I have three servers with server_ids 1,2 and 3.
My design is like this: /products/server_id/1 and with GET request I get json list of product_ids with server_id = 1, similarly /products/server_id/2 would output list of product_ids for server_id = 2.
Should I remove these routes and make a requirement to send POST request with instructions to receive product_ids for specific server_id in /products route only?
For example sending payload {"server_id":1} would yield a response of list of product_ids for server_id = 1.
Should I remove these routes and make a requirement to send POST request with instructions to receive product_ids for specific server_id in /products route only?
Not usually, no.
GET communicates to general purpose components that the semantics of the request message are effectively read only (see "safe"). That affordance alone makes a number of things possible; for instance, spiders can crawl and index your API, just as they would for a web site. User agents can "pre-fetch" resources, and so on.
All of that goes right out the window when you decide to use POST.
Furthermore, the URI itself serves a number of useful purposes - caches use the URI as the primary key for matching a request. Therefore we can reduce the load on the origin server by re-using representations have have been stored using a specific identifier. We can also perform magic like sticking that URI into an email message, without the context of any specific HTTP request, and the receiver of the message will be able to GET that identifier and fetch the resource we intend.
Again, we lose all of that when the identifying information is in the request payload, rather than in the identifier metadata where it belongs.
That said, we sometimes do use the payload for identifying information, as a work around: for example, if we need so much identifying information that we start seeing 414 URI Too Long responses, then we may need to change our interaction protocol to use a POST request with the identifying information in the payload (losing, as above, the advantages of using GET).
An online example of this might be something like an HTML validator, that accepts a candidate document and returns a representation of the problems found. That's effectively a read only action, but in the general case an HTML document is too long to comfortably fit in the target-uri of an HTTP request.
So we punt.
In a hypermedia api, like those used on the world wide web, we can get away with it, because the HTTP method to use is provided by the server as part of the metadata of the form itself. You as the client don't need to know the server's preferred semantics, you just need to know how to process the form data.
For instance, as I type this answer into my browser, I don't need to know what the target URI is, or what HTTP method is going to be used, because the browser already knows what to do (based on the HTML and whatever scripts are running "on demand").
In REST APIs, POST requests should only be used in order to create new resource, so in order to retrieve data from server, the best practice is to perform a GET request.
If you want to load products 1,2,4,8 on server 9 for example, you can use this kind of request :
GET https://website/servers/9/products/1,2,4,8
On server side, if products value contains a coma separated list, then return an array with all results, if not return just an array with only one item in order to keep consistency between calls.
In case you need to get all products, you can keep only the following url :
GET https://website/servers/9/products
As there is no id provided in products parameter, then the server should return all existing products for requested server parameter.
Note : in case of big amount of results, they must by paginated.

Get Headers/Cookies from Bottle API request

I was making an API call to a Bottle service and was passing headers in the call using Python's request Library.
requests.get('http://localhost/API/call', headers={"cat":"tax"})
I wanted to get the custom headers passed in the function that gets called through the API call.
Using bottle.request.headers I get the following data:
Now, the custom header I passed is present in the environ dictionary with key/value 'HTTP_CAT':tax.
Same thing for cookies. Cookie data can be retrieved using bottle.request.cookies
How can I filter out only the custom header that I am passing in the request?
I'm not sure exactly what you mean by "filter," but the typical way to retrieve request headers from Bottle is with get_header:
cat_value = request.get_header('cat')
Bottle also has a specific API for retrieving individual cookies. Perhaps there's a good reason you're going down to the raw environ, but if not, then you should be using these built-in methods.
PS, you may also want to prefix your custom headers with "X-", e.g. X-Cat.

Distinguish data received via POST and GET in Cherrypy

The variable cherrypy.request.params as it is described in the API contains the query string and the POST variables in a dictionary. However combing over this, it seems that it contains every variable received after processing the full request URI to pull the GET data. This then becomes indistinguishable from POST data in the dictionary.
There seems to be no way to tell the difference, or perhaps I am wrong.
Can someone please enlighten me as to how to use purely posted data and ignore any data in the query string beyond the request URI. And yes I am aware I can find out whether it was a POST or GET request but this does not stop forgery in requests to URIs containing GET data in a POST request.
>http://localhost:8080/testURL/part2?test=1
>POST username = test
"cherrypy.request.params" has 2 variables
test = 1
username=test
The docs aren't very clear on this point, but starting in CherryPy 3.2, you can reference request.body.params to obtain just the POST/PUT params. In 3.2 and below, try request.body_params. See http://docs.cherrypy.org/dev/refman/_cprequest.html#cherrypy._cprequest.Request.body_params

Request current route including query strings?

I've been looking in the Pyramid API and haven't been able to find a method that allows me to extract the url in the user's address bar, specifically including the query strings. Is there a method I keep skimming across?
http://docs.pylonsproject.org/projects/pyramid/dev/api/request.html
It sounds like you just want request.url which is whatever the user typed in the address bar.
request.GET is a dictionary of key/values in the query string.
request.POST is a dictionary of key/values in the request body.
request.params is a dictionary of the combination of both.
This might be better explained in the webob documentation, which is effectively what Pyramid is using for its request and response objects.
http://docs.webob.org/en/latest/index.html
Now one can use request.query_string if you only want the URL-encoded text after the ? (ie id=10&name=Bob)
http://docs.pylonsproject.org/projects/pyramid/en/latest/narr/webob.html

Distinguishing between GET and POST data in CherryPy?

I've been deciding between Python web frameworks for a project of mine and I've really liked how lightweight, flexible, and concise CherryPy is compared to others. The only problem I'm having is I can't find any documentation on how to distinguish between data sent via GET and via POST.
For example, I don't want users to be able to provide their login credentials through a GET request (http://example.com/login?username=user&password=pass) but, according to CherryPy's tutorial, all data is sent as method parameters, no matter what HTTP method they're sent as. Is there some way to say I only want the POST data or do I have to use MethodDispatcher?
Thanks!
See the docs.
A string containing the HTTP method, such as "GET" or "POST". Set
in the "run" phase.
looks like checking cherrypy.request.method is what you want to do.

Categories