|
17 | 17 | throughout the library. |
18 | 18 | """ |
19 | 19 |
|
20 | | -import os |
21 | 20 | import sys |
22 | 21 | import platform |
23 | 22 | from collections import Sequence |
24 | 23 | import json |
25 | | -from requests import RequestException, Session |
26 | 24 |
|
27 | | -from ._2to3 import LONGTYPE, STRTYPE, NONETYPE, UNITYPE, iteritems_, url_join |
| 25 | +from ._2to3 import LONGTYPE, STRTYPE, NONETYPE, UNITYPE, iteritems_ |
28 | 26 | from .error import CloudantArgumentError, CloudantException |
29 | 27 |
|
30 | 28 | # Library Constants |
@@ -290,211 +288,6 @@ def __new__(cls, code): |
290 | 288 | return str.__new__(cls, code) |
291 | 289 |
|
292 | 290 |
|
293 | | -class ClientSession(Session): |
294 | | - """ |
295 | | - This class extends Session and provides a default timeout. |
296 | | - """ |
297 | | - |
298 | | - def __init__(self, **kwargs): |
299 | | - super(ClientSession, self).__init__() |
300 | | - self._timeout = kwargs.get('timeout', None) |
301 | | - |
302 | | - def request(self, method, url, **kwargs): # pylint: disable=W0221 |
303 | | - """ |
304 | | - Overrides ``requests.Session.request`` to set the timeout. |
305 | | - """ |
306 | | - resp = super(ClientSession, self).request( |
307 | | - method, url, timeout=self._timeout, **kwargs) |
308 | | - |
309 | | - return resp |
310 | | - |
311 | | - |
312 | | -class CookieSession(ClientSession): |
313 | | - """ |
314 | | - This class extends ClientSession and provides cookie authentication. |
315 | | - """ |
316 | | - |
317 | | - def __init__(self, username, password, server_url, **kwargs): |
318 | | - super(CookieSession, self).__init__(**kwargs) |
319 | | - self._username = username |
320 | | - self._password = password |
321 | | - self._auto_renew = kwargs.get('auto_renew', False) |
322 | | - self._session_url = url_join(server_url, '_session') |
323 | | - |
324 | | - def info(self): |
325 | | - """ |
326 | | - Get cookie based login user information. |
327 | | - """ |
328 | | - resp = self.get(self._session_url) |
329 | | - resp.raise_for_status() |
330 | | - |
331 | | - return resp.json() |
332 | | - |
333 | | - def login(self): |
334 | | - """ |
335 | | - Perform cookie based user login. |
336 | | - """ |
337 | | - resp = super(CookieSession, self).request( |
338 | | - 'POST', |
339 | | - self._session_url, |
340 | | - data={'name': self._username, 'password': self._password}, |
341 | | - ) |
342 | | - resp.raise_for_status() |
343 | | - |
344 | | - def logout(self): |
345 | | - """ |
346 | | - Logout cookie based user. |
347 | | - """ |
348 | | - resp = super(CookieSession, self).request('DELETE', self._session_url) |
349 | | - resp.raise_for_status() |
350 | | - |
351 | | - def request(self, method, url, **kwargs): # pylint: disable=W0221 |
352 | | - """ |
353 | | - Overrides ``requests.Session.request`` to renew the cookie and then |
354 | | - retry the original request (if required). |
355 | | - """ |
356 | | - resp = super(CookieSession, self).request(method, url, **kwargs) |
357 | | - |
358 | | - if not self._auto_renew: |
359 | | - return resp |
360 | | - |
361 | | - is_expired = any(( |
362 | | - resp.status_code == 403 and |
363 | | - resp.json().get('error') == 'credentials_expired', |
364 | | - resp.status_code == 401 |
365 | | - )) |
366 | | - |
367 | | - if is_expired: |
368 | | - self.login() |
369 | | - resp = super(CookieSession, self).request(method, url, **kwargs) |
370 | | - |
371 | | - return resp |
372 | | - |
373 | | - def set_credentials(self, username, password): |
374 | | - """ |
375 | | - Set a new username and password. |
376 | | -
|
377 | | - :param str username: New username. |
378 | | - :param str password: New password. |
379 | | - """ |
380 | | - if username is not None: |
381 | | - self._username = username |
382 | | - |
383 | | - if password is not None: |
384 | | - self._password = password |
385 | | - |
386 | | - |
387 | | -class IAMSession(ClientSession): |
388 | | - """ |
389 | | - This class extends ClientSession and provides IAM authentication. |
390 | | - """ |
391 | | - |
392 | | - def __init__(self, api_key, server_url, **kwargs): |
393 | | - super(IAMSession, self).__init__(**kwargs) |
394 | | - self._api_key = api_key |
395 | | - self._auto_renew = kwargs.get('auto_renew', False) |
396 | | - self._session_url = url_join(server_url, '_iam_session') |
397 | | - self._token_url = os.environ.get( |
398 | | - 'IAM_TOKEN_URL', 'https://iam.bluemix.net/oidc/token') |
399 | | - |
400 | | - def info(self): |
401 | | - """ |
402 | | - Get IAM cookie based login user information. |
403 | | - """ |
404 | | - resp = self.get(self._session_url) |
405 | | - resp.raise_for_status() |
406 | | - |
407 | | - return resp.json() |
408 | | - |
409 | | - def login(self): |
410 | | - """ |
411 | | - Perform IAM cookie based user login. |
412 | | - """ |
413 | | - access_token = self._get_access_token() |
414 | | - try: |
415 | | - super(IAMSession, self).request( |
416 | | - 'POST', |
417 | | - self._session_url, |
418 | | - headers={'Content-Type': 'application/json'}, |
419 | | - data=json.dumps({'access_token': access_token}) |
420 | | - ).raise_for_status() |
421 | | - |
422 | | - except RequestException: |
423 | | - raise CloudantException( |
424 | | - 'Failed to exchange IAM token with Cloudant') |
425 | | - |
426 | | - def logout(self): |
427 | | - """ |
428 | | - Logout IAM cookie based user. |
429 | | - """ |
430 | | - self.cookies.clear() |
431 | | - |
432 | | - def request(self, method, url, **kwargs): # pylint: disable=W0221 |
433 | | - """ |
434 | | - Overrides ``requests.Session.request`` to renew the IAM cookie |
435 | | - and then retry the original request (if required). |
436 | | - """ |
437 | | - # The CookieJar API prevents callers from getting an individual Cookie |
438 | | - # object by name. |
439 | | - # We are forced to use the only exposed method of discarding expired |
440 | | - # cookies from the CookieJar. Internally this involves iterating over |
441 | | - # the entire CookieJar and calling `.is_expired()` on each Cookie |
442 | | - # object. |
443 | | - self.cookies.clear_expired_cookies() |
444 | | - |
445 | | - if self._auto_renew and 'IAMSession' not in self.cookies.keys(): |
446 | | - self.login() |
447 | | - |
448 | | - resp = super(IAMSession, self).request(method, url, **kwargs) |
449 | | - |
450 | | - if not self._auto_renew: |
451 | | - return resp |
452 | | - |
453 | | - if resp.status_code == 401: |
454 | | - self.login() |
455 | | - resp = super(IAMSession, self).request(method, url, **kwargs) |
456 | | - |
457 | | - return resp |
458 | | - |
459 | | - def set_credentials(self, username, api_key): |
460 | | - """ |
461 | | - Set a new IAM API key. |
462 | | -
|
463 | | - :param str username: Username parameter is unused. |
464 | | - :param str api_key: New IAM API key. |
465 | | - """ |
466 | | - if api_key is not None: |
467 | | - self._api_key = api_key |
468 | | - |
469 | | - def _get_access_token(self): |
470 | | - """ |
471 | | - Get IAM access token using API key. |
472 | | - """ |
473 | | - err = 'Failed to contact IAM token service' |
474 | | - try: |
475 | | - resp = super(IAMSession, self).request( |
476 | | - 'POST', |
477 | | - self._token_url, |
478 | | - auth=('bx', 'bx'), # required for user API keys |
479 | | - headers={'Accepts': 'application/json'}, |
480 | | - data={ |
481 | | - 'grant_type': 'urn:ibm:params:oauth:grant-type:apikey', |
482 | | - 'response_type': 'cloud_iam', |
483 | | - 'apikey': self._api_key |
484 | | - } |
485 | | - ) |
486 | | - err = resp.json().get('errorMessage', err) |
487 | | - resp.raise_for_status() |
488 | | - |
489 | | - return resp.json()['access_token'] |
490 | | - |
491 | | - except KeyError: |
492 | | - raise CloudantException('Invalid response from IAM token service') |
493 | | - |
494 | | - except RequestException: |
495 | | - raise CloudantException(err) |
496 | | - |
497 | | - |
498 | 291 | class CloudFoundryService(object): |
499 | 292 | """ Manages Cloud Foundry service configuration. """ |
500 | 293 |
|
|
0 commit comments