Python 在redis py中使用锁

Python 在redis py中使用锁,python,django,redis,Python,Django,Redis,我试图在django项目中为redis值创建一个锁,但遇到了麻烦。非阻塞代码工作正常,即: r = redis.StrictRedis(host='localhost', port=6379) data_dict = {'key': 'value'} r.hmset('hash', data_dict) 但是,当尝试使用锁来防止其他线程写入时,请使用以下代码: r = redis.StrictRedis(host='localhost', port=6379) data_dict = {'ke

我试图在django项目中为redis值创建一个锁,但遇到了麻烦。非阻塞代码工作正常,即:

r = redis.StrictRedis(host='localhost', port=6379)
data_dict = {'key': 'value'}
r.hmset('hash', data_dict)
但是,当尝试使用锁来防止其他线程写入时,请使用以下代码:

r = redis.StrictRedis(host='localhost', port=6379)
data_dict = {'key': 'value'}
lock = r.lock('hash')
with lock.acquire() as l:
    r.hmset('hash', data_dict)
抛出:
redis.exceptions.ResponseError:针对持有错误类型值的键的错误类型操作


如果这是一个非常愚蠢的问题,我很抱歉,但我不明白我是如何得到这个错误的,正在设置的数据实际上与您试图将字典设置为与锁相同的键相同。您需要一把钥匙用于锁,另一把钥匙用于字典。

有两个问题:

  • 正如其他人所说,您需要为锁和散列使用两个不同的键
  • 语法错误
  • 为了详细说明第2点,以下是使用锁所涉及的步骤:

  • 创建一个
    对象
  • 拿到锁
  • 做重要的事情
  • 松开锁
  • 如果不使用上下文管理器(带…语句的
    ),代码可能如下所示:

    lock = r.lock('my_lock')
    lock.acquire(blocking=True)
    r.set('foo', 'bar')
    lock.release()
    
    使用上下文管理器,代码简化为:

    with r.lock('my_lock'):
        r.set('foo', 'bar')
    
    这里发生的情况如下:

  • r.lock()
    创建并返回一个
    lock
    对象
  • Lock.\uuuu enter\uuuu()
    会自动调用,然后调用
    Lock.acquire()
  • 执行缩进的代码
  • Lock.\uuuu exit\uuuu()
    会自动调用,然后调用
    Lock.release()
  • 您可以在redis py源代码中看到这一点

    • (包含
      lock()
    • (包含
      类)

    您已锁定
    散列
    密钥,因此无法在
    r.hmset('hash',data_dict')中设置密钥。