2011-10-24 73 views
12

我想使用的Redis的發佈 - 訂閱功能來實現彗星,但發佈訂閱沒有超時,所以如果我ps.listen(),它會阻止,即使客戶端關閉瀏覽器。如何實現redis的pubsub超時功能?

當spawn進程時,greenlet具有超時功能。但我不知道如何將它們結合在一起。

瓶的僞

@app.route('/') 
def comet(): 
    rc = redis.Redis() 
    ps = rc.pubsub() 
    ps.subscribe('foo') 
    for item in ps.listen(): 
     if item['type'] == 'message': 
      return item['data'] 
    # ps.listen() will block, so how to make it timeout after 30 s? 

回答

1

因爲你沒有線程(我假設這是故意的,在某些情況下,明智的),你必須使用一個類型的中斷。信號是Unix系統中的一種中斷,允許您在可能阻塞的呼叫期間返回回調。

開放,這將永遠不會返回文件的這個例子是符合你想要做什麼。這是一個從http://docs.python.org/library/signal.html#module-signal

但警告服用。由於Python使用全局解釋器鎖執行操作系統信號處理,因此會受到一些穩定性問題的影響。儘管如此,這些問題應該很少見。

import signal, os 

def handler(signum, frame): 
    print 'Signal handler called with signal', signum 
    raise IOError("Couldn't open device!") 

# Set the signal handler and a 5-second alarm 
signal.signal(signal.SIGALRM, handler) 
signal.alarm(5) 

# This open() may hang indefinitely 
fd = os.open('/dev/ttyS0', os.O_RDWR) 

signal.alarm(0)   # Disable the alarm