◉RORK LABJP
●GPT-6.1 SOL — Added to Rork's model menu (09-29) with Low, Medium and High effort; included on Pro and Max●SONNET 5.5 — Claude Sonnet 5.5 is selectable: strong at UI design and faster than Sonnet 5 (09-28)●SDK 58 — Beta since 09/15 with no stable date yet; running projects in Expo Go has required login since 09/03●WIDGET — A write-up traces an iOS widget that renders black only in production builds●OBSERVE — EAS Observe now records native crashes too (SDK 57.0.21 or later, 10/07)●NEW — My App Open Ad Only Showed When the App…●GPT-6.1 SOL — Added to Rork's model menu (09-29) with Low, Medium and High effort; included on Pro and Max●SONNET 5.5 — Claude Sonnet 5.5 is selectable: strong at UI design and faster than Sonnet 5 (09-28)●SDK 58 — Beta since 09/15 with no stable date yet; running projects in Expo Go has required login since 09/03●WIDGET — A write-up traces an iOS widget that renders black only in production builds●OBSERVE — EAS Observe now records native crashes too (SDK 57.0.21 or later, 10/07)●NEW — My App Open Ad Only Showed When the App…
Articles/Dev Tools
⬡ Dev Tools/2026-05-31Advanced

Running Crash-Free Rate as a Budget: An SLO Design Note for Deciding Where to Invest Across 6 Indie Apps

Notes from running 6 wallpaper apps in parallel and the shift from treating crash-free rate as a pass/fail threshold to treating it as an error budget. A working write-up on turning burn rate into investment and sunset decisions.

Rork585SLOCrashlytics12Cloudflare Workers25ReliabilityAdMob73

✦ Premium Article

One of my apps dropped from 99.7% to 99.2% crash-free right after a release. Half a percentage point. And I genuinely could not decide whether to pause the next feature and dig into the cause, or treat it as ordinary noise and keep moving. I had no internal sense of whether 99.2% was "dangerous" or "fine."

I have been building apps independently since 2014 — twelve years now — and somewhere after crossing 50 million cumulative downloads, this question of how to judge fragility started following me everywhere. With a single app, intuition is enough. But running 6 wallpaper and calming apps in parallel means deciding, almost weekly, where to spend my time: which app to grow, which to wind down. This post is about the moment I stopped looking at crash-free rate as a pass/fail number and started treating it as an error budget — and how I turned that number into investment and sunset decisions, with the actual figures and code behind it.

A pass/fail threshold makes your judgment wobble

When I ran crash-free rate as "above 99% is fine, below means act," my decisions were shockingly inconsistent. The same 99.2% would feel "still okay" on a good morning and "we're in trouble" on a tired evening — so I'd freeze everything and start investigating. My judgment was tracking my mood, not the app.

The real problem is that a threshold only ever looks at the instantaneous value. Crash-free rate jumps around daily. On a low-DAU app, a single user crashing repeatedly can swing it 0.3 points. Decide feature freezes off the instantaneous number and you either get whipsawed by noise or miss a slow, steady decline.

This is exactly where the SRE idea of an SLO (Service Level Objective) and error budget earns its keep. Once you decide "I'm targeting 99.5% crash-free," the remaining 0.5% becomes a budget of failures you are allowed to spend. While budget remains, you keep shipping features. When you're burning through it fast, you act in proportion to that speed — the burn rate. Just by shifting what I was judging — from "the current value" to "the pace of consumption" — the wobble dropped dramatically.

Don't apply the same SLO to all 6 apps

My first mistake was setting the same "99.5% crash-free" target on all 6. It did not work. A single crash means something completely different on a flagship wallpaper app than on a small calming app doing a few thousand downloads a month.

Today I split the apps into 3 tiers along two axes — revenue contribution and DAU — and set a different SLO per tier.

  • Tier 1 (core, DAU in the tens of thousands): 99.5% crash-free (user-based) / ANR under 0.47%. Carries most of the AdMob revenue, so the strictest target
  • Tier 2 (growing, DAU in the thousands): 99.0% / ANR under 0.6%. Still being grown, so I balance quality against feature velocity
  • Tier 3 (mature, DAU in the hundreds to a thousand): 98.5%. Apps I've decided not to invest in further. Breaching the budget mostly means "observe"; breaching it repeatedly becomes input for a sunset decision

The key idea: an SLO is not a quota to hit, it's a tool for deciding where your time goes. When a Tier 3 app breaks its SLO I don't jump. Instead I read "Tier 3 keeps exhausting its budget" as a signal that it's no longer worth my hands, and feed that into the sunset call. The point of the SLO isn't perfect quality — it's mechanically deciding how to allocate finite time across 6 apps.

✦

Thank you for reading this far.

Continue Reading

What follows includes implementation code, benchmarks, and practical content we hope you'll find useful. This site runs without ads — server and development costs are supported entirely by members like you. If it's been helpful, we'd be truly grateful for your support.

WHAT YOU'LL LEARN
✦How to assign different SLOs per app by revenue contribution and DAU, with a concrete 3-tier target table for a 6-app portfolio
✦A 90-line Cloudflare Workers implementation (copy-paste ready) that computes error-budget remaining and burn rate over a 28-day rolling window
✦A decision gate that mechanically separates freeze, hotfix, and sunset-review from budget consumption, plus how to handle noise on low-DAU apps
Secure payment via Stripe · Cancel anytime
✦

Unlock This Article

Get full access to the rest of this article. Buy once, read anytime. This site is ad-free — your support goes directly toward keeping it running.

or
Unlock all articles with Membership →
Share

Thank You for Reading

Rork Lab is ad-free, supported entirely by members like you. We publish practical guides daily with implementation code, benchmarks, and production-ready patterns. If you've found it useful, we'd love to have you on board.

  • ✦Copy-paste ready implementation code
  • ✦New advanced guides published daily
  • ✦$5/mo or $10 for lifetime access
View Membership →

Related Articles

⬡ Dev Tools2026-05-19
Rolling Out Firebase App Check in Rork Without Breaking AdMob or Crashlytics
A practical, staged rollout for Firebase App Check in Rork apps that keeps Crashlytics reporting, Realtime Database listeners, and AdMob payouts intact — written from running AdMob-funded indie apps in production.
⬡ Dev Tools2026-06-12
Building a Developer Debug Menu Into Your Rork App — Verify Ads, Purchases, and Remote Config Before Release
A production-safe developer debug menu for Rork apps — switch environments, force test ads, simulate entitlements, and override Remote Config, with working TypeScript code and the pitfalls I hit running six apps.
⬡ Dev Tools2026-05-09
Building a Rork A/B Testing Platform with GrowthBook and PostHog from Scratch
Drop Firebase and pair GrowthBook with PostHog to ship a production-grade A/B testing stack for your Rork apps. SDK wiring, edge evaluation on Cloudflare Workers, Bayesian statistics interpretation, and the operational pitfalls I learned the hard way.