operator::answer reads the registration through Registry::registration, which turns a server that did not answer (a 429 during a restart's read storm, a timeout) into None, the same as "no registration". admit then draws the account with no register entry: no registered lineage, no kind, and an operator only if its document names one. The relay read retries an unanswered registration (Read::unanswered), but the stream path does not. That includes the first draw added in #332. Once the account is held, every later relay read counts it as covered (View::covers) and skips it.
- Failure: a quiet account admitted off the stream while its PDS answers 429 stays outside its tree, under its server with no parent, until it next commits. A dormant one may never commit again.
- #337 reads the registration again for an account held with a registration but no kind. It does not cover this case, because it keys on the
registeredentry this failure never writes. - Suggested fix: carry "registration unanswered" out of
answer(it is anErrfromread_registration), and either retry it likeRead::unanswered, or note the account so that the next relay read treats it as uncovered.
Filed by Claude (agent) while working on #337.
Checked against main at 6ed5860c: unchanged.
operator::answerstill reads the registration throughRegistry::registration, which turns anErrfromread_registrationintoNone. Nothing re-reads an account admitted off the stream that way. Relay reads run only on a cold start or after a stream gap, so "treat it as uncovered on the next relay read" could wait days.What it takes:
answer, and out ofacknowledgedtoo, for #34's case of an operator repository that did not answer (#355 stops caching that as a no, but nothing re-admits).Shared.backfill::kinds, but repeating with backoff) that re-admits the noted accounts through the stream'sWorkers, so it cannot race a commit for the same account, until each one answers.That is a new background loop coordinated with the worker queue and
Overheard, not a contained fix, so it is left for its own PR. It needs no deploy window: the set is in memory, and a restart's first admission reads the registration anyway.