Metabolic tasks (Python)#

raven-toolbox objects in raven_toolbox.tasks.

Functions#

Function

Summary

apply_task_constraints

Apply a task's inputs/outputs/equations/bound-changes to model in place.

check_tasks

Run a task list against model and return a TaskResult per task.

EssentialReactionsResult

Reactions a model must use to perform a task list (RAVEN essentialRxns).

find_task_essential_reactions

Find the reactions a model must use to satisfy a task list.

parse_task_list

Parse a task-list file into Task objects.

Task

One metabolic task. Bounds are (metabolite_or_reaction, lb, ub) triples.

task_name_maps

Build name[comp]→[ids] and comp→[ids] lookups for a model's metabolites.

TaskResult

Result of one task: passed is the verdict (accounts for should_fail).

Reference#

apply_task_constraints#

apply_task_constraints(model: cobra.Model, task: Task, name_to_id, comp_to_ids)

Apply a task's inputs/outputs/equations/bound-changes to model in place.

Sets a feasibility (zero) objective. Returns (task_metabolite_ids, error); task_metabolite_ids are the model metabolites the task references (RAVEN's essentialMetsForTasks). On error the model may be partially modified.

check_tasks#

check_tasks(model: cobra.Model, tasks: str | Iterable[Task], *, close_boundaries: bool=False)

Run a task list against model and return a TaskResult per task.

tasks is a parsed list of Task or a path to a task-list file. By default (close_boundaries=False), existing exchange/sink/demand reactions are left open, so a task's inputs/outputs add to whatever the model's own boundary already allows, as RAVEN's checkTasks does on a model without boundary metabolites. Pass close_boundaries=True for the stricter reading, where inputs/outputs are defined purely by the tasks, as with RAVEN's checkTasks(closeModel(model), ...).

EssentialReactionsResult#

Reactions a model must use to perform a task list (RAVEN essentialRxns).

reactions maps reaction id → forced flux direction (+1 forward, -1 reverse): the reaction must carry flux of that sign in every feasible solution of at least one task. per_task is the same, split by task id. task_metabolites are the model metabolites the tasks reference (RAVEN essentialMetsForTasks, protected from removal). failed_tasks are tasks that were infeasible or malformed and thus skipped (RAVEN drops these from the task list).

find_task_essential_reactions#

find_task_essential_reactions(model: cobra.Model, tasks: str | Iterable[Task], *, close_boundaries: bool=False, cache_path: str | Path | None=None, verbose: bool=False, processes: int=1, checkpoint_every: int=10)

Find the reactions a model must use to satisfy a task list.

A faithful port of RAVEN's checkTasks(getEssential=true) → getEssentialRxns: each task is constrained as in check_tasks, then _task_essential_reactions finds the reactions it must use (min-flux solve → shrink loop → exact constrain-to-0 test). This is the prepINITModel step that feeds (ft)INIT: essential reactions are kept regardless of expression score and made irreversible in their forced direction. When a reaction is essential in several tasks with conflicting directions, the majority wins (ties → forward), matching RAVEN's pos < neg. close_boundaries defaults to False: a task's inputs/outputs add to whatever the model's own open exchanges already allow, rather than replacing them, as in check_tasks. RAVEN's prepINITModel calls closeModel first, which corresponds to close_boundaries=True.

The solver is configured per task to match RAVEN's solveLP (FeasibilityTol = 1e-9, single-threaded with a fixed seed) so the degenerate min-flux vertex — and thus the discovered essential set — is reproducible. Threads=1 only pins that one solve; it says nothing about the tasks themselves, which are independent of each other. processes (default 1, sequential) parallelises across tasks with a ProcessPoolExecutor — each worker still solves single-threaded, so results are identical to the sequential run, just computed concurrently. Pick it against available cores and memory: each worker holds its own copy of model, sent once at pool startup, not per task.

On a genome-scale model this is slow (a min-flux solve plus a feasibility LP per candidate, per task). Pass cache_path to make it resumable: the accumulated results are written there (atomically) every checkpoint_every tasks (across both sequential and parallel execution) and once more after the last one, and a re-run skips tasks already cached — so it survives interruptions across sessions. Re-serializing the whole accumulated result after every single task would make total checkpoint I/O grow quadratically in the task count; checkpoint_every trades a little resumability granularity (at most that many completed tasks are redone after an interruption) for checkpoint I/O that scales with n_tasks / checkpoint_every instead. verbose prints one line per task as it completes (or is skipped because it is already cached), silent by default. In parallel, lines print in completion order, not task order.

parse_task_list#

parse_task_list(path: str | Path)

Parse a task-list file into Task objects.

Task#

One metabolic task. Bounds are (metabolite_or_reaction, lb, ub) triples.

In changed, a bound is None when the cell was empty, meaning "leave that bound of the reaction as it is" (RAVEN reads it as NaN).

task_name_maps#

task_name_maps(model: cobra.Model)

Build name[comp]→[ids] and comp→[ids] lookups for a model's metabolites.

name[comp] maps to a list because a model can carry several metabolites with the same name and compartment. A task referencing it constrains all of them. RAVEN's checkTasks constrains only the first match; both sides warn when a task hits duplicates, so the difference is visible instead of silent.

TaskResult#

Result of one task: passed is the verdict (accounts for should_fail).