tests.py 23.9 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42
#!/usr/bin/env python
#
# Copyright (C) 2012, 2013 GRNET S.A. All rights reserved.
#
# Redistribution and use in source and binary forms, with or
# without modification, are permitted provided that the following
# conditions are met:
#
#   1. Redistributions of source code must retain the above
#      copyright notice, this list of conditions and the following
#      disclaimer.
#
#   2. Redistributions in binary form must reproduce the above
#      copyright notice, this list of conditions and the following
#      disclaimer in the documentation and/or other materials
#      provided with the distribution.
#
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
# POSSIBILITY OF SUCH DAMAGE.
#
# The views and conclusions contained in the software and
# documentation are those of the authors and should not be
# interpreted as representing official policies, either expressed
# or implied, of GRNET S.A.

"""Unit Tests for the astakos-client module

Provides unit tests for the code implementing
the astakos client library

"""

43
import sys
44
import socket
45
import simplejson
46 47

import astakosclient
48 49
from astakosclient import AstakosClient
from astakosclient.errors import \
50
    AstakosClientException, Unauthorized, BadRequest, NotFound, \
51
    NoUserName, NoUUID
52 53

# Use backported unittest functionality if Python < 2.7
54 55 56 57 58 59
try:
    import unittest2 as unittest
except ImportError:
    if sys.version_info < (2, 7):
        raise Exception("The unittest2 package is required for Python < 2.7")
    import unittest
60 61 62 63 64 65 66


# --------------------------------------------------------------------
# Helper functions

# ----------------------------
# This functions will be used as mocked requests
67
def _request_offline(conn, method, url, **kwargs):
68 69 70 71
    """This request behaves as we were offline"""
    raise socket.gaierror


72
def _request_status_302(conn, method, url, **kwargs):
73
    """This request returns 302"""
74
    message = "FOUND"
75 76 77 78
    status = 302
    data = '<html>\r\n<head><title>302 Found</title></head>\r\n' \
        '<body bgcolor="white">\r\n<center><h1>302 Found</h1></center>\r\n' \
        '<hr><center>nginx/0.7.67</center>\r\n</body>\r\n</html>\r\n'
79
    return (message, data, status)
80 81


82
def _request_status_404(conn, method, url, **kwargs):
83
    """This request returns 404"""
84
    message = "Not Found"
85 86 87 88 89
    status = 404
    data = '<html><head><title>404 Not Found</title></head>' \
        '<body><h1>Not Found</h1><p>The requested URL /foo was ' \
        'not found on this server.</p><hr><address>Apache Server ' \
        'at example.com Port 80</address></body></html>'
90
    return (message, data, status)
91 92


93
def _request_status_401(conn, method, url, **kwargs):
94
    """This request returns 401"""
95
    message = "UNAUTHORIZED"
96 97
    status = 401
    data = "Invalid X-Auth-Token\n"
98
    return (message, data, status)
99 100


101
def _request_status_400(conn, method, url, **kwargs):
102
    """This request returns 400"""
103
    message = "BAD REQUEST"
104 105
    status = 400
    data = "Method not allowed.\n"
106
    return (message, data, status)
107 108


109
def _request_ok(conn, method, url, **kwargs):
110
    """This request behaves like original Astakos does"""
111
    if url.startswith("/im/authenticate"):
112
        return _req_authenticate(conn, method, url, **kwargs)
113
    elif url.startswith("/user_catalogs"):
114
        return _req_catalogs(conn, method, url, **kwargs)
115 116
    elif url.startswith("/astakos/api/resources"):
        return _req_resources(conn, method, url, **kwargs)
117
    else:
118
        return _request_status_404(conn, method, url, **kwargs)
119 120


121
def _req_authenticate(conn, method, url, **kwargs):
122
    """Check if user exists and return his profile"""
123
    global user_1, user_2, token_1, token_2
124

125
    # Check input
126
    if conn.__class__.__name__ != "HTTPSConnection":
127
        return _request_status_302(conn, method, url, **kwargs)
128
    if method != "GET":
129
        return _request_status_400(conn, method, url, **kwargs)
