Search code examples
pythonpython-requestsbasic-authentication

use headers and basic authentication in python requests


I have a test url

https://test.app.com/api/rest

In order to access the url and its contents, it is necessary to send headers as

headers={"Content-Type":"application/json"}

And also basic authentication is to be used, where credentials are

username=apple , password=ball

I have used

from requests.auth import HTTPBasicAuth

requests.post(URL,auth=HTTPBasicAuth(username, password),
                                 data=data,
                                 headers=headers)

Is this the correct way to send post request to a url also sending headers and basic authentication ?


Solution

  • In general: yes, it seems alright.

    But some notes/fixes/hints:

    1. BasicAuth can be used as just tuple, so auth=(username, password) is enough - docs say that BasicAuth is common that it they made it a shorthand

    2. When you do any request, you should save its result to know whether it was successful or nor and diagnose it. Usually r = requests.post(...) is enough. You can then either manually check r.status_code (and examine r.content) or do r.raise_for_status() to just get an error for 4xx and 5xx codes.

      r.raise_for_status() will raise an error only based on the code itself and what it seems. But sometimes r.content might provide info on what actually broke - e.g. "400 bad request", while response might have in its content what field is missing).

    3. As for json headers and data=data... another shorthand. data= requires you to pass data in a form that you want it to be sent directly. But requests lib knows that a lot of times we want to send json data, so they implemented a json= arguments - which takes care of converting your dict/list structure to json for you and sets the content-type header as well!

    So in your case:

    data = {"example": "data"}
    r = requests.post(URL, # save the result to examine later
                      auth=(username, password), # you can pass this without constructor
                      json=data) # no need to json.dumps or add the header manually!