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

fix: add back python 2.7 for gcloud usage only #892

Merged
merged 8 commits into from Oct 21, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
4 changes: 3 additions & 1 deletion google/auth/_cloud_sdk.py
Expand Up @@ -18,6 +18,8 @@
import os
import subprocess

import six

from google.auth import environment_vars
from google.auth import exceptions

Expand Down Expand Up @@ -154,4 +156,4 @@ def get_auth_access_token(account=None):
new_exc = exceptions.UserAccessTokenError(
"Failed to obtain access token", caught_exc
)
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)
11 changes: 8 additions & 3 deletions google/auth/_credentials_async.py
Expand Up @@ -18,10 +18,13 @@
import abc
import inspect

import six

from google.auth import credentials


class Credentials(credentials.Credentials, metaclass=abc.ABCMeta):
@six.add_metaclass(abc.ABCMeta)
class Credentials(credentials.Credentials):
"""Async inherited credentials class from google.auth.credentials.
The added functionality is the before_request call which requires
async/await syntax.
Expand Down Expand Up @@ -81,7 +84,8 @@ class AnonymousCredentials(credentials.AnonymousCredentials, Credentials):
"""


class ReadOnlyScoped(credentials.ReadOnlyScoped, metaclass=abc.ABCMeta):
@six.add_metaclass(abc.ABCMeta)
class ReadOnlyScoped(credentials.ReadOnlyScoped):
"""Interface for credentials whose scopes can be queried.

OAuth 2.0-based credentials allow limiting access using scopes as described
Expand Down Expand Up @@ -167,5 +171,6 @@ def with_scopes_if_required(credentials, scopes):
return credentials


class Signing(credentials.Signing, metaclass=abc.ABCMeta):
@six.add_metaclass(abc.ABCMeta)
class Signing(credentials.Signing):
"""Interface for credentials that can cryptographically sign messages."""
8 changes: 5 additions & 3 deletions google/auth/_default.py
Expand Up @@ -23,6 +23,8 @@
import os
import warnings

import six

from google.auth import environment_vars
from google.auth import exceptions
import google.auth.transport._http_client
Expand Down Expand Up @@ -116,7 +118,7 @@ def load_credentials_from_file(
new_exc = exceptions.DefaultCredentialsError(
"File {} is not a valid json file.".format(filename), caught_exc
)
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)

# The type key should indicate that the file is either a service account
# credentials file or an authorized user credentials file.
Expand All @@ -132,7 +134,7 @@ def load_credentials_from_file(
except ValueError as caught_exc:
msg = "Failed to load authorized user credentials from {}".format(filename)
new_exc = exceptions.DefaultCredentialsError(msg, caught_exc)
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)
if quota_project_id:
credentials = credentials.with_quota_project(quota_project_id)
if not credentials.quota_project_id:
Expand All @@ -149,7 +151,7 @@ def load_credentials_from_file(
except ValueError as caught_exc:
msg = "Failed to load service account credentials from {}".format(filename)
new_exc = exceptions.DefaultCredentialsError(msg, caught_exc)
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)
if quota_project_id:
credentials = credentials.with_quota_project(quota_project_id)
return credentials, info.get("project_id")
Expand Down
8 changes: 5 additions & 3 deletions google/auth/_default_async.py
Expand Up @@ -21,6 +21,8 @@
import json
import os

import six

from google.auth import _default
from google.auth import environment_vars
from google.auth import exceptions
Expand Down Expand Up @@ -61,7 +63,7 @@ def load_credentials_from_file(filename, scopes=None, quota_project_id=None):
new_exc = exceptions.DefaultCredentialsError(
"File {} is not a valid json file.".format(filename), caught_exc
)
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)

# The type key should indicate that the file is either a service account
# credentials file or an authorized user credentials file.
Expand All @@ -77,7 +79,7 @@ def load_credentials_from_file(filename, scopes=None, quota_project_id=None):
except ValueError as caught_exc:
msg = "Failed to load authorized user credentials from {}".format(filename)
new_exc = exceptions.DefaultCredentialsError(msg, caught_exc)
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)
if quota_project_id:
credentials = credentials.with_quota_project(quota_project_id)
if not credentials.quota_project_id:
Expand All @@ -94,7 +96,7 @@ def load_credentials_from_file(filename, scopes=None, quota_project_id=None):
except ValueError as caught_exc:
msg = "Failed to load service account credentials from {}".format(filename)
new_exc = exceptions.DefaultCredentialsError(msg, caught_exc)
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)
return credentials, info.get("project_id")

else:
Expand Down
17 changes: 11 additions & 6 deletions google/auth/_helpers.py
Expand Up @@ -17,7 +17,9 @@
import base64
import calendar
import datetime
import urllib

import six
from six.moves import urllib


# Token server doesn't provide a new a token when doing refresh unless the
Expand Down Expand Up @@ -85,6 +87,9 @@ def datetime_to_secs(value):
def to_bytes(value, encoding="utf-8"):
"""Converts a string value to bytes, if necessary.

