SMS authentication on android NullPointerException

I'm getting this error

Updated error:

E/AndroidRuntime: FATAL EXCEPTION: main
                  Process: xxx.com.xxx, PID: 4963
                  java.lang.NullPointerException: Attempt to invoke virtual method 'com.google.android.gms.tasks.Task
com.google.android.gms.common.api.GoogleApi.zzb(com.google.android.gms.common.api.internal.zzdf)'
on a null object reference
                      at com.google.android.gms.internal.zzdtp.zzb(Unknown Source)
                      at com.google.android.gms.internal.zzdtw.zza(Unknown Source)
                      at com.google.firebase.auth.FirebaseAuth.zza(Unknown Source)
                      at com.google.firebase.auth.PhoneAuthProvider.zza(Unknown Source)
                      at com.google.firebase.auth.PhoneAuthProvider.verifyPhoneNumber(Unknown
Source)
                      at xxx.com.xxx.PhoneNumberActivity.onClick(PhoneNumberActivity.java:110)
                      at android.view.View.performClick(View.java:5265)
                      at android.view.View$PerformClick.run(View.java:21534)
                      at android.os.Handler.handleCallback(Handler.java:815)
                      at android.os.Handler.dispatchMessage(Handler.java:104)
                      at android.os.Looper.loop(Looper.java:207)
                      at android.app.ActivityThread.main(ActivityThread.java:5728)
                      at java.lang.reflect.Method.invoke(Native Method)
                      at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:789)
                      at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:679)

When I try to run this code

PhoneAuthProvider.getInstance().verifyPhoneNumber(
            phoneNumber,        // Phone number to verify
            60,                 // Timeout duration
            TimeUnit.SECONDS,   // Unit of timeout
            this,               // Activity (for callback binding)
            mCallbacks);        // OnVerificationStateChangedCallbacks

In app build.gradle

implementation 'com.google.firebase:firebase-database:11.6.0'
implementation 'com.google.firebase:firebase-auth:11.6.0'

Why is it saying it's null? What is null? I'm running it on android device Android version 6.0. Is it because there's no sim card on the phone? I've already enabled phone authentication in the console and it's working on iOS.

Updates:

After Updating the version of firebase-core and firebasse-auth, the app doesn't crash any more.

implementation 'com.google.firebase:firebase-core:16.0.5'
implementation 'com.google.firebase:firebase-auth:16.0.5'

Found out it's caused by version 8.3.01 (2385995-434) Google Play services of the phone I'm testing on. Any solution to make it work with 8.3.01?

Error:

" W/GooglePlayServicesUtil: Google Play services out of date. Requires 12451000 but found 8301434"

Question:

How to control the min Google Play services version?


You can have a look at this working code.

build.gradle(app-level)

dependencies {
    implementation 'com.google.firebase:firebase-core:16.0.5'
    implementation 'com.google.firebase:firebase-auth:16.0.5'
}

build.gradle(project-level)

buildscript {
    dependencies {
        classpath 'com.google.gms:google-services:4.1.0'
    }
}

Activity:

import android.content.DialogInterface;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v7.app.AlertDialog;
import android.support.v7.app.AppCompatActivity;
import android.view.View;
import android.widget.EditText;
import android.widget.Toast;
import com.google.android.gms.tasks.OnCompleteListener;
import com.google.android.gms.tasks.Task;
import com.google.firebase.FirebaseException;
import com.google.firebase.FirebaseTooManyRequestsException;
import com.google.firebase.auth.AuthResult;
import com.google.firebase.auth.FirebaseAuth;
import com.google.firebase.auth.FirebaseAuthInvalidCredentialsException;
import com.google.firebase.auth.FirebaseUser;
import com.google.firebase.auth.PhoneAuthCredential;
import com.google.firebase.auth.PhoneAuthProvider;
import java.util.concurrent.TimeUnit;

public class FCMsmsTest extends AppCompatActivity {

    private EditText editText;
    private String mVerificationId = "";
    PhoneAuthProvider.OnVerificationStateChangedCallbacks mCallbacks = new PhoneAuthProvider.OnVerificationStateChangedCallbacks() {

        @Override
        public void onVerificationCompleted(PhoneAuthCredential phoneAuthCredential) {
            Toast.makeText(FCMsmsTest.this, "onVerificationCompleted " + phoneAuthCredential.toString(), Toast.LENGTH_SHORT).show();
            signInWithPhoneAuthCredential(phoneAuthCredential);
        }

        @Override
        public void onVerificationFailed(FirebaseException e) {
            Toast.makeText(FCMsmsTest.this, "onVerificationFailed " + e.toString(), Toast.LENGTH_SHORT).show();

            if (e instanceof FirebaseAuthInvalidCredentialsException) {
                Toast.makeText(FCMsmsTest.this, "Invalid Request " + e.toString(), Toast.LENGTH_SHORT).show();
            } else if (e instanceof FirebaseTooManyRequestsException) {
                Toast.makeText(FCMsmsTest.this, "The SMS quota for the project has been exceeded " + e.toString(), Toast.LENGTH_SHORT).show();
            }
        }

        @Override
        public void onCodeSent(String verificationId,
                               PhoneAuthProvider.ForceResendingToken token) {
            Toast.makeText(FCMsmsTest.this, "onCodeSent " + verificationId, Toast.LENGTH_SHORT).show();
            editText.setText("");

            mVerificationId = verificationId;
            PhoneAuthProvider.ForceResendingToken mResendToken = token;

            showDialog();

        }

    };

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_fcm_sms_test);

        editText = findViewById(R.id.edit_text);
        findViewById(R.id.btn_send_sms).setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                if (editText.getText().toString().trim().length() > 9) {
                    sendSMS("+91" + editText.getText().toString().trim());
                } else {
                    Toast.makeText(FCMsmsTest.this, "Enter Valid PhoneNumber", Toast.LENGTH_SHORT).show();
                }

            }
        });
    }

    private void sendSMS(String phoneNumber) {
        PhoneAuthProvider.getInstance().verifyPhoneNumber(
                phoneNumber,        // Phone number to verify
                60,                 // Timeout duration
                TimeUnit.SECONDS,   // Unit of timeout
                this,               // Activity (for callback binding)
                mCallbacks);
    }

    private void signInWithPhoneAuthCredential(PhoneAuthCredential credential) {
        FirebaseAuth mAuth = FirebaseAuth.getInstance();
        mAuth.signInWithCredential(credential)
                .addOnCompleteListener(this, new OnCompleteListener<AuthResult>() {
                    @Override
                    public void onComplete(@NonNull Task<AuthResult> task) {
                        if (task.isSuccessful()) {
                            Toast.makeText(FCMsmsTest.this, "signInWithCredential:success", Toast.LENGTH_SHORT).show();
                            FirebaseUser user = task.getResult().getUser();
                        } else {
                            Toast.makeText(FCMsmsTest.this, "signInWithCredential:failure", Toast.LENGTH_SHORT).show();
                            if (task.getException() instanceof FirebaseAuthInvalidCredentialsException) {
                                Toast.makeText(FCMsmsTest.this, "The verification code entered was invalid", Toast.LENGTH_SHORT).show();
                            }
                        }
                    }
                });
    }

    private void showDialog() {
        AlertDialog.Builder alert = new AlertDialog.Builder(this);
        final EditText edittextCode = new EditText(FCMsmsTest.this);
        alert.setMessage("Enter Your Message");
        alert.setTitle("Enter Your Title");

        alert.setView(edittextCode);

        alert.setPositiveButton("Yes", new DialogInterface.OnClickListener() {
            public void onClick(DialogInterface dialog, int whichButton) {
                String YouEditTextValueString = edittextCode.getText().toString();

                PhoneAuthCredential credential = PhoneAuthProvider.getCredential(mVerificationId, YouEditTextValueString);
                signInWithPhoneAuthCredential(credential);

            }
        });
        alert.show();
    }
}

xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:gravity="center"
    android:orientation="vertical"
    android:padding="50dp">

    <TableRow
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:gravity="center">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="+91" />

        <EditText
            android:id="@+id/edit_text"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:inputType="phone" />
    </TableRow>

    <Button
        android:id="@+id/btn_send_sms"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="50dp"
        android:text="Send OTP" />

</LinearLayout>

Update your project accordingly.