异步:通过单个WebSocket连接多路复用消息

时间:2019-01-18 15:06:40

标签: python websocket python-asyncio

我正在使用Python 3.6,asyncio和websockets库。我正在尝试为基于websocket的服务构建客户端,其工作方式如下:

客户端可以发送带有自定义idmethod和某些params的JSON请求。该服务将使用回显相同的id并返回data的JSON负载作为方法调用的结果。

我想在这个设备上建立一个抽象,就像这样:

wsc = get_websocket_connection()

async def call_method(method, **params):
    packet = make_json_packet(method, params)
    await wsc.send(packet)
    resp = await wsc.recv()
    return decode_json_packet(resp)

async def working_code():
    separate_request = asyncio.ensure_future(call_method("quux"))

    first_result = await call_method("foo", x=1)
    second_result = await call_method("bar", y=first_result)
    print(second_result)

    return await separate_request

现在,我希望separate_request在处理first_resultsecond_result的同时异步等待。但是我不能保证wsc.recv()调用会返回匹配的响应;实际上,我不能保证该服务按请求的顺序返回响应。

我可以使用id字段消除响应的歧义。但是,我该如何写call_method(),以便它在内部管理请求并在收到相应答复时恢复“正确的”协程?

1 个答案:

答案 0 :(得分:0)

在我将这种事情分解为两部分之前完成了这种事情之后:

  1. “发送代码”(可以是多个线程),它设置了响应应该到达的位置(例如,对功能或dict的{​​{1}}中的id,然后发送请求和响应阻止
  2. “接收代码”(每个套接字大概一个线程),它监视所有入站流量并将响应传递给对Future感兴趣的任何代码。这也是处理套接字意外关闭的明智之地,应该适当地排除异常

这可能是几百行代码和特定于应用程序的……