summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLudwig Hähne <lhaehne@gmail.com>2021-10-15 15:28:10 +0200
committerGitHub <noreply@github.com>2021-10-15 06:28:10 -0700
commit79d98d23cd589556b0dc51a7d10ea338e90a944e (patch)
tree182a76f4aabcb727e96643459eb527a32a57bd03
parent25e38dfbf488d969b42af7a3299e33044e7a8730 (diff)
downloadpymemcache-79d98d23cd589556b0dc51a7d10ea338e90a944e.tar.gz
Return default from hash client when using positional argument (#354)
When using HashClient with ignore_exc, get would always return None if no server is available and the default is passed as a positional argument. The other clients return the default value in this case. An earlier fix only had the desired effect when passing default as a keyword argument. For example, Django passes the default as a positional argument. Return the default value so HashClient behaves like the other clients.
-rw-r--r--ChangeLog.rst5
-rw-r--r--pymemcache/client/hash.py5
-rw-r--r--pymemcache/test/test_client_hash.py17
3 files changed, 22 insertions, 5 deletions
diff --git a/ChangeLog.rst b/ChangeLog.rst
index a73b219..cc448d9 100644
--- a/ChangeLog.rst
+++ b/ChangeLog.rst
@@ -1,6 +1,11 @@
Changelog
=========
+Unreleased
+----------
+* ``Client.get`` returns the default when using ``ignore_exc`` and if memcached
+ is unavailable
+
New in version 3.5.0
--------------------
* Sockets are now closed on ``MemcacheUnexpectedCloseError``.
diff --git a/pymemcache/client/hash.py b/pymemcache/client/hash.py
index db00d51..e5d89fe 100644
--- a/pymemcache/client/hash.py
+++ b/pymemcache/client/hash.py
@@ -356,9 +356,8 @@ class HashClient:
def set(self, key, *args, **kwargs):
return self._run_cmd('set', key, False, *args, **kwargs)
- def get(self, key, *args, **kwargs):
- default = kwargs.get('default', None)
- return self._run_cmd('get', key, default, *args, **kwargs)
+ def get(self, key, default=None, **kwargs):
+ return self._run_cmd('get', key, default, default=default, **kwargs)
def incr(self, key, *args, **kwargs):
return self._run_cmd('incr', key, False, *args, **kwargs)
diff --git a/pymemcache/test/test_client_hash.py b/pymemcache/test/test_client_hash.py
index 9ce48aa..f747845 100644
--- a/pymemcache/test/test_client_hash.py
+++ b/pymemcache/test/test_client_hash.py
@@ -262,6 +262,19 @@ class TestHashClient(ClientTestMixin, unittest.TestCase):
result = client.set('foo', 'bar')
assert result is False
+ def test_no_servers_left_return_positional_default(self):
+ from pymemcache.client.hash import HashClient
+ client = HashClient(
+ [], use_pooling=True,
+ ignore_exc=True,
+ timeout=1, connect_timeout=1
+ )
+
+ # Ensure compatibility with clients that pass the default as a
+ # positional argument
+ result = client.get('foo', 'default')
+ assert result == 'default'
+
def test_no_servers_left_with_set_many(self):
from pymemcache.client.hash import HashClient
client = HashClient(
@@ -381,7 +394,7 @@ class TestHashClient(ClientTestMixin, unittest.TestCase):
# Client gets removed because of socket timeout
assert ("127.0.0.1", 11211) in client._dead_clients
- test_client.get.side_effect = lambda *_: "Some value"
+ test_client.get.side_effect = lambda *_, **_kw: "Some value"
# Client should be retried and brought back
assert client.get(b"key") == "Some value"
assert ("127.0.0.1", 11211) not in client._dead_clients
@@ -400,7 +413,7 @@ class TestHashClient(ClientTestMixin, unittest.TestCase):
with pytest.raises(socket.timeout):
client.get(b"key", noreply=False)
- test_client.get.side_effect = lambda *_: "Some value"
+ test_client.get.side_effect = lambda *_, **_kw: "Some value"
assert client.get(b"key") == "Some value"
assert client_patch.call_count == 1