Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Client state is incorrect #1463

Closed
tamir-laminar opened this issue May 11, 2024 · 1 comment
Closed

Client state is incorrect #1463

tamir-laminar opened this issue May 11, 2024 · 1 comment

Comments

@tamir-laminar
Copy link

There is a problem with the client state when sending messaged over a closed socket.

look at the example below:

import asyncio
import websockets

PORT = 22334


async def handle_connection(ws):
    print(f"Got connection request on path: {ws.path}")
    # this code is in comment on propose to see the behaviour of `send` when connection is closed
    # async for message in ws:
    #     print(f"Received message: {message}")
    return


async def main():
    print(f"Starting server on port {PORT}")
    async with websockets.serve(ws_handler=handle_connection, host="localhost", port=PORT):
        print(f"Starting client")
        async with websockets.connect(f"ws://localhost:{PORT}/connect") as client:
            print(f"Sending messages")
            await client.send("Hello, world!")  # expected to fail
            await client.send("Hello, world!")  # expected to fail
            await client.send("Hello, world!")  # expected to fail

            print("Client state is:", client.state.name)  # this should be `CLOSING`, instead we are getting `OPEN`

            try:
                await client.recv()  # this fails correctly because the connection is closed
            except websockets.exceptions.ConnectionClosedOK:
                print("Connection is closed")


if __name__ == "__main__":
    asyncio.run(main())

output:

Starting server on port 22334
Starting client
Got connection request on path: /connect
Sending messages
Client state is: OPEN
Connection is closed

In this example the server gets a connection request from the client and just drop the connection.
The client can still sends messages without getting ConnectionClosedOK exception.

Notes:

  • This behaviour changed in version 11.0, in version 10.4 we would get error in that case.
  • When I'm debugging the code I can see that we are changing the state to CLOSING, but other routine changes the state back to OPEN although it is still close.
@aaugustin
Copy link
Member

This is essentially https://websockets.readthedocs.io/en/stable/faq/asyncio.html#why-does-my-program-never-receive-any-messages

This code doesn't actually yield control to the event loop until await client.recv(). Only then does the event loop get a chance to run and to notice that the connection has been close.

If you add await asyncio.sleep(0.1) right after connect(), you should get the behavior that you expect.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants