Android Phone Number Verification in Firebase - java

I'm trying to create a login screen which will use Phone Number Authentication in Firebase. I wrote a code;
package com.example.logindeneme;
import android.app.ProgressDialog;
import android.content.Intent;
import android.support.annotation.NonNull;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.text.TextUtils;
import android.view.View;
import android.widget.Button;
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.auth.AuthResult;
import com.google.firebase.auth.FirebaseAuth;
import com.google.firebase.auth.PhoneAuthCredential;
import com.google.firebase.auth.PhoneAuthProvider;
import java.util.concurrent.TimeUnit;
public class PhoneLoginActivity extends AppCompatActivity {
private Button SendVerificationButton, VerifyButton;
private EditText InputPhoneNumber, InputVerificationCode;
private PhoneAuthProvider.OnVerificationStateChangedCallbacks callbacks;
private FirebaseAuth mAuth;
private ProgressDialog loadingBar;
private String mVerificationId;
private PhoneAuthProvider.ForceResendingToken mResendToken;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_phone_login);
mAuth = FirebaseAuth.getInstance();;
SendVerificationButton = (Button) findViewById(R.id.send_ver_code_button);
VerifyButton = (Button)findViewById(R.id.verify_button);
InputPhoneNumber = (EditText) findViewById(R.id.phone_number_input);
InputVerificationCode = (EditText) findViewById(R.id.verification_code_input);
loadingBar = new ProgressDialog(this);
SendVerificationButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String phoneNumber = InputPhoneNumber.getText().toString();
if(TextUtils.isEmpty(phoneNumber)){
Toast.makeText(PhoneLoginActivity.this, "Please enter your phone number first...", Toast.LENGTH_SHORT).show();
}
else{
loadingBar.setTitle("Phone Verification");
loadingBar.setMessage("please wait, while we are authenticating your phone...");
loadingBar.setCanceledOnTouchOutside(false);
loadingBar.show();
PhoneAuthProvider.getInstance().verifyPhoneNumber(
phoneNumber, // Phone number to verify
60, // Timeout duration
TimeUnit.SECONDS, // Unit of timeout
PhoneLoginActivity.this, // Activity (for callback binding)
callbacks); // OnVerificationStateChangedCallbacks
}
}
});
VerifyButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
SendVerificationButton.setVisibility(View.INVISIBLE);
InputPhoneNumber.setVisibility(View.INVISIBLE);
String verificationCode = InputVerificationCode.getText().toString();
if(TextUtils.isEmpty(verificationCode)){
Toast.makeText(PhoneLoginActivity.this, "Please write verification code first...", Toast.LENGTH_SHORT).show();
}
else{
loadingBar.setTitle("Verification Code");
loadingBar.setMessage("please wait, while we are verifying verification code...");
loadingBar.setCanceledOnTouchOutside(false);
loadingBar.show();
PhoneAuthCredential credential = PhoneAuthProvider.getCredential(mVerificationId, verificationCode);
signInWithPhoneAuthCredential(credential);
}
}
});
callbacks = new PhoneAuthProvider.OnVerificationStateChangedCallbacks() {
#Override
public void onVerificationCompleted(PhoneAuthCredential phoneAuthCredential) {
signInWithPhoneAuthCredential(phoneAuthCredential);
}
#Override
public void onVerificationFailed(FirebaseException e) {
loadingBar.dismiss();
Toast.makeText(PhoneLoginActivity.this, "Invalid Phone Number, Please enter correct phone number with your country code...", Toast.LENGTH_SHORT).show();
SendVerificationButton.setVisibility(View.VISIBLE);
InputPhoneNumber.setVisibility(View.VISIBLE);
VerifyButton.setVisibility(View.INVISIBLE);
InputVerificationCode.setVisibility(View.INVISIBLE);
}
public void onCodeSent(String verificationId,
PhoneAuthProvider.ForceResendingToken token) {
// Save verification ID and resending token so we can use them later
mVerificationId = verificationId;
mResendToken = token;
loadingBar.dismiss();
Toast.makeText(PhoneLoginActivity.this, "Code has been sent, please check and verify.", Toast.LENGTH_SHORT).show();
SendVerificationButton.setVisibility(View.INVISIBLE);
InputPhoneNumber.setVisibility(View.INVISIBLE);
VerifyButton.setVisibility(View.VISIBLE);
InputVerificationCode.setVisibility(View.VISIBLE);
}
};
}
private void signInWithPhoneAuthCredential(PhoneAuthCredential credential) {
mAuth.signInWithCredential(credential)
.addOnCompleteListener(this, new OnCompleteListener<AuthResult>() {
#Override
public void onComplete(#NonNull Task<AuthResult> task) {
if (task.isSuccessful()) {
loadingBar.dismiss();
Toast.makeText(PhoneLoginActivity.this, "Congratulations, you're logged in successfully...", Toast.LENGTH_SHORT).show();
SendUserToMainActivity();
}
else {
String message = task.getException().toString();
Toast.makeText(PhoneLoginActivity.this, "Error: " + message, Toast.LENGTH_SHORT).show();
}
}
});
}
private void SendUserToMainActivity() {
Intent mainIntent = new Intent(PhoneLoginActivity.this,MainActivity.class);
startActivity(mainIntent);
finish();
}
}
But when I try to enter my phone number and want a code, always says "Invalid phone number". However, if I enter my number and random verify code in Test Phone Numbers in Firebase, and if I enter in my app; it works.
My country uses "+90" phone code. So I tried +9053XXXXXXXX, +90 53X XXX XX XX, +90-53X-XXX-XX-XX and etc. but never works.
Where is my fault? Can you fix it ?

#Wicaledon
Go to your firebase console.
In Settings, enter your add your SHA-1 key.
This will definitely work.
To get SHA-1 key
https://developers.google.com/android/guides/client-auth

Related

Why does Firebase Auth work on emulator but not on real device

I have an app where the user can login using their mobile number. I used Firebase Auth for this. It works like a charm on the emulator.It runs fast and the app works well. But, when I try that on my Samsung M30s, it does not login. This is my code:
package com.sk.telegram.Activities.Login;
import static android.view.View.GONE;
import static android.view.View.VISIBLE;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import android.app.Dialog;
import android.app.ProgressDialog;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.Toast;
import com.google.android.gms.tasks.OnCompleteListener;
import com.google.android.gms.tasks.Task;
import com.google.firebase.FirebaseApp;
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.PhoneAuthOptions;
import com.google.firebase.auth.PhoneAuthProvider;
import com.google.firebase.firestore.FirebaseFirestore;
import com.sambhav2358.tinydb.TinyDB;
import com.sambhav2358.tinydb.TinyDBManager;
import com.sk.telegram.Activities.MainActivity;
import com.sk.telegram.Models.User;
import com.sk.telegram.Utils.KeyUtils;
import com.sk.telegram.Utils.PreferenceManager;
import com.sk.telegram.Utils.TextUtils;
import com.sk.telegram.databinding.ActivityLoginBinding;
import java.util.Random;
import java.util.concurrent.TimeUnit;
public class LoginActivity extends AppCompatActivity {
ActivityLoginBinding binding;
FirebaseAuth mAuth;
String mVerificationId;
PhoneAuthProvider.ForceResendingToken mResendToken;
PhoneAuthProvider.OnVerificationStateChangedCallbacks mCallbacks;
private String TAG = "LoginActivity";
boolean isLoggedIn = false;
Dialog dialog;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
binding = ActivityLoginBinding.inflate(getLayoutInflater());
FirebaseApp.initializeApp(this);
setContentView(binding.getRoot());
init();
binding.btnNext.setOnClickListener(v -> {
if (!isLoggedIn) {
isLoggedIn = true;
dialog = ProgressDialog.show(this,"","Please wait...");
startPhoneNumberVerification(getPhoneNumber());
}else {
dialog = ProgressDialog.show(this,"","Please wait...");
verifyPhoneNumberWithCode(mVerificationId,binding.otp.getText().toString());
}
});
}
private void init(){
binding.countryCodePicker.setAutoDetectedCountry(true);
// [START initialize_auth]
// Initialize Firebase Auth
mAuth = FirebaseAuth.getInstance();
// [END initialize_auth]
// Initialize phone auth callbacks
// [START phone_auth_callbacks]
mCallbacks = new PhoneAuthProvider.OnVerificationStateChangedCallbacks() {
#Override
public void onVerificationCompleted(PhoneAuthCredential credential) {
// This callback will be invoked in two situations:
// 1 - Instant verification. In some cases the phone number can be instantly
// verified without needing to send or enter a verification code.
// 2 - Auto-retrieval. On some devices Google Play services can automatically
// detect the incoming verification SMS and perform verification without
// user action.
Log.d(TAG, "onVerificationCompleted:" + credential);
signInWithPhoneAuthCredential(credential);
Toast.makeText(LoginActivity.this, "verified", Toast.LENGTH_SHORT).show();
}
#Override
public void onVerificationFailed(FirebaseException e) {
// This callback is invoked in an invalid request for verification is made,
// for instance if the the phone number format is not valid.
Log.w(TAG, "onVerificationFailed", e);
dialog.dismiss();
Toast.makeText(LoginActivity.this, "There was and error.", Toast.LENGTH_SHORT).show();
if (e instanceof FirebaseAuthInvalidCredentialsException) {
// Invalid request
} else if (e instanceof FirebaseTooManyRequestsException) {
// The SMS quota for the project has been exceeded
}
// Show a message and update the UI
}
#Override
public void onCodeSent(#NonNull String verificationId,
#NonNull PhoneAuthProvider.ForceResendingToken token) {
// The SMS verification code has been sent to the provided phone number, we
// now need to ask the user to enter the code and then construct a credential
// by combining the code with a verification ID.
Log.d("LoginActivity", "onCodeSent:" + verificationId);
//dismiss the dialog and update the UI
dialog.dismiss();
binding.phoneAuthLayout.setVisibility(GONE);
binding.otpLayout.setVisibility(VISIBLE);
// Save verification ID and resending token so we can use them later
mVerificationId = verificationId;
mResendToken = token;
}
};
// [END phone_auth_callbacks]
}
#Override
public void onStart() {
super.onStart();
}
private void startPhoneNumberVerification(String phoneNumber) {
// [START start_phone_auth]
PhoneAuthOptions options =
PhoneAuthOptions.newBuilder(mAuth)
.setPhoneNumber(phoneNumber) // Phone number to verify
.setTimeout(60L, TimeUnit.SECONDS) // Timeout and unit
.setActivity(this) // Activity (for callback binding)
.setCallbacks(mCallbacks) // OnVerificationStateChangedCallbacks
.build();
PhoneAuthProvider.verifyPhoneNumber(options);
// [END start_phone_auth]
}
private void verifyPhoneNumberWithCode(String verificationId, String code) {
// [START verify_with_code]
PhoneAuthCredential credential = PhoneAuthProvider.getCredential(verificationId, code);
signInWithPhoneAuthCredential(credential);
// [END verify_with_code]
}
private void resendVerificationCode(String phoneNumber,
PhoneAuthProvider.ForceResendingToken token) {
PhoneAuthOptions options =
PhoneAuthOptions.newBuilder(mAuth)
.setPhoneNumber(phoneNumber) // Phone number to verify
.setTimeout(60L, TimeUnit.SECONDS) // Timeout and unit
.setActivity(this) // Activity (for callback binding)
.setCallbacks(mCallbacks) // OnVerificationStateChangedCallbacks
.setForceResendingToken(token) // ForceResendingToken from callbacks
.build();
PhoneAuthProvider.verifyPhoneNumber(options);
}
private void signInWithPhoneAuthCredential(PhoneAuthCredential credential) {
mAuth.signInWithCredential(credential)
.addOnCompleteListener(this, new OnCompleteListener<AuthResult>() {
#Override
public void onComplete(#NonNull Task<AuthResult> task) {
if (task.isSuccessful()) {
// Sign in success, update UI with the signed-in user's information
Log.d(TAG, "signInWithCredential:success");
FirebaseUser user = task.getResult().getUser();
User mUser = new User("User" + new Random().nextInt(999999),task.getResult().getUser().getUid(),task.getResult().getUser().getPhoneNumber());
if (user != null){
FirebaseFirestore.getInstance().collection(KeyUtils.KEY_COLLECTION_USERS)
.document(task.getResult().getUser().getUid())
.set(mUser);
TinyDBManager tinyDB = TinyDB.getInstance(LoginActivity.this);
tinyDB.put("current_user",mUser);
new PreferenceManager(getApplicationContext()).putString("uid",mUser.getUserId());
startActivity(new Intent(LoginActivity.this, MainActivity.class));
finish();
}
} else {
// Sign in failed, display a message and update the UI
Log.w(TAG, "signInWithCredential:failure", task.getException());
if (task.getException() instanceof FirebaseAuthInvalidCredentialsException) {
// The verification code entered was invalid
Toast.makeText(LoginActivity.this, "Something went wrong!", Toast.LENGTH_SHORT).show();
}
}
}
});
}
private String getPhoneNumber(){
return binding.countryCodePicker.getSelectedCountryCodeWithPlus() + " " + binding.number.getText().toString();
}
}
I also tried using test phone numbers but that doesn't work either

Android Java - How do I generate and verify OTP only when user mobile number is already in Firebase Realtime Database

I am making a project for which the login should be done only when the user data is already in the Firebase Realtime Database, no new users are to be registered, I only have to work with pre-existing users. My current code generates and verifies OTP regardless of whether the user mobile number is already present or not. So how do I modify to serve my purpose?
Here is my code:
package com.lalbhaibrokers.lalbhaibrokerspvtltd;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
import com.google.android.gms.tasks.OnCompleteListener;
import com.google.android.gms.tasks.Task;
import com.google.android.gms.tasks.TaskExecutors;
import com.google.android.material.textfield.TextInputEditText;
import com.google.firebase.FirebaseException;
import com.google.firebase.auth.AuthResult;
import com.google.firebase.auth.FirebaseAuth;
import com.google.firebase.auth.PhoneAuthCredential;
import com.google.firebase.auth.PhoneAuthProvider;
import com.google.firebase.database.DatabaseReference;
import com.google.firebase.database.FirebaseDatabase;
import java.util.concurrent.TimeUnit;
public class LoginActivity extends AppCompatActivity {
//Variables
TextInputEditText mobileNumber, otp;
TextView forgotPassword, errorMessage, sendOtp, verifyOtpAndLogin;
Context context = this;
String verificationCode;
boolean isVerified;
FirebaseDatabase database;
DatabaseReference reference;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_login);
//Hooks
mobileNumber = (TextInputEditText) findViewById(R.id.mobile_no_editText);
otp = (TextInputEditText) findViewById(R.id.otp_editText);
errorMessage = (TextView) findViewById(R.id.error_message_textView);
sendOtp = (TextView) findViewById(R.id.send_otp_btn);
verifyOtpAndLogin = (TextView) findViewById(R.id.verify_otp_and_login);
verifyOtpAndLogin.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String userCode = otp.getText().toString();
if (!userCode.isEmpty()) {
verifyCode(userCode); //verifying the code Entered by user
}
}
});
}
//method for start the OTP process
public void sendOtp(View view){
if(mobileNumber.getText().toString().equals("")){
errorMessage.setText("Please Enter phone number");
errorMessage.setVisibility(View.VISIBLE);
}else if(mobileNumber.getText().toString().length() != 10){
errorMessage.setText("PhoneNumber is Invalid"); //we can only accept phoneNumbers with 10 digits
errorMessage.setVisibility(View.VISIBLE);
}else{
String phoneNum= "+91"+mobileNumber.getText().toString(); //we have to add country code in order to receive OTP
//method that will send the OTP to given number
PhoneAuthProvider.getInstance().verifyPhoneNumber( //sending message
phoneNum, // Phone number to verify
60, // Timeout duration
TimeUnit.SECONDS, // Unit of timeout
TaskExecutors.MAIN_THREAD, // Activity (for callback binding)
mCallbacks); // OnVerificationStateChangedCallbacks
Toast.makeText(context, "OTP send to"+phoneNum, Toast.LENGTH_SHORT).show();
verifyOtpAndLogin.setVisibility(View.VISIBLE);
}
}
//method that verify the OTP received or not
private PhoneAuthProvider.OnVerificationStateChangedCallbacks mCallbacks = new PhoneAuthProvider.OnVerificationStateChangedCallbacks() {
#Override
public void onCodeSent(#NonNull String s, #NonNull PhoneAuthProvider.ForceResendingToken forceResendingToken) {
super.onCodeSent(s, forceResendingToken);
verificationCode = s; //verification code that should be received by phoneNumber
}
#Override
public void onVerificationCompleted(#NonNull PhoneAuthCredential phoneAuthCredential) {
String code = phoneAuthCredential.getSmsCode(); //verification code that actually received by phoneNumber
if (code != null) {
verifyCode(code);
}
}
#Override
public void onVerificationFailed(#NonNull FirebaseException e) {
Toast.makeText(context, "Verification Failed: OTP not received", Toast.LENGTH_SHORT).show();
}
};
//verifying the OTP
public void verifyCode(String code) {
PhoneAuthCredential credential = PhoneAuthProvider.getCredential(verificationCode, code); //comparing both verification code
signin(credential);
}
//signing in the User to update in database
private void signin(PhoneAuthCredential credential) {
FirebaseAuth firebaseAuth = FirebaseAuth.getInstance();
firebaseAuth.signInWithCredential(credential).addOnCompleteListener(new OnCompleteListener<AuthResult>() {
#Override
public void onComplete(#NonNull Task<AuthResult> task) {
if (task.isSuccessful()) {
Toast.makeText(context, "Verification Complete", Toast.LENGTH_SHORT).show();
isVerified=true;
Intent intent = new Intent(context, UserDashboard.class);
startActivity(intent);
finish();
} else {
Toast.makeText(context, "Verification Faild: OTP wrong", Toast.LENGTH_SHORT).show();
}
}
});
}
}
Set up a method that verifies if the UID of the verified user already exists on your database
if (task.isSuccessful()) {
//verify UID here
Toast.makeText(context, "Verification Complete", Toast.LENGTH_SHORT).show();
isVerified=true;
Intent intent = new Intent(context, UserDashboard.class);
startActivity(intent);
finish();
} else {
Toast.makeText(context, "Verification Faild: OTP wrong", Toast.LENGTH_SHORT).show();
}
}
});

how can do signup form include fname last name etc on firebase using android studio

this code for signup form on firebase using an android studio and it's working fine but I need to add first name, last name, gender with the signup form, and record to a firebase user group and direct go to a specific group
This picture shows what I want and I do it manually.
package com.example.showapps;
import android.content.Intent;
import android.os.Bundle;
import android.util.Patterns;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ProgressBar;
import android.widget.TextView;
import android.widget.Toast;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import com.google.android.gms.tasks.OnCompleteListener;
import com.google.android.gms.tasks.Task;
import com.google.firebase.auth.AuthResult;
import com.google.firebase.auth.FirebaseAuth;
public class signupActivity extends AppCompatActivity implements View.OnClickListener {
EditText s_email, s_password, s_cpasserd , fname,lname,phone;
ProgressBar progressBar;
FirebaseAuth firebaseAuth;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_signup);
s_email = findViewById(R.id.s_email);
s_password = findViewById(R.id.s_password);
s_cpasserd = findViewById(R.id.s_cpassword);
lname= findViewById(R.id.s_lname);
fname = findViewById(R.id.s_fname);
phone= findViewById(R.id.s_phone);
firebaseAuth = FirebaseAuth.getInstance();
progressBar = findViewById(R.id.progressBar2);
findViewById(R.id.btn_signup).setOnClickListener(this);
findViewById(R.id.mTologin).setOnClickListener(this);
}
#Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.btn_signup:
signup();
break;
case R.id.mTologin:
startActivity(new Intent(getApplicationContext(), login_Activity.class));
break;
}
}
private void signup() {
String email = s_email.getText().toString().trim();
String password = s_password.getText().toString().trim();
String cpassword = s_cpasserd.getText().toString().trim();
String fname= s_fname.getText().toString().trim();
String lname = s_lname.getText().toString().trim();
String phone = s_phone.getText().toString().trim();
if (email.isEmpty()) {
s_email.setError("The Email is required");
s_email.requestFocus();
return;
}
if (Patterns.EMAIL_ADDRESS.matcher(email).matches()) {
Toast.makeText(getApplicationContext(), "The Email is regietered",
Toast.LENGTH_SHORT).show();
}
if (password.length() < 6) {
s_password.setError("The password is less than 6 characters");
s_password.requestFocus();
return;
}
if (password.isEmpty()) {
s_password.setError("The password is required");
s_password.requestFocus();
return;
}
if (cpassword.isEmpty()) {
s_password.setError("The comfirm password is required");
s_password.requestFocus();
return;
}
if(!cpassword.equals(password)){
s_cpasserd.setError("The password is not much! ");
s_cpasserd.requestFocus();
return;
}
progressBar.setVisibility(View.VISIBLE);
firebaseAuth.createUserWithEmailAndPassword(email, password).addOnCompleteListener(new
OnCompleteListener<AuthResult>() {
#Override
public void onComplete(#NonNull Task<AuthResult> task) {
progressBar.setVisibility(View.GONE);
if (!task.isSuccessful()) {
Toast.makeText(getApplicationContext(), "Error ! ", Toast.LENGTH_SHORT).show();
} else {
Toast.makeText(getApplicationContext(), "The user has been registered ",
Toast.LENGTH_SHORT).show();
startActivity(new Intent(getApplicationContext(), login_Activity.class));
}
}
});
}
}
here what i need to add for this code to complete my task ?
firebaseAuth.createUserWithEmailAndPassword(email, password).addOnCompleteListener(new
OnCompleteListener<AuthResult>() {
#Override
public void onComplete(#NonNull Task<AuthResult> task) {
progressBar.setVisibility(View.GONE);
if (!task.isSuccessful()) {
Toast.makeText(getApplicationContext(), "Error ! ", Toast.LENGTH_SHORT).show();
} else {
Toast.makeText(getApplicationContext(), "The user has been registered ",
Toast.LENGTH_SHORT).show();
startActivity(new Intent(getApplicationContext(), login_Activity.class));
}
}
});
Thanks
Inside the else statement, you need to send the data to firestore:
} else {
Map<String, Object> userInfo = new HashMap<>();
city.put("name", "name_here");
city.put("gender", "gender_here");
city.put("email", email);
FirebaseFirestore db = FirebaseFirestore.getInstance();
db.collection("customer _user").document("1")
.set(userInfo)
.addOnSuccessListener(new OnSuccessListener<Void>() {
#Override
public void onSuccess(Void aVoid) {
Log.d(TAG, "DocumentSnapshot successfully written!");
Toast.makeText(getApplicationContext(), "The user has been registered ",
Toast.LENGTH_SHORT).show();
startActivity(new Intent(getApplicationContext(), login_Activity.class));
}
})
.addOnFailureListener(new OnFailureListener() {
#Override
public void onFailure(#NonNull Exception e) {
Log.w(TAG, "Error writing document", e);
}
});
}
Create a hashmap then using set you can add the data to the document and navigate to the other activity in case it was successful.

How to users can't login before verifying email which after registering account on Firebase?

I have problem with login account. After registering account, Firebase sent verification to email I registered. And then,application notify via toast that user must check the email. If the user doesn't verify the email, they can't login the application but the case is opposite. I can login the registered email when I don't verify so that I guess the email verrification is useless
So, there is some code from Register Activity.java class where code for verrification I embeded there and Login Activity.java for login logic
LoginActivity.java class
package id.co.dolansemarang.loginfirebaseds;
import android.content.Intent;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.v7.app.AppCompatActivity;
import android.text.TextUtils;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;
import com.google.android.gms.tasks.OnCompleteListener;
import com.google.android.gms.tasks.Task;
import com.google.firebase.auth.AuthResult;
import com.google.firebase.auth.FirebaseAuth;
import com.google.firebase.auth.FirebaseUser;
import com.google.firebase.database.DatabaseReference;
public class LoginActivity extends BaseActivity implements View.OnClickListener {
private static final String TAG = "Login User";
Button btnLogin;
EditText edtEmailLogin, edtPasswordLogin;
TextView tvResetPass;
FirebaseAuth firebaseAuthLogin;
DatabaseReference userRefLogin;
FirebaseUser curUser;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_login);
btnLogin = findViewById(R.id.btn_login);
edtEmailLogin = findViewById(R.id.edt_email_login);
edtPasswordLogin = findViewById(R.id.edt_password_login);
tvResetPass = findViewById(R.id.tv_reset_pass);
firebaseAuthLogin = FirebaseAuth.getInstance();
btnLogin.setOnClickListener(this);
tvResetPass.setOnClickListener(this);
}
//
// #Override
// protected void onStart() {
// super.onStart();
// // cek apakah pengguna sudah pernah masuk sehingga ada update UI disini
// FirebaseUser currentUser = firebaseAuthLogin.getCurrentUser();
// updateUI(currentUser);
// }
private void loginUserWithFirebase(String email, String password) {
Log.d(TAG, "signIn:" + email);
if (!validateForm()) {
return;
}
showProgressDialog();
firebaseAuthLogin.signInWithEmailAndPassword(email, password).addOnCompleteListener(this, new OnCompleteListener<AuthResult>() {
#Override
public void onComplete(#NonNull Task<AuthResult> task) {
if (task.isSuccessful()) {
Log.d(TAG, "your account has been success to register");
FirebaseUser user = firebaseAuthLogin.getCurrentUser();
updateUI(user);
} else {
Log.w(TAG, "please, try again", task.getException());
Toast.makeText(LoginActivity.this, "Gagal Login, silakan coba lagi", Toast.LENGTH_LONG).show();
// updateUI(null);
}
hideProgressDialog();
}
});
}
private void updateUI(FirebaseUser user) {
hideProgressDialog();
if (user != null) {
startActivity(new Intent(LoginActivity.this, MainActivity.class));
Toast.makeText(this, "Welcome " + user.getEmail() + "", Toast.LENGTH_LONG).show();
finish();
} else {
startActivity(new Intent(LoginActivity.this, RegisterActivity.class));
finish();
}
}
private boolean validateForm() {
boolean valid = true;
String email = edtEmailLogin.getText().toString();
String password = edtPasswordLogin.getText().toString();
if (TextUtils.isEmpty(email)) {
Toast.makeText(getApplicationContext(), "Harap isi email kembali", Toast.LENGTH_LONG).show();
valid = false;
} else {
if (TextUtils.isEmpty(password)) {
Toast.makeText(getApplicationContext(), "Harap isi password kembali", Toast.LENGTH_LONG).show();
valid = false;
} else {
if (password.length() <= 6) {
Toast.makeText(getApplicationContext(), "password contained minimum 6 character", Toast.LENGTH_LONG).show();
valid = false;
} else {
Toast.makeText(getApplicationContext(), "Authentication failed, please try again", Toast.LENGTH_LONG).show();
valid = false;
}
}
}
return valid;
}
#Override
public void onClick(View v) {
int i = v.getId();
if (i == R.id.btn_login) {
loginUserWithFirebase(edtEmailLogin.getText().toString(), edtPasswordLogin.getText().toString());
} else if (i == R.id.tv_reset_pass) {
startActivity(new Intent(LoginActivity.this, ResetPasswordActivity.class));
finish();
}
}
}
ResgiterActivity.java class
package id.co.dolansemarang.loginfirebaseds;
import android.content.Intent;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.design.widget.Snackbar;
import android.support.v7.app.AppCompatActivity;
import android.text.TextUtils;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;
import com.google.android.gms.tasks.OnCompleteListener;
import com.google.android.gms.tasks.Task;
import com.google.firebase.FirebaseApp;
import com.google.firebase.auth.AuthResult;
import com.google.firebase.auth.FirebaseAuth;
import com.google.firebase.auth.FirebaseUser;
import java.util.Random;
public class RegisterActivity extends BaseActivity implements View.OnClickListener{
private static final String TAG = "EmailPassword";
EditText edtNama, edtEmail, edtPassword;
Button btnRegisterOne;
TextView tvLoginLink;
FirebaseAuth firebaseAuthReg;
// //yangakandisimpan
//
// String NAMA_KEY = "namakey";
// String nama_key = "";
// Integer nomor_daftar_user = new Random().nextInt();
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_register);
edtNama = findViewById(R.id.edt_nama_register);
edtEmail = findViewById(R.id.edt_email_register);
edtPassword = findViewById(R.id.edt_password_register);
btnRegisterOne = findViewById(R.id.btn_register_one);
tvLoginLink = findViewById(R.id.tv_login_direct);
btnRegisterOne.setOnClickListener(this);
tvLoginLink.setOnClickListener(this);
firebaseAuthReg = FirebaseAuth.getInstance();
}
// #Override
// protected void onStart() {
// super.onStart();
// // cek apakah pengguna sudah pernah masuk sehingga ada update UI disini
// FirebaseUser currentUser = firebaseAuthReg.getCurrentUser();
// updateUI(currentUser);
// }
private void updateUI(FirebaseUser user) {
hideProgressDialog();
if(user != null){
startActivity(new Intent(RegisterActivity.this, LoginActivity.class));
finish();
}
else{
Toast.makeText(this,"Welcome to Firebase Authentication",Toast.LENGTH_LONG).show();
}
}
private void registerUser(String Nama, String email, String password) {
Log.d(TAG, "createAccount:"+email);
if(!validateForm()){
return;
}
showProgressDialog();
//start register
firebaseAuthReg.createUserWithEmailAndPassword(email, password).addOnCompleteListener(RegisterActivity.this, new OnCompleteListener<AuthResult>() {
#Override
public void onComplete(#NonNull Task<AuthResult> task) {
if(task.isSuccessful()){
Log.d(TAG,"your account has been success to register");
sendEmailVerification();
FirebaseUser user = firebaseAuthReg.getCurrentUser();
updateUI(user);
}
else{
Log.w (TAG, "please, try again", task.getException());
Toast.makeText(RegisterActivity.this,task.getException().getMessage(),Toast.LENGTH_LONG).show();
updateUI(null);
}
hideProgressDialog();
}
});
}
private void sendEmailVerification() {
final FirebaseUser user = firebaseAuthReg.getCurrentUser();
user.sendEmailVerification().addOnCompleteListener(this, new OnCompleteListener<Void>() {
#Override
public void onComplete(#NonNull Task<Void> task) {
if (task.isSuccessful()) {
Toast.makeText(RegisterActivity.this,
"Verification email sent to " + user.getEmail(),
Toast.LENGTH_LONG).show();
} else {
Log.e(TAG, "sendEmailVerification", task.getException());
Toast.makeText(RegisterActivity.this,
"Failed to send verification email.",
Toast.LENGTH_SHORT).show();
}
}
});
}
private boolean validateForm() {
boolean valid = true;
String nama = edtNama.getText().toString();
String email = edtEmail.getText().toString();
String password = edtPassword.getText().toString();
if(TextUtils.isEmpty(nama)){
Toast.makeText(getApplicationContext(), "Harap isi nama kembali", Toast.LENGTH_LONG).show();
valid = false;
}
else if( TextUtils.isEmpty(email))
{
Toast.makeText(getApplicationContext(), "Harap isi email kembali", Toast.LENGTH_LONG).show();
valid = false;
}
else{
if(TextUtils.isEmpty(password)){
Toast.makeText(getApplicationContext(), "Harap isi password kembali", Toast.LENGTH_LONG).show();
valid = false;
}
else{
if(password.length()<=6){
Toast.makeText(getApplicationContext(), "password contained minimum 6 character", Toast.LENGTH_LONG).show();
valid = false;
}
}
}
return valid;
}
#Override
public void onClick(View v) {
int i = v.getId();
if(i == R.id.btn_register_one){
registerUser(edtNama.getText().toString(),edtEmail.getText().toString(),edtPassword.getText().toString());
}
else if(i == R.id.tv_login_direct){
startActivity(new Intent(RegisterActivity.this, LoginActivity.class));
finish();
}
}
}
I expect the output is user can't login before verifiying email but I couldnt find effective code for 3 months :)
Thank you
Use this:
if(user!=null && user.isEmailVerified()){
// Add your stuff here
}else{
// Not Authenticated User Message
}
Refer this

How can I alert the user if he doesn't pick any photo from gallery while registering?

In the register page, when a user clicks on the "ImageUserPhoto", he can pick an image from the gallery. My code works fine when he picks the photo and fills up all given fields. But if he doesn't pick any photo, the app crashes. How can I give a warning if he doesn't choose any photo in the same section where I check all the fields?
Thanks in advance!!
package com.ayon.austmart.activities;
import android.Manifest;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.net.Uri;
import android.os.Build;
import android.support.annotation.NonNull;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.ProgressBar;
import android.widget.Toast;
import com.ayon.austmart.R;
import com.google.android.gms.tasks.OnCompleteListener;
import com.google.android.gms.tasks.OnSuccessListener;
import com.google.android.gms.tasks.Task;
import com.google.firebase.auth.AuthResult;
import com.google.firebase.auth.FirebaseAuth;
import com.google.firebase.auth.FirebaseUser;
import com.google.firebase.auth.UserProfileChangeRequest;
import com.google.firebase.storage.FirebaseStorage;
import com.google.firebase.storage.StorageReference;
import com.google.firebase.storage.UploadTask;
import de.hdodenhof.circleimageview.CircleImageView;
public class RegisterActivity extends AppCompatActivity {
CircleImageView ImgUserPhoto;
static int PReqCode = 1;
static int REQUESCODE = 1;
Uri pickedImgUri;
private EditText userEmail, userPassword, userPassword2, userName;
private ProgressBar loadingProgress;
private Button regBtn;
private Intent homeIntent;
private FirebaseAuth mAuth;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_register);
userEmail = findViewById(R.id.Email);
userPassword = findViewById(R.id.Password);
userPassword2 = findViewById(R.id.ConfirmPassword);
userName = findViewById(R.id.Name);
loadingProgress = findViewById(R.id.progressBarRegister);
regBtn = findViewById(R.id.buttonRegister);
loadingProgress.setVisibility(View.INVISIBLE);
mAuth = FirebaseAuth.getInstance();
ImgUserPhoto = findViewById(R.id.avatar);
regBtn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
regBtn.setVisibility(View.INVISIBLE);
loadingProgress.setVisibility(View.VISIBLE);
final String email = userEmail.getText().toString();
final String password = userPassword.getText().toString();
final String password2 = userPassword2.getText().toString();
final String name =userName.getText().toString();
if(email.isEmpty() || name.isEmpty() || password.isEmpty() || password2.isEmpty() || !password.equals(password2))
{
//something goes wrong... display an error message
showMessage("Please verify full fields!!");
regBtn.setVisibility(View.VISIBLE);
loadingProgress.setVisibility(View.INVISIBLE);
}
else
{
//Everything is ok..
createUserAccount(email,name,password);
}
}
});
ImgUserPhoto.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if(Build.VERSION.SDK_INT >= 22)
{
checkAndRequestForPermission();
}
else
{
openGallery();
}
}
});
}
private void createUserAccount(String email, final String name, String password) {
//this method create user account with valid email and pass
mAuth.createUserWithEmailAndPassword(email,password)
.addOnCompleteListener(this, new OnCompleteListener<AuthResult>() {
#Override
public void onComplete(#NonNull Task<AuthResult> task) {
if(task.isSuccessful())
{
//user account is created successfully
showMessage("Account Created!");
//now update the pro pic and username
updateUserInfo(name,pickedImgUri,mAuth.getCurrentUser());
}
else
{
showMessage("Account creation failed"+task.getException().getMessage());
regBtn.setVisibility(View.VISIBLE);
loadingProgress.setVisibility(View.INVISIBLE);
}
}
});
}
private void updateUserInfo(final String name, Uri pickedImgUri, final FirebaseUser currentUser){
StorageReference mStorage = FirebaseStorage.getInstance().getReference().child("user_photos");
final StorageReference imageFilePath = mStorage.child(pickedImgUri.getLastPathSegment());
imageFilePath.putFile(pickedImgUri).addOnSuccessListener(new OnSuccessListener<UploadTask.TaskSnapshot>() {
#Override
public void onSuccess(UploadTask.TaskSnapshot taskSnapshot) {
//image uploaded successfully
//getting image url
imageFilePath.getDownloadUrl().addOnSuccessListener(new OnSuccessListener<Uri>() {
#Override
public void onSuccess(Uri uri) {
// uri contains user image url
UserProfileChangeRequest profileUpdate = new UserProfileChangeRequest.Builder()
.setDisplayName(name)
.setPhotoUri(uri)
.build();
currentUser.updateProfile(profileUpdate)
.addOnCompleteListener(new OnCompleteListener<Void>() {
#Override
public void onComplete(#NonNull Task<Void> task) {
if(task.isSuccessful())
{
//user info updated successfully
showMessage("Register Complete!");
updateUI();
}
}
});
}
});
}
});
}
private void updateUI() {
homeIntent = new Intent(getApplicationContext(), Home.class);
startActivity(homeIntent);
finish();
}
//message show
private void showMessage(String message) {
Toast.makeText(getApplicationContext(),message,Toast.LENGTH_LONG).show();
}
private void openGallery() {
//Open gallery intent and wait for user to pick an image
Intent galleryIntent = new Intent(Intent.ACTION_GET_CONTENT);
galleryIntent.setType("image/*");
startActivityForResult(galleryIntent,REQUESCODE);
}
public void checkAndRequestForPermission()
{
if(ContextCompat.checkSelfPermission(RegisterActivity.this, Manifest.permission.READ_EXTERNAL_STORAGE)
!= PackageManager.PERMISSION_GRANTED)
{
if(ActivityCompat.shouldShowRequestPermissionRationale(RegisterActivity.this,Manifest.permission.READ_EXTERNAL_STORAGE))
{
Toast.makeText(RegisterActivity.this,"Please accept for required permission",Toast.LENGTH_SHORT ).show();
}
else
{
ActivityCompat.requestPermissions(RegisterActivity.this,new String[]{Manifest.permission.READ_EXTERNAL_STORAGE},PReqCode);
}
}
else
openGallery();
}
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if(resultCode == RESULT_OK && requestCode == REQUESCODE && data !=null)
{
//user has successfully picked an image...
//saving its reference to a Uri variable
pickedImgUri = data.getData();
ImgUserPhoto.setImageURI(pickedImgUri);
}
}
}
your pickedImgUri is null if the user does not select the image from gallery.
So when you call createUserAccount() when register button is clicked and user has not selected the image pickedImgUri is not updated as per your code.
Hence updateUserInfo() will fail calling an exception which causes the crash.
please add a null checker like
if(pickedImgUri!=null){
//then update the user account
}
If you are interested in forcing the user to select the profile photo then simply use above checker and alert user to please select a photo first but i'd advice against that. Not everyone likes to upload a photo. use any generic avatar png file instead when user does not want to update/remove the avatar.
Happy coding
Thanks a lot!! I have added a few lines and it worked!!! Thank you very much!!
if(email.isEmpty() || name.isEmpty() || password.isEmpty() || password2.isEmpty() || !password.equals(password2))
{
//something goes wrong... display an error message
showMessage("Please verify full fields!!");
regBtn.setVisibility(View.VISIBLE);
loadingProgress.setVisibility(View.INVISIBLE);
}
else
{
if(pickedImgUri == null)
{
showMessage("Please select an image");
regBtn.setVisibility(View.VISIBLE);
loadingProgress.setVisibility(View.INVISIBLE);
}
else {
createUserAccount(email, name, password);
//Everything is ok..
}
}
}
});

Categories