composeui.core.jobs

Work run in threads, its results given back on the main thread (see Jobs).

exception composeui.core.jobs.CalledInJobError[source]

Bases: RuntimeError

A job’s function tried to start or change jobs instead of using a main-thread callback.

class composeui.core.jobs.Job[source]

Bases: Generic[R, ProgressT]

A function running in a thread of its own, started by Jobs.start.

The function gets its job first: it calls sleep, or reads is_canceled, to stop early once canceled. Its result, or what it raised, is emitted on the main thread. Programming errors instead escape the worker after dispatching cleanup; see Jobs.

__init__(hand_over)[source]
Parameters:

hand_over (Callable[[Job[Any, Any], Callable[[], None]], None])

Return type:

None

finished

the function’s return value, on the main thread

failed

a non-programming exception, on the main thread (logged too; see Jobs)

progress

progress values reported by the worker, on the main thread

property is_canceled: bool
cancel()[source]

Ask the function to stop; it still finishes, as soon as it notices.

Return type:

None

sleep(seconds)[source]

Wait seconds, in the job’s thread; False if it was canceled meanwhile.

Parameters:

seconds (float)

Return type:

bool

call_on_main_thread(callback)[source]

Call callback on the main thread, e.g. to show how far the function has gone.

Called in order, before the job’s outcome is emitted; not at all once the job is dropped (New, Open, closing the app). Without a toolkit, Jobs.wait calls it.

Parameters:

callback (Callable[[], None])

Return type:

None

report_progress(value)[source]

Emit progress on the main thread, in order and before the job’s outcome.

Pass a count, percentage, message, or another application-defined value. Dropped jobs do not emit queued progress, as with call_on_main_thread.

Parameters:

value (ProgressT)

Return type:

None

class composeui.core.jobs.Jobs[source]

Bases: object

The jobs of a main view (MainView.jobs): functions run in threads.

A job’s function runs in a thread, so that the app stays responsive. It must not touch a view, because a toolkit’s widgets belong to the main thread. It returns its result instead, and its job’s finished emits the result on the main thread. There, callbacks update the views. Like the callbacks of any signal, they get the main_view and model they ask for. Job.report_progress emits the job’s progress signal on the main thread. Job.call_on_main_thread hands it an arbitrary callback instead. A SqliteModel hands it the changed signals of the job’s writes.

task configures a reusable worker with progress, result and error state. Its changed signal shows the loading state, and its finished and failed signals the outcome of each run.

Call start, cancel and drop on the main thread, e.g. from a callback. Never call them from a job’s function: the jobs aren’t locked, as the main thread alone changes them. Job.cancel is the exception: any thread can call it. Called from a job’s function, they raise CalledInJobError. To start another job, return what it needs instead, and start it from the callback that gets it.

Uncaught CalledInJobError, AssertionError, AttributeError, NameError, NotImplementedError and TypeError escape the worker to Python’s thread exception handler. Cleanup is dispatched to the main thread, without emitting failed or setting a task’s error. The affected task returns to its idle state.

New, Open and closing the app cancel the jobs running, and drop their results: the results belong to the study replaced.

__init__(main_view)[source]
Parameters:

main_view (MainView)

Return type:

None

running_changed

True as the first job starts, False once the last one is over

property is_running: bool
set_model(model)[source]

Give model to the callbacks asking for it (the app does).

Parameters:

model (Model)

Return type:

None

task(work)[source]

Build a reusable task for work, without starting it; call on the main thread.

Parameters:

work (Callable[[Concatenate[Job[R, ProgressT], ~P]], R])

Return type:

Task[R, ~P, ProgressT]

start(work, *args, **kwargs)[source]

Run work(job, *args, **kwargs) in a thread; call it on the main thread.

Connect to the job’s signals right away: its outcome is emitted on the main thread, so no sooner than the code calling start is done. Raises CalledInJobError in a job’s thread.

Parameters:
Return type:

Job[R, ProgressT]

cancel()[source]

Cancel every job running; each still finishes, as soon as it notices.

Raises CalledInJobError in a job’s thread: a job cancels itself with Job.cancel.

Return type:

None

drop()[source]

Cancel every job running and forget it: its result won’t be emitted.

Reset all tasks, including completed ones, before emitting their changed. Raises CalledInJobError in a job’s thread.

Return type:

None

wait(timeout=10.0)[source]

Wait for every job to be over, and emit the results here: for a main view not rendered.

Use it for a main view that no toolkit shows, e.g. in a test. Its jobs’ results wait for this call, which emits them on its own thread, as a toolkit would on its main one. Raises TimeoutError if jobs are still running after timeout seconds.

Parameters:

timeout (float)

Return type:

None

hand_over_to(renderer)[source]

Hand the results queued before the main view was rendered to renderer, its own.

In order, before any later one: a job started as the app is built, e.g. by setup_model, may be over before its main view is shown. MainView.render calls it.

Parameters:

renderer (Renderer[Any, Any] | RendererContainer[Any])

Return type:

None

class composeui.core.jobs.Task[source]

Bases: Generic[R, P, ProgressT]

A reusable worker with read-only loading state, built by Jobs.task.

changed emits on the main thread when a run starts, reports progress, finishes, fails, or is dropped. After it, finished emits a run’s result, and failed its exception, as a Job’s do. Their callbacks can ask for main_view and model. Starting an already running task does nothing. Dropping the owner’s jobs resets the task and discards queued progress and outcomes, as with ordinary jobs.

__init__(jobs, work)[source]
Parameters:
Return type:

None

finished

the result of a run that succeeded, on the main thread

failed

the exception of a run that failed, on the main thread

property is_running: bool

Get whether this task is waiting for its current run’s outcome.

property is_canceled: bool

Get whether the current run was asked to stop; False once it is over.

property progress: ProgressT | None

Get the last progress value, or None before the run reports one.

property result: R | None

Get the successful result, or None before success; see has_result.

property error: Exception | None

Get the run’s exception, or None before failure.

property has_result: bool

Get whether the last run succeeded, including a result of None.

start(*args, **kwargs)[source]

Start the worker with fresh state; return False if it is already running.

Parameters:
  • args (~P)

  • kwargs (~P)

Return type:

bool

cancel()[source]

Ask the current run to stop; it still emits its outcome, as with Job.cancel.

changed emits, is_canceled then true until the outcome.

Return type:

None

disables(*views)[source]

Disable views while this task runs, from now on, e.g. the fields of its run.

The task sets their is_enabled at each start and outcome, a failure or a cancel’s included, and when New or Open drop the run.

Parameters:

views (View)

Return type:

None

cancel_with(*controls)[source]

Cancel the run when one of controls is clicked or triggered, from now on.

A button, or a menu’s or a toolbar’s action, e.g. Stop. Each is enabled only while a run goes on, until it is asked to stop.

Parameters:

controls (ButtonView | ActionView)

Return type:

None

show_state(status, *, views=(), loading_text='Loading...', progress_text='Loading... ({progress})', failed_text='Failed: {error}')[source]

Show this task’s state in status, and views only once it has a result, from now on.

status shows while there is no result: loading_text, progress_text once the run reports progress, or failed_text after a failure. New and Open drop the result: the views hide again, until the next run’s.

Parameters:
Return type:

None