spacr.qt.shutdown¶
Provide graceful-stop, force-quit, and force-restart controls for Qt.
Cooperative cancellation remains the default because it lets active writes
finish safely. When a worker cannot respond, this module presents the user
with the consequences of stopping immediately, supports a verified restart
record, and can repeat the choice after RECHECK_MS.
Classes¶
Re-ask about force quitting while a graceful stop is still running. |
Functions¶
|
Ask whether to stop cooperatively or to kill. |
|
One line per running job, for the prompts above. |
|
Flush available logs and terminate the process immediately. |
|
Save the current state and restart spaCR in a new process. |
|
Paint |
Module Contents¶
- class spacr.qt.shutdown.GracefulQuitWatcher(parent: PySide6.QtWidgets.QWidget | None, still_running: Callable[[], bool], *, what: str, describe: Callable[[], str] | None = None, on_force: Callable[[], None] | None = None, interval_ms: int = RECHECK_MS)[source]¶
Bases:
PySide6.QtCore.QObjectRe-ask about force quitting while a graceful stop is still running.
Owned by whoever started the graceful attempt. It holds no reference to the jobs themselves – it calls
still_running()each time, so a caller is free to retire handles underneath it.Stops asking as soon as
still_running()reports False, and stops for good once force is chosen, so a user who is already leaving is not asked a second time on the way out.- Parameters:
parent – widget the question is shown over, or
None.still_running – called with no arguments before each prompt and answers whether anything is left to wait for. A callable rather than a list of handles, so the caller may retire them underneath.
what – what is still running, named in the question the user reads. Keyword-only.
describe – called with no arguments for a longer line under that question, when there is more worth saying than
what.on_force – called if the user chooses to force the quit. Nothing here kills anything itself.
interval_ms – milliseconds between prompts.
Arm the watcher that asks again while something is still running.
- Parameters:
parent – the window the question is asked on, or
None.still_running – called to ask whether the work is still going.
what – what is running, named in the question.
describe – called for a longer description of the work.
on_force – called when the user chooses to quit anyway; defaults to the module’s own force-quit.
interval_ms – how often to ask again.
- spacr.qt.shutdown.ask_how_to_quit(parent: PySide6.QtWidgets.QWidget | None, *, what: str, detail: str = '', verb: str = 'Quit', offer_restart: bool = False, restart_detail: str = '') str[source]¶
Ask whether to stop cooperatively or to kill.
- Parameters:
parent – widget that owns and centres the modal question, or
Nonefor an application-level dialog.what – what is being quit, in the user’s words – “spaCR” or the name of a module. It is used in the sentence, so it reads as a noun: “Quit Mask Generation?”.
verb – the word for what is about to happen. “Quit” for the application and the Home banner, “Stop” for a module’s Stop button – a button labelled Stop that opens a dialog headed “Quit” reads as the wrong dialog, and a user who thinks they have mis-clicked cancels out of the thing they wanted.
detail – appended under the question. Callers use it to name what is still running, because “something is still running” is not enough information to choose with.
offer_restart – add a Force restart button. This option is disabled by default for ordinary quit dialogs.
restart_detail – what Force restart will cost, from
spacr.restart_state.warning_text(). Shown only when the button is offered, and REQUIRED to be meaningful when it is – a button whose consequences are not on screen beside it is one people press once.
- Returns:
GRACEFUL,FORCE,RESTARTorCANCEL.
Cancel is the default button and the escape action. Force quit is reachable in one click but is never what a stray Return key does, and Force restart is LAST because it is the most destructive thing on the dialog.
- spacr.qt.shutdown.describe_active(handles: Iterable) str[source]¶
One line per running job, for the prompts above.
“Something is still running” is not information anybody can decide with; the name of the module and how long it has been going is.
- Parameters:
handles – running job handles; each one’s
app_key(or'job') andelapsed()seconds, shown in whole minutes, are listed.
- spacr.qt.shutdown.force_quit_now(exit_code: int = 1) None[source]¶
Flush available logs and terminate the process immediately.
This function uses
os._exit(), so Python finalizers,atexithandlers, and Qt teardown do not run. Use it only after the user confirms a force quit.- Parameters:
exit_code – process exit status.
- spacr.qt.shutdown.restart_spacr(module: str, settings=None, *, running=(), run_folders=(), launcher=None, exiter=None) bool[source]¶
Save the current state and restart spaCR in a new process.
The restart is cancelled if the state cannot be written and verified.
- Parameters:
module – key of the module to reopen.
settings – module settings to restore after launch.
running – active-run records for the restart summary.
run_folders – paths that may contain interrupted-run output.
launcher – optional process-launch function. Defaults to a detached
subprocess.Popencall.exiter – optional exit function. Defaults to
force_quit_now().
- Returns:
Truewhen the replacement process was started;Falsewhen saving or launching failed and the current process remains open.
- spacr.qt.shutdown.style_as_danger(button: PySide6.QtWidgets.QPushButton, palette: dict | None = None) None[source]¶
Paint
buttonin the theme’s danger colour.Scoped to the one button rather than added to the application sheet: this is the only red control on its row, and a global
#DangerButtonrule would be a new thing for every later screen to trip over.- Parameters:
button – the push button to restyle; it is given the object name
DangerButtonwhen it has none.