Веб-сокеты с Python на Python с websockets и flask-socketio

#flask #websocket #socket.io #python-3.6

#flask #веб-сокет #socket.io #python-3.6

Вопрос:

Проблема

Итак, мне нужно создать приложение python, которое может находиться на компьютере, открыть канал websocket для сервера, на котором работает flask-socketio, затем передать данные на сервер. Данные будут данными json, на данный момент я тестирую со строкой.

У меня возникла проблема с использованием библиотеки «websockets» в python для подключения к серверной части «flask-socketio», которую я создаю.

Код

Сервер

 from flask import Flask, render_template, request, url_for, 

copy_current_request_context
from flask_socketio import SocketIO, emit
import logging

logging.basicConfig()

app = Flask(__name__)
app.config['SECRET_KEY'] = 'secret!'
app.config['DEBUG'] = True
socketio = SocketIO(app)


@socketio.on('connect', namespace='/')
def connect():
    print('Client connected')


@socketio.on('disconnect', namespace='/')
def disconnect():
    print('Client disconnected')


if __name__ == '__main__':
    socketio.run(app, debug=True)
  

Клиент 1 — библиотека веб-сокетов

 import asyncio
import websockets

async def hello():
    async with websockets.connect(
            'ws://127.0.0.1:5000') as websocket:
        name = 'joe'  # input("What's your name? ")

        await websocket.send('message', name)
        print(f"> {name}")

        greeting = await websocket.recv()
        print(f"< {greeting}")

asyncio.get_event_loop().run_until_complete(hello())

print("end")
  

Использовать вывод

Когда я использую клиент 1, я получаю это в качестве вывода в клиентском процессе: Traceback (most recent call last):
File "C:/project_files/aWebUAS/micro-services/New-Capabilities-Investigation/web_socket_client.py", line 15, in <module>
asyncio.get_event_loop().run_until_complete(hello())
File "C:Program FilesAnaconda3libasynciobase_events.py", line 466, in run_until_complete
return future.result()
File "C:/project_files/aWebUAS/micro-services/New-Capabilities-Investigation/web_socket_client.py", line 6, in hello
'ws://127.0.0.1:5000') as websocket:
File "C:Program FilesAnaconda3libsite-packageswebsocketspy35client.py", line 2, in __aenter__
return await self
File "C:Program FilesAnaconda3libsite-packageswebsocketspy35client.py", line 20, in __await_impl__
extra_headers=protocol.extra_headers,
File "C:Program FilesAnaconda3libsite-packageswebsocketsclient.py", line 286, in handshake
raise InvalidStatusCode(status_code)
websockets.exceptions.InvalidStatusCode: Status code not 101: 404

and on the flask process I see:
127.0.0.1 - - [2019-04-05 09:17:13] "GET / HTTP/1.1" 404 342 0.000999

Клиент 2 — websocket-клиентская библиотека

 import websocket
ws = websocket.WebSocket()
ws.connect("ws://127.0.0.1:5000")
ws.send("Hello, World")
  

Использовать вывод

В процессе клиента 2 я получаю это в качестве вывода: Traceback (most recent call last):
File "C:/project_files/aWebUAS/micro-services/New-Capabilities-Investigation/web_socket_client_2.py", line 3, in <module>
ws.connect("ws://127.0.0.1:5000")
File "C:Program FilesAnaconda3libsite-packageswebsocket_core.py", line 226, in connect
self.handshake_response = handshake(self.sock, *addrs, **options)
File "C:Program FilesAnaconda3libsite-packageswebsocket_handshake.py", line 79, in handshake
status, resp = _get_resp_headers(sock)
File "C:Program FilesAnaconda3libsite-packageswebsocket_handshake.py", line 160, in _get_resp_headers
raise WebSocketBadStatusException("Handshake status %d %s", status, status_message, resp_headers)
websocket._exceptions.WebSocketBadStatusException: Handshake status 404 NOT FOUND

и процесс flask показывает это:
127.0.0.1 - - [2019-04-05 09:11:57] "GET / HTTP/1.1" 404 342 0.001000

Заключение

Некоторые чтения говорят мне, что я неправильно нажимаю на свой обработчик socketio в flask, но я не уверен, как на это ориентироваться.

Любая помощь очень ценится. Моя цель — создать скрипт python, взаимодействующий с сервером flask socketio. Я не женат ни на какой части этого, но предпочел бы придерживаться flask для сервера.

ТИА — Ян

Ответ №1:

Возможно, вы уже поняли это, но проблема, скорее всего, в том, что flask-socketio является сокетом.Реализация ввода-вывода, а не реализация websocket. Сокет.IO использует websockets в качестве одного из своих протоколов связи, но вам понадобится сокет.Клиент ввода-вывода для подключения к серверу flask-socketio.

Смотрите документы socketio, в частности:

Сокет.IO НЕ является реализацией WebSocket. Хотя сокет.IO действительно использует WebSocket в качестве транспорта, когда это возможно, он добавляет некоторые метаданные к каждому пакету: тип пакета, пространство имен и идентификатор подтверждения, когда требуется подтверждение сообщения. Вот почему клиент WebSocket не сможет успешно подключиться к сокету.Сервер ввода-вывода и сокет.Клиент ввода-вывода также не сможет подключиться к серверу WebSocket.

Взгляните на этот сокет python.Клиент ввода-вывода. https://github.com/miguelgrinberg/python-socketio