barrel_ngram_shard_sup (barrel_ngram v0.9.0)

View Source

Dynamic supervisor for ngram shard processes.

Plain one_for_one with NO static children -- every shard is added and removed dynamically, each keyed by an EXPLICIT, deterministic child id, {shard, Ref} (computable directly from a shard ref alone, no lookup needed). one_for_one preserves the isolation a simple_one_for_one strategy gave (one shard's crash/restart never touches a sibling shard); what changed is purely HOW an individual shard is addressed -- explicit ids instead of anonymous pids.

This matters for rollback/close: a captured pid that has already died cannot be used to authoritatively cancel or wait out an in-flight restart of ITS replacement, because terminate_child/2 only synchronizes with a restart when it targets THAT restart's own pid -- and a dead pid never is. Addressed by a stable id instead, terminate_child/2/delete_child/2 are synchronous requests into this supervisor's own single process, serialized against its internal restart-on-EXIT handling by construction: no registry lookup, no retry loop needed to know a ref is durably vacated.

Summary

Functions

Start a shard by ref. Returns the existing shard if one is already running for that ref. Public contract UNCHANGED from before the simple_one_for_one -> id-based conversion.

New, narrowly-scoped, exported specifically for barrel_ngram_corpus_lifecycle: distinguishes started from existing, which start_shard/2 above deliberately collapses for its other callers.

Stop the shard for a ref, leaving no trace in the supervisor afterward (matching simple_one_for_one's old "a stopped child vanishes completely" behavior). Public contract UNCHANGED (today's real contract already includes {error, not_found}; this widens the possible error reasons -- running/restarting from delete_child/2 -- it does not introduce error-returning where there was none).

Stop every ref in Refs, reporting ok only once EVERY one is CONFIRMED vacated -- not merely attempted. Retries (with a short delay, since running/restarting reflects a supervisor-side restart backoff that needs real time to resolve) rather than trusting a single attempt, converging even against a stale captured pid whose replacement was mid-restart when this was first called.

Functions

init(_)

-spec init([]) -> {ok, {supervisor:sup_flags(), [supervisor:child_spec()]}}.

start_link()

-spec start_link() -> {ok, pid()} | {error, term()}.

start_shard(Ref, Config)

-spec start_shard(barrel_ngram_shards:ref(), map()) -> {ok, pid()} | {error, term()}.

Start a shard by ref. Returns the existing shard if one is already running for that ref. Public contract UNCHANGED from before the simple_one_for_one -> id-based conversion.

start_shard_tracked(Ref, Config)

-spec start_shard_tracked(barrel_ngram_shards:ref(), map()) ->
                             {ok, pid(), started | existing} | {error, term()}.

New, narrowly-scoped, exported specifically for barrel_ngram_corpus_lifecycle: distinguishes started from existing, which start_shard/2 above deliberately collapses for its other callers.

stop_shard(Ref)

-spec stop_shard(barrel_ngram_shards:ref()) -> ok | {error, term()}.

Stop the shard for a ref, leaving no trace in the supervisor afterward (matching simple_one_for_one's old "a stopped child vanishes completely" behavior). Public contract UNCHANGED (today's real contract already includes {error, not_found}; this widens the possible error reasons -- running/restarting from delete_child/2 -- it does not introduce error-returning where there was none).

stop_shards_confirmed(Refs)

-spec stop_shards_confirmed([barrel_ngram_shards:ref()]) -> ok | {error, term()}.

Stop every ref in Refs, reporting ok only once EVERY one is CONFIRMED vacated -- not merely attempted. Retries (with a short delay, since running/restarting reflects a supervisor-side restart backoff that needs real time to resolve) rather than trusting a single attempt, converging even against a stale captured pid whose replacement was mid-restart when this was first called.