Part of lp.services.twistedsupport.processmonitor View In Hierarchy
Support for running a process and reporting on its progress.
The idea is this: you want to run a child process. Occasionally, you want to report on what it is doing to some other entity: maybe it's a multistep task and you want to update a row in a database to reflect which step it is currently on. This class provides a runNotification() method that helps with this, taking a callable that performs this notfication, maybe returning a deferred.
- The notifications are serialized. If you call runNotification() with two callables, the deferred returned by the first must fire before the second callable will be called.
- A notification failing is treated as a fatal error: the child process is killed and the 'termination deferred' fired.
- Because there are multiple things that can go wrong more-or-less at once (the process can exit with an error condition at the same time as unexpectedError is called for some reason), we take the policy of reporting the first thing that we notice going wrong to the termination deferred and log.err()ing the others.
- The deferred passed into the constructor will not be fired until the child process has exited and all pending notifications have completed. Note that Twisted does not tell us the process has exited until all of it's output has been processed.
|Instance Variables||_deferred||The deferred that will be fired when the child process exits.|
|_notification_lock||A DeferredLock, used to serialize the notifications.|
|_termination_failure||When we kill the child process in response to some unexpected error, we report the reason we killed it to self._deferred, not that it exited because we killed it.|
|Method||__init__||Construct an instance of the protocol, for listening to a worker.|
|Method||runNotification||Run a given function in series with other notifications.|
|Method||unexpectedError||Something's gone wrong: kill the subprocess and report failure.|
Inherited from ProcessProtocolWithTwoStageKill:
|Method||terminateProcess||Terminate the process by SIGINT initially, but SIGKILL if needed.|
|Method||_sigkill||Forcefully kill the process.|
|Parameters||deferred||A Deferred that will be fired when the subprocess has finished (either successfully or unsuccesfully).|
Run a given function in series with other notifications. "func(*args)" will be called when any other running or queued notifications have completed. func() may return a Deferred. Note that if func() errors out, this is considered a fatal error and the subprocess will be killed.
Note that we depend on terminateProcess() killing the process: we depend on the fact that processEnded will be called after calling it.
We fire the termination deferred, after waiting for any in-progress notifications to complete.