API reference¶
The API card is the one-page version. This page is generated from the docstrings.
Tolquane: parallel programming with composable building blocks.
Nodes speak on channels. Pipelines, farms and all-to-all blocks compose them, and the
same graph runs on threads, processes or across a network. The design lives in
DESIGN.md at the repository root.
import tolquane as tq
@tq.source
def numbers():
yield from range(1, 101)
@tq.node
def double(x):
return x * 2
out = tq.to_list()
tq.run(numbers >> tq.farm(double, workers=4) >> out)
print(sorted(out.items))
Context
¶
What a node can do while it runs: send items, see where they came from, stop.
cancelled
property
¶
True once the run is being cancelled; long-running raw nodes should return.
is_feedback
property
¶
True when the current item arrived on a feedback edge.
input_waiting
property
¶
True when another item is already queued for this node (raw nodes batch on it).
feedback_inputs
property
¶
Input indexes that are feedback edges, for recv(source=...) in raw heads.
send(item, *, to=None)
¶
Send item downstream: round robin by default, or to output to.
broadcast(item)
¶
Send the same object to every output. Receivers must treat it as read-only.
feedback(item, *, to=None)
¶
Send item back to the start of the enclosing tq.feedback block.
flush()
¶
Send any batched output now. Raw nodes that block outside Tolquane (a socket, a queue) should call this before blocking, so downstream is not kept waiting.
stop()
¶
Finish this node after the current item. Its outputs are closed normally.
recv(source=None)
¶
Raw nodes: next (source, item), or None once every input has ended.
With source=i only that input is read (others are held back with their
backpressure) and None means that input has ended.
inputs()
¶
Raw nodes: iterate (source, item) pairs until every input has ended.
Report
dataclass
¶
node(fn=None, *, name=None, distribute='round_robin')
¶
A processing node: def f(item) returns what to send, def f(item, ctx) sends.
source(fn=None, *, name=None)
¶
A node with no inputs that yields (or returns an iterable of) items.
sink(fn=None, *, name=None)
¶
A node with no outputs. Its return value is ignored.
raw(fn=None, *, name=None)
¶
Full control: def f(ctx) reads with ctx.recv()/ctx.inputs() and sends itself.
farm(worker, workers=4, **options)
¶
Emitter, workers copies of worker and a collector. See Farm for options.
comb(first, second)
¶
Fuse two nodes into one so they run on one thread with no channel between them.
pipeline(*blocks)
¶
Connect blocks left to right; the same thing as a >> b >> c.
all2all(left, right, *, R=None, G=None, merge=False)
¶
Join two farms worker to worker, removing the collector and emitter between them.
R is fused after every left worker, G before every right worker. With
merge=True the two farms stay in a pipeline through one node (R, G or
comb(R, G)), or worker to worker when neither is given.
feedback(block, *, name=None)
¶
Wire a block's outputs back to its inputs. Send back with ctx.feedback(item).
The loop closes by itself once every outside input has ended and nothing is in
flight; ctx.stop() in the first stage ends it earlier.
check(block)
¶
Expand and validate a block without running it. Raises GraphError with a fix.
explain(block)
¶
One line per node and per edge saying what was inferred and which rule wired it.
to_list(name='to_list')
¶
A sink for tests and quick scripts: run the graph, then read sink.items.
from_iterable(items, name='from_iterable')
¶
A source that yields the given items.
Bases: Block
Emitter, N workers and a collector.
A worker is a function, a class, a comb() or any block: a pipeline, a farm, a
feedback loop or an all-to-all. A block worker is copied workers times, each copy
named <farm>.<i>.<node>, and must have one input and at most one output.
clone(**changes)
¶
A copy of this farm with some options replaced.
A running graph you feed with put and read with get or iteration.
Use it as a context manager; leaving the block closes the input, waits for the
graph to drain and re-raises any failure. on_progress, progress_interval,
tap and stop work as they do in run; a session that is stopped raises
RunCancelled when the block is left.
Read a deploy file (TOML) or an equivalent dict.
[groups.G1]
endpoint = "10.0.0.1:7000"
nodes = ["numbers", "double"] # node names, farm names, or glob patterns
[groups.G2]
endpoint = "10.0.0.2:7000"
nodes = ["show"]
ssh = "me@10.0.0.2" # optional; where `tolquane launch` starts it
[options]
secret = "change-me" # optional; HMAC handshake on every connection
connect_timeout = 60 # seconds to wait for a peer to come up
reconnect_timeout = 30 # seconds to tolerate a dropped connection
python = "python3" # optional; interpreter `tolquane launch` uses
workdir = "/srv/flow" # optional; directory it starts each group in
ssh, python and workdir may also be given per group.