I am making a web application which creates a user on Firebase using email and password firebase.auth().createUserUsingEmailAndPassowrd()
After the account
You can do it in your OnComplete method of createUserUsingEmailAndPassowrd().
mAuth.createUserWithEmailAndPassword(email, password)
.addOnCompleteListener(this, new OnCompleteListener<AuthResult>() {
@Override
public void onComplete(@NonNull Task<AuthResult> task) {
if (task.isSuccessful()) {
//Create your user in DB here
}
}
});
Because you're so afraid of worst case scenario (which is absolutely normal), here is one way to do it: Consider you have these fields: email, password, and address. The address field is the one you need to store in your database (with user uid, of course).
First you try to register the user, and like Faizy said, you use onCompleteListener
like this
mAuth.createUserWithEmailAndPassword(email, password)
.onCompleteListener(... {
... onComplete (... task) {
if (task.isSuccessful()) {
doInsertTheData();
}
...
When task is successful, then you want to insert the data into database, which doInsertTheData()
is created for
private void doInsertTheData() {
// I believe you familiar with Firebase database inserting method, so I skip the long part
FirebaseDatabase...setValue(address, new CompletionListener() {
... onComplete(FirebaseError firebaseError, ...) {
if (firebaseError == null) {
// if your code reach here, its a happy ending
} else {
// if it reach here, then you can remove the signed in user
// and tell the user that their registration is failed and should try again
FirebaseAuth.getInstance().getCurrentUser().delete();
}
And there you go, as long as the database saving process failed, the user credential will be deleted
Note: I actually have another method in mind when I type this, but it's too complicated and I think this one is more easy to understand (I haven't try/use this though)
If you need user to have certain data to use app, then might have to always check.. when they sign in:
firebase.auth().onAuthStateChanged(user => {
if (user) {
// ... access ref to userData field(s) you care about..
someUserFieldRef.once('value').then(snap => {
if (! snap.exists()) {
// redirect to setup page to add missing data..
}
})
}
})
If they can use other parts of app, then you can defer check to when specific user data is necessary, get currentUser
, then check for data..
firebaser here
There are no cross-feature transactions in Firebase at the moment. The common approach is to:
This means you decide which one if more important: that each existing user has a database node or that each database node points to an existing user. You seem to want to answer "both", but as said: that's not possible, you'll have to pick. In most scenarios I've seen developers will pick option 1: every Firebase Authentication user must have a node in the database.
In that case, you'll want to run the code that registers a user in the database before actually registering the user with Firebase Authentication. And since the user only gets their UID once they do register with Auth, you'll need some two-stepped process here. All quite nasty code that is bound to have problems. Which is why you'll see that most developers with an app in production care a lot less about this approach than you think.
Instead they rely on regular clean-up of their database. They run an administrative process every day or so that scans the database for users without a corresponding Firebase Authentication registration. This handles all kinds of edge cases with a fairly simple process, even edge cases not related to registration. You might even call this "eventual consistency": eventually the data in the database will match the registered users.
Final shout-out on your original question: you can drastically reduce the chance of a cross-feature failure by running the register-and-write-to-database code in a Cloud Function for Firebase. Using the Admin SDK in a Cloud Function makes this all nice and tidy. But while the chance of failures reduces a lot, it can still fail. So if you care about the cleanliness of your data, you'll still need the clean-up process.