---
name: intercom-android-push-credential-invalid
description: |
  Fix the Intercom dashboard error "Your push credential appears invalid. Please
  update and try again." when configuring Android push notifications. Use when:
  (1) you uploaded a JSON file to Intercom's "Service Account private key" field
  in the Android push setup dialog and got the invalid-credential error,
  (2) the dialog now shows `google-services.json` as the current file but
  Intercom still rejects it, (3) you're confused which Firebase JSON Intercom
  wants — Firebase has two superficially similar JSONs and most setup docs don't
  emphasize the difference, (4) you're setting up Intercom push for Android in
  Flutter, native Android, or React Native (same dashboard, same dialog, same
  trap). Root cause: `google-services.json` is the Firebase CLIENT config
  (project ID, app ID, public API key — embedded in the app, safe to commit).
  Intercom needs the Firebase SERVER credential: a service account JSON
  downloaded from Firebase Console → Project Settings → Service accounts tab →
  "Generate new private key". The two files come from the same console, both
  end in .json, both relate to FCM — but only the second one contains the
  private key Intercom needs to sign FCM API requests on your behalf. Intercom's
  error message doesn't hint at the file-type mismatch and the dialog accepts
  the wrong file at upload time without pre-validating.
author: Claude Code
version: 1.0.0
date: 2026-05-14
---

# Intercom Android Push: "credential appears invalid" Means Wrong Firebase JSON

## Problem

You're configuring Intercom Android push notifications. The "Setup push
notifications" dialog asks for a "Service Account private key" via an
"Upload JSON file" button. You upload your `google-services.json` (the
Firebase JSON you already have on hand in `android/app/`) and Intercom flashes:

> Your push credential appears invalid. Please update and try again.

The dialog now shows `google-services.json` as the "current" file (with a
"Change file" link) but the error persists no matter how many times you save.

## Trigger Conditions

- You're in **Intercom dashboard → Settings → Installation → Android → Setup push notifications**
- You uploaded a JSON file from Firebase to the "Service Account private key" field
- The error reads exactly: "Your push credential appears invalid. Please update and try again."
- The filename shown in the dialog is `google-services.json` or any JSON that
  has a `client[].api_key[].current_key` block but no `private_key` field

## Solution

Intercom doesn't want `google-services.json` (the client config). It wants a
**Firebase service account JSON** (the server credential). They come from
different tabs of the same Firebase Console.

### Steps to get the right file

1. Go to https://console.firebase.google.com/
2. Select the right Firebase project (the same one your app uses)
3. Click the **⚙ gear icon** at the top of the left sidebar → **Project settings**
4. Click the **Service accounts** tab (NOT the "General" tab where
   `google-services.json` is downloaded from)
5. Make sure **Firebase Admin SDK** is selected on the left
6. Scroll down and click **Generate new private key**
7. Confirm in the modal warning
8. A `.json` file downloads — name pattern is
   `<projectId>-firebase-adminsdk-<random>-<random>.json`
9. Back in Intercom's dialog, click **Change file** and upload this file
10. Click Save — the "credential appears invalid" error clears

### Steps to verify you have the right file

Open the JSON in a text editor. The right file looks like:

```json
{
  "type": "service_account",
  "project_id": "your-project-id",
  "private_key_id": "abc123...",
  "private_key": "-----BEGIN PRIVATE KEY-----\nMIIE...\n-----END PRIVATE KEY-----\n",
  "client_email": "firebase-adminsdk-xxx@your-project.iam.gserviceaccount.com",
  ...
}
```

Top-level `"type": "service_account"` and a `"private_key"` field are the
tells.

The WRONG file (`google-services.json`) looks like:

```json
{
  "project_info": {...},
  "client": [
    {
      "client_info": {...},
      "api_key": [{"current_key": "AIzaSy..."}],
      ...
    }
  ]
}
```

Note: `client[].api_key[].current_key` (a public API key, not a private key)
and no `"type": "service_account"` field.

## Security

The service account JSON is a **real secret**. Anyone with it can send
arbitrary pushes to your users and read FCM admin data. After uploading to
Intercom:

- **Do NOT commit it** to your repo (add the filename pattern to `.gitignore`
  if you keep it locally)
- **Do NOT paste it** into chat threads or share with screenshots visible
- Once Intercom has it, you can delete the local copy — Intercom will re-prompt
  if it ever needs it again, at which point you can regenerate from Firebase
- If it leaks, immediately revoke from Firebase Console → IAM → find the
  service account → disable or rotate the key

`google-services.json`, by contrast, is safe to commit — its API key is
locked to your app's package name and SHA-1 fingerprint by Firebase, so
exposing it doesn't grant attackers anything useful.

## Why This Is Sneaky

- Both files come from `console.firebase.google.com`
- Both are JSON
- Both relate to FCM (one for receiving, one for sending)
- File names overlap thematically — "google-services" vs "firebase-adminsdk"
- Intercom's UI label "Service Account private key" is technically correct
  but if you arrive at the dialog with `google-services.json` already in your
  Downloads folder (because Flutter/Android setup docs told you to download
  it), you reach for the wrong one
- Intercom **accepts** the upload at the UI layer without validating it as
  a service account JSON, then rejects it server-side with a generic error
- The error message gives no hint about the file-type mismatch

This trap exists for anyone integrating Intercom on Android — Flutter, native,
React Native — because they all use the same Intercom dashboard.

## Notes for Flutter / RN / native setups

- The presence of `google-services.json` in `android/app/` is necessary for
  the app to RECEIVE pushes (it's the FCM client config). Don't remove it.
- The service account JSON is **only** uploaded to Intercom — it does NOT
  go into your app bundle.
- You do NOT need to upload the service account JSON to Firebase or
  anywhere else. Generating it from Firebase Console is sufficient — Firebase
  remembers that key was issued, and Intercom uses it to authenticate to
  Firebase as your project.
- Same Firebase project can mint multiple service account keys (e.g., one
  for Intercom, one for your own backend if it also sends FCM pushes).

## Related

After fixing this and saving, Android push delivery still requires:

1. The app to forward an FCM token to Intercom via
   `Intercom.sendTokenToIntercom(token)` — this happens automatically in
   `intercom_flutter` if you call it after `loginIdentifiedUser`
2. A user to be logged in to Intercom in the app (identified, not anonymous)
3. The user to have granted Android 13+ POST_NOTIFICATIONS permission
4. A fresh app launch after any native Android changes (gradle / Application
   class) — hot reload doesn't pick those up

If pushes still don't arrive after the credential is fixed, check those.

## References

- Firebase Service Accounts docs: https://firebase.google.com/docs/admin/setup
- Intercom Android push setup (official): https://www.intercom.com/help/en/articles/3414-set-up-android-push-notifications
- The migration from legacy server keys to service accounts happened in
  mid-2024 when Google deprecated the FCM legacy HTTP API. Older Intercom
  setup tutorials may still say "server key" — that path is now closed.
