feat(transport): add HTTP retry with exponential backoff#1520
Draft
feat(transport): add HTTP retry with exponential backoff#1520
Conversation
Instructions and example for changelogPlease add an entry to Example: ## Unreleased
### Features
- add HTTP retry with exponential backoff ([#1520](https://github.com/getsentry/sentry-native/pull/1520))If none of the above apply, you can opt out of this check by adding |
df2be97 to
b083a57
Compare
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The deferred startup retry scan (100ms delay) could pick up files written by the current session. Filter by startup_time so only previous-session files are processed. Also ensure the cache directory exists when cache_keep is enabled, since sentry__process_old_runs only creates it conditionally. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Monotonic time is process-relative and doesn't work across restarts. Retry envelope timestamps need to persist across sessions, so use time() (seconds since epoch) for file timestamps, startup_time, and backoff comparison. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Rename SENTRY_RETRY_BACKOFF_BASE_MS to SENTRY_RETRY_BACKOFF_BASE_S and sentry__retry_backoff_ms to sentry__retry_backoff, since file timestamps are now in seconds. The bgworker delay sites multiply by 1000 to convert to the milliseconds it expects. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Move startup_time initialization into sentry__retry_new and remove the unnecessary sentry__retry_set_startup_time indirection. Tests now use write_retry_file with timestamps well in the past to match production behavior where retry files are from previous sessions. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
When files exist but aren't eligible yet (backoff not elapsed), foreach was returning 0 causing the retry polling task to stop. Return total valid retry files found instead of just the eligible count so the caller keeps rescheduling. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Make handle_result return bool (true = file rescheduled for retry, false = file consumed) and use it in foreach to decrement the total count. This avoids one extra no-op poll cycle after the last retry. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…Y_THROTTLE Replace SENTRY_RETRY_BACKOFF_BASE_S and SENTRY_RETRY_STARTUP_DELAY_MS with ms-based constants so the transport uses them directly without leaking unit conversion details. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Give the retry module a bgworker ref and send callback so it owns all scheduling. Transport just calls _start and _enqueue. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
sentry__retry_new only returns NULL on failure, not based on options. sentry__retry_start and _enqueue require non-NULL retry. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Deduplicate prepare/send/free sequence shared by retry_send_cb and http_send_task. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Already covered by retry_throttle and retry_result. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…ashpad Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Pass startup_time directly to _foreach as a `before` filter instead of a bool. Clear it after the first run so subsequent polls use backoff. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Deduplicate filename construction across write_envelope, handle_result, and tests. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
When the transport supports retry and http_retries > 0, sentry__process_old_runs now skips caching .envelope files from old runs. The retry system handles persistence, so duplicating into cache/ is unnecessary. Also simplifies sentry__retry_handle_result: only cache on max retries exhausted, not on successful send. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Move the retry-aware check before cache_dir creation so we avoid mkdir when the retry system handles persistence. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The retry callback now receives a sentry_envelope_t and returns a status code. The retry system handles deserialization and file lifecycle internally, keeping path concerns out of the transport. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add test case for successful send at max retry count with cache_keep enabled, confirming envelopes are cached regardless of send outcome. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…lopes The startup poll used `ts >= startup_time` to skip envelopes written after startup. With second-precision timestamps, this also skipped cross-session envelopes written in the same second as a fast restart. Reset `startup_time` in `sentry__retry_enqueue` so the startup poll falls through to the backoff path for same-session envelopes. The bgworker processes the send task (immediate) before the startup poll (delayed), so by the time the poll fires, `startup_time` is already 0. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
b083a57 to
a264f66
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Add
sentry_options_set_http_retries()to configure retry attempts for transient network errors. Failed envelopes are written to<db>/retry/and retried with exponential backoff (15min, 30min, 1h, 2h, ...) modeled after Crashpad's upload retry behavior. When retries are exhausted and offline caching is enabled, envelopes are moved to<db>/cache/instead of being discarded.See also: https://develop.sentry.dev/sdk/expected-features/#buffer-to-disk
Depends on: