using
Scopes a resource to one iteration: acquired on the first pull, released exactly once — on completion or on error.
Lecture
Files, sockets, database cursors — the value they produce is a
sequence, but their lifetime is a bracket:
open, read, close, even when reading throws. Writing that
bracket around a lazy pipeline is awkward, because "when the
iteration ends" is wherever the consumer happens to be.
using(acquire, use, release) ties the bracket to the
iteration itself: acquire runs on the first pull (not
when the pipeline is built — laziness is preserved),
use(resource) supplies the elements, and
release(resource) runs exactly once, after the last
element or right before an error propagates.
The async form usingAsync lets all three steps be
asynchronous and composes with
concurrent — release still
fires exactly once even with overlapping pulls in flight. If
acquire itself fails there is nothing to release, and
the error simply propagates.
One honest caveat, straight from the pull model: a consumer that
abandons the iteration — break inside a
for-in, dropping the iterator — never reaches the end,
so release cannot run. Bound the iteration with
take (a bounded pipeline
completes, and completion releases) or manage the resource with
try/finally when early exit is the plan.
fxdart extension (no FxTS counterpart), after Rx's using.
Demo 1 · The bracket around a lazy read
Demo 2 · Release on error, exactly once
Try it yourself
Exercise: give the connection a lifetime.