How to Fix 'invalid-app-credential' Token Mismatch Error in Flutter Firebase Phone Authentication
Firebase Phone Authentication is a popular choice for Flutter developers to verify user identities via SMS, offering a seamless and secure login experience. However, integrating it can sometimes lead to frustrating errors, and one of the most common is the invalid-app-credential token mismatch error. This error occurs when Firebase fails to validate the app’s credentials during the authentication flow, preventing users from signing in.
If you’ve encountered this error, you’re not alone. It typically stems from misconfigurations in your app’s setup, Firebase project settings, or code-level issues. In this blog, we’ll break down the root causes of the invalid-app-credential error and provide a step-by-step guide to fix it, ensuring your Flutter app’s phone authentication works flawlessly.
Table of Contents#
- Understanding the 'invalid-app-credential' Error
- Common Causes of Token Mismatch
- Step-by-Step Fixes
- Advanced Troubleshooting
- Conclusion
- References
Understanding the 'invalid-app-credential' Error#
The invalid-app-credential error is thrown by Firebase when it cannot authenticate the app’s identity during the phone authentication flow. In simpler terms, Firebase does not recognize your app as a valid client, leading to a mismatch between the token it generates and the one your app provides.
Flow Context:#
Firebase Phone Authentication works as follows:
- Your app sends the user’s phone number to Firebase.
- Firebase sends an SMS OTP to the user’s device.
- The user enters the OTP, and your app sends this OTP along with a
verificationID(generated by Firebase) back to Firebase. - Firebase validates the
verificationID+ OTP combination and returns a user credential.
The invalid-app-credential error occurs at step 4, indicating Firebase rejects the app’s request due to untrusted or misconfigured credentials.
Common Causes of Token Mismatch#
Before diving into fixes, let’s identify the most likely culprits:
- Missing/Incorrect SHA-1/SHA-256 Certificates: Firebase uses these certificates to verify your app’s identity. Omitting them or using outdated ones causes validation failures.
- Outdated
google-services.json: This file contains critical Firebase project configuration. An old version may reference expired keys or incorrect project settings. - Misconfigured reCAPTCHA: Invisible reCAPTCHA (used to prevent abuse) may block the flow if domains/settings are misconfigured.
- Disabled Phone Auth in Firebase: Phone Authentication might not be enabled in your Firebase project.
- API Key Restrictions: Overly restrictive API key settings in Google Cloud Console can block Firebase Phone Auth requests.
- Code-Level Errors: Mishandling
verificationIDor OTP, such as using incorrect values or async/await issues.
Step-by-Step Fixes#
Let’s address each cause with actionable solutions.
3.1 Verify SHA-1/SHA-256 Certificates#
Firebase requires your app’s SHA-1 and SHA-256 certificates to link your app to the Firebase project. Both debug and release certificates must be added (especially if testing with a release build).
How to Generate and Add SHA Certificates:#
For Debug Builds (Android):#
- Locate your debug keystore (default path:
~/.android/debug.keystore). - Run this command in Terminal to get SHA-1 and SHA-256:
keytool -list -v -alias androiddebugkey -keystore ~/.android/debug.keystore- Default password:
android(if prompted).
- Default password:
For Release Builds (Android):#
Use your app’s release keystore:
keytool -list -v -alias <your-alias> -keystore <path-to-release-keystore> Add to Firebase:#
- Go to Firebase Console → Your Project → Project Settings (gear icon).
- Under Your apps, select your Android app.
- Scroll to SHA certificate fingerprints and click Add fingerprint.
- Paste the SHA-1 and SHA-256 values generated above.
3.2 Update google-services.json#
The google-services.json file (for Android) contains Firebase project credentials. An outdated file will cause mismatches.
Steps to Update:#
- In Firebase Console → Project Settings → Your Android app.
- Click Download google-services.json.
- Replace the existing file in your Flutter project at
android/app/google-services.json. - Critical: Ensure the file is not modified manually (e.g., avoid editing package names or API keys).
3.3 Check reCAPTCHA Configuration#
Firebase uses reCAPTCHA to prevent abuse. Misconfigurations here can block valid requests.
For Android Apps:#
- Firebase uses invisible reCAPTCHA by default for mobile. No extra setup is needed, but ensure:
- Your app’s
AndroidManifest.xmldoes not restrict network access (e.g.,android:usesCleartextTraffic="true"for debug builds). - You’re testing on a real device (emulators often fail reCAPTCHA checks).
- Your app’s
For Web/Desktop (Flutter Web):#
- Add your app’s domain (e.g.,
localhost,yourdomain.com) to Firebase’s Authorized domains (Project Settings → General → Authorized domains).
3.4 Validate Firebase Project Settings#
Ensure your Firebase project is correctly configured for Phone Auth:
-
Enable Phone Authentication:
Go to Firebase Console → Authentication → Sign-in method → Enable Phone. -
Check API Key Restrictions:
- Go to Google Cloud Console → Your Project → APIs & Services → Credentials.
- Select the API key used by Firebase (labeled "Android key" or "iOS key").
- Under Application restrictions, ensure "None" (for testing) or "Android apps" with your app’s package name + SHA-1 is selected.
- Under API restrictions, ensure "Firebase Phone Authentication API" is allowed.
3.5 Code-Level Verification#
Even with correct setup, code mistakes can cause token mismatches. Let’s verify your Flutter code.
Correct Implementation Example:#
import 'package:firebase_auth/firebase_auth.dart';
// Step 1: Send verification code
Future<void> sendOTP(String phoneNumber) async {
await FirebaseAuth.instance.verifyPhoneNumber(
phoneNumber: phoneNumber,
verificationCompleted: (PhoneAuthCredential credential) async {
// Auto-retrieved OTP (rare on real devices)
await FirebaseAuth.instance.signInWithCredential(credential);
},
verificationFailed: (FirebaseAuthException e) {
print("Verification failed: ${e.message}"); // Check for errors here
},
codeSent: (String verificationId, int? resendToken) {
// Store verificationId (e.g., in state management)
_verificationId = verificationId;
},
codeAutoRetrievalTimeout: (String verificationId) {},
);
}
// Step 2: Verify OTP and sign in
Future<void> verifyOTP(String smsCode) async {
try {
// Create credential with stored verificationId and user-entered SMS code
PhoneAuthCredential credential = PhoneAuthProvider.credential(
verificationId: _verificationId, // Ensure this is the SAME as from codeSent
smsCode: smsCode,
);
// Sign in
await FirebaseAuth.instance.signInWithCredential(credential);
} catch (e) {
print("Sign-in failed: $e"); // 'invalid-app-credential' may appear here
}
} Common Code Mistakes to Avoid:#
- Overwriting
verificationId: Ensure_verificationIdis not reset before the user enters the OTP (e.g., in stateful widgets, usesetStateor a state manager like Provider). - Incorrect SMS Code: Ensure the user enters the 6-digit code without spaces/hyphens.
- Async/Await Issues: Always use
awaitwhen callingsignInWithCredentialto avoid race conditions.
Advanced Troubleshooting#
If the above steps don’t resolve the error, try these:
1. Check Firebase Console Logs#
Go to Firebase Console → Authentication → Logs to see detailed error reports (e.g., "API key not found" or "SHA fingerprint missing").
2. Enable Verbose Logging#
Add this to your main.dart to debug Firebase Auth flows:
import 'package:firebase_core/firebase_core.dart';
void main() async {
WidgetsFlutterBinding.ensureInitialized();
await Firebase.initializeApp();
FirebaseAuth.instance.setSettings(appVerificationDisabledForTesting: false); // Disable only for testing
runApp(MyApp());
} 3. Test on a Real Device#
Emulators often have issues with Google Play Services or reCAPTCHA. Test on a physical Android/iOS device.
4. Check Google Play Services (Android)#
Ensure Google Play Services is up-to-date on the test device (Settings → Apps → Google Play Services → Check for updates).
Conclusion#
The invalid-app-credential error is typically caused by misconfigured app credentials or Firebase settings. By methodically verifying SHA certificates, updating google-services.json, checking reCAPTCHA, and validating your code, you can resolve the token mismatch.
Remember: Start with the basics (SHA certificates and google-services.json) before diving into code or advanced troubleshooting. Firebase’s validation is strict, so even small mismatches in app identity will trigger this error.