Skip to content

Commit

Permalink
Adding _DEFAULTS stubs in all tests that use it.
Browse files Browse the repository at this point in the history
Introduces
- concept of `implicit` for `_DefaultsContainer`.
- testing module for datastore for patching

Verified all test cases that would accidentally rely on _DEFAULTS implicit
behavior by using a custom `_DefaultsContainer` that raises when the
instance is implicit.

Main delta for the custom properties:

diff --git a/gcloud/datastore/_implicit_environ.py b/gcloud/datastore/_implicit_environ.py
index 3afc954..1d38562 100644
--- a/gcloud/datastore/_implicit_environ.py
+++ b/gcloud/datastore/_implicit_environ.py
@@ -38,9 +38,37 @@ class _DefaultsContainer(object):
     :param dataset_id: Persistent implied dataset ID from environment.
     """

-    def __init__(self, connection=None, dataset_id=None):
-        self.connection = connection
-        self.dataset_id = dataset_id
+    class FooError(Exception):
+        pass
+
+    @Property
+    def dataset_id(self):
+        if self.implicit:
+            raise self.FooError
+        return self._dataset_id
+
+    @dataset_id.setter
+    def dataset_id(self, value):
+        if self.implicit:
+            raise self.FooError
+        self._dataset_id = value
+
+    @Property
+    def connection(self):
+        if self.implicit:
+            raise self.FooError
+        return self._connection
+
+    @connection.setter
+    def connection(self, value):
+        if self.implicit:
+            raise self.FooError
+        self._connection = value
+
+    def __init__(self, connection=None, dataset_id=None, implicit=False):
+        self.implicit = implicit
+        self._connection = connection
+        self._dataset_id = dataset_id

 def app_engine_id():
  • Loading branch information
dhermes committed Feb 19, 2015
1 parent 998c724 commit 5e281dd
Show file tree
Hide file tree
Showing 11 changed files with 158 additions and 105 deletions.
5 changes: 3 additions & 2 deletions gcloud/datastore/_implicit_environ.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,8 @@ class _DefaultsContainer(object):
:param dataset_id: Persistent implied dataset ID from environment.
"""

def __init__(self, connection=None, dataset_id=None):
def __init__(self, connection=None, dataset_id=None, implicit=False):
self.implicit = implicit
self.connection = connection
self.dataset_id = dataset_id

Expand Down Expand Up @@ -107,4 +108,4 @@ def get_default_dataset_id():
return _DEFAULTS.dataset_id


_DEFAULTS = _DefaultsContainer()
_DEFAULTS = _DefaultsContainer(implicit=True)
33 changes: 33 additions & 0 deletions gcloud/datastore/_testing.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
# Copyright 2014 Google Inc. All rights reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

"""Shared datastore testing utilities."""

from gcloud._testing import _Monkey
from gcloud.datastore import _implicit_environ
from gcloud.datastore._implicit_environ import _DefaultsContainer


def _monkey_defaults(*args, **kwargs):
mock_defaults = _DefaultsContainer(*args, **kwargs)
return _Monkey(_implicit_environ, _DEFAULTS=mock_defaults)


def _setup_defaults(test_case):
test_case._replaced_defaults = _implicit_environ._DEFAULTS
_implicit_environ._DEFAULTS = _DefaultsContainer()


def _tear_down_defaults(test_case):
_implicit_environ._DEFAULTS = test_case._replaced_defaults
20 changes: 8 additions & 12 deletions gcloud/datastore/test___init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,14 +18,12 @@
class Test_set_default_dataset_id(unittest2.TestCase):

def setUp(self):
from gcloud.datastore import _implicit_environ
self._replaced_defaults = _implicit_environ._DEFAULTS
_implicit_environ._DEFAULTS = _implicit_environ._DefaultsContainer(
None, None)
from gcloud.datastore._testing import _setup_defaults
_setup_defaults(self)

def tearDown(self):
from gcloud.datastore import _implicit_environ
_implicit_environ._DEFAULTS = self._replaced_defaults
from gcloud.datastore._testing import _tear_down_defaults
_tear_down_defaults(self)

def _callFUT(self, dataset_id=None):
from gcloud.datastore import set_default_dataset_id
Expand Down Expand Up @@ -276,14 +274,12 @@ def test_set_implicit_three_env_appengine_and_compute(self):
class Test_set_default_connection(unittest2.TestCase):

def setUp(self):
from gcloud.datastore import _implicit_environ
self._replaced_defaults = _implicit_environ._DEFAULTS
_implicit_environ._DEFAULTS = _implicit_environ._DefaultsContainer(
None, None)
from gcloud.datastore._testing import _setup_defaults
_setup_defaults(self)

def tearDown(self):
from gcloud.datastore import _implicit_environ
_implicit_environ._DEFAULTS = self._replaced_defaults
from gcloud.datastore._testing import _tear_down_defaults
_tear_down_defaults(self)

def _callFUT(self, connection=None):
from gcloud.datastore import set_default_connection
Expand Down
28 changes: 20 additions & 8 deletions gcloud/datastore/test__implicit_environ.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,14 @@

class Test_get_default_connection(unittest2.TestCase):

def setUp(self):
from gcloud.datastore._testing import _setup_defaults
_setup_defaults(self)

def tearDown(self):
from gcloud.datastore._testing import _tear_down_defaults
_tear_down_defaults(self)

def _callFUT(self):
from gcloud.datastore._implicit_environ import get_default_connection
return get_default_connection()
Expand All @@ -25,17 +33,23 @@ def test_default(self):
self.assertEqual(self._callFUT(), None)

def test_preset(self):
from gcloud._testing import _Monkey
from gcloud.datastore import _implicit_environ
from gcloud.datastore._testing import _monkey_defaults

SENTINEL = object()
MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(SENTINEL, None)
with _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS):
with _monkey_defaults(connection=SENTINEL):
self.assertEqual(self._callFUT(), SENTINEL)


class Test_get_default_dataset_id(unittest2.TestCase):

def setUp(self):
from gcloud.datastore._testing import _setup_defaults
_setup_defaults(self)

def tearDown(self):
from gcloud.datastore._testing import _tear_down_defaults
_tear_down_defaults(self)

def _callFUT(self):
from gcloud.datastore._implicit_environ import get_default_dataset_id
return get_default_dataset_id()
Expand All @@ -44,10 +58,8 @@ def test_default(self):
self.assertEqual(self._callFUT(), None)

def test_preset(self):
from gcloud._testing import _Monkey
from gcloud.datastore import _implicit_environ
from gcloud.datastore._testing import _monkey_defaults

SENTINEL = object()
MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(None, SENTINEL)
with _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS):
with _monkey_defaults(dataset_id=SENTINEL):
self.assertEqual(self._callFUT(), SENTINEL)
81 changes: 44 additions & 37 deletions gcloud/datastore/test_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,10 +26,8 @@ def _callFUT(self, passed=_MARKER, first_key=None):
return _require_dataset_id(dataset_id=passed, first_key=first_key)

def _monkey(self, dataset_id):
from gcloud.datastore import _implicit_environ
from gcloud._testing import _Monkey
MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(None, dataset_id)
return _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS)
from gcloud.datastore._testing import _monkey_defaults
return _monkey_defaults(dataset_id=dataset_id)

def test_implicit_unset_wo_keys(self):
with self._monkey(None):
Expand Down Expand Up @@ -121,10 +119,8 @@ def _callFUT(self, passed=_MARKER):
return _require_connection(passed)

def _monkey(self, connection):
from gcloud.datastore import _implicit_environ
from gcloud._testing import _Monkey
MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(connection, None)
return _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS)
from gcloud.datastore._testing import _monkey_defaults
return _monkey_defaults(connection=connection)

def test_implicit_unset(self):
with self._monkey(None):
Expand Down Expand Up @@ -164,6 +160,14 @@ def test_implicit_set_passed_explicitly(self):

class Test_get_function(unittest2.TestCase):

def setUp(self):
from gcloud.datastore._testing import _setup_defaults
_setup_defaults(self)

def tearDown(self):
from gcloud.datastore._testing import _tear_down_defaults
_tear_down_defaults(self)

def _callFUT(self, keys, missing=None, deferred=None,
connection=None, dataset_id=None):
from gcloud.datastore.api import get
Expand Down Expand Up @@ -455,10 +459,9 @@ def test_hit_multiple_keys_different_dataset(self):
dataset_id=DATASET_ID1)

