How to quit a thrift server in Python - python

I am writing an application in Python that uses thrift to communicate between itself and a client. Whenever I try to exit the application (using Ctrl-C or the exit button on the window), the thrift server keeps the application alive, probably because the server.serve() function enters an infinite loop. What is the best way to exit this server when the rest of the application quits?

It turns out my problem was not actually thrift-specific. I was running an infinite loop in a non-daemonic thread; therefore, python waited for that thread to close before my whole program would close. Setting "self.daemon = True" in the thread's init method fixed the problem nicely.

Related

Twisted and a command line interface

I have a program where I want to do two things:
Interact with a server and respond to events from the server. I am doing this using twisted.
Have a command line prompt for the user where he can issue additional commands. I am using the python cmd module for this so far.
There seems to be no other choice than having two threads, as readline only has a blocking interface and needs to handle stuff like auto completion. Twisted on the other hand has to continuously run the reactor.
Now the problem is that it seems very hard to handle Ctrl-C for this. The easy solution would seem to have the command line run in the main thread and just use reactor.callFromThread for every interaction with the rest of the program. This is very easy, as overwriting Cmd.onecmd can do this in a generic way. However when I try to spawn the reactor in a thread with
t = Thread(target=reactor.run)
t.start()
I immediately get an exception
File "/usr/lib/python3.6/signal.py", line 47, in signal
handler = _signal.signal(_enum_to_int(signalnum), _enum_to_int(handler))
builtins.ValueError: signal only works in main thread
Everyone using twisted insists that the twisted reactor should run in the main thread, as that would be a better design.
When trying to do it that way and running twisted in the main thread, it will catch the Ctrl-C, exit the reactor and I am stuck with a thread that does not exit, as the call to input() inside cmdloop does not return. I tried searching for a solution to this and how to get out of the input() call, but everyone also insists that a command line interface should run in the main thread.
One potential option I found was to run twisted as the main thread and make the input thread a daemon, so it should exit when the reactor exits, however the daemon flag did not change anything (the thread did not exit when the main thread did). Furthermore this is likely dangerous, as the thread might be doing something important when it is killed.
Is there any way out of this?
Take a look at how invective does this with Twisted and without threads (one way to read the code might be to start at the mainpoint and work your way in).

Gracefully stop multi-process application in Python

I have an application which is stuck in a file.read call. Before it goes into a loop where this call is made it forks a child which starts a gevent WSGI server. The purpose of this setup is that I want to wait for a keystroke, send this keystroke to the child websocket server which spreads the message among other connected websocket-clients. My problem is that I don't know how to stop this thing.
If I Ctrl+C the child server process gets the sigint and stops. But my parent only responds if it can read something out of his file. Isn't there something like an asynchronous handler? I also tried registering for SIGINT via signal.signal and manually sending the signal, but the signal handler was only called if something was written to the file.
BTW: I'm runnning Linux.

Process Doesn't End When Closed

I built a web-scraper application with Python. It consists of three main parts:
The GUI (built on tkinter)
A Client (controls interface between front- and back-end)
Back-end code (various threaded processes).
The problem I have is that when the user hits X to exit the program instead of quitting through the interface, it seems like root.destroy() never gets called and the application runs forever, even though the window does disappear. This ends up consuming vast amounts of system resources.
I have tried setting all threads to Daemon without much success. Is there any other reason the program would keep eating up CPU after exit?
You don't want to set all threads to daemon. You want to set the client thread and the back-end thread to daemon. That way, when the GUI thread dies, the threads with daemon set to True end as well.
From the documentation:
A thread can be flagged as a “daemon thread”. The significance of this flag is that the entire Python program exits when only daemon threads are left.

Non-blocking server in Twisted

I am building an application that needs to run a TCP server on a thread other than the main. When trying to run the following code:
reactor.listenTCP(ServerConfiguration.tcpport, TcpCommandFactory())
reactor.run()
I get the following error
exceptions.ValueError: signal only works in main thread
Can I run the twisted servers on threads other than the main one?
Twisted can run in any thread - but only one thread at a time. If you want to run in the non-main thread, simply do reactor.run(installSignalHandlers=False). However, you cannot use a reactor on the non-main thread to spawn subprocesses, because their termination will never be detected. (This is a limitation of UNIX, really, not of Twisted.)

How to shutdown cherrypy from within?

I am developing on cherrypy, I start it from a python script.
For better development I wonder what is the correct way to stop cherrypy from within the main process (and not from the outside with ctrl-c or SIGTERM).
I assume I have to register a callback function from the main application to be able to stop the cherrypy main process from a worker thread.
But how do I stop the main process from within?
import sys
class MyCherryPyApplication(object):
def default(self):
sys.exit()
default.exposed = True
cherrypy.quickstart(MyCherryPyApplication())
Putting a sys.exit() in any request handler exits the whole server
I would have expected this only terminates the current thread, but it terminates the whole server. That's what I wanted.

Categories