Here is a simple wrapper around Redis which pickles/unpickles data structures:
from redis import Redis
from collections import MutableMapping
from pickle import loads, dumps
class RedisStore(MutableMapping):
def __init__(self, engine):
self._store = Redis.from_url(engine)
def __getitem__(self, key):
return loads(self._store[dumps(key)])
def __setitem__(self, key, value):
self._store[dumps(key)] = dumps(value)
def __delitem__(self, key):
del self._store[dumps(key)]
def __iter__(self):
return iter(self.keys())
def __len__(self):
return len(self._store.keys())
def keys(self):
return [loads(x) for x in self._store.keys()]
def clear(self):
self._store.flushdb()
d = RedisStore('redis://localhost:6379/0')
d['a'] = {'b': 1, 'c': 10}
print repr(d.items())
# this will not work: (it updates a temporary copy and not the real data)
d['a']['b'] = 2
print repr(d.items())
# this is how to update sub-structures:
t = d['a']
t['b'] = 2
d['a'] = t
print repr(d.items())
del d['a']
# Here is another way to implement dict-of-dict eg d['a']['b']
d[('a', 'b')] = 1
d[('a', 'b')] = 2
print repr(d.items())
# Hopefully you do not need the equivalent of d['a']
print repr([{x[0][1]: x[1]} for x in d.items() if x[0][0] == 'a'])
del d[('a', 'b')]
del d[('a', 'c')]
If you prefer plaintext-readable data in redis (pickle stores a binary version of it), you can replace pickle.dumps with repr and pickle.loads with ast.literal_eval. For json, use json.dumps and json.loads.
If you always use keys which are a simple string, you can remove the pickling from the key.