Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Cherry pick from "next" branch #45

Open
wants to merge 8 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 21 additions & 0 deletions ChangeLog.md
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,23 @@ Upcoming
Unscheduled
-----------


* Support reusing TCP connections, and "pipelining" of requests, a la
RFC 2068, Sect 8.1, L2377

- The user must ask for pipelining, and supply a callback function
to be called after a response is received.
- Rename Client.request() -> Client.addRequest() (or such)
- Have Client.addRequest() check whether a persistent connection is
wanted, and save the entire request in a Client.pendingRequests
list in that case
- Create a new Client.sendRequests() method which the user may call
to send all requests up the pipeline. (It should work even if the
server does not support pipelining)
- Call the user-supplied callback whenever a request is received.
There are some concurrency issues here, and we may elect to call
the callback only after *all* requests are received.

* Create a script to pack the basic module and any given set of
service-specific classes as one file. I still like the idea that a
given API (e.g. Facebook) could be packed into a single file, and
Expand Down Expand Up @@ -82,6 +99,10 @@ v2.0
- Use `application/octet-stream` for unknown media type
- Spell 'GitHub' correctly

* Parse Content-Type header correctly; make a dict of the
parameters (Content.ctypeParameters) available to the media-type
handlers

v1.3
----
A stable branch, with a lot of bug fixes! (Thanks to all who
Expand Down
4 changes: 2 additions & 2 deletions agithub/GitHub.py
Original file line number Diff line number Diff line change
Expand Up @@ -51,8 +51,8 @@ def generateAuthHeader(self, username=None, password=None, token=None):
if token is not None:
if password is not None:
raise TypeError(
"You cannot use both password and oauth token "
"authenication"
"You cannot use both password and OAuth token "
"authentication"
)
return 'Token %s' % token
elif username is not None:
Expand Down
32 changes: 22 additions & 10 deletions agithub/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@
import json
from functools import partial, update_wrapper

import xml.dom.minidom

import sys
if sys.version_info[0:2] > (3, 0):
from http.client import HTTPConnection, HTTPSConnection
Expand Down Expand Up @@ -134,18 +136,12 @@ def setConnectionProperties(self, prop):
"Expected ConnectionProperties object"
)

self.default_headers = _default_headers.copy()
if prop.extra_headers is not None:
prop.filterEmptyHeaders()
self.default_headers = _default_headers.copy()
self.default_headers.update(prop.extra_headers)
self.prop = prop

# Enforce case restrictions on self.default_headers
tmp_dict = {}
for k, v in self.default_headers.items():
tmp_dict[k.lower()] = v
self.default_headers = tmp_dict

def head(self, url, headers=None, **params):
headers = headers or {}
url += self.urlencode(params)
Expand Down Expand Up @@ -223,7 +219,7 @@ def _fix_headers(self, headers):
# Add default headers (if unspecified)
for k, v in self.default_headers.items():
if k not in headers:
headers[k] = v
headers[k.lower()] = v
return headers

def urlencode(self, params):
Expand Down Expand Up @@ -315,7 +311,7 @@ def decode_body(self):

def processBody(self):
"""
Retrieve the body of the response, encoding it into a usuable
Retrieve the body of the response, encoding it into a usable
form based on the media-type (mime-type)
"""
handlerName = self.mangled_mtype()
Expand Down Expand Up @@ -347,8 +343,24 @@ def application_json(self):
text_javascript = application_json
# XXX: This isn't technically correct, but we'll hope for the best.
# Patches welcome!
# Insert new media-type handlers here

def application_xml(self):
self.decode_body()

try:
pybody = xml.dom.minidom.parseString(self.body)
except Exception: #TODO: What kind of exceptions?
pybody = self.body

return pybody


text_xml = application_xml
# The difference between text/xml and application/xml is whether it
# is human-readable or not. For our purposes, there is no
# difference. RFC 3023, L270.

# Insert new Response media-type handlers here

class RequestBody(Body):
"""
Expand Down
23 changes: 8 additions & 15 deletions agithub/test.py
Original file line number Diff line number Diff line change
Expand Up @@ -44,21 +44,14 @@ def doTestsFor(self, api):
raise ValueError('Bad test result ' + (res))

print(
'\n'
' Results\n'
'--------------------------------------\n'
'Tests Run: ',
len(results),
'\n'
' Passed: ',
passes,
'\n'
' Failed: ',
fails,
'\n'
' Skipped: ',
skips
)
'\n'
' Results\n'
'--------------------------------------\n'
'Tests Run: ', len(results), '\n'
' Passed: ', passes, '\n'
' Failed: ', fails, '\n'
' Skipped: ', skips
)

def runTest(self, test, api):
"""Run a single test with the given API session"""
Expand Down