Skip to content

feat(android): Raise default maxCacheItems to 100 and send startup crash first - #6608

Draft
sentry-junior[bot] wants to merge 3 commits into
mainfrom
feat/android-cache-100-startup-crash-first
Draft

sentry-junior[bot] wants to merge 3 commits into
mainfrom
feat/android-cache-100-startup-crash-first

Conversation

@sentry-junior

@sentry-junior sentry-junior Bot commented Nov 13, 2026

Copy link
Copy Markdown
Contributor

📜 Description

  • Android-only default: SentryAndroidOptions sets maxCacheItems to 100, up from 30. JVM keeps 30. maxQueueSize moves to 100 with it.
  • The startup crash marker (outbox/startup_crash) now contains the file name of the cached crash envelope. On the next launch, init blocks (same startupCrashFlushTimeoutMillis budget) only until that one file is sent. The rest of the cache drains in the background in the usual order.
  • If the marker is empty (older SDK or hybrid SDK) or the named file no longer exists, it falls back to the current behavior and blocks on the whole drain.
  • Small hooks: SendFireAndForget.sendFile(name) (default false), DirectoryProcessor.processSingleFile(file) (uses the same hint and processedEnvelopes dedupe, so the crash file isn't sent twice), EnvelopeCache.getEnvelopeFile is now protected. AndroidEnvelopeCache.hasStartupCrashMarker is replaced by readStartupCrashMarker (internal API).

Eviction order and general send order don't change.

💡 Motivation and Context

Offline devices fill 30 cache slots quickly, and older envelopes get evicted. Spec context: getsentry/sentry-docs#20026.

Eviction cost at 100 items, measured on a device, is fine: 2–7ms without init. In the worst case, init does a full scan: 31ms with 2KB attachments, 720ms with 1MB attachments.

Why maxQueueSize moves too: it was only a field initializer copy of maxCacheItems, so it would have stayed at 30. DirectoryProcessor dedupes in-flight files with a CircularFifoQueue(maxQueueSize), and the transport queue has the same size. With a cache of 100 and a queue of 30, the dedupe ring forgets paths, so files can be sent twice, and a queue overflow can drop cached files.

Why the startup crash goes first: with a startup crash marker, init (usually on the main thread) blocked for up to 5s while the whole cache drained, with a 100ms delay and a flush wait per file. With 100 files and the crash at a random position in listFiles() order, the crash would likely miss that window.

This changes behavior, so it should go out in a minor release.

💚 How did you test it?

New unit tests cover:

  • the marker naming the crash envelope file
  • reading a named, empty, or missing marker
  • the crash file being sent first while only that file blocks
  • the fallback when the marker is empty or the file is missing
  • the crash file being handled only on the first run
  • processSingleFile, including the dedupe with processDirectory
  • the new Android defaults

Ran locally:

  • :sentry:test for DirectoryProcessor, EnvelopeSender, SendCachedEnvelopeFireAndForgetIntegration, EnvelopeCache, OutboxSender, and SentryOptions tests
  • :sentry-android-core:testReleaseUnitTest for SendCachedEnvelopeIntegration, AndroidEnvelopeCache, SentryAndroidOptions, AndroidOptionsInitializer, and SentryAndroid tests
  • make format api

📝 Checklist

  • I added GH Issue ID & Linear ID
  • I added tests to verify the changes.
  • No new PII added or SDK only sends newly added PII if sendDefaultPII is enabled.
  • I updated the docs if needed.
  • I updated the wizard if needed.
  • Review from the native team if needed.
  • No breaking change or entry added to the changelog.
  • No breaking change for hybrid SDKs or communicated to hybrid SDKs.
  • Public API changes reviewed by another Mobile SDK team member or implemented according to the develop docs spec.

🔮 Next steps

  • Update the Android maxCacheItems default in the docs.

via roman.

--

View Session [Sentry]

sentry-junior Bot and others added 3 commits November 13, 2026 15:18
…ash first

Android devices are offline more often than servers, so the Android default
for maxCacheItems goes from 30 to 100, and maxQueueSize follows it so the
transport queue and the dedupe of in-flight cached files fit the cache.

The startup crash marker now names the cached crash envelope. On the next
launch only that envelope is sent while init blocks, and the rest of the
cache drains in the background. An empty marker, or one naming a file that
is gone, falls back to blocking on the whole cache as before.

Co-Authored-By: roman <roman.zavarnitsyn@sentry.io>
Co-Authored-By: roman <roman.zavarnitsyn@sentry.io>
Co-Authored-By: roman <roman.zavarnitsyn@sentry.io>
@github-actions

Copy link
Copy Markdown
Contributor
Messages
📖 Do not forget to update Sentry-docs with your feature once the pull request gets approved.

Generated by 🚫 dangerJS against dad6a0a

@sentry

sentry Bot commented Nov 13, 2026

Copy link
Copy Markdown

📲 Install Builds

Android

🔗 App Name App ID Version Configuration
SDK Size io.sentry.tests.size 8.64.0 (1) release

⚙️ sentry-android Build Distribution Settings

This branch has not been deployed

No deployments
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.

0 participants