RORK LABJP
TOOLING — Rork's developer repos keep moving: rork-xcode was updated on July 16, rork-device on July 15, and rork-plist on July 13OPUS46 — Claude Opus 4.6 is live in Rork, and Rork Max is built to assemble apps on top of Claude CodeSIM — A cloud iOS simulator runs in the browser, with one click to install on a device and two clicks to publish to the App StoreMAX — Rork Max emits pure Swift rather than React Native, reaching iPhone, iPad, Apple Watch, Apple TV, Vision Pro, and even iMessageNATIVE — That opens up HealthKit, ARKit and LiDAR, NFC, Dynamic Island, Live Activities, 3D through Metal, and on-device inference with Core MLSEED — Rork raised a $15M seed led by Left Lane Capital, with Peak XV and a16z Speedrun joining the roundTOOLING — Rork's developer repos keep moving: rork-xcode was updated on July 16, rork-device on July 15, and rork-plist on July 13OPUS46 — Claude Opus 4.6 is live in Rork, and Rork Max is built to assemble apps on top of Claude CodeSIM — A cloud iOS simulator runs in the browser, with one click to install on a device and two clicks to publish to the App StoreMAX — Rork Max emits pure Swift rather than React Native, reaching iPhone, iPad, Apple Watch, Apple TV, Vision Pro, and even iMessageNATIVE — That opens up HealthKit, ARKit and LiDAR, NFC, Dynamic Island, Live Activities, 3D through Metal, and on-device inference with Core MLSEED — Rork raised a $15M seed led by Left Lane Capital, with Peak XV and a16z Speedrun joining the round
Articles/Dev Tools
Dev Tools/2026-05-26Advanced

Aggregating App Store Connect, RevenueCat, and AdMob into One Morning Digest with Cloudflare Workers — A Six-App Indie Architecture

A practical architecture for indie developers running multiple Rork apps: aggregate App Store Connect API, RevenueCat REST, and AdMob Reporting API in a Cloudflare Workers Cron job and ship a single daily Slack digest each morning.

Rork515Cloudflare Workers24App Store Connect API4RevenueCat29AdMob70indie developer37metricsarchitecture12

Premium Article

Before I'd even poured the coffee, I would open App Store Connect, then RevenueCat, then AdMob, then Firebase Console, then Crashlytics. Six tabs per app. For six apps, that's thirty-something tabs, a spreadsheet copy-paste session, and forty minutes gone. Some mornings the Crashlytics graph would pull my mood down; other mornings the RevenueCat MRR line would loosen my shoulders. Either way, by the time I had the numbers in my head I had also lost the freshest part of my day.

I have been shipping iOS and Android apps as a one-person developer since 2014. Cumulative downloads now exceed 50 million, mostly across wallpaper, healing, and manifestation-style image apps. My current portfolio of 5–7 active titles holds AdMob revenue over one million yen per month, but that number is held up by the unglamorous habit of looking at numbers every morning and deciding the day's tuning. When the numbers alone took 30–40 minutes, that habit was being squeezed at its narrowest point.

This article walks through the architecture I actually run in production today: an App Store Connect API + RevenueCat REST + AdMob Reporting API aggregator on Cloudflare Workers Cron Triggers, posting a single morning digest to Slack at 08:00 JST. The morning check is now under five minutes. The monthly Cloudflare bill sits at $0–$5, which is fair for a one-person operation.

What we're aggregating, and where the data comes from

Before any code, lay the sources side by side. Each API has its own auth, rate limit, and freshness, and ignoring this leads to swampy code later.

SourceMetricsAuthFreshnessRate limit
App Store Connect APIdownloads, revenue, IAP counts per appJWT (ES256)T-1 day200 req/min
RevenueCat REST v1MRR, retention, cancellationsBearer Tokennear real-time1,200 req/min
AdMob Reporting APIeCPM, impressions, revenue per appOAuth 2.0T-1 day750 req/min
Firebase Crashlytics (via BigQuery export)crash-free users, impacted usersService AccountT-1 day (requires export)BigQuery quotas

App Store Connect API and AdMob Reporting API finalize "yesterday" sometime around noon the next day. For an 08:00 run, you're safely reading the day before yesterday. RevenueCat allows same-day reads, but cancellations take up to two hours to reflect, so I anchor on the 23:59 JST snapshot of the previous day. Stable beats fresh here.

High-level architecture

The whole system runs on Cloudflare Workers. To keep the monthly cost at zero, the only state stores are Workers KV (for the previous-day snapshot used in diff calculations) and D1 (for the rolling 30-day history that powers weekly retro views).

┌────────────────────────────────────────────┐
│  Cloudflare Workers (Cron: 0 23 * * *)     │
│  ┌────────────────────────────────────┐    │
│  │  1. fetch App Store Connect API    │    │
│  │  2. fetch RevenueCat REST           │    │
│  │  3. fetch AdMob Reporting API       │    │
│  │  4. fetch Crashlytics (BigQuery)    │    │
│  │  5. normalize + diff vs prev day    │    │
│  │  6. detect anomalies (±20% / +0.5pt)│    │
│  │  7. post to Slack (Block Kit)       │    │
│  └────────────────────────────────────┘    │
│              ↓                ↓             │
│        Workers KV         D1 (history)      │
│   (last snapshot)    (last 30 days)         │
└────────────────────────────────────────────┘

Anything older than 30 days I defer to GA4's BigQuery export rather than carry inside Workers. As an indie, dragging long-horizon data into a hand-rolled store creates a quiet maintenance debt I do not want to own.

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
Full code for signing App Store Connect JWTs (ES256), pulling RevenueCat REST overview, and calling the AdMob Reporting API from a Cloudflare Workers Cron — including the gotchas with JWT aud, gzipped TSV, and AdMob streaming JSON
Real numbers: 30–40 minutes of morning dashboard hopping compressed to under 5 minutes across six apps, run on Workers + KV + D1 within a monthly cost of $0–$5
Anomaly detection thresholds (DL ±20%, revenue ±25%, crash-free-users dropping below 99.5%) routed into Slack Block Kit so only the abnormal lines demand attention
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-27
Making Silent Failures Visible Across 6 Rork Apps: An Early-Warning Design Note for Non-Crash Degradation
Notes from running 6 wallpaper apps in parallel and the layer I built in 3 weeks to make Crashlytics-invisible failures observable. Beacons, timeouts, and a small Cloudflare Worker for cross-app aggregation.
Dev Tools2026-06-28
Build Your Settings Screen From One Schema and Reuse It Across Apps
Hand-building a settings screen per app falls apart as your app count grows. Here is a schema-driven design that assembles the screen from declarative data and shares a common base across multiple apps, with working code.
Dev Tools2026-06-22
Serving Both Plain Rork and Rork Max From One Backend — Designing an API Response Contract That Never Breaks Old Binaries
When plain Rork (React Native / Expo) and Rork Max (native Swift) both call the same Cloudflare Workers backend, the whole design centers on not breaking old binaries you cannot force-update. Wrap responses in an envelope, evolve them additively, absorb client differences with capability flags, and retire old contracts safely — shown in code.
📚RECOMMENDED BOOKS
Build a Large Language Model (From Scratch)
Sebastian Raschka
LLM Dev
Prompt Engineering for LLMs
Berryman & Ziegler
Prompting
AI Engineering
Chip Huyen
AI Eng
* Contains affiliate links
See all →