DEV Community

Cover image for Monitoring Android Staged Rollouts from the Terminal
Yasser's studio
Yasser's studio

Posted on

Monitoring Android Staged Rollouts from the Terminal

Staged rollouts are the safest way to ship an Android release. Push to 1% of users, check crash rates, bump to 5%, check again, then gradually ramp to 100%. Google Play has supported this for years.

The monitoring part, though? That's still manual for most teams. Open the Play Console, navigate to the vitals dashboard, eyeball the crash rate, compare it to last week, decide whether to proceed. Repeat every few hours across a multi-day rollout.

This article walks through automating that loop with a single terminal command.

The setup

You need:

  • GPC (Google Play Console CLI) v0.9.67+
  • A Google Play service account with access to the Reporting API

Install:

npm install -g @gpc-cli/cli

# or Homebrew
brew install yasserstudio/tap/gpc

# or standalone binary (no Node.js)
curl -fsSL https://raw.githubusercontent.com/yasserstudio/gpc/main/scripts/install.sh | sh
Enter fullscreen mode Exit fullscreen mode

Authenticate:

gpc auth login --service-account path/to/key.json
gpc doctor  # verify everything works
Enter fullscreen mode Exit fullscreen mode

Basic monitoring

After pushing a release to production, start watching:

gpc watch
Enter fullscreen mode Exit fullscreen mode

That's it. GPC polls the Google Play API every 15 minutes by default, fetching two things:

  1. Rollout status (near real-time): version code, user fraction, track, release status
  2. Vitals data (24-48h delayed): crash rate and ANR rate averaged over 7 days

Each round prints the current state:

[14:30:02] Round 1
  Rollout: v142 at 10% (inProgress)
  crashes: 1.2% (threshold: 2.0%) OK
  anr: 0.3% (threshold: 1.0%) OK

[14:45:01] Round 2
  Rollout: v142 at 10% (inProgress)
  crashes: 1.3% (threshold: 2.0%) OK
  anr: 0.4% (threshold: 1.0%) OK
Enter fullscreen mode Exit fullscreen mode

The loop stops automatically when the rollout reaches 100%, or you press Ctrl+C.

Configuring thresholds

Default thresholds are:

Metric Default
Crash rate 2%
ANR rate 1%
LMK rate 3%
Slow start 5%
Slow render 10%

Override any of them from the command line:

gpc watch --crash-threshold 0.015 --anr-threshold 0.005
Enter fullscreen mode Exit fullscreen mode

Or set them once in .gpcrc.json so they apply to every gpc watch and gpc vitals call:

{
  "vitals": {
    "thresholds": {
      "crashRate": 0.015,
      "anrRate": 0.005,
      "lmkRate": 0.03
    }
  }
}
Enter fullscreen mode Exit fullscreen mode

Priority: CLI flags beat config, config beats defaults.

Watching more metrics

By default, gpc watch monitors crashes and ANR. Add more:

gpc watch --metrics crashes,anr,lmk,slowStarts,slowRender
Enter fullscreen mode Exit fullscreen mode

Six metrics are available: crashes, anr, lmk, slowStarts, slowRender, errorCount.

Auto-halt on breach

This is where it gets useful. Instead of watching numbers scroll by, tell GPC to halt the rollout automatically if a threshold breaches:

gpc watch --on-breach halt
Enter fullscreen mode Exit fullscreen mode

If the crash rate crosses 2%, GPC calls the Google Play API to halt the release. No human in the loop. The watch session logs it and exits.

You can combine actions:

gpc watch --on-breach notify,halt
Enter fullscreen mode Exit fullscreen mode

This sends an OS notification AND halts the rollout.

Webhook integration

For teams using Slack, PagerDuty, or any webhook-based alerting:

gpc watch --on-breach webhook --webhook-url https://hooks.slack.com/services/XXX
Enter fullscreen mode Exit fullscreen mode

GPC POSTs a JSON payload on breach:

{
  "type": "breach",
  "round": 3,
  "timestamp": "2026-04-25T14:45:00.000Z",
  "rollout": {
    "track": "production",
    "versionCode": "142",
    "userFraction": 0.1,
    "status": "inProgress"
  },
  "vitals": {
    "crashes": { "value": 0.025, "threshold": 0.02, "breached": true },
    "anr": { "value": 0.005, "threshold": 0.01, "breached": false }
  },
  "breaches": ["crashes"],
  "halted": true
}
Enter fullscreen mode Exit fullscreen mode

Combine all three for maximum coverage:

gpc watch --on-breach notify,halt,webhook --webhook-url https://hooks.slack.com/services/XXX
Enter fullscreen mode Exit fullscreen mode

Set the webhook URL in config to avoid passing it every time:

{
  "webhooks": {
    "watch": "https://hooks.slack.com/services/XXX"
  }
}
Enter fullscreen mode Exit fullscreen mode

CI/CD integration

For automated pipelines, run a fixed number of rounds with JSON output:

gpc watch --rounds 3 --interval 300 --json
Enter fullscreen mode Exit fullscreen mode

This outputs NDJSON (one JSON object per round), runs 3 polling cycles at 5-minute intervals, and exits with code 6 if any threshold was breached. Code 0 means clean.

In a GitHub Actions workflow:

- name: Monitor rollout vitals
  run: gpc watch --rounds 3 --interval 300 --on-breach halt --json
  env:
    GPC_SERVICE_ACCOUNT: ${{ secrets.GPC_SERVICE_ACCOUNT }}
    GPC_APP: com.example.app
Enter fullscreen mode Exit fullscreen mode

Watching a specific track

Monitor a beta rollout instead of production:

gpc watch --track beta --crash-threshold 0.015
Enter fullscreen mode Exit fullscreen mode

Beta rollouts often warrant tighter thresholds since you want to catch problems before they reach production users.

A note on data freshness

Google Play vitals data lags 24-48 hours behind real-time. Rollout status (version code, user fraction, track) is near real-time.

This means gpc watch is most useful for multi-day staged rollouts, which is exactly when you need it. You push to 1% on Monday, vitals data for that cohort is available by Wednesday, and you decide whether to ramp to 10%.

For the first few hours after a release, rollout status is the primary signal. Vitals data fills in as it becomes available.

Putting it together

A typical staged rollout workflow:

# Upload and release to 1%
gpc releases upload app.aab --track production
gpc releases rollout --fraction 0.01

# Watch with auto-halt and Slack alerts
gpc watch --on-breach notify,halt,webhook \
  --webhook-url https://hooks.slack.com/services/XXX

# If vitals look good after 24-48h, bump to 10%
gpc releases rollout --fraction 0.10

# Watch again
gpc watch --on-breach notify,halt

# Ramp to 100%
gpc releases rollout --fraction 1.0
Enter fullscreen mode Exit fullscreen mode

Or automate the entire flow with gpc train, which chains staged rollout steps with time gates and vitals gates.


Free to use. Code is on GitHub.

Top comments (0)