简体   繁体   中英

How to have Sanic respond with http and ws?

I have the following code for a Sanic hello world based off combining different endpoints here:

Code is:

from sanic import Sanic
from sanic import response
from sanic.websocket import WebSocketProtocol

app = Sanic()

@app.route("/")
async def test(request):
    return response.json({"hello": "world"})


@app.route('/html')
async def handle_request(request):
    return response.html('<p>Hello world!</p>')

@app.websocket('/feed')
async def feed(request, ws):
    while True:
        data = 'hello!'
        print('Sending: ' + data)
        await ws.send(data)
        data = await ws.recv()
        print('Received: ' + data)

@app.route('/html2')
async def handle_request(request):
  return response.html("""<html><head><script>
         var exampleSocket = new WebSocket("wss://0.0.0.0:8000/feed",      "protocolOne");
         exampleSocket.onmessage = function (event) {
         console.log(event.data)};</script></head><body><h1>Hello socket!</h1><p>hello</p></body></html>""")

app.run(host="0.0.0.0", port=8000)
# app.run(host="0.0.0.0", port=8000, protocol=WebSocketProtocol)    # ws 

The routes "/" and "/html" work fine, but

http://0.0.0.0:8000/feed

produces:

Error: Invalid websocket request

and "/html2" renders the page fine, but doesn't log to console, showing in the debugger:

Firefox can’t establish a connection to the server at wss://0.0.0.0:8000/feed.

What should I change or add to make a viable websocket endpoint that plays nicely with the http ones, too?

Using 0.0.0.0 as your endpoint within your client html doesn't make any sense and you're not using SSL so you want to use ws:// rather than wss://. In other words,

from sanic import Sanic
from sanic import response
from sanic.websocket import WebSocketProtocol

app = Sanic()

@app.websocket('/feed')
async def feed(request, ws):
    while True:
        data = 'hello!'
        print('Sending: ' + data)
        await ws.send(data)
        data = await ws.recv()
        print('Received: ' + data)

@app.route('/html2')
async def handle_request(request):
  return response.html("""<html><head><script>
         var exampleSocket = new WebSocket("ws://" + location.host + '/feed');
         exampleSocket.onmessage = function (event) {
         console.log(event.data)};</script></head><body><h1>Hello socket!</h1><p>hello</p></body></html>""")

app.run(host="0.0.0.0", port=8000)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM