Skip to content
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.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
51 changes: 27 additions & 24 deletions bigtable/google/cloud/bigtable/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -31,16 +31,13 @@

import os

import google.auth
import google.auth.credentials
from google.gax.utils import metrics
from google.longrunning import operations_grpc

from google.cloud._helpers import make_insecure_stub
from google.cloud._helpers import make_secure_stub
from google.cloud._http import DEFAULT_USER_AGENT
from google.cloud.client import _ClientFactoryMixin
from google.cloud.client import _ClientProjectMixin
from google.cloud.client import ClientWithProject
from google.cloud.environment_vars import BIGTABLE_EMULATOR

from google.cloud.bigtable import __version__
Expand Down Expand Up @@ -166,13 +163,13 @@ def _make_table_stub(client):
client.emulator_host)


class Client(_ClientFactoryMixin, _ClientProjectMixin):
class Client(ClientWithProject):
"""Client for interacting with Google Cloud Bigtable API.

.. note::

Since the Cloud Bigtable API requires the gRPC transport, no
``http`` argument is accepted by this class.
``_http`` argument is accepted by this class.

:type project: :class:`str` or :func:`unicode <unicode>`
:param project: (Optional) The ID of the project which owns the
Expand Down Expand Up @@ -209,31 +206,21 @@ class Client(_ClientFactoryMixin, _ClientProjectMixin):

def __init__(self, project=None, credentials=None,
read_only=False, admin=False, user_agent=DEFAULT_USER_AGENT):
_ClientProjectMixin.__init__(self, project=project)
if credentials is None:
credentials, _ = google.auth.default()

if read_only and admin:
raise ValueError('A read-only client cannot also perform'
'administrative actions.')

scopes = []
if read_only:
scopes.append(READ_ONLY_SCOPE)
else:
scopes.append(DATA_SCOPE)

# NOTE: We set the scopes **before** calling the parent constructor.
# It **may** use those scopes in ``with_scopes_if_required``.
self._read_only = bool(read_only)

if admin:
scopes.append(ADMIN_SCOPE)

self._admin = bool(admin)
self.SCOPE = self._get_scopes()

credentials = google.auth.credentials.with_scopes_if_required(
credentials, scopes)

self._credentials = credentials
# NOTE: This API has no use for the _http argument, but sending it
# will have no impact since the _http() @property only lazily
# creates a working HTTP object.
super(Client, self).__init__(
project=project, credentials=credentials, _http=None)
self.user_agent = user_agent
self.emulator_host = os.getenv(BIGTABLE_EMULATOR)

Expand All @@ -244,6 +231,22 @@ def __init__(self, project=None, credentials=None,
self._operations_stub_internal = _make_operations_stub(self)
self._table_stub_internal = _make_table_stub(self)

def _get_scopes(self):
"""Get the scopes corresponding to admin / read-only state.

Returns:
Tuple[str, ...]: The tuple of scopes.
"""
if self._read_only:
scopes = (READ_ONLY_SCOPE,)
else:
scopes = (DATA_SCOPE,)

if self._admin:
scopes += (ADMIN_SCOPE,)

return scopes

def copy(self):
"""Make a copy of this client.

Expand Down
13 changes: 10 additions & 3 deletions bigtable/nox.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,10 +37,17 @@ def unit_tests(session, python_version):
session.install('-e', '.')

# Run py.test against the unit tests.
session.run('py.test', '--quiet',
'--cov=google.cloud.bigtable', '--cov=tests.unit', '--cov-append',
'--cov-config=.coveragerc', '--cov-report=', '--cov-fail-under=97',
session.run(
'py.test',
'--quiet',
'--cov=google.cloud.bigtable',
'--cov=tests.unit',
'--cov-append',
'--cov-config=.coveragerc',
'--cov-report=',
'--cov-fail-under=97',
'tests/unit',
*session.posargs
)


Expand Down
Loading