130 131
    token = kwargs['headers']['X-Auth-Token']
    if token == token_1:
132
        user = dict(user_1)
133
    elif token == token_2:
134
        user = dict(user_2)
135 136
    else:
        # No user found
137
        return _request_status_401(conn, method, url, **kwargs)
138

139
    # Return
140
    if "usage=1" not in url:
141
        # Strip `usage' key from `user'
142
        del user['usage']
143
    return ("", simplejson.dumps(user), 200)
144 145


146
def _req_catalogs(conn, method, url, **kwargs):
147
    """Return user catalogs"""
148 149
    global token_1, token_2, user_1, user_2

150
    # Check input
151
    if conn.__class__.__name__ != "HTTPSConnection":
152
        return _request_status_302(conn, method, url, **kwargs)
153
    if method != "POST":
154
        return _request_status_400(conn, method, url, **kwargs)
155 156
    token = kwargs['headers']['X-Auth-Token']
    if token != token_1 and token != token_2:
157
        return _request_status_401(conn, method, url, **kwargs)
158 159 160

    # Return
    body = simplejson.loads(kwargs['body'])
161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180
    if 'uuids' in body:
        # Return uuid_catalog
        uuids = body['uuids']
        catalogs = {}
        if user_1['uuid'] in uuids:
            catalogs[user_1['uuid']] = user_1['username']
        if user_2['uuid'] in uuids:
            catalogs[user_2['uuid']] = user_2['username']
        return_catalog = {"displayname_catalog": {}, "uuid_catalog": catalogs}
    elif 'displaynames' in body:
        # Return displayname_catalog
        names = body['displaynames']
        catalogs = {}
        if user_1['username'] in names:
            catalogs[user_1['username']] = user_1['uuid']
        if user_2['username'] in names:
            catalogs[user_2['username']] = user_2['uuid']
        return_catalog = {"displayname_catalog": catalogs, "uuid_catalog": {}}
    else:
        return_catalog = {"displayname_catalog": {}, "uuid_catalog": {}}
181
    return ("", simplejson.dumps(return_catalog), 200)
182 183


184 185 186 187 188 189 190 191 192 193 194 195 196 197
def _req_resources(conn, method, url, **kwargs):
    """Return quota resources"""
    global resources

    # Check input
    if conn.__class__.__name__ != "HTTPSConnection":
        return _request_status_302(conn, method, url, **kwargs)
    if method != "GET":
        return _request_status_400(conn, method, url, **kwargs)

    # Return
    return ("", simplejson.dumps(resources), 200)


198 199
# ----------------------------
# Mock the actual _doRequest
200
def _mock_request(new_requests):
201 202 203 204 205 206 207 208 209 210 211 212 213
    """Mock the actual request

    Given a list of requests to use (in rotation),
    replace the original _doRequest function with
    a new one

    """
    def _mock(conn, method, url, **kwargs):
        # Get first request
        request = _mock.requests[0]
        # Rotate requests
        _mock.requests = _mock.requests[1:] + _mock.requests[:1]
        # Use first request
214
        return request(conn, method, url, **kwargs)
215 216 217

    _mock.requests = new_requests
    # Replace `_doRequest' with our `_mock'
218
    astakosclient._do_request = _mock
219 220 221 222 223


# ----------------------------
# Local users
token_1 = "skzleaFlBl+fasFdaf24sx=="
224
user_1 = \
225 226 227 228 229 230
    {"username": "user1@example.com",
     "auth_token_created": 1359386939000,
     "name": "Example User One",
     "email": ["user1@example.com"],
     "auth_token_expires": 1361978939000,
     "id": 108,
231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250
     "uuid": "73917abc-abcd-477e-a1f1-1763abcdefab",
     "usage": [
         {"currValue": 42949672960,
          "display_name": "System Disk",
          "name": "cyclades.disk"},
         {"currValue": 4,
          "display_name": "CPU",
          "name": "cyclades.cpu"},
         {"currValue": 4294967296,
          "display_name": "RAM",
          "name": "cyclades.ram"},
         {"currValue": 3,
          "display_name": "VM",
          "name": "cyclades.vm"},
         {"currValue": 0,
          "display_name": "private network",
          "name": "cyclades.network.private"},
         {"currValue": 152,
          "display_name": "Storage Space",
          "name": "pithos+.diskspace"}]}
