Flutter user registration with Firebase: Add extra user information (age, username) - firebase

With a phpMySQL background, I'm a little bit lost.
I've successfully created a registration process with Flutter and Firebase Auth (simple email/password method) following a tutorial.
I would like add a "username" and "age" field to the registration form.
In Firebase I've created a database called "users", and in it a String typed "userid" that's blank. But is it even necessary? What do I do next? How is it mapped to the User UID in the authentication table? How do I push it and retrieve it with Flutter?
I've explored this post to no avail Add extra User Information with firebase
If that helps, my authentication file contains this:
class Auth implements BaseAuth {
final FirebaseAuth _firebaseAuth = FirebaseAuth.instance;
Future<String> signIn(String email, String password) async {
FirebaseUser user = await _firebaseAuth.signInWithEmailAndPassword(
email: email, password: password);
return user.uid;
}
Future<String> signUp(String email, String password) async {
FirebaseUser user = await _firebaseAuth.createUserWithEmailAndPassword(
email: email, password: password);
return user.uid;
}
Have tried this:
Future<String> signUp(String email, String password) async {
FirebaseUser user = await _firebaseAuth.createUserWithEmailAndPassword(
email: email, password: password);
Firestore.instance.collection('users').document().setData({ 'userid': user.uid, 'displayName': 'bobby' });
return user.uid;
}
But it throws an error:
5.17.0 - [Firebase/Firestore][I-FST000001] Write at users/-L_6e1CFkU1YchxsSPay failed: Missing or insufficient permissions.

Ok seems the above is all good.
Just had to change the Database rules from false to true as per the below post:
https://stackoverflow.com/a/46925637/3475894

Related

I am trying to add authentication to my application, and I am getting the following mapping error when doing so:

I am currently coding the authentication for my application from a code that was already working. But firebase_auth had a recent update which changed a lot of the function/method names.
Error: The method 'map' isn't defined for the type 'Function'.
Try correcting the name to the name of an existing method, or defining a method named 'map'.
abstract class BaseAuth {
Stream<String> get authStateChanges;
Future<String> signInWithEmailAndPassword(
String email,
String password,
);
Future<String> createUserWithEmailAndPassword(
String email,
String password,
);
Future<String> currentUser();
Future<void> signOut();
Future<String> signInWithGoogle();
}
class Auth implements BaseAuth {
final FirebaseAuth _firebaseAuth = FirebaseAuth.instance;
final GoogleSignIn _googleSignIn = GoogleSignIn();
Stream<String> get authStateChanges => _firebaseAuth.authStateChanges.map(
(User user) => user?.uid,
);
If anybody has a potential solution it would be greatly appreciated.
I can only tell you how I solved the process of login/register and login check with firebase and flutter.
For login I used the following method:
await FirebaseAuth.instance.signInWithEmailAndPassword(
email: emailController.text,
password: passwordController.text);
For Register:
await FirebaseAuth.instance
.createUserWithEmailAndPassword(
email: emailController.text,
password: passwordController.text);
And to check if the user is currently logged in you can use:
if(User? user = FirebaseAuth.instance.CurrentUser != null){}
I hope that helps you somehow

How to get the UID Authentication from Firebase in Flutter and save in Firestore

I'm trying to get the uid, but it always returns the uid of the previously created account.
createUserWithEmailAndPassword does not execute the login after being completed.
So it should be returning the uid correctly, right?
Below are 2 pictures of the database and Authentication, as well as the code.
Future _singUp() async {
final User? user = auth.currentUser;
final uid = user!.uid;
try {
await FirebaseAuth.instance.createUserWithEmailAndPassword(
email: _emailController.text,
password: _passwordController.text,
);
await FirebaseFirestore.instance.collection('users').add({
'email': _emailController.text,
'name': _nameController.text,
'Id_usuario': uid
});
} on FirebaseAuthException catch (e) {
_handleSingUpError(e);
}
}
When you use createUserWithEmailAndPassword it will return a UserCredential as a result, you can use that to update your user variable, so in code it would be something like this:
UserCredential result = await FirebaseAuth.instance.createUserWithEmailAndPassword(email: email, password: password);
User? user = result.user;

Firebase authenthication

Im trying to use firebase for my flutter apps, and its seem there is an error in my code , i know firebaseuser need to change to user, but its seem it does not work , please help me , im new.
import 'package:firebase_auth/firebase_auth.dart';
import 'package:quizmaker/view/signin.dart';
import 'package:quizmaker/models/user.dart';
class AuthService {
FirebaseAuth _auth = FirebaseAuth.instance;
Future signInEmailAndPass(String email, String password) async {
try {
UserCredential userCredential = await _auth.signInWithEmailAndPassword(
email: email, password: password);
User user = authResult.user; //the error is in this part
} catch (e) {
print(e.toString());
}
}
}
In this code snippet:
UserCredential userCredential = await _auth.signInWithEmailAndPassword(
email: email, password: password);
User user = authResult.user;
You're trying to use an authResult variable that is never defined. My best guess is that you want to get the user from the userCredential instead, so:
UserCredential userCredential = await _auth.signInWithEmailAndPassword(
email: email, password: password);
User user = userCredential.user;
This still won't work though, since userCredential.user may be null, and is thus defined as User? and not User. Since you're using await, you can be certain that there is a user, so you can do:
User user = userCredential.user!;

Flutter: Firebase authentication create user without logging In

I have a user management feature in my flutter app that uses firebase authentication. I can register new user accounts using firebase_auth's createUserWithEmailAndPassword() function.
return await FirebaseAuth.instance.
createUserWithEmailAndPassword(email: email, password: password);
The problem is when the registration is successful it automatically authenticates my FirebaseAuth instance as the new user even though I am already logged in.
I came across this answer: Firebase kicks out current user but it's in javascript and has a slightly different api.
How can I do the equivalent in dart?
Updated: firebase_core ^0.5.0 and firebase_auth ^0.18.0+1 has deprecated some of the old classes.
Below is code updated for firebase_core ^0.5.1 and firebase_auth ^0.18.2.
static Future<UserCredential> register(String email, String password) async {
FirebaseApp app = await Firebase.initializeApp(
name: 'Secondary', options: Firebase.app().options);
try {
UserCredential userCredential = await FirebaseAuth.instanceFor(app: app)
.createUserWithEmailAndPassword(email: email, password: password);
}
on FirebaseAuthException catch (e) {
// Do something with exception. This try/catch is here to make sure
// that even if the user creation fails, app.delete() runs, if is not,
// next time Firebase.initializeApp() will fail as the previous one was
// not deleted.
}
await app.delete();
return Future.sync(() => userCredential);
}
Original Answer
I experimented with the firebase authentication api and my current working solution is:
// Deprecated as of `firebase_core ^0.5.0` and `firebase_auth ^0.18.0`.
// Use code above instead.
static Future<FirebaseUser> register(String email, String password) async {
FirebaseApp app = await FirebaseApp.configure(
name: 'Secondary', options: await FirebaseApp.instance.options);
return FirebaseAuth.fromApp(app)
.createUserWithEmailAndPassword(email: email, password: password);
}
Essentially it comes down to creating a new instance of FirebaseAuth so the automatic login from createUserWithEmailAndPassword() do not affect the default instance.
Based on Swift's answer I post updated code for this work around.
Future signUpWithEmailPasswordAdminPastor(String email, String password, String role, String nama, String keuskupan, String kevikepan, String paroki) async {
try {
FirebaseApp tempApp = await Firebase.initializeApp(name: 'temporaryregister', options: Firebase.app().options);
UserCredential result = await FirebaseAuth.instanceFor(app: tempApp).createUserWithEmailAndPassword(
email: email, password: password);
// create a new document user for the user with uid
await DatabaseService(uid: result.user.uid).updateUserDataSelf(
true,
role,
nama,
keuskupan,
kevikepan,
paroki,
'',
DateTime.now(),
DateTime.now());
tempApp.delete();
return 'OK';
} catch (e) {
print(e.toString());
return null;
}
}
Above code works for firebase_core: ^0.5.0 and firebase_auth: ^0.18.0+1.

Example of Firebase Auth with Email and Password on Flutter?

First time implementing Firebase Auth, also new to Flutter dev, and I'm looking to use email and passwords, not Google sign-in. The only examples I see of Firebase Auth being used are anonymously or with Google. Is there a resource / tutorial that shows how to properly set up the calls with the signInWithEmailAndPassword method?
Many thanks!
In my app I have an auth class because I don't like to litter my widget classes with non-widget code, but you can plop this code inside your widget class if you want.
In auth.dart I have:
import 'package:firebase_auth/firebase_auth.dart';
class Auth {
final FirebaseAuth auth = FirebaseAuth.instance;
Future<User> handleSignInEmail(String email, String password) async {
UserCredential result =
await auth.signInWithEmailAndPassword(email: email, password: password);
final User user = result.user!;
return user;
}
Future<User> handleSignUp(email, password) async {
UserCredential result = await auth.createUserWithEmailAndPassword(
email: email, password: password);
final User user = result.user!;
return user;
}
}
Then in my login/register screen I create an instance of my auth class:
var authHandler = new Auth();
Finally, in my login buttons onPressed callback I have:
onPressed: () {
authHandler.handleSignInEmail(emailController.text, passwordController.text)
.then((FirebaseUser user) {
Navigator.push(context, new MaterialPageRoute(builder: (context) => new HomePage()));
}).catchError((e) => print(e));
}
Here is one example from my service. I ask for the email, name and password fields.
registerWithEmail(String name, String email, String password) async {
First I check if the email is already registered with facebook or something.
List<String> providers = await firebaseAuth.fetchProvidersForEmail(email: email);
This is not ideal solution, but you want to handle if the user is already registered, and than link email with current user
if (providers != null && providers.length > 0) {
print("already has providers: ${providers.toString()}");
return handleProviders(providers);
}
Create new User
FirebaseUser newUser = await firebaseAuth.createUserWithEmailAndPassword(email: email, password: password);
await newUser.sendEmailVerification();
This is basically it. I update the name filed of the user, since I have it.
var userUpdateInfo = new UserUpdateInfo();
userUpdateInfo.displayName = name;
await firebaseAuth.updateProfile(userUpdateInfo);
await newUser.reload();
And later You can save the user inside your firestore, where user uid is document ID. So I can get it later.
Git repo with full explanation example for Email/Password Sign in Firebase using flutter
This may help you.
Git Repo: https://github.com/myvsparth/firebase_email_signin
Full Article Step by Step: https://www.c-sharpcorner.com/article/how-to-do-simple-login-with-email-id-in-flutter-using-google-firebase/
This code is for register new user
fb_auth.UserCredential userCredential = await fb_auth
.FirebaseAuth.instance
.createUserWithEmailAndPassword(email: email, password: password);
And this is for login previous user
fb_auth.UserCredential userCredential = await fb_auth
.FirebaseAuth.instance
.signInWithEmailAndPassword(email: email, password: password)
And that fb_auth is
import 'package:firebase_auth/firebase_auth.dart' as fb_auth;

Resources