Question

I am trying to connect to the FreshBooks API using python and httplib module. I have managed to do the job with the Requests package but because I am a starter, and want to learn, I would like also to make it work using the standard Python library.

So that's the code using httplib:

import base64, httplib

# test script created to connect with my test Freshbooks account

headers = {}
body = '/api/2.1/xml-in'
headers["Authorization"] = "Basic {0}".format(
    base64.b64encode("{0}:{1}".format('I have put here my Auth Token', 'user')))
headers["Content-type"] = "application/xml"

# the XML we ll send to Freshbooks
XML = """<?xml version="1.0" encoding="utf-8"?>
<request method="task.list">
  <page>1</page>
  <per_page>15</per_page>
</request>"""


# Enable the job
conn = httplib.HTTPSConnection('devjam-billing.freshbooks.com')
conn.request('POST', body, None, headers)
resp = conn.getresponse()
print resp.status
conn.send(XML)

print resp.read()
conn.close()

And that's what Freshbooks returns:

200                                                                                                                                                                                                                                                                               
<?xml version="1.0" encoding="utf-8"?>                                                                                                                                                                                                                                            
<response xmlns="http://www.freshbooks.com/api/" status="fail">                                                                                                                                                                                                                   
  <error>Your XML is not formatted correctly.</error>                                                                                                                                                                                                                             
  <code>40010</code>                                                                                                                                                                                                                                                              
</response

On my second script where I used Packages I had the same response which I fixed adding headers in the post() function:

import requests

XML = """<?xml version="1.0" encoding="utf-8"?>
<request method="task.list">
    <page>1</page>
    <per_page>15</per_page>
</request>"""
headers = {'Content-Type': 'application/xml'} # set what your server accepts
 r = requests.post('https://devjam-billing.freshbooks.com/api/2.1/xml-in', auth=      ('my auth token', 'user'), data=XML, headers=headers)

 print r.status_code
 print r.headers['content-type']
 # get the response
 print r.text

I tried on the first one to do something similar by adding:

headers["Content-type"] = "application/xml"

without success.

Any ideas? Also is the b64encode a safe security option for encoding or is there a safer way to do it? Thanks.

Was it helpful?

Solution

you actually need to send the POST data (the XML string) in the request, so, replace this:

conn.request('POST', body, None, headers)
resp = conn.getresponse()
print resp.status
conn.send(XML)
print resp.read()

with this:

conn.request('POST', body, XML, headers)
resp = conn.getresponse()
print resp.status
print resp.read()

I hope it helps!

OTHER TIPS

You appear to be sending data at the wrong time. Look from the docs (emphasis mine).

HTTPConnection.send(data)

Send data to the server. This should be used directly only after the endheaders() method has been called and before getresponse() is called.

In your case:

conn.endheaders()
conn.send(XML)
resp = conn.getresponse()
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top