251 252

token_2 = "fasdfDSFdf98923DF+sdfk=="
253
user_2 = \
254 255 256 257 258 259
    {"username": "user2@example.com",
     "auth_token_created": 1358386938997,
     "name": "Example User Two",
     "email": ["user1@example.com"],
     "auth_token_expires": 1461998939000,
     "id": 109,
260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279
     "uuid": "73917bca-1234-5678-a1f1-1763abcdefab",
     "usage": [
         {"currValue": 68719476736,
          "display_name": "System Disk",
          "name": "cyclades.disk"},
         {"currValue": 1,
          "display_name": "CPU",
          "name": "cyclades.cpu"},
         {"currValue": 1073741824,
          "display_name": "RAM",
          "name": "cyclades.ram"},
         {"currValue": 2,
          "display_name": "VM",
          "name": "cyclades.vm"},
         {"currValue": 1,
          "display_name": "private network",
          "name": "cyclades.network.private"},
         {"currValue": 2341634510,
          "display_name": "Storage Space",
          "name": "pithos+.diskspace"}]}
280

281 282 283 284 285 286 287 288 289 290
resources = {
    "cyclades.vm": {
        "unit": None,
        "description": "Number of virtual machines",
        "service": "cyclades"},
    "cyclades.ram": {
        "unit": "bytes",
        "description": "Virtual machine memory",
        "service": "cyclades"}}

291 292 293 294 295 296 297

# --------------------------------------------------------------------
# The actual tests

class TestCallAstakos(unittest.TestCase):
    """Test cases for function _callAstakos"""

298 299 300
    # ----------------------------------
    # Test the response we get if we don't have internet access
    def _offline(self, pool):
301
        global token_1
302
        _mock_request([_request_offline])
303
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
304
            client = AstakosClient("https://example.com", use_pool=pool)
305
            client._call_astakos(token_1, "/im/authenticate")
306
        except AstakosClientException:
307 308
            pass
        else:
309
            self.fail("Should have raised AstakosClientException")
310

311
    def test_offline(self):
312 313 314
        """Test _offline without pool"""
        self._offline(False)

315
    def test_offline_pool(self):
316 317 318 319 320
        """Test _offline using pool"""
        self._offline(True)

    # ----------------------------------
    # Test the response we get if we send invalid token
321
    def _invalid_token(self, pool):
322
        token = "skaksaFlBl+fasFdaf24sx=="
323
        _mock_request([_request_ok])
324
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
325
            client = AstakosClient("https://example.com", use_pool=pool)
326
            client._call_astakos(token, "/im/authenticate")
327
        except Unauthorized:
328 329 330
            pass
        except Exception:
            self.fail("Should have returned 401 (Invalid X-Auth-Token)")
331 332 333
        else:
            self.fail("Should have returned 401 (Invalid X-Auth-Token)")

334 335 336
    def test_invalid_token(self):
        """Test _invalid_token without pool"""
        self._invalid_token(False)
337

338 339 340
    def test_invalid_token_pool(self):
        """Test _invalid_token using pool"""
        self._invalid_token(True)
341 342 343

    # ----------------------------------
    # Test the response we get if we send invalid url
344
    def _invalid_url(self, pool):
345
        global token_1
346
        _mock_request([_request_ok])
347
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
348
            client = AstakosClient("https://example.com", use_pool=pool)
349
            client._call_astakos(token_1, "/im/misspelled")
350
        except NotFound:
351 352 353
            pass
        except Exception:
            self.fail("Should have returned 404 (Not Found)")
354 355 356
        else:
            self.fail("Should have returned 404 (Not Found)")

357 358 359
    def test_invalid_url(self):
        """Test _invalid_url without pool"""
        self._invalid_url(False)
360

361 362 363
    def test_invalid_url_pool(self):
        """Test _invalid_url using pool"""
        self._invalid_url(True)
364 365 366

    # ----------------------------------
    # Test the response we get if we use an unsupported scheme
