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

Improved the handling of cookies. #172

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 1 commit
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
18 changes: 18 additions & 0 deletions rtcclient/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@ def get(self,
url,
verify=False,
headers=None,
cookies=None,
proxies=None,
timeout=60,
**kwargs):
Expand All @@ -66,6 +67,8 @@ def get(self,
A CA_BUNDLE path can also be provided.
:param headers: (optional) Dictionary of HTTP Headers to send with
the :class:`Request`.
:param cookies: (optional) Dict or CookieJar object to send with
the :class:`Request`.
:param proxies: (optional) Dictionary mapping protocol to the URL of
the proxy.
:param timeout: (optional) How long to wait for the server to send data
Expand All @@ -81,6 +84,7 @@ def get(self,
response = requests.get(url,
verify=verify,
headers=headers,
cookies=cookies,
proxies=proxies,
timeout=timeout,
**kwargs)
Expand All @@ -97,6 +101,7 @@ def post(self,
json=None,
verify=False,
headers=None,
cookies=None,
proxies=None,
timeout=60,
**kwargs):
Expand All @@ -111,6 +116,8 @@ def post(self,
A CA_BUNDLE path can also be provided.
:param headers: (optional) Dictionary of HTTP Headers to send with
the :class:`Request`.
:param cookies: (optional) Dict or CookieJar object to send with
the :class:`Request`.
:param proxies: (optional) Dictionary mapping protocol to the URL of
the proxy.
:param timeout: (optional) How long to wait for the server to send data
Expand All @@ -129,6 +136,7 @@ def post(self,
json=json,
verify=verify,
headers=headers,
cookies=cookies,
proxies=proxies,
timeout=timeout,
**kwargs)
Expand All @@ -146,6 +154,7 @@ def put(self,
data=None,
verify=False,
headers=None,
cookies=None,
proxies=None,
timeout=60,
**kwargs):
Expand All @@ -158,6 +167,8 @@ def put(self,
A CA_BUNDLE path can also be provided.
:param headers: (optional) Dictionary of HTTP Headers to send with
the :class:`Request`.
:param cookies: (optional) Dict or CookieJar object to send with
the :class:`Request`.
:param proxies: (optional) Dictionary mapping protocol to the URL of
the proxy.
:param timeout: (optional) How long to wait for the server to send data
Expand All @@ -174,6 +185,7 @@ def put(self,
data=data,
verify=verify,
headers=headers,
cookies=cookies,
proxies=proxies,
timeout=timeout,
**kwargs)
Expand All @@ -187,6 +199,7 @@ def put(self,
def delete(self,
url,
headers=None,
cookies=None,
verify=False,
proxies=None,
timeout=60,
Expand All @@ -196,6 +209,8 @@ def delete(self,
:param url: URL for the new :class:`Request` object.
:param headers: (optional) Dictionary of HTTP Headers to send with
the :class:`Request`.
:param cookies: (optional) Dict or CookieJar object to send with
the :class:`Request`.
:param verify: (optional) if ``True``, the SSL cert will be verified.
A CA_BUNDLE path can also be provided.
:param proxies: (optional) Dictionary mapping protocol to the URL of
Expand All @@ -212,6 +227,7 @@ def delete(self,
self.log.debug("Delete a request to %s", url)
response = requests.delete(url,
headers=headers,
cookies=cookies,
verify=verify,
proxies=proxies,
timeout=timeout,
Expand Down Expand Up @@ -270,6 +286,7 @@ def _initialize(self):
verify=False,
proxies=self.rtc_obj.proxies,
headers=self.rtc_obj.headers,
cookies=self.rtc_obj.cookies,
)
self.__initialize(resp)
self.log.info("Finish the initialization for <%s %s>",
Expand Down Expand Up @@ -344,6 +361,7 @@ def __get_rdf_resource_title(self, rdf_url):
verify=False,
proxies=self.rtc_obj.proxies,
headers=self.rtc_obj.headers,
cookies=self.rtc_obj.cookies,
)
raw_data = xmltodict.parse(resp.content)

Expand Down
36 changes: 25 additions & 11 deletions rtcclient/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ def __init__(self,

self.jazz = ends_with_jazz
self.headers = self._get_headers()
self.cookies = self._get_cookies()
self.searchpath = searchpath
self.templater = Templater(self, searchpath=self.searchpath)
self.query = Query(self)
Expand All @@ -82,6 +83,12 @@ def get_rtc_obj(self):
return self

def _get_headers(self):
_headers = {}
_headers["Content-Type"] = self.CONTENT_XML
_headers["Accept"] = self.CONTENT_XML
return _headers

def _get_cookies(self):
if self.jazz is True:
_allow_redirects = True
else:
Expand All @@ -107,23 +114,25 @@ def _get_headers(self):
raise exception.RTCException("Authentication Failed: "
"Invalid username or password")

_cookies = None
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

L97 _headers = {"Content-Type": self.CONTENT_XML} is useless for now.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you for your review. I've modified the source code.


# fix issue #68
if not _allow_redirects:
if resp.headers.get("set-cookie") is not None:
_headers["Cookie"] = resp.headers.get("set-cookie")
_cookies = resp.cookies

resp = self.get(self.url + "/authenticated/identity",
auth=(self.username, self.password),
verify=False,
headers=_headers,
cookies=_cookies,
proxies=self.proxies,
allow_redirects=_allow_redirects)

# fix issue #68
if not _allow_redirects:
_headers["Cookie"] += "; " + resp.headers.get("set-cookie")
_cookies.add_cookie_header(resp)
else:
_headers["Cookie"] = resp.headers.get("set-cookie")
_cookies = resp.cookies

# For Form Challenge
auth_msg = resp.headers.get("X-com-ibm-team-repository-web-auth-msg")
Expand All @@ -137,6 +146,7 @@ def _get_headers(self):
data=post_data,
verify=False,
headers=temp_headers,
cookies=_cookies,
proxies=self.proxies,
allow_redirects=True)

Expand All @@ -157,12 +167,11 @@ def _get_headers(self):
"Invalid username or password")

if not _allow_redirects:
_headers["Cookie"] += "; " + resp.headers.get("set-cookie")
_cookies.add_cookie_header(resp)
else:
_headers["Cookie"] = resp.headers.get("set-cookie")
_cookies = resp.cookies

_headers["Accept"] = self.CONTENT_XML
return _headers
return _cookies

def relogin(self):
"""Relogin the RTC Server/Jazz when the token expires
Expand All @@ -172,6 +181,7 @@ def relogin(self):
self.log.info("Cookie expires. Relogin to get a new cookie.")
self.headers = None
self.headers = self._get_headers()
self.cookies = self._get_cookies()
self.log.debug("Successfully relogin.")

def getProjectAreas(self, archived=False, returned_properties=None):
Expand Down Expand Up @@ -988,7 +998,8 @@ def getWorkitem(self, workitem_id, returned_properties=None):
resp = self.get(req_url,
verify=False,
proxies=self.proxies,
headers=self.headers)
headers=self.headers,
cookies=self.cookies)
raw_data = xmltodict.parse(resp.content)
workitem_raw = raw_data["oslc_cm:ChangeRequest"]

Expand Down Expand Up @@ -1213,6 +1224,7 @@ def _createWorkitem(self, url_post, workitem_raw):
resp = self.post(url_post,
verify=False,
headers=headers,
cookies=self.cookies,
proxies=self.proxies,
data=workitem_raw)

Expand Down Expand Up @@ -1456,7 +1468,8 @@ def _get_paged_resources(self,
resp = self.get(resource_url,
verify=False,
proxies=self.proxies,
headers=self.headers)
headers=self.headers,
cookies=self.cookies)
raw_data = xmltodict.parse(resp.content)

try:
Expand Down Expand Up @@ -1504,7 +1517,8 @@ def _get_paged_resources(self,
resp = self.get(url_next,
verify=False,
proxies=self.proxies,
headers=self.headers)
headers=self.headers,
cookies=self.cookies)
raw_data = xmltodict.parse(resp.content)
else:
break
Expand Down
8 changes: 6 additions & 2 deletions rtcclient/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -191,7 +191,8 @@ def getChanges(self):
resp = self.get(resource_url,
verify=False,
proxies=self.rtc_obj.proxies,
headers=self.rtc_obj.headers)
headers=self.rtc_obj.headers,
cookies=self.rtc_obj.cookies)
raw_data = xmltodict.parse(resp.content).get("scm:ChangeSet")
common_changes = dict()
changes = raw_data.get("changes")
Expand Down Expand Up @@ -291,7 +292,10 @@ def _fetchFile(self, state_id, file_folder, override=True):

self.log.debug("Start fetching file from %s ..." % file_url)

resp = self.get(file_url, verify=False, headers=self.rtc_obj.headers)
resp = self.get(file_url,
verify=False,
headers=self.rtc_obj.headers,
cookies=self.rtc_obj.cookies)
file_name = re.findall(r".+filename\*=UTF-8''(.+)",
resp.headers["content-disposition"])[0]
file_path = os.path.join(file_folder, file_name)
Expand Down
3 changes: 2 additions & 1 deletion rtcclient/project_area.py
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,8 @@ def getRoles(self):
resp = self.get(roles_url,
verify=False,
proxies=self.rtc_obj.proxies,
headers=self.rtc_obj.headers)
headers=self.rtc_obj.headers,
cookies=self.rtc_obj.cookies)

roles_list = list()
raw_data = xmltodict.parse(resp.content)
Expand Down
3 changes: 2 additions & 1 deletion rtcclient/template.py
Original file line number Diff line number Diff line change
Expand Up @@ -278,7 +278,8 @@ def getTemplate(self,
resp = self.get(workitem_url,
verify=False,
proxies=self.rtc_obj.proxies,
headers=self.rtc_obj.headers)
headers=self.rtc_obj.headers,
cookies=self.rtc_obj.cookies)
raw_data = xmltodict.parse(resp.content)

# pre-adjust the template:
Expand Down
3 changes: 1 addition & 2 deletions rtcclient/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ def token_expire_handler(func):
def wrapper(*args, **kwargs):
rtc_obj = args[0].get_rtc_obj()

if not hasattr(rtc_obj, "headers") or rtc_obj.headers is None:
if not hasattr(rtc_obj, "cookies") or rtc_obj.cookies is None:
# still in the initialization or relogin
# directly call the method
return func(*args, **kwargs)
Expand All @@ -39,7 +39,6 @@ def wrapper(*args, **kwargs):
except RTCException:
raise RTCException("Relogin Failed: "
"Invalid username or password")
kwargs["headers"]["Cookie"] = rtc_obj.headers["Cookie"]
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here should be kwargs["cookies"] = rtc_obj.cookies

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you for your review. I've modified the source code.

return func(*args, **kwargs)
else:
# not expires
Expand Down
14 changes: 12 additions & 2 deletions rtcclient/workitem.py
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,8 @@ def addComment(self, msg=None):
resp = self.get(comments_url,
verify=False,
proxies=self.rtc_obj.proxies,
headers=headers)
headers=headers,
cookies=self.rtc_obj.cookies)

raw_data = xmltodict.parse(resp.content)

Expand All @@ -123,6 +124,7 @@ def addComment(self, msg=None):
resp = self.post(req_url,
verify=False,
headers=headers,
cookies=self.rtc_obj.cookies,
proxies=self.rtc_obj.proxies,
data=comment_msg)
self.log.info("Successfully add comment: [%s] for <Workitem %s>", msg,
Expand Down Expand Up @@ -236,6 +238,7 @@ def _update_subscribe(self, headers, raw_data):
verify=False,
proxies=self.rtc_obj.proxies,
headers=headers,
cookies=self.rtc_obj.cookies,
data=xmltodict.unparse(raw_data))

def _perform_subscribe(self):
Expand All @@ -248,7 +251,8 @@ def _perform_subscribe(self):
resp = self.get(subscribers_url,
verify=False,
proxies=self.rtc_obj.proxies,
headers=headers)
headers=headers,
cookies=self.rtc_obj.cookies)
headers["If-Match"] = resp.headers.get("etag")
raw_data = xmltodict.parse(resp.content)
return headers, raw_data
Expand Down Expand Up @@ -544,6 +548,7 @@ def addParent(self, parent_id):
verify=False,
proxies=self.rtc_obj.proxies,
headers=headers,
cookies=self.rtc_obj.cookies,
data=json.dumps(parent_original))
self.log.info(
"Successfully add a parent <Workitem %s> to current "
Expand Down Expand Up @@ -617,6 +622,7 @@ def _addChildren(self, child_ids):
self.put(req_url,
verify=False,
headers=headers,
cookies=self.rtc_obj.cookies,
proxies=self.rtc_obj.proxies,
data=json.dumps(children_original))

Expand Down Expand Up @@ -670,6 +676,7 @@ def removeParent(self):
verify=False,
proxies=self.rtc_obj.proxies,
headers=headers,
cookies=self.rtc_obj.cookies,
data=json.dumps(parent_original))
self.log.info(
"Successfully remove the parent workitem of current "
Expand Down Expand Up @@ -738,6 +745,7 @@ def _removeChildren(self, child_ids):
self.put(req_url,
verify=False,
headers=headers,
cookies=self.rtc_obj.cookies,
proxies=self.rtc_obj.proxies,
data=json.dumps(children_original))

Expand Down Expand Up @@ -771,6 +779,7 @@ def addAttachment(self, filepath):
resp = self.post(req_url,
verify=False,
headers=headers,
cookies=self.rtc_obj.cookies,
proxies=self.rtc_obj.proxies,
params=params,
files=files)
Expand All @@ -794,6 +803,7 @@ def _add_attachment_link(self, attachment_info):
payload,
verify=False,
headers=self.rtc_obj.headers,
cookies=self.rtc_obj.cookies,
proxies=self.rtc_obj.proxies)
raw_data = xmltodict.parse(resp.content)

Expand Down
6 changes: 3 additions & 3 deletions tests/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,10 @@
def rtcclient(mocker):
mock_resp = mocker.MagicMock(spec=requests.Response)
mock_resp.status_code = 200
mock_resp.headers = {"set-cookie": "cookie-id"}
mock_resp.cookies = {"set-cookie": "cookie-id"}

mocked_headers = mocker.patch("rtcclient.client.RTCClient._get_headers")
mocked_headers.return_value = mock_resp
mocked_cookies = mocker.patch("rtcclient.client.RTCClient._get_cookies")
mocked_cookies.return_value = mock_resp

return RTCClient(url="http://test.url:9443/jazz",
username="[email protected]",
Expand Down
Loading