diff --git a/gcloud/credentials.py b/gcloud/credentials.py index 582537f324cc..37ce209e69b4 100644 --- a/gcloud/credentials.py +++ b/gcloud/credentials.py @@ -24,6 +24,7 @@ from Crypto.PublicKey import RSA from Crypto.Signature import PKCS1_v1_5 from oauth2client import client +from oauth2client.client import _get_application_default_credential_from_file from oauth2client import crypt from oauth2client import service_account import pytz @@ -72,8 +73,37 @@ def get_credentials(): return client.GoogleCredentials.get_application_default() +def get_for_service_account_json(json_credentials_path, scope=None): + """Gets the credentials for a service account with JSON key. + + :type json_credentials_path: string + :param json_credentials_path: The path to a private key file (this file was + given to you when you created the service + account). This file must contain a JSON + object with a private key and other + credentials information (downloaded from the + Google APIs console). + + :type scope: string or tuple of string + :param scope: The scope against which to authenticate. (Different services + require different scopes, check the documentation for which + scope is required for the different levels of access to any + particular API.) + + :rtype: :class:`oauth2client.client.GoogleCredentials`, + :class:`oauth2client.service_account._ServiceAccountCredentials` + :returns: New service account or Google (for a user JSON key file) + credentials object. + """ + credentials = _get_application_default_credential_from_file( + json_credentials_path) + if scope is not None: + credentials = credentials.create_scoped(scope) + return credentials + + def get_for_service_account_p12(client_email, private_key_path, scope=None): - """Gets the credentials for a service account. + """Gets the credentials for a service account with PKCS12 / p12 key. .. note:: This method is not used by default, instead :func:`get_credentials` diff --git a/gcloud/test_credentials.py b/gcloud/test_credentials.py index 7f352a70fac1..bb9c223c8408 100644 --- a/gcloud/test_credentials.py +++ b/gcloud/test_credentials.py @@ -61,6 +61,54 @@ def test_get_for_service_account_p12_w_scope(self): self.assertEqual(client._called_with, expected_called_with) +class Test_get_for_service_account_json(unittest2.TestCase): + + def _callFUT(self, json_credentials_path, scope=None): + from gcloud.credentials import get_for_service_account_json + return get_for_service_account_json(json_credentials_path, scope=scope) + + def test_it(self): + from gcloud._testing import _Monkey + from gcloud import credentials as MUT + + CREDS = _Credentials() + _filenames = [] + + def get_creds(filename): + _filenames.append(filename) + return CREDS + + FILENAME = object() + + renames = {'_get_application_default_credential_from_file': get_creds} + with _Monkey(MUT, **renames): + self._callFUT(FILENAME) + + self.assertEqual(_filenames, [FILENAME]) + self.assertFalse(hasattr(CREDS, '_scopes')) + + def test_it_with_scope(self): + from gcloud._testing import _Monkey + from gcloud import credentials as MUT + + CREDS = _Credentials() + _filenames = [] + + def get_creds(filename): + _filenames.append(filename) + return CREDS + + FILENAME = object() + SCOPE = object() + + renames = {'_get_application_default_credential_from_file': get_creds} + with _Monkey(MUT, **renames): + self._callFUT(FILENAME, scope=SCOPE) + + self.assertEqual(_filenames, [FILENAME]) + self.assertEqual(CREDS._scopes, SCOPE) + + class Test_generate_signed_url(unittest2.TestCase): def _callFUT(self, *args, **kwargs):