From 92fad17cc72007abdda46a3b6a98ec26e486f9cc Mon Sep 17 00:00:00 2001 From: Alejandro Cabrera Date: Wed, 2 Oct 2013 11:25:22 -0400 Subject: [PATCH] fix: encode keys before caching This patch addresses an error in the caching layer that prevented it from playing nice with backends like memcached that expect keys to be bytestrings rather than unicode strings. The change is made in oslo.cache to make its use as transparent as possible to users. Change-Id: Iee48e16393321ff7908807a9f0f7fa20480ec5f4 Closes-Bug: 1230556 --- marconi/common/cache/backends.py | 19 ++++++++++++++----- marconi/proxy/utils/lookup.py | 2 +- 2 files changed, 15 insertions(+), 6 deletions(-) diff --git a/marconi/common/cache/backends.py b/marconi/common/cache/backends.py index 1960cf95b..0f1b9f0bf 100644 --- a/marconi/common/cache/backends.py +++ b/marconi/common/cache/backends.py @@ -13,12 +13,12 @@ # under the License. import abc +import six +@six.add_metaclass(abc.ABCMeta) class BaseCache(object): - __metaclass__ = abc.ABCMeta - def __init__(self, conf, group, cache_namespace): self.conf = conf[group] self._cache_namespace = cache_namespace @@ -68,10 +68,19 @@ class BaseCache(object): :param key: The key to be prefixed """ + prepared = key if self._cache_namespace: - return ("%(prefix)s-%(key)s" % - {'prefix': self._cache_namespace, 'key': key}) - return key + prepared = ("%(prefix)s-%(key)s" % + {'prefix': self._cache_namespace, 'key': key}) + + # NOTE(cpp-cabrera): some caching backends (memcache) enforce + # that the key type must be bytes. This is here to ensure that + # this precondition is respected and that users can continue + # to use the caching layer transparently. + if isinstance(prepared, six.text_type): + prepared = prepared.encode('utf8') + + return prepared def add(self, key, value, ttl=0): """Sets the value for a key if it doesn't exist diff --git a/marconi/proxy/utils/lookup.py b/marconi/proxy/utils/lookup.py index 9ee0fd016..85bd9dc8d 100644 --- a/marconi/proxy/utils/lookup.py +++ b/marconi/proxy/utils/lookup.py @@ -27,7 +27,7 @@ def partition(project, queue, catalogue_controller, cache): :param cache: cache for catalogue - updated if lookup fails :returns: Maybe text - partition name or None if not found """ - key = u'q.{project}.{queue}'.format(project=project, queue=queue) + key = u'q.{project}/{queue}'.format(project=project, queue=queue) name = cache.get(key) if not name: try: