11import os
2- import httplib2
2+ import requests
33from urllib import urlencode
44from datetime import datetime
55
@@ -30,37 +30,35 @@ def __init__(self, http_response, content):
3030self .content = content
3131
3232class HTTPBackend (object ):
33- """
34- Abstracts out an HTTP backend, but defaults to httplib2. Required arguments
35- are `base_url` and `api_key`.
33+ """ Abstracts out an HTTP backend. Required argument are `base_url` and
34+ `api_key`. """
35+ def __init__ (self ,
36+ base_url ,
37+ api_key ,
38+ resource_name = None ,
39+ timeout = None ,
40+ test = False ,
41+ version = None ):
3642
37- .. note::
38- While `as_xml` is provided as a keyword argument, XML or input or output
39- is not supported.
40- """
41- def __init__ (self ,base_url ,api_key ,as_xml = False ,resource_name = None ,timeout = None ,test = False ,version = None ):
4243self .base_url = base_url
44+
4345if resource_name :
4446self .base_url = self .base_url + resource_name
4547
46- self .http = httplib2 .Http (timeout = timeout )
47- self .as_xml = as_xml
48+ self .http = requests .Session ()
49+
50+ self .as_xml = False
4851self .api_key = api_key
4952self .test = test
5053self .version = version
5154
52- def content_length (self ,body ):
53- """
54- Returns the content length as an int for the given `body` data. Used by
55- PUT and POST requests to set the Content-Length header.
56- """
57- return str (len (body ))if body else "0"
55+ # sets request headers for the entire session
56+ self .http .headers .update (self .headers )
5857
5958@property
6059def headers (self ):
61- """ Returns default headers, by setting the Content-Type and Accepts
62- headers.
63- """
60+ """ Returns default headers, by setting the Content-Type, Accepts,
61+ User-Agent and API Key headers."""
6462content_type = 'xml' if self .as_xml else 'json'
6563
6664headers = {
@@ -85,35 +83,14 @@ def encode(self, data):
8583else :
8684raise NotImplementedError ('Encoding as XML is not supported.' )
8785
88- def decode (self ,raw_body ):
89- """
90- Returns the JSON-encoded `raw_body` and decodes it to a `dict` (using
91- `json.loads`).
92-
93- .. note::
94- Decoding as XML is not supported.
95- """
96- if not self .as_xml :
97- # only parse json when it exists, else just return None
98- if not raw_body or raw_body == ' ' :
99- return None
100- else :
101- return json .loads (raw_body )
102- else :
103- raise NotImplementedError ('Decoding as XML is not supported.' )
104-
10586def delete (self ,url ,params = None ):
10687"""
10788 Executes an HTTP DELETE request for the given URL
10889
109- params should be aurllib.urlencoded string
90+ params should be adictionary
11091 """
111- if params :
112- url = '?' .join ([url ,params ])
113-
114- response ,content = self .http .request (url ,method = "DELETE" ,
115- headers = self .headers )
116- return self .process (response ,content )
92+ response = self .http .delete (url ,params = params )
93+ return self .process (response )
11794
11895def get (self ,url ,data = None ):
11996"""
@@ -125,66 +102,58 @@ def get(self, url, data=None):
125102params = urlencode (data )
126103url = '?' .join ([url ,params ])
127104
128- response ,content = self .http .request (url ,method = "GET" ,
129- headers = self .headers )
130- return self .process (response ,content )
105+ response = self .http .get (url ,headers = self .headers ,params = data )
106+ return self .process (response )
131107
132108def post (self ,url ,body = None ):
133109"""
134110 Executes an HTTP POST request for the given URL
135111 """
136- headers = self .headers
137- headers ['Content-Length' ]= self .content_length (body )
138- response ,content = self .http .request (url ,method = "POST" ,
139- body = body ,
140- headers = self .headers )
112+ response = self .http .post (url ,data = body ,headers = self .headers )
141113
142- return self .process (response , content )
114+ return self .process (response )
143115
144116def put (self ,url ,data = None ,body = None ):
145117"""
146118 Executes an HTTP PUT request for the given URL
147119 """
148- headers = self .headers
149- headers ['Content-Length' ]= self .content_length (body )
120+ response = self .http .put (url ,params = data ,data = body ,headers = self .headers )
150121
151- if data :
152- params = urlencode (data )
153- url = '?' .join ([url ,params ])
122+ return self .process (response )
154123
155- response ,content = self .http .request (url ,method = "PUT" ,
156- body = body ,
157- headers = headers )
158-
159- return self .process (response ,content )
160-
161- def process (self ,http_response ,content ):
162- """
163- Returns HTTP backend agnostic Response data
164- """
124+ def process (self ,response ):
125+ """ Returns HTTP backend agnostic Response data. """
165126
166127try :
167- code = http_response .status
168- body = self .decode (content )
169- response = Response (code ,body ,content ,http_response )
170-
171- return response
128+ code = response .status_code
129+
130+ # 204 - No Content
131+ if code == 204 :
132+ body = None
133+ # add an error message to 402 errors
134+ elif code == 402 :
135+ body = {
136+ "message" :"Payment Required" ,
137+ "status" :"error"
138+ }
139+ else :
140+ body = response .json ()
172141
142+ return Response (code ,body ,response .content ,response )
173143except ValueError :
174- raise ZencoderResponseError (http_response ,content )
144+ raise ZencoderResponseError (response ,content )
175145
176146class Zencoder (object ):
177147""" This is the entry point to the Zencoder API """
178148def __init__ (self ,api_key = None ,api_version = None ,as_xml = False ,timeout = None ,test = False ):
179149"""
180- Initializes Zencoder. You must have a validAPI_KEY .
150+ Initializes Zencoder. You must have a valid`api_key` .
181151
182152 You can pass in the api_key as an argument, or set
183153 `ZENCODER_API_KEY` as an environment variable, and it will use
184- that, if api_key is unspecified.
154+ that, if` api_key` is unspecified.
185155
186156 Set api_version='edge' to get the Zencoder development API. (defaults to 'v2')
187- Set as_xml=True to get back xml data instead of the default json.
188157 """
189158if not api_version :
190159api_version = 'v2'