1. 程式人生 > 其它 >Python訂閱Redis主題,實現前端通過Websocket實時獲取訂閱資訊【訊息推送】

Python訂閱Redis主題,實現前端通過Websocket實時獲取訂閱資訊【訊息推送】

參考:
(23條訊息) Python訂閱Redis主題,實現前端通過Websocket實時獲取訂閱資訊【訊息推送】_YelloooBlue's Blog-CSDN部落格]

終極解決方案
第二天起來清醒了一點,靈光一現
既然redis老是死迴圈,那我們能不能照葫蘆畫瓢,弄個非同步的redis訂閱?
又惡補了一下非同步的知識,上網找答案
功夫不負有心人,找到個aioredis非同步redis庫

咋實現非同步訂閱嘞?這次直接在Google上搜了一下
發現了老外的一篇文章
wok,這不就是我要的嗎,趕緊copy一下試試

# producer.py

import asyncio
from aioredis import create_connection, Channel
import websockets

async def subscribe_to_redis(path):
    conn = await create_connection(('localhost', 6379))

    # Set up a subscribe channel
    channel = Channel('lightlevel{}'.format(path), is_pattern=False)
    await conn.execute_pubsub('subscribe', channel)
    return channel, conn


async def browser_server(websocket, path):
    channel, conn = await subscribe_to_redis(path)
    try:
        while True:
            # Wait until data is published to this channel
            message = await channel.get()

            # Send unicode decoded data over to the websocket client
            await websocket.send(message.decode('utf-8'))

    except websockets.exceptions.ConnectionClosed:
        # Free up channel if websocket goes down
        await conn.execute_pubsub('unsubscribe', channel)
        conn.close()

if __name__ == '__main__':
    # Runs a server process on 8767. Just do 'python producer.py'
    loop = asyncio.get_event_loop()
    loop.set_debug(True)
    ws_server = websockets.serve(browser_server, 'localhost', 8767)
    loop.run_until_complete(ws_server)
    loop.run_forever()

除錯了一下,完美,多客戶端也有了,redis訂閱也有了。

按照非同步邏輯await,每有一個ws客戶端連線,python都會建立一個redis訂閱連線,果不其然,
在redis命令列測試的時候發現確實如此,會不會佔用過多資源,還有待考究

可以說是實現了
websocket連線 轉換為 redis訂閱連線
也大致滿足了我的專案需求了

後期需求(進階)
redis只需要訂閱一次(一個訂閱連結)就可以實現對多個客戶端傳送,以及客戶端session的判別

學習
非同步IO又是一個大坑,不論是python的asyncio還是PHP的swoole,都還要學習,本文大概就到這裡,記錄一下研究過過程,有特別多的不足,目前專案需要跟進,有些內容暫時沒法深入學習,還請見諒。

python伺服器訊息推送_Python Web實時訊息後臺伺服器推送技術---GoEasy_weixin_39587407的部落格-程式設計師宅基地 - 程式設計師宅基地]