154 lines
8.7 KiB
Plaintext
154 lines
8.7 KiB
Plaintext
|
{
|
||
|
"metadata": {
|
||
|
"language_info": {
|
||
|
"codemirror_mode": {
|
||
|
"name": "ipython",
|
||
|
"version": 3
|
||
|
},
|
||
|
"file_extension": ".py",
|
||
|
"mimetype": "text/x-python",
|
||
|
"name": "python",
|
||
|
"nbconvert_exporter": "python",
|
||
|
"pygments_lexer": "ipython3",
|
||
|
"version": "3.9.5"
|
||
|
},
|
||
|
"orig_nbformat": 2,
|
||
|
"kernelspec": {
|
||
|
"name": "python395jvsc74a57bd0916dbcbb3f70747c44a77c7bcd40155683ae19c65e1c03b4aa3499c5328201f1",
|
||
|
"display_name": "Python 3.9.5 64-bit"
|
||
|
},
|
||
|
"metadata": {
|
||
|
"interpreter": {
|
||
|
"hash": "916dbcbb3f70747c44a77c7bcd40155683ae19c65e1c03b4aa3499c5328201f1"
|
||
|
}
|
||
|
}
|
||
|
},
|
||
|
"nbformat": 4,
|
||
|
"nbformat_minor": 2,
|
||
|
"cells": [
|
||
|
{
|
||
|
"cell_type": "code",
|
||
|
"execution_count": 1,
|
||
|
"metadata": {},
|
||
|
"outputs": [],
|
||
|
"source": [
|
||
|
"import websockets\n",
|
||
|
"import asyncio\n",
|
||
|
"import json\n",
|
||
|
"import logging"
|
||
|
]
|
||
|
},
|
||
|
{
|
||
|
"cell_type": "code",
|
||
|
"execution_count": 2,
|
||
|
"metadata": {},
|
||
|
"outputs": [],
|
||
|
"source": [
|
||
|
"class JsonWebsocketConnection(object):\n",
|
||
|
"\n",
|
||
|
" def __init__(self,\n",
|
||
|
" websocket: websockets.WebSocketServerProtocol):\n",
|
||
|
" \n",
|
||
|
" logging.debug(\"incoming connection\")\n",
|
||
|
" self._websocket = websocket\n",
|
||
|
" self._is_closed = False;\n",
|
||
|
" \n",
|
||
|
" def is_closed(self):\n",
|
||
|
" return self.is_closed\n",
|
||
|
" \n",
|
||
|
" async def close(self):\n",
|
||
|
" logging.debug(\"closing connection\")\n",
|
||
|
" try:\n",
|
||
|
" if self._is_closed:\n",
|
||
|
" return\n",
|
||
|
" self._websocket.close()\n",
|
||
|
" self._is_closed = True\n",
|
||
|
" except Exception as e:\n",
|
||
|
" logging.warning(\"error closing connection: %s\", str(e))\n",
|
||
|
" \n",
|
||
|
" async def send(self, message: dict):\n",
|
||
|
" string_message = json.dumps(message)\n",
|
||
|
" logging.debug(\"sending message: %s\", string_message)\n",
|
||
|
" try:\n",
|
||
|
" await self._websocket.send(string_message)\n",
|
||
|
" except Exception as e:\n",
|
||
|
" logging.warning(\"error sending message: %s\", str(e))\n",
|
||
|
" \n",
|
||
|
" async def handle_message(self, message: dict):\n",
|
||
|
" pass # override this function\n",
|
||
|
"\n",
|
||
|
" async def run(self):\n",
|
||
|
" try:\n",
|
||
|
" async for message in self._websocket:\n",
|
||
|
" try:\n",
|
||
|
" json_message = json.loads(message)\n",
|
||
|
" except ValueError as e:\n",
|
||
|
" logging.warning(\"received unprocessable message %s\", str(e))\n",
|
||
|
" await self.handle_message(message) \n",
|
||
|
" \n",
|
||
|
" except Exception as e:\n",
|
||
|
" logging.warning(\"error in websocket connection: %s\", str(e))\n",
|
||
|
"\n",
|
||
|
"\n",
|
||
|
"\n",
|
||
|
"class JsonWebsocketServer(object):\n",
|
||
|
" def __init__(self, handler_class: JsonWebsocketConnection, host:str = 'localhost', port:int = 8765):\n",
|
||
|
" self._host = host\n",
|
||
|
" self._port = port\n",
|
||
|
" self._handler_class = handler_class\n",
|
||
|
"\n",
|
||
|
" def run(self):\n",
|
||
|
" async def main(websocket: websockets.WebSocketServerProtocol,\n",
|
||
|
" path: str):\n",
|
||
|
"\n",
|
||
|
" connection = self._handler_class(websocket)\n",
|
||
|
"\n",
|
||
|
" connection.run()\n",
|
||
|
" \n",
|
||
|
" start_server = websockets.serve(main, self._host, self._port)\n",
|
||
|
"\n",
|
||
|
" asyncio.get_event_loop().run_until_complete(start_server)\n",
|
||
|
" asyncio.get_event_loop().run_forever()\n",
|
||
|
" \n",
|
||
|
"\n",
|
||
|
"def CrosswordConnection(JsonWebsocketConnection): \n",
|
||
|
" async def handle_message(self, message: dict):\n",
|
||
|
" await self.send({\"message\": \"hello\"})\n",
|
||
|
" \n",
|
||
|
"\n"
|
||
|
]
|
||
|
},
|
||
|
{
|
||
|
"cell_type": "code",
|
||
|
"execution_count": 3,
|
||
|
"metadata": {},
|
||
|
"outputs": [
|
||
|
{
|
||
|
"output_type": "error",
|
||
|
"ename": "RuntimeError",
|
||
|
"evalue": "This event loop is already running",
|
||
|
"traceback": [
|
||
|
"\u001b[0;31m---------------------------------------------------------------------------\u001b[0m",
|
||
|
"\u001b[0;31mRuntimeError\u001b[0m Traceback (most recent call last)",
|
||
|
"\u001b[0;32m<ipython-input-3-ecab008e957f>\u001b[0m in \u001b[0;36m<module>\u001b[0;34m\u001b[0m\n\u001b[1;32m 1\u001b[0m \u001b[0mserver\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mJsonWebsocketServer\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mCrosswordConnection\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m----> 2\u001b[0;31m \u001b[0mserver\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mrun\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m",
|
||
|
"\u001b[0;32m<ipython-input-2-3c372b72dd90>\u001b[0m in \u001b[0;36mrun\u001b[0;34m(self)\u001b[0m\n\u001b[1;32m 62\u001b[0m \u001b[0mstart_server\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mwebsockets\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mserve\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mmain\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mself\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0m_host\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mself\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0m_port\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 63\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m---> 64\u001b[0;31m \u001b[0masyncio\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mget_event_loop\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mrun_until_complete\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mstart_server\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 65\u001b[0m \u001b[0masyncio\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mget_event_loop\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mrun_forever\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 66\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n",
|
||
|
"\u001b[0;32m/usr/lib/python3.9/asyncio/base_events.py\u001b[0m in \u001b[0;36mrun_until_complete\u001b[0;34m(self, future)\u001b[0m\n\u001b[1;32m 616\u001b[0m \"\"\"\n\u001b[1;32m 617\u001b[0m \u001b[0mself\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0m_check_closed\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m--> 618\u001b[0;31m \u001b[0mself\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0m_check_running\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 619\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 620\u001b[0m \u001b[0mnew_task\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0;32mnot\u001b[0m \u001b[0mfutures\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0misfuture\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mfuture\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n",
|
||
|
"\u001b[0;32m/usr/lib/python3.9/asyncio/base_events.py\u001b[0m in \u001b[0;36m_check_running\u001b[0;34m(self)\u001b[0m\n\u001b[1;32m 576\u001b[0m \u001b[0;32mdef\u001b[0m \u001b[0m_check_running\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mself\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 577\u001b[0m \u001b[0;32mif\u001b[0m \u001b[0mself\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mis_running\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m--> 578\u001b[0;31m \u001b[0;32mraise\u001b[0m \u001b[0mRuntimeError\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m'This event loop is already running'\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 579\u001b[0m \u001b[0;32mif\u001b[0m \u001b[0mevents\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0m_get_running_loop\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m \u001b[0;32mis\u001b[0m \u001b[0;32mnot\u001b[0m \u001b[0;32mNone\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 580\u001b[0m raise RuntimeError(\n",
|
||
|
"\u001b[0;31mRuntimeError\u001b[0m: This event loop is already running"
|
||
|
]
|
||
|
}
|
||
|
],
|
||
|
"source": [
|
||
|
"server = JsonWebsocketServer(CrosswordConnection)\n",
|
||
|
"server.run()"
|
||
|
]
|
||
|
},
|
||
|
{
|
||
|
"cell_type": "code",
|
||
|
"execution_count": null,
|
||
|
"metadata": {},
|
||
|
"outputs": [],
|
||
|
"source": []
|
||
|
}
|
||
|
]
|
||
|
}
|