367
    def _unsupported_scheme(self, pool):
368
        global token_1
369
        _mock_request([_request_ok])
370
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
371
            client = AstakosClient("ftp://example.com", use_pool=pool)
372
            client._call_astakos(token_1, "/im/authenticate")
373
        except ValueError:
374 375
            pass
        except Exception:
376
            self.fail("Should have raise ValueError Exception")
377
        else:
378 379
            self.fail("Should have raise ValueError Exception")

380 381 382
    def test_unsupported_scheme(self):
        """Test _unsupported_scheme without pool"""
        self._unsupported_scheme(False)
383

384 385 386
    def test_unsupported_scheme_pool(self):
        """Test _unsupported_scheme using pool"""
        self._unsupported_scheme(True)
387 388 389

    # ----------------------------------
    # Test the response we get if we use http instead of https
390
    def _http_scheme(self, pool):
391
        global token_1
392
        _mock_request([_request_ok])
393
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
394
            client = AstakosClient("http://example.com", use_pool=pool)
395
            client._call_astakos(token_1, "/im/authenticate")
396 397
        except AstakosClientException as err:
            if err.status != 302:
398 399 400 401
                self.fail("Should have returned 302 (Found)")
        else:
            self.fail("Should have returned 302 (Found)")

402 403 404
    def test_http_scheme(self):
        """Test _http_scheme without pool"""
        self._http_scheme(False)
405

406 407 408
    def test_http_scheme_pool(self):
        """Test _http_scheme using pool"""
        self._http_scheme(True)
409 410 411

    # ----------------------------------
    # Test the response we get if we use authenticate with POST
412
    def _post_authenticate(self, pool):
413
        global token_1
414
        _mock_request([_request_ok])
415
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
416
            client = AstakosClient("https://example.com", use_pool=pool)
417
            client._call_astakos(token_1, "/im/authenticate", method="POST")
418
        except BadRequest:
419 420 421
            pass
        except Exception:
            self.fail("Should have returned 400 (Method not allowed)")
422 423 424
        else:
            self.fail("Should have returned 400 (Method not allowed)")

425 426 427
    def test_post_authenticate(self):
        """Test _post_authenticate without pool"""
        self._post_authenticate(False)
428

429 430 431
    def test_post_authenticate_pool(self):
        """Test _post_authenticate using pool"""
        self._post_authenticate(True)
432

433 434
    # ----------------------------------
    # Test the response if we request user_catalogs with GET
435
    def _get_user_catalogs(self, pool):
436
        global token_1
437
        _mock_request([_request_ok])
438
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
439
            client = AstakosClient("https://example.com", use_pool=pool)
440
            client._call_astakos(token_1, "/user_catalogs")
441
        except BadRequest:
442 443 444
            pass
        except Exception:
            self.fail("Should have returned 400 (Method not allowed)")
445 446 447
        else:
            self.fail("Should have returned 400 (Method not allowed)")

448 449 450
    def test_get_user_catalogs(self):
        """Test _get_user_catalogs without pool"""
        self._get_user_catalogs(False)
451

452 453 454
    def test_get_user_catalogs_pool(self):
        """Test _get_user_catalogs using pool"""
        self._get_user_catalogs(True)
455

456

457
class TestAuthenticate(unittest.TestCase):
458
    """Test cases for function getUserInfo"""
459 460 461

    # ----------------------------------
    # Test the response we get if we don't have internet access
462
    def test_offline(self):
463 464
        """Test offline after 3 retries"""
        global token_1
465
        _mock_request([_request_offline])
466
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
467
            client = AstakosClient("https://example.com", retry=3)
468
            client.get_user_info(token_1)
469 470 471 472 473 474 475
        except AstakosClientException:
            pass
        else:
            self.fail("Should have raised AstakosClientException exception")

    # ----------------------------------
    # Test the response we get for invalid token
476
    def _invalid_token(self, pool):
477
        token = "skaksaFlBl+fasFdaf24sx=="
478
        _mock_request([_request_ok])
479
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
480
            client = AstakosClient("https://example.com", use_pool=pool)
481
            client.get_user_info(token)
482
        except Unauthorized:
483 484 485
            pass
        except Exception:
            self.fail("Should have returned 401 (Invalid X-Auth-Token)")
486
        else:
487
            self.fail("Should have returned 401 (Invalid X-Auth-Token)")
488

489 490 491
    def test_invalid_token(self):
        """Test _invalid_token without pool"""
        self._invalid_token(False)
492

493 494 495
    def test_invalid_token_pool(self):
        """Test _invalid_token using pool"""
        self._invalid_token(True)
496 497 498

    #- ---------------------------------
    # Test response for user 1
499 500
    def _auth_user(self, token, user_info, usage, pool):
        _mock_request([_request_ok])
501
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
502
            client = AstakosClient("https://example.com", use_pool=pool)
503
            auth_info = client.get_user_info(token, usage=usage)
504 505 506 507
        except:
            self.fail("Shouldn't raise an Exception")
        self.assertEqual(user_info, auth_info)

508 509
    def test_auth_user_one(self):
        """Test _auth_user for User 1 without pool, without usage"""
510 511 512
        global token_1, user_1
        user_info = dict(user_1)
        del user_info['usage']
513
        self._auth_user(token_1, user_info, False, False)
514

515 516
    def test_auth_user_one_usage(self):
        """Test _auth_user for User 1 without pool, with usage"""
517
        global token_1, user_1
518
        self._auth_user(token_1, user_1, True, False)
519

520 521
    def test_auth_user_one_usage_pool(self):
        """Test _auth_user for User 1 using pool, with usage"""
522
        global token_1, user_1
523
        self._auth_user(token_1, user_1, True, True)
524

525 526
    def test_auth_user_two(self):
        """Test _auth_user for User 2 without pool, without usage"""
527 528 529
        global token_2, user_2
        user_info = dict(user_2)
        del user_info['usage']
530
        self._auth_user(token_2, user_info, False, False)
531

532 533
    def test_auth_user_two_usage(self):
        """Test _auth_user for User 2 without pool, with usage"""
534
        global token_2, user_2
535
        self._auth_user(token_2, user_2, True, False)
536

537 538
    def test_auth_user_two_usage_pool(self):
        """Test _auth_user for User 2 using pool, with usage"""
539
        global token_2, user_2
540
        self._auth_user(token_2, user_2, True, True)
541 542 543

    # ----------------------------------
    # Test retry functionality
544
    def test_offline_retry(self):
545
        """Test retry functionality for getUserInfo"""
546
        global token_1, user_1
547
        _mock_request([_request_offline, _request_offline, _request_ok])
548
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
549
            client = AstakosClient("https://example.com", retry=2)
550
            auth_info = client.get_user_info(token_1, usage=True)
551 552 553
        except:
            self.fail("Shouldn't raise an Exception")
        self.assertEqual(user_1, auth_info)
554 555


556 557 558 559 560
class TestDisplayNames(unittest.TestCase):
    """Test cases for functions getDisplayNames/getDisplayName"""

    # ----------------------------------
    # Test the response we get for invalid token
561
    def test_invalid_token(self):
562 563 564
        """Test the response we get for invalid token (without pool)"""
        global user_1
        token = "skaksaFlBl+fasFdaf24sx=="
565
        _mock_request([_request_ok])
566
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
567
            client = AstakosClient("https://example.com")
568
            client.get_usernames(token, [user_1['uuid']])
569
        except Unauthorized:
570 571 572
            pass
        except Exception:
            self.fail("Should have returned 401 (Invalid X-Auth-Token)")
573 574 575 576 577
        else:
            self.fail("Should have returned 401 (Invalid X-Auth-Token)")

    # ----------------------------------
    # Get Info for both users
578 579
    def test_usernames(self):
        """Test get_usernames with both users"""
580
        global token_1, user_1, user_2
581
        _mock_request([_request_ok])
582
        try:
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
583
            client = AstakosClient("https://example.com")
584
            catalog = client.get_usernames(
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
585
                token_1, [user_1['uuid'], user_2['uuid']])
