prompt: We are currently solving the following issue within our repository. Here is the issue text:
  --- BEGIN ISSUE ---
  (websockets 12.0) DeprecationWarning: websockets.connection was renamed to websockets.protocol and Connection was renamed to Protocol
  ### Is there an existing issue for this?
  
  - [X] I have searched the existing issues
  
  ### Describe the bug
  
  The DeprecationWarning is thrown here:
  
  https://github.com/sanic-org/sanic/blob/82bf46bea3b55e6b1371107cccda280add8e70eb/sanic/server/protocols/websocket_protocol.py#L4-L9
  
  With websockets 12 the try block would run successfully with the warning while the catch block does not have chance to be run.
  
  ### Code snippet
  
  _No response_
  
  ### Expected Behavior
  
  The catch block is being run instead.
  
  ### How do you run Sanic?
  
  Sanic CLI
  
  ### Operating System
  
  MacOS
  
  ### Sanic Version
  
  Sanic 23.6.0; Routing 23.6.0
  
  ### Additional context
  
  _No response_
  
  --- END ISSUE ---
  
  Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
  --- BEGIN FILES ---
  Path: `sanic/server/protocols/websocket_protocol.py`
  Content:
  ```
  1 from typing import Optional, Sequence, cast
  2 
  3 
  4 try:  # websockets < 11.0
  5     from websockets.connection import State
  6     from websockets.server import ServerConnection as ServerProtocol
  7 except ImportError:  # websockets >= 11.0
  8     from websockets.protocol import State  # type: ignore
  9     from websockets.server import ServerProtocol  # type: ignore
  10 
  11 from websockets import http11
  12 from websockets.datastructures import Headers as WSHeaders
  13 from websockets.typing import Subprotocol
  14 
  15 from sanic.exceptions import SanicException
  16 from sanic.log import logger
  17 from sanic.request import Request
  18 from sanic.server import HttpProtocol
  19 
  20 from ..websockets.impl import WebsocketImplProtocol
  21 
  22 
  23 OPEN = State.OPEN
  24 CLOSING = State.CLOSING
  25 CLOSED = State.CLOSED
  26 
  27 
  28 class WebSocketProtocol(HttpProtocol):
  29     __slots__ = (
  30         "websocket",
  31         "websocket_timeout",
  32         "websocket_max_size",
  33         "websocket_ping_interval",
  34         "websocket_ping_timeout",
  35     )
  36 
  37     def __init__(
  38         self,
  39         *args,
  40         websocket_timeout: float = 10.0,
  41         websocket_max_size: Optional[int] = None,
  42         websocket_ping_interval: Optional[float] = 20.0,
  43         websocket_ping_timeout: Optional[float] = 20.0,
  44         **kwargs,
  45     ):
  46         super().__init__(*args, **kwargs)
  47         self.websocket: Optional[WebsocketImplProtocol] = None
  48         self.websocket_timeout = websocket_timeout
  49         self.websocket_max_size = websocket_max_size
  50         self.websocket_ping_interval = websocket_ping_interval
  51         self.websocket_ping_timeout = websocket_ping_timeout
  52 
  53     def connection_lost(self, exc):
  54         if self.websocket is not None:
  55             self.websocket.connection_lost(exc)
  56         super().connection_lost(exc)
  57 
  58     def data_received(self, data):
  59         if self.websocket is not None:
  60             self.websocket.data_received(data)
  61         else:
  62             # Pass it to HttpProtocol handler first
  63             # That will (hopefully) upgrade it to a websocket.
  64             super().data_received(data)
  65 
  66     def eof_received(self) -> Optional[bool]:
  67         if self.websocket is not None:
  68             return self.websocket.eof_received()
  69         else:
  70             return False
  71 
  72     def close(self, timeout: Optional[float] = None):
  73         # Called by HttpProtocol at the end of connection_task
  74         # If we've upgraded to websocket, we do our own closing
  75         if self.websocket is not None:
  76             # Note, we don't want to use websocket.close()
  77             # That is used for user's application code to send a
  78             # websocket close packet. This is different.
  79             self.websocket.end_connection(1001)
  80         else:
  81             super().close()
  82 
  83     def close_if_idle(self):
  84         # Called by Sanic Server when shutting down
  85         # If we've upgraded to websocket, shut it down
  86         if self.websocket is not None:
  87             if self.websocket.ws_proto.state in (CLOSING, CLOSED):
  88                 return True
  89             elif self.websocket.loop is not None:
  90                 self.websocket.loop.create_task(self.websocket.close(1001))
  91             else:
  92                 self.websocket.end_connection(1001)
  93         else:
  94             return super().close_if_idle()
  95 
  96     @staticmethod
  97     def sanic_request_to_ws_request(request: Request):
  98         return http11.Request(
  99             path=request.path,
  100             headers=WSHeaders(request.headers),
  101         )
  102 
  103     async def websocket_handshake(
  104         self, request, subprotocols: Optional[Sequence[str]] = None
  105     ):
  106         # let the websockets package do the handshake with the client
  107         try:
  108             if subprotocols is not None:
  109                 # subprotocols can be a set or frozenset,
  110                 # but ServerProtocol needs a list
  111                 subprotocols = cast(
  112                     Optional[Sequence[Subprotocol]],
  113                     list(
  114                         [
  115                             Subprotocol(subprotocol)
  116                             for subprotocol in subprotocols
  117                         ]
  118                     ),
  119                 )
  120             ws_proto = ServerProtocol(
  121                 max_size=self.websocket_max_size,
  122                 subprotocols=subprotocols,
  123                 state=OPEN,
  124                 logger=logger,
  125             )
  126             resp = ws_proto.accept(self.sanic_request_to_ws_request(request))
  127         except Exception:
  128             msg = (
  129                 "Failed to open a WebSocket connection.\n"
  130                 "See server log for more information.\n"
  131             )
  132             raise SanicException(msg, status_code=500)
  133         if 100 <= resp.status_code <= 299:
  134             first_line = (
  135                 f"HTTP/1.1 {resp.status_code} {resp.reason_phrase}\r\n"
  136             ).encode()
  137             rbody = bytearray(first_line)
  138             rbody += (
  139                 "".join([f"{k}: {v}\r\n" for k, v in resp.headers.items()])
  140             ).encode()
  141             rbody += b"\r\n"
  142             if resp.body is not None:
  143                 rbody += resp.body
  144                 rbody += b"\r\n\r\n"
  145             await super().send(rbody)
  146         else:
  147             raise SanicException(resp.body, resp.status_code)
  148         self.websocket = WebsocketImplProtocol(
  149             ws_proto,
  150             ping_interval=self.websocket_ping_interval,
  151             ping_timeout=self.websocket_ping_timeout,
  152             close_timeout=self.websocket_timeout,
  153         )
  154         loop = (
  155             request.transport.loop
  156             if hasattr(request, "transport")
  157             and hasattr(request.transport, "loop")
  158             else None
  159         )
  160         await self.websocket.connection_made(self, loop=loop)
  161         return self.websocket
  162
  ```
  --- END FILES ---
  
  Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.
  
  Here is an example:
  
  ```diff
  diff --git a/examples/server_async.py b/examples/server_async.py
  --- a/examples/server_async.py
  +++ b/examples/server_async.py
  @@ -313,4 +313,4 @@
   
   
   if __name__ == "__main__":
  -    asyncio.run(run_async_server("."), debug=True)
  +    asyncio.run(run_async_server(), debug=True)
  diff --git a/examples/server_sync.py b/examples/server_sync.py
  --- a/examples/server_sync.py
  +++ b/examples/server_sync.py
  @@ -313,5 +313,5 @@
   
   
   if __name__ == "__main__":
  -    server = run_sync_server(".")
  +    server = run_sync_server()
       server.shutdown()
  
  ```
  
golden_diff: diff --git a/sanic/server/protocols/websocket_protocol.py b/sanic/server/protocols/websocket_protocol.py
  --- a/sanic/server/protocols/websocket_protocol.py
  +++ b/sanic/server/protocols/websocket_protocol.py
  @@ -1,12 +1,12 @@
   from typing import Optional, Sequence, cast
   
   
  -try:  # websockets < 11.0
  -    from websockets.connection import State
  -    from websockets.server import ServerConnection as ServerProtocol
  -except ImportError:  # websockets >= 11.0
  +try:  # websockets >= 11.0
       from websockets.protocol import State  # type: ignore
       from websockets.server import ServerProtocol  # type: ignore
  +except ImportError:  # websockets < 11.0
  +    from websockets.connection import State
  +    from websockets.server import ServerConnection as ServerProtocol
   
   from websockets import http11
   from websockets.datastructures import Headers as WSHeaders
  
verification_info: {"golden_diff": "diff --git a/sanic/server/protocols/websocket_protocol.py b/sanic/server/protocols/websocket_protocol.py\n--- a/sanic/server/protocols/websocket_protocol.py\n+++ b/sanic/server/protocols/websocket_protocol.py\n@@ -1,12 +1,12 @@\n from typing import Optional, Sequence, cast\n \n \n-try:  # websockets < 11.0\n-    from websockets.connection import State\n-    from websockets.server import ServerConnection as ServerProtocol\n-except ImportError:  # websockets >= 11.0\n+try:  # websockets >= 11.0\n     from websockets.protocol import State  # type: ignore\n     from websockets.server import ServerProtocol  # type: ignore\n+except ImportError:  # websockets < 11.0\n+    from websockets.connection import State\n+    from websockets.server import ServerConnection as ServerProtocol\n \n from websockets import http11\n from websockets.datastructures import Headers as WSHeaders\n", "issue": "(websockets 12.0) DeprecationWarning: websockets.connection was renamed to websockets.protocol and Connection was renamed to Protocol\n### Is there an existing issue for this?\n\n- [X] I have searched the existing issues\n\n### Describe the bug\n\nThe DeprecationWarning is thrown here:\r\n\r\nhttps://github.com/sanic-org/sanic/blob/82bf46bea3b55e6b1371107cccda280add8e70eb/sanic/server/protocols/websocket_protocol.py#L4-L9\r\n\r\nWith websockets 12 the try block would run successfully with the warning while the catch block does not have chance to be run.\n\n### Code snippet\n\n_No response_\n\n### Expected Behavior\n\nThe catch block is being run instead.\n\n### How do you run Sanic?\n\nSanic CLI\n\n### Operating System\n\nMacOS\n\n### Sanic Version\n\nSanic 23.6.0; Routing 23.6.0\n\n### Additional context\n\n_No response_\n", "before_files": [{"content": "from typing import Optional, Sequence, cast\n\n\ntry:  # websockets < 11.0\n    from websockets.connection import State\n    from websockets.server import ServerConnection as ServerProtocol\nexcept ImportError:  # websockets >= 11.0\n    from websockets.protocol import State  # type: ignore\n    from websockets.server import ServerProtocol  # type: ignore\n\nfrom websockets import http11\nfrom websockets.datastructures import Headers as WSHeaders\nfrom websockets.typing import Subprotocol\n\nfrom sanic.exceptions import SanicException\nfrom sanic.log import logger\nfrom sanic.request import Request\nfrom sanic.server import HttpProtocol\n\nfrom ..websockets.impl import WebsocketImplProtocol\n\n\nOPEN = State.OPEN\nCLOSING = State.CLOSING\nCLOSED = State.CLOSED\n\n\nclass WebSocketProtocol(HttpProtocol):\n    __slots__ = (\n        \"websocket\",\n        \"websocket_timeout\",\n        \"websocket_max_size\",\n        \"websocket_ping_interval\",\n        \"websocket_ping_timeout\",\n    )\n\n    def __init__(\n        self,\n        *args,\n        websocket_timeout: float = 10.0,\n        websocket_max_size: Optional[int] = None,\n        websocket_ping_interval: Optional[float] = 20.0,\n        websocket_ping_timeout: Optional[float] = 20.0,\n        **kwargs,\n    ):\n        super().__init__(*args, **kwargs)\n        self.websocket: Optional[WebsocketImplProtocol] = None\n        self.websocket_timeout = websocket_timeout\n        self.websocket_max_size = websocket_max_size\n        self.websocket_ping_interval = websocket_ping_interval\n        self.websocket_ping_timeout = websocket_ping_timeout\n\n    def connection_lost(self, exc):\n        if self.websocket is not None:\n            self.websocket.connection_lost(exc)\n        super().connection_lost(exc)\n\n    def data_received(self, data):\n        if self.websocket is not None:\n            self.websocket.data_received(data)\n        else:\n            # Pass it to HttpProtocol handler first\n            # That will (hopefully) upgrade it to a websocket.\n            super().data_received(data)\n\n    def eof_received(self) -> Optional[bool]:\n        if self.websocket is not None:\n            return self.websocket.eof_received()\n        else:\n            return False\n\n    def close(self, timeout: Optional[float] = None):\n        # Called by HttpProtocol at the end of connection_task\n        # If we've upgraded to websocket, we do our own closing\n        if self.websocket is not None:\n            # Note, we don't want to use websocket.close()\n            # That is used for user's application code to send a\n            # websocket close packet. This is different.\n            self.websocket.end_connection(1001)\n        else:\n            super().close()\n\n    def close_if_idle(self):\n        # Called by Sanic Server when shutting down\n        # If we've upgraded to websocket, shut it down\n        if self.websocket is not None:\n            if self.websocket.ws_proto.state in (CLOSING, CLOSED):\n                return True\n            elif self.websocket.loop is not None:\n                self.websocket.loop.create_task(self.websocket.close(1001))\n            else:\n                self.websocket.end_connection(1001)\n        else:\n            return super().close_if_idle()\n\n    @staticmethod\n    def sanic_request_to_ws_request(request: Request):\n        return http11.Request(\n            path=request.path,\n            headers=WSHeaders(request.headers),\n        )\n\n    async def websocket_handshake(\n        self, request, subprotocols: Optional[Sequence[str]] = None\n    ):\n        # let the websockets package do the handshake with the client\n        try:\n            if subprotocols is not None:\n                # subprotocols can be a set or frozenset,\n                # but ServerProtocol needs a list\n                subprotocols = cast(\n                    Optional[Sequence[Subprotocol]],\n                    list(\n                        [\n                            Subprotocol(subprotocol)\n                            for subprotocol in subprotocols\n                        ]\n                    ),\n                )\n            ws_proto = ServerProtocol(\n                max_size=self.websocket_max_size,\n                subprotocols=subprotocols,\n                state=OPEN,\n                logger=logger,\n            )\n            resp = ws_proto.accept(self.sanic_request_to_ws_request(request))\n        except Exception:\n            msg = (\n                \"Failed to open a WebSocket connection.\\n\"\n                \"See server log for more information.\\n\"\n            )\n            raise SanicException(msg, status_code=500)\n        if 100 <= resp.status_code <= 299:\n            first_line = (\n                f\"HTTP/1.1 {resp.status_code} {resp.reason_phrase}\\r\\n\"\n            ).encode()\n            rbody = bytearray(first_line)\n            rbody += (\n                \"\".join([f\"{k}: {v}\\r\\n\" for k, v in resp.headers.items()])\n            ).encode()\n            rbody += b\"\\r\\n\"\n            if resp.body is not None:\n                rbody += resp.body\n                rbody += b\"\\r\\n\\r\\n\"\n            await super().send(rbody)\n        else:\n            raise SanicException(resp.body, resp.status_code)\n        self.websocket = WebsocketImplProtocol(\n            ws_proto,\n            ping_interval=self.websocket_ping_interval,\n            ping_timeout=self.websocket_ping_timeout,\n            close_timeout=self.websocket_timeout,\n        )\n        loop = (\n            request.transport.loop\n            if hasattr(request, \"transport\")\n            and hasattr(request.transport, \"loop\")\n            else None\n        )\n        await self.websocket.connection_made(self, loop=loop)\n        return self.websocket\n", "path": "sanic/server/protocols/websocket_protocol.py"}], "after_files": [{"content": "from typing import Optional, Sequence, cast\n\n\ntry:  # websockets >= 11.0\n    from websockets.protocol import State  # type: ignore\n    from websockets.server import ServerProtocol  # type: ignore\nexcept ImportError:  # websockets < 11.0\n    from websockets.connection import State\n    from websockets.server import ServerConnection as ServerProtocol\n\nfrom websockets import http11\nfrom websockets.datastructures import Headers as WSHeaders\nfrom websockets.typing import Subprotocol\n\nfrom sanic.exceptions import SanicException\nfrom sanic.log import logger\nfrom sanic.request import Request\nfrom sanic.server import HttpProtocol\n\nfrom ..websockets.impl import WebsocketImplProtocol\n\n\nOPEN = State.OPEN\nCLOSING = State.CLOSING\nCLOSED = State.CLOSED\n\n\nclass WebSocketProtocol(HttpProtocol):\n    __slots__ = (\n        \"websocket\",\n        \"websocket_timeout\",\n        \"websocket_max_size\",\n        \"websocket_ping_interval\",\n        \"websocket_ping_timeout\",\n    )\n\n    def __init__(\n        self,\n        *args,\n        websocket_timeout: float = 10.0,\n        websocket_max_size: Optional[int] = None,\n        websocket_ping_interval: Optional[float] = 20.0,\n        websocket_ping_timeout: Optional[float] = 20.0,\n        **kwargs,\n    ):\n        super().__init__(*args, **kwargs)\n        self.websocket: Optional[WebsocketImplProtocol] = None\n        self.websocket_timeout = websocket_timeout\n        self.websocket_max_size = websocket_max_size\n        self.websocket_ping_interval = websocket_ping_interval\n        self.websocket_ping_timeout = websocket_ping_timeout\n\n    def connection_lost(self, exc):\n        if self.websocket is not None:\n            self.websocket.connection_lost(exc)\n        super().connection_lost(exc)\n\n    def data_received(self, data):\n        if self.websocket is not None:\n            self.websocket.data_received(data)\n        else:\n            # Pass it to HttpProtocol handler first\n            # That will (hopefully) upgrade it to a websocket.\n            super().data_received(data)\n\n    def eof_received(self) -> Optional[bool]:\n        if self.websocket is not None:\n            return self.websocket.eof_received()\n        else:\n            return False\n\n    def close(self, timeout: Optional[float] = None):\n        # Called by HttpProtocol at the end of connection_task\n        # If we've upgraded to websocket, we do our own closing\n        if self.websocket is not None:\n            # Note, we don't want to use websocket.close()\n            # That is used for user's application code to send a\n            # websocket close packet. This is different.\n            self.websocket.end_connection(1001)\n        else:\n            super().close()\n\n    def close_if_idle(self):\n        # Called by Sanic Server when shutting down\n        # If we've upgraded to websocket, shut it down\n        if self.websocket is not None:\n            if self.websocket.ws_proto.state in (CLOSING, CLOSED):\n                return True\n            elif self.websocket.loop is not None:\n                self.websocket.loop.create_task(self.websocket.close(1001))\n            else:\n                self.websocket.end_connection(1001)\n        else:\n            return super().close_if_idle()\n\n    @staticmethod\n    def sanic_request_to_ws_request(request: Request):\n        return http11.Request(\n            path=request.path,\n            headers=WSHeaders(request.headers),\n        )\n\n    async def websocket_handshake(\n        self, request, subprotocols: Optional[Sequence[str]] = None\n    ):\n        # let the websockets package do the handshake with the client\n        try:\n            if subprotocols is not None:\n                # subprotocols can be a set or frozenset,\n                # but ServerProtocol needs a list\n                subprotocols = cast(\n                    Optional[Sequence[Subprotocol]],\n                    list(\n                        [\n                            Subprotocol(subprotocol)\n                            for subprotocol in subprotocols\n                        ]\n                    ),\n                )\n            ws_proto = ServerProtocol(\n                max_size=self.websocket_max_size,\n                subprotocols=subprotocols,\n                state=OPEN,\n                logger=logger,\n            )\n            resp = ws_proto.accept(self.sanic_request_to_ws_request(request))\n        except Exception:\n            msg = (\n                \"Failed to open a WebSocket connection.\\n\"\n                \"See server log for more information.\\n\"\n            )\n            raise SanicException(msg, status_code=500)\n        if 100 <= resp.status_code <= 299:\n            first_line = (\n                f\"HTTP/1.1 {resp.status_code} {resp.reason_phrase}\\r\\n\"\n            ).encode()\n            rbody = bytearray(first_line)\n            rbody += (\n                \"\".join([f\"{k}: {v}\\r\\n\" for k, v in resp.headers.items()])\n            ).encode()\n            rbody += b\"\\r\\n\"\n            if resp.body is not None:\n                rbody += resp.body\n                rbody += b\"\\r\\n\\r\\n\"\n            await super().send(rbody)\n        else:\n            raise SanicException(resp.body, resp.status_code)\n        self.websocket = WebsocketImplProtocol(\n            ws_proto,\n            ping_interval=self.websocket_ping_interval,\n            ping_timeout=self.websocket_ping_timeout,\n            close_timeout=self.websocket_timeout,\n        )\n        loop = (\n            request.transport.loop\n            if hasattr(request, \"transport\")\n            and hasattr(request.transport, \"loop\")\n            else None\n        )\n        await self.websocket.connection_made(self, loop=loop)\n        return self.websocket\n", "path": "sanic/server/protocols/websocket_protocol.py"}]}