0

I'm using flask-socketio for server side in python. When running on windows10 the .stop() function of the flask_socketio.SocketIO works and closes the socket which terminates my script but on Unubtu it thrown exception. I want it to be closed properly. My code:

import time
import threading
import flask
import flask_socketio

def start_server( vars ):
    vars[ "app" ] = flask.Flask(__name__)
    vars[ "app" ].config['SECRET_KEY'] = 'secret!'
    vars[ "socketio" ] = flask_socketio.SocketIO( vars[ "app" ] )

    vars[ "thread" ] = threading.Thread( target= vars[ "socketio" ].run , kwargs={
        "app": vars[ "app" ],
        "host": '127.0.0.1',
        "port": 5000,
    })
    vars["thread"].start()

    return vars

vars = {}

print( "flask version: {}".format( flask.__version__ ) )
print( "flask_socketio version: {}".format( flask_socketio.__version__ ) )

start_server( vars )

time.sleep( 20 )

print( "Stopps" )
vars[ "socketio" ].stop()
print( "Done" )

I get the following output:

flask version: 1.0.2
flask_socketio version: 3.0.1
WebSocket transport not available. Install eventlet or gevent and gevent-websocket for improved performance.
 * Serving Flask app "socket_closer" (lazy loading)
 * Environment: production
   WARNING: Do not use the development server in a production environment.
   Use a production WSGI server instead.
 * Debug mode: off
 * Running on http://127.0.0.1:5000/ (Press CTRL+C to quit)
Stopps
Traceback (most recent call last):
  File "socket_closer.py", line 30, in <module>
    vars[ "socketio" ].stop()
  File "/home/administrator/miniconda3/envs/main/lib/python3.6/site-packages/flask_socketio/__init__.py", line 564, in stop
    func = flask.request.environ.get('werkzeug.server.shutdown')
  File "/home/administrator/miniconda3/envs/main/lib/python3.6/site-packages/werkzeug/local.py", line 347, in __getattr__
    return getattr(self._get_current_object(), name)
  File "/home/administrator/miniconda3/envs/main/lib/python3.6/site-packages/werkzeug/local.py", line 306, in _get_current_object
    return self.__local()
  File "/home/administrator/miniconda3/envs/main/lib/python3.6/site-packages/flask/globals.py", line 37, in _lookup_req_object
    raise RuntimeError(_request_ctx_err_msg)
RuntimeError: Working outside of request context.

This typically means that you attempted to use functionality that needed
an active HTTP request.  Consult the documentation on testing for
information about how to avoid this problem.
1
  • 2
    Sidenote- PEP8: no space before or after square/round bracket. It's ugly and not recommended ;) Commented Aug 22, 2018 at 22:18

2 Answers 2

1

If you look at the documentation for the stop() function, it has the following note:

This method must be called from a HTTP or SocketIO handler function.

What this means is that you have to define an event that stops the server, and then invoke this event from a client. You can't just call the stop function from another thread like you are doing it.

Sign up to request clarification or add additional context in comments.

Comments

0

I think stop from another thread is possible. This is what I have done:

Define a shutdown hanlder:

@g_app.route("/shutdown", methods=['GET'])
def shutdown():
    g_socket_io.stop()
    return "Shutting down..."

Call shutdown from another threaad:

    import requests
    try:
        requests.get("http://localhost:9572/shutdown")
    except requests.exceptions.ConnectionError as e:
        print("Shutdown with Connection Error" + e.__str__())
    except BaseException as e:
        print("Shutdown Error " + e.__str__())

There would print a connection error message as

Shutdown with Connection Error('Connection aborted.', RemoteDisconnected('Remote end closed connection without response',))

But surely it is closed.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.