Skip to content

feat: success callback + success_log for post-retry recovery - #662

Open
MohammedAnasNathani wants to merge 3 commits into
jd:mainfrom
MohammedAnasNathani:feat/success-callback
Open

feat: success callback + success_log for post-retry recovery#662
MohammedAnasNathani wants to merge 3 commits into
jd:mainfrom
MohammedAnasNathani:feat/success-callback

Conversation

@MohammedAnasNathani

Copy link
Copy Markdown
Contributor

Summary

Fixes the long-standing gap behind #531 / SO: people wire after= expecting a “retry_success” log, but after only runs on failed attempts that may still be retried.

@retry(
    stop=stop_after_attempt(5),
    success=success_log(logger, logging.INFO),  # only if attempt_number > 1
)
def might_fail():
    ...

API

Hook When it runs
before before each attempt
after after a failed attempt that may retry / stop
before_sleep after failure, before wait
success (new) when the call ultimately succeeds
  • success_log(logger, level, only_if_retried=True) — built-in helper for the common “log recovery only” case
  • Wired through BaseRetrying, AsyncRetrying, and @retry (kwargs pass-through)
  • No change to existing after semantics

Tests

  • Recovery fires success with final attempt_number
  • First-try success still fires (for custom callbacks)
  • Exhausted retries → success never called
  • Regression: after still only on failed attempts
  • success_log respects only_if_retried

Local: 174 passed (tornado not installed in this env; CI has it)

Docs

index.rst documents the after vs success distinction with a short example.

Closes #531

``after`` only runs on failed attempts that may be retried, so there was
no first-class way to log "retry_success" when a call finally works.

Add optional ``success=`` on Retrying / AsyncRetrying / @Retry, fired only
on a clean terminal outcome. Ship ``success_log`` (default: only if
attempt_number > 1) and document the distinction from ``after`` / after_log.
Copilot AI review requested due to automatic review settings July 25, 2026 20:56

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

Mechanical reordering required for green CI under current ruff.
Runtime already accepted the kwarg via **dkw; overloads omitted it so
mypy rejected tests and user code with call-overload.
self,
sleep: t.Callable[
[int | float], None | t.Awaitable[None]
[int | float], t.Awaitable[None] | None

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Noise, avoid this please.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Not able to log "retry_success", only if retry was triggered

3 participants