Flex calls retry under bounded exponential backoff (flexAttempts, default
3; backoff from flexInitialBackoffSeconds (30) up to
flexMaxBackoffSeconds (120), with up to flexJitterSeconds (10) of
deterministic jitter). Each retry attempt is admitted against the remaining
budget before it runs and charged when admitted, so retries can stop for either
of two reasons: exhausting the attempt count, or the remaining budget refusing
the next attempt.
A finder pack that exhausts its retries — or whose next retry the budget
refuses — downgrades: it is recorded in lunaDowngrades and
metrics.lunaDowngradeCount, and the review continues with the surviving
candidates. An audit call that exhausts its retries, or whose next retry the
budget refuses, defers the whole review instead: the result is ok: false,
stage: "deferred", no recordInput is present, and the CLI exits non-zero
without recording anything, so the head remains unreviewed. A budget-refused
retry keeps the actual spend within the hard ceiling rather than overrunning
it; the deferral or downgrade reason names the budget so operators can tell it
apart from a capacity exhaustion.
The dry run reports reservedAuditChainUsd alongside reservedAuditUsd: the
former is the audit's chain-level worst case (one attempt's reserve times
flexAttempts), shown so operators can see the full retry cost, while
admission only ever reserves the single-attempt reservedAuditUsd.
A deferred review retried later re-pays its Luna finder calls: Luna output is
not cached across separate dakar-review invocations, so a retry after a
deferral repeats the finder phase's spend (roughly USD 0.04 worst case at
default limits). Operators should space retries after a deferral rather than
tight-looping them.
worstCaseReviewSeconds (2,020 s at default limits, shown in the dry run) is
the worst-case wall clock for one review's finder and audit retry chains.
Operators overriding --timeout should keep it above this figure.