586 587 588 589 590 591 592
        except:
            self.fail("Shouldn't raise an Exception")
        self.assertEqual(catalog[user_1['uuid']], user_1['username'])
        self.assertEqual(catalog[user_2['uuid']], user_2['username'])

    # ----------------------------------
    # Get info for user 1
593 594
    def test_username_user_one(self):
        """Test get_username for User One"""
595
        global token_2, user_1
596
        _mock_request([_request_offline, _request_ok])
597 598
        try:
            client = AstakosClient(
Ilias Tsitsimpis's avatar
Ilias Tsitsimpis committed
599
                "https://example.com", use_pool=True, retry=2)
600
            info = client.get_username(token_2, user_1['uuid'])
601 602 603 604
        except:
            self.fail("Shouldn't raise an Exception")
        self.assertEqual(info, user_1['username'])

605 606
    # ----------------------------------
    # Get info with wrong uuid
607
    def test_no_username(self):
608
        global token_1
609
        _mock_request([_request_ok])
610 611
        try:
            client = AstakosClient("https://example.com")
612 613
            client.get_username(token_1, "1234")
        except NoUserName:
614 615 616 617 618 619
            pass
        except:
            self.fail("Should have raised NoDisplayName exception")
        else:
            self.fail("Should have raised NoDisplayName exception")

620

621 622 623 624 625
class TestGetUUIDs(unittest.TestCase):
    """Test cases for functions getUUIDs/getUUID"""

    # ----------------------------------
    # Test the response we get for invalid token
626
    def test_invalid_token(self):
627 628 629
        """Test the response we get for invalid token (using pool)"""
        global user_1
        token = "skaksaFlBl+fasFdaf24sx=="
630
        _mock_request([_request_ok])
631 632
        try:
            client = AstakosClient("https://example.com")
633
            client.get_uuids(token, [user_1['username']])
634
        except Unauthorized:
635 636 637
            pass
        except Exception:
            self.fail("Should have returned 401 (Invalid X-Auth-Token)")
638 639 640 641 642
        else:
            self.fail("Should have returned 401 (Invalid X-Auth-Token)")

    # ----------------------------------
    # Get info for both users
643 644
    def test_uuids(self):
        """Test get_uuids with both users"""
645
        global token_1, user_1, user_2
646
        _mock_request([_request_ok])
647 648
        try:
            client = AstakosClient("https://example.com")
649
            catalog = client.get_uuids(
650 651 652 653 654 655 656 657
                token_1, [user_1['username'], user_2['username']])
        except:
            self.fail("Shouldn't raise an Exception")
        self.assertEqual(catalog[user_1['username']], user_1['uuid'])
        self.assertEqual(catalog[user_2['username']], user_2['uuid'])

    # ----------------------------------
    # Get uuid for user 2
658 659
    def test_get_uuid_user_two(self):
        """Test get_uuid for User Two"""
660
        global token_1, user_2
661
        _mock_request([_request_offline, _request_ok])
662 663
        try:
            client = AstakosClient("https://example.com", retry=1)
664
            info = client.get_uuid(token_2, user_1['username'])
665 666 667 668
        except:
            self.fail("Shouldn't raise an Exception")
        self.assertEqual(info, user_1['uuid'])

669 670
    # ----------------------------------
    # Get uuid with wrong username
671
    def test_no_uuid(self):
672
        global token_1
673
        _mock_request([_request_ok])
674 675
        try:
            client = AstakosClient("https://example.com")
676
            client.get_uuid(token_1, "1234")
677 678 679 680 681 682 683
        except NoUUID:
            pass
        except:
            self.fail("Should have raised NoUUID exception")
        else:
            self.fail("Should have raised NoUUID exception")

684

685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700
class TestResources(unittest.TestCase):
    """Test cases for function get_resources"""

    # ----------------------------------
    # Test function call of get_resources
    def test_get_resources(self):
        global resources
        _mock_request([_request_offline, _request_ok])
        try:
            client = AstakosClient("https://example.com", retry=1)
            result = client.get_resources()
        except Exception as err:
            self.fail("Shouldn't raise Exception %s" % err)
        self.assertEqual(resources, result)


701 702 703 704
# ----------------------------
# Run tests
if __name__ == "__main__":
    unittest.main()