def test_implicit_wo_transaction(self):
from gcloud.datastore import _implicit_environ
from gcloud.datastore._testing import _monkey_defaults
from gcloud.datastore.key import Key
from gcloud.datastore.test_connection import _Connection
from gcloud._testing import _Monkey

DATASET_ID = 'DATASET'
KIND = 'Kind'
Expand All @@ -473,9 +476,8 @@ def test_implicit_wo_transaction(self):
CUSTOM_CONNECTION = _Connection(entity_pb)

key = Key(KIND, ID, dataset_id=DATASET_ID)
MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(CUSTOM_CONNECTION,
DATASET_ID)
with _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS):
with _monkey_defaults(connection=CUSTOM_CONNECTION,
dataset_id=DATASET_ID):
result, = self._callFUT([key])

expected_called_with = {
Expand Down Expand Up @@ -566,6 +568,14 @@ def test_max_loops(self):

class Test_put_function(unittest2.TestCase):

def setUp(self):
from gcloud.datastore._testing import _setup_defaults
_setup_defaults(self)

def tearDown(self):
from gcloud.datastore._testing import _tear_down_defaults
_tear_down_defaults(self)

def _callFUT(self, entities, connection=None, dataset_id=None):
from gcloud.datastore.api import put
return put(entities, connection=connection, dataset_id=dataset_id)
Expand Down Expand Up @@ -668,8 +678,7 @@ def test_existing_batch_w_completed_key(self):
self.assertEqual(len(CURR_BATCH.mutation.delete), 0)

def test_implicit_connection(self):
from gcloud._testing import _Monkey
from gcloud.datastore import _implicit_environ
from gcloud.datastore._testing import _monkey_defaults
from gcloud.datastore.test_batch import _Connection
from gcloud.datastore.test_batch import _Entity
from gcloud.datastore.test_batch import _Key
Expand All @@ -680,8 +689,7 @@ def test_implicit_connection(self):
entity = _Entity(foo=u'bar')
key = entity.key = _Key(_DATASET)

MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(connection, None)
with _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS):
with _monkey_defaults(connection=connection):
# Set up Batch on stack so we can check it is used.
with _NoCommitBatch(_DATASET, connection) as CURR_BATCH:
result = self._callFUT([entity])
Expand All @@ -700,6 +708,14 @@ def test_implicit_connection(self):

class Test_delete_function(unittest2.TestCase):

def setUp(self):
from gcloud.datastore._testing import _setup_defaults
_setup_defaults(self)

def tearDown(self):
from gcloud.datastore._testing import _tear_down_defaults
_tear_down_defaults(self)

def _callFUT(self, keys, connection=None, dataset_id=None):
from gcloud.datastore.api import delete
return delete(keys, connection=connection, dataset_id=dataset_id)
Expand Down Expand Up @@ -761,8 +777,7 @@ def test_no_batch(self):
self.assertEqual(list(mutation.delete), [key.to_protobuf()])

def test_wo_batch_w_key_different_than_default_dataset_id(self):
from gcloud._testing import _Monkey
from gcloud.datastore import _implicit_environ
from gcloud.datastore._testing import _monkey_defaults
from gcloud.datastore.test_batch import _Connection
from gcloud.datastore.test_batch import _Key

Expand All @@ -772,9 +787,8 @@ def test_wo_batch_w_key_different_than_default_dataset_id(self):
connection = _Connection()
key = _Key(_DATASET)

MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(connection,
_DEFAULT_DATASET)
with _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS):
with _monkey_defaults(connection=connection,
dataset_id=_DEFAULT_DATASET):
result = self._callFUT([key])
self.assertEqual(result, None)
self.assertEqual(len(connection._committed), 1)
Expand Down Expand Up @@ -825,8 +839,7 @@ def test_w_existing_transaction(self):
self.assertEqual(len(connection._committed), 0)

def test_implicit_connection_and_dataset_id(self):
from gcloud._testing import _Monkey
from gcloud.datastore import _implicit_environ
from gcloud.datastore._testing import _monkey_defaults
from gcloud.datastore.test_batch import _Connection
from gcloud.datastore.test_batch import _Key

Expand All @@ -835,9 +848,7 @@ def test_implicit_connection_and_dataset_id(self):
connection = _Connection()
key = _Key(_DATASET)

MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(connection,
_DATASET)
with _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS):
with _monkey_defaults(connection=connection, dataset_id=_DATASET):
# Set up Batch on stack so we can check it is used.
with _NoCommitBatch(_DATASET, connection) as CURR_BATCH:
result = self._callFUT([key])
Expand Down Expand Up @@ -875,32 +886,28 @@ def test_w_explicit_connection(self):
self.assertEqual(len(CONNECTION._called_key_pbs), NUM_IDS)

def test_w_implicit_connection(self):
from gcloud.datastore import _implicit_environ
from gcloud.datastore._testing import _monkey_defaults
from gcloud.datastore.key import Key
from gcloud.datastore.test_connection import _Connection
from gcloud._testing import _Monkey

CUSTOM_CONNECTION = _Connection()
NUM_IDS = 2
MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(CUSTOM_CONNECTION,
'DATASET')
with _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS):
with _monkey_defaults(connection=CUSTOM_CONNECTION,
dataset_id='DATASET'):
INCOMPLETE_KEY = Key('KIND')
result = self._callFUT(INCOMPLETE_KEY, NUM_IDS)

# Check the IDs returned.
self.assertEqual([key.id for key in result], list(range(NUM_IDS)))

def test_with_already_completed_key(self):
from gcloud.datastore import _implicit_environ
from gcloud.datastore._testing import _monkey_defaults
from gcloud.datastore.key import Key
from gcloud.datastore.test_connection import _Connection
from gcloud._testing import _Monkey

CUSTOM_CONNECTION = _Connection()
MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(CUSTOM_CONNECTION,
'DATASET')
with _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS):
with _monkey_defaults(connection=CUSTOM_CONNECTION,
dataset_id='DATASET'):
COMPLETE_KEY = Key('KIND', 1234)
self.assertRaises(ValueError, self._callFUT,
COMPLETE_KEY, 2)
Expand Down
13 changes: 4 additions & 9 deletions gcloud/datastore/test_batch.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,11 +27,9 @@ def _makeOne(self, dataset_id=None, connection=None):
connection=connection)

def test_ctor_missing_required(self):
from gcloud._testing import _Monkey
from gcloud.datastore import _implicit_environ
from gcloud.datastore._testing import _monkey_defaults

MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(None, None)
with _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS):
with _monkey_defaults():
self.assertRaises(ValueError, self._makeOne)
self.assertRaises(ValueError, self._makeOne, dataset_id=object())
self.assertRaises(ValueError, self._makeOne, connection=object())
Expand All @@ -48,15 +46,12 @@ def test_ctor_explicit(self):
self.assertEqual(batch._auto_id_entities, [])

def test_ctor_implicit(self):
from gcloud._testing import _Monkey
from gcloud.datastore import _implicit_environ
from gcloud.datastore._testing import _monkey_defaults
from gcloud.datastore._datastore_v1_pb2 import Mutation
_DATASET = 'DATASET'
CONNECTION = _Connection()

MOCK_DEFAULTS = _implicit_environ._DefaultsContainer(CONNECTION,
_DATASET)
with _Monkey(_implicit_environ, _DEFAULTS=MOCK_DEFAULTS):
with _monkey_defaults(connection=CONNECTION, dataset_id=_DATASET):
batch = self._makeOne()

self.assertEqual(batch.dataset_id, _DATASET)
Expand Down
10 changes: 4 additions & 6 deletions gcloud/datastore/test_entity.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,14 +22,12 @@
class TestEntity(unittest2.TestCase):

def setUp(self):
from gcloud.datastore import _implicit_environ
self._replaced_defaults = _implicit_environ._DEFAULTS
_implicit_environ._DEFAULTS = _implicit_environ._DefaultsContainer(
None, None)
from gcloud.datastore._testing import _setup_defaults
_setup_defaults(self)

def tearDown(self):
from gcloud.datastore import _implicit_environ
_implicit_environ._DEFAULTS = self._replaced_defaults
from gcloud.datastore._testing import _tear_down_defaults
_tear_down_defaults(self)

def _getTargetClass(self):
from gcloud.datastore.entity import Entity
Expand Down
Loading

0 comments on commit 5e281dd

Please sign in to comment.