Redisは同期メソッド呼び出しのような機能を実現する(一)

2421 ワード

まず、このようにするのは純粋に面白いためだと宣言します.
通常、Redisは主にいくつかのデータを格納するために使用されます.データはメモリにあるので、クエリーの更新が速いです.また、Pub/sub機能を利用して、メッセージの公開/購読を実現することもできます.しかし、今日はRedisのlistを通じてServer-Clientの同期通信を実現する方法について説明します.

具体的なニーズ


Client側は、実行後にサーバ側から送信された要求をリスニングし、いくつかの操作を実行し、結果をサーバ側に返します.

考えを実現する.

  • Redisのlistデータ構造を利用して、popをブロックする方式を使用してClient側待機配布コマンドとServer側待機返却結果を実現する.
  • まず、サーバ側はグローバル一意のkeyを生成し、keyとdataを一緒に指定したキューにpushします.ここでは「myqueue」です.lpushの後、サーバ側はbrpopを使用してkeyキューから結果を返すのを待機し、タイムアウト時間を2秒に設定します.
  • Client側起動後、brpopを使用して指定されたキューから配布コマンドを取得し、サーバ側から配布されたデータを受信すると、Clientはkeyとdataを取得し、独自の処理を行い、処理が完了すると、「key」キューに結果をlpush実行します.
  • 最後に、サーバ側はbrpopを使用して「key」キューから実行結果を取得します.

  • インプリメンテーションコード

    import redis
    import time
    import json
    import threading
    
    host = 'localhost'
    port = 6322
    queue = 'myqueue'
    
    
    class Server(threading.Thread):
    
        def __init__(self):
            threading.Thread.__init__(self)
    
        def run(self):
            pool = redis.BlockingConnectionPool(host=host, port=port, db='0')
            conn = redis.Redis(connection_pool=pool)
            idx = 0
    
            while True:
                idx = idx + 1
    
                key = str(idx)
                data = "request_" + key
                request = {'id': key, 'data': data}
                print 'Server: Send request: %s' % request
                conn.lpush(queue, json.dumps(request))
    
                response = conn.brpop(key, 2)
                if response:
                    print 'Server: Receive response: %s' % response[1]
                else:
                    print "Server: Timeout!!!"
    
                time.sleep(1)
    
    
    class Client(threading.Thread):
    
        def __init__(self):
            threading.Thread.__init__(self)
    
        def run(self):
            pool = redis.BlockingConnectionPool(host=host, port=port, db='0')
            conn = redis.Redis(connection_pool=pool)
    
            while True:
                msg = conn.brpop(queue)[1]
                print 'Client: Receive request: %s' % msg
    
                time.sleep(0.1)
    
                d = json.loads(msg)
                key = d.get('id')
                d['data'] = "response_" + key
                print 'Client: Send response: %s' % d
                conn.lpush(key, json.dumps(d))
                conn.expire(key, 5)
    
    
    server = Server()
    server.start()
    
    client = Client()
    client.start()