Unfortunately, ``six.b`` is insufficient for this task since in
Python 2 because it does not modify ``unicode`` objects.

Args:
value (Union[str, bytes]): The value to be converted.
encoding (str): The encoding to use to convert unicode to bytes.
Expand All @@ -97,8 +102,8 @@ def to_bytes(value, encoding="utf-8"):
Raises:
ValueError: If the value could not be converted to bytes.
"""
result = value.encode(encoding) if isinstance(value, str) else value
if isinstance(result, bytes):
result = value.encode(encoding) if isinstance(value, six.text_type) else value
if isinstance(result, six.binary_type):
return result
else:
raise ValueError("{0!r} could not be converted to bytes".format(value))
Expand All @@ -117,8 +122,8 @@ def from_bytes(value):
Raises:
ValueError: If the value could not be converted to unicode.
"""
result = value.decode("utf-8") if isinstance(value, bytes) else value
if isinstance(result, str):
result = value.decode("utf-8") if isinstance(value, six.binary_type) else value
if isinstance(result, six.text_type):
return result
else:
raise ValueError("{0!r} could not be converted to unicode".format(value))
Expand Down Expand Up @@ -160,7 +165,7 @@ def update_query(url, params, remove=None):
query_params.update(params)
# Remove any values specified in remove.
query_params = {
key: value for key, value in query_params.items() if key not in remove
key: value for key, value in six.iteritems(query_params) if key not in remove
}
# Re-encoded the query string.
new_query = urllib.parse.urlencode(query_params, doseq=True)
Expand Down
6 changes: 4 additions & 2 deletions google/auth/_oauth2client.py
Expand Up @@ -21,6 +21,8 @@

from __future__ import absolute_import

import six

from google.auth import _helpers
import google.auth.app_engine
import google.auth.compute_engine
Expand All @@ -32,7 +34,7 @@
import oauth2client.contrib.gce
import oauth2client.service_account
except ImportError as caught_exc:
raise ImportError("oauth2client is not installed.") from caught_exc
six.raise_from(ImportError("oauth2client is not installed."), caught_exc)

try:
import oauth2client.contrib.appengine # pytype: disable=import-error
Expand Down Expand Up @@ -164,4 +166,4 @@ def convert(credentials):
return _CLASS_CONVERSION_MAP[credentials_class](credentials)
except KeyError as caught_exc:
new_exc = ValueError(_CONVERT_ERROR_TMPL.format(credentials_class))
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)
4 changes: 3 additions & 1 deletion google/auth/_service_account_info.py
Expand Up @@ -17,6 +17,8 @@
import io
import json

import six

from google.auth import crypt


Expand All @@ -41,7 +43,7 @@ def from_dict(data, require=None):
"""
keys_needed = set(require if require is not None else [])

missing = keys_needed.difference(data)
missing = keys_needed.difference(six.iterkeys(data))

if missing:
raise ValueError(
Expand Down
21 changes: 15 additions & 6 deletions google/auth/aws.py
Expand Up @@ -39,13 +39,20 @@

import hashlib
import hmac
import http.client
import io
import json
import os
import posixpath
import re
import urllib
from urllib.parse import urljoin

try:
from urllib.parse import urljoin
# Python 2.7 compatibility
except ImportError: # pragma: NO COVER
from urlparse import urljoin

from six.moves import http_client
from six.moves import urllib

from google.auth import _helpers
from google.auth import environment_vars
Expand Down Expand Up @@ -116,7 +123,9 @@ def get_request_options(
# Normalize the URL path. This is needed for the canonical_uri.
# os.path.normpath can't be used since it normalizes "/" paths
# to "\\" in Windows OS.
normalized_uri = urllib.parse.urlparse(urljoin(url, uri.path))
normalized_uri = urllib.parse.urlparse(
urljoin(url, posixpath.normpath(uri.path))
)
# Validate provided URL.
if not uri.hostname or uri.scheme != "https":
raise ValueError("Invalid AWS service URL")
Expand Down Expand Up @@ -631,7 +640,7 @@ def _get_metadata_security_credentials(self, request, role_name):
else response.data
)

if response.status != http.client.OK:
if response.status != http_client.OK:
raise exceptions.RefreshError(
"Unable to retrieve AWS security credentials", response_body
)
Expand Down Expand Up @@ -670,7 +679,7 @@ def _get_metadata_role_name(self, request):
else response.data
)

if response.status != http.client.OK:
if response.status != http_client.OK:
raise exceptions.RefreshError(
"Unable to retrieve AWS role name", response_body
)
Expand Down
12 changes: 7 additions & 5 deletions google/auth/compute_engine/_metadata.py
Expand Up @@ -18,11 +18,13 @@
"""

import datetime
import http.client
import json
import logging
import os
from urllib import parse as urlparse

import six
from six.moves import http_client
from six.moves.urllib import parse as urlparse

from google.auth import _helpers
from google.auth import environment_vars
Expand Down Expand Up @@ -89,7 +91,7 @@ def ping(request, timeout=_METADATA_DEFAULT_TIMEOUT, retry_count=3):

metadata_flavor = response.headers.get(_METADATA_FLAVOR_HEADER)
return (
response.status == http.client.OK
response.status == http_client.OK
and metadata_flavor == _METADATA_FLAVOR_VALUE
)

Expand Down Expand Up @@ -163,7 +165,7 @@ def get(
"metadata service. Compute Engine Metadata server unavailable".format(url)
)

if response.status == http.client.OK:
if response.status == http_client.OK:
content = _helpers.from_bytes(response.data)
if response.headers["content-type"] == "application/json":
try:
Expand All @@ -173,7 +175,7 @@ def get(
"Received invalid JSON from the Google Compute Engine"
"metadata service: {:.20}".format(content)
)
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)
else:
return content
else:
Expand Down
6 changes: 4 additions & 2 deletions google/auth/compute_engine/credentials.py
Expand Up @@ -21,6 +21,8 @@

import datetime

import six

from google.auth import _helpers
from google.auth import credentials
from google.auth import exceptions
Expand Down Expand Up @@ -112,7 +114,7 @@ def refresh(self, request):
)
except exceptions.TransportError as caught_exc:
new_exc = exceptions.RefreshError(caught_exc)
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)

@property
def service_account_email(self):
Expand Down Expand Up @@ -350,7 +352,7 @@ def _call_metadata_identity_endpoint(self, request):
id_token = _metadata.get(request, path, params=params)
except exceptions.TransportError as caught_exc:
new_exc = exceptions.RefreshError(caught_exc)
raise new_exc from caught_exc
six.raise_from(new_exc, caught_exc)

_, payload, _, _ = jwt._unverified_decode(id_token)
return id_token, datetime.datetime.fromtimestamp(payload["exp"])
Expand Down
11 changes: 8 additions & 3 deletions google/auth/credentials.py
Expand Up @@ -17,10 +17,13 @@

import abc

import six

from google.auth import _helpers


class Credentials(object, metaclass=abc.ABCMeta):
@six.add_metaclass(abc.ABCMeta)
class Credentials(object):
"""Base class for all credentials.

All credentials have a :attr:`token` that is used for authentication and
Expand Down Expand Up @@ -184,7 +187,8 @@ def before_request(self, request, method, url, headers):
"""Anonymous credentials do nothing to the request."""


class ReadOnlyScoped(object, metaclass=abc.ABCMeta):
@six.add_metaclass(abc.ABCMeta)
class ReadOnlyScoped(object):
"""Interface for credentials whose scopes can be queried.

OAuth 2.0-based credentials allow limiting access using scopes as described
Expand Down Expand Up @@ -325,7 +329,8 @@ def with_scopes_if_required(credentials, scopes, default_scopes=None):
return credentials


class Signing(object, metaclass=abc.ABCMeta):
@six.add_metaclass(abc.ABCMeta)
class Signing(object):
"""Interface for credentials that can cryptographically sign messages."""

@abc.abstractmethod
Expand Down
4 changes: 3 additions & 1 deletion google/auth/crypt/__init__.py
Expand Up @@ -37,6 +37,8 @@
version is at least 1.4.0.
"""

import six

from google.auth.crypt import base
from google.auth.crypt import rsa

Expand Down Expand Up @@ -88,7 +90,7 @@ class to use for verification. This can be used to select different
Returns:
bool: True if the signature is valid, otherwise False.
"""
if isinstance(certs, (str, bytes)):
if isinstance(certs, (six.text_type, six.binary_type)):
certs = [certs]

for cert in certs:
Expand Down