1
votes

I am trying to build an ionic application which does basic authentication.

My registration system is working in terms of pushing data into my Firebase URL and logging the user in, adding user into the Login and Auth system, but my login is not doing proper Authentication. Note, this is just the first step - my aim is the check if the user's UID matches the UID I have stored in firebaseurl/uids/firebasekey/uid. I get this error:

Login Failed! TypeError: Cannot read property 'email' of undefined(…) 

this is the error that is caught.

Even though I know the user with that email exists in the Firebase instance.

Here is my LoginCtrl:

.controller('LoginCtrl', ['Auth', '$state', '$location', '$scope', '$rootScope', '$firebaseAuth', '$window',
        function (Auth, $state, $location, $scope, $rootScope, $firebaseAuth, $window) {
            // check session
            //$rootScope.checkSession;
            // Create a callback to handle the result of the authentication

            $scope.user = {
                email: this.email,
                password: this.password
            };

            $scope.validateUser = function (user) {

                $rootScope.show('Please wait.. Authenticating');
                console.log('Please wait.. Authenticating');

                var email = this.user.email;
                var password = this.user.password;

                /* Check user fields*/
                if (!email || !password) {
                    $rootScope.hide();
                    $rootScope.notify('Error', 'Email or Password is incorrect!');
                    return;
                }

                /* All good, let's authentify */
                Auth.$authWithPassword({
                    email: email,
                    password: password
                }).then(function (authData) {
                    console.log(authData);
                    $rootScope.userEmail = user.email;
                    $window.location.href = ('#/app/meals');
                    $rootScope.hide();
                }).catch(function (error) {
                    console.log("Login Failed!", error);
                    if (error.code == 'INVALID_EMAIL') {
                        $rootScope.notify('Invalid Email Address');
                    }
                    else if (error.code == 'INVALID_PASSWORD') {
                        $rootScope.notify('Invalid Password');
                    }
                    else if (error.code == 'INVALID_USER') {
                        $rootScope.notify('Invalid User');
                    }
                    else {
                        $rootScope.notify('Oops something went wrong. Please try again later');
                    }
                    $rootScope.hide();
                    //$rootScope.notify('Error', 'Email or Password is incorrect!');
                });
            };

            this.loginWithGoogle = function loginWithGoogle() {
                Auth.$authWithOAuthPopup('google')
                    .then(function (authData) {
                        $state.go($location.path('app/meals'));
                    });
            };

            this.loginWithFacebook = function loginWithFacebook() {
                Auth.$authWithOAuthPopup('facebook')
                    //Use the authData factory
                    .then(function (authData) {
                        $state.go($location.path('app/meals'));
                    });
            };

        }
    ])

And here is my SignupCtrl:

.controller('SignUpCtrl', [
        '$scope', '$rootScope', '$firebaseAuth', '$window', 'Auth',
        function ($scope, $rootScope, $firebaseAuth, $window, Auth) {

            $scope.user = {
                firstname: this.firstname,
                lastname: this.lastname,
                email: "",
                password: ""
            };
            $scope.createUser = function () {
                var firstname = this.user.firstname;
                var lastname = this.user.lastname;
                var email = this.user.email;
                var password = this.user.password;

                //https://www.firebase.com/docs/web/guide/login/password.html

                if (!email || !password) {
                    $rootScope.notify("Please enter valid credentials");
                    return false;
                }

                $rootScope.show('Please wait.. Registering');
                $rootScope.auth.$createUser(
                    {email: email, password: password})
                    .then(function (user) {
                        console.log('user is created');
                        $rootScope.hide();
                        $rootScope.userEmail = user.email;
                        var usersRef = new Firebase('https://foodsharingapp.firebaseio.com/users');
                        var keyRef = usersRef.push({
                            'uid': user.uid,
                            'email': email,
                            'firstname': firstname,
                            'lastname': lastname
                        });
                        var uidRef = new Firebase('https://foodsharingapp.firebaseio.com/uids/' + user.uid + '/' + keyRef.key());
                        uidRef.set({'registered': true});
                        $window.location.href = ('#/app/meals');
                    }, function (error) {
                        console.log('error unfortunately');
                        $rootScope.hide();
                        if (error.code == 'INVALID_EMAIL') {
                            console.log('invalid email');
                            $rootScope.notify('Invalid Email Address');
                        }
                        else if (error.code == 'EMAIL_TAKEN') {
                            console.log('email taken');
                            $rootScope.notify('Email Address already taken');
                        }
                        else {
                            console.log('not sure what happened');
                            $rootScope.notify('Oops something went wrong. Please try again later');
                        }
                    });

            }

            Auth.$onAuth(function (user) {
                if (user === null) {
                    console.log("Not logged in yet");
                } else {
                    console.log("Logged in as", user.uid);
                }
                $scope.user = user; // This will display the user's name in our view
            });
        }
    ])

And here is my Auth factory:

app.factory('Auth', ['rootRef', '$firebaseAuth',function(rootRef, $firebaseAuth){
    return $firebaseAuth(rootRef);
}]);

And here is my app.js related to Auth:

$rootScope.userEmail = null;
            $rootScope.baseUrl = 'https://foodsharingapp.firebaseio.com/';
            var authRef = new Firebase($rootScope.baseUrl);
            $rootScope.auth = $firebaseAuth(authRef);
            $rootScope.authData = authRef.getAuth();


            $rootScope.logout = function() {
                authRef.unauth();
                $rootScope.authDataCallBack;
            };


            $rootScope.checkSession = function() {
                if ($rootScope.authData) {
                    console.log("User " + authData.uid + " is logged in with " + authData.provider);
                    $rootScope.userEmail = user.email;
                    $window.location.href = ('#/app/meals');
                } else {
                    console.log("No session so logout");
                    $rootScope.userEmail = null;
                    $window.location.href = '#/auth/signin';
                }
            }

            $rootScope.authDataCallBack = function(authData) {
                if ($rootScope.authData) {
                    console.log("User " + authData.uid + " is logged in with " + authData.provider);
                } else {
                    console.log("User is logged out");
                    $window.location.href = '#/auth/signin';
                }
            };

            //Listens for changes
            authRef.onAuth($rootScope.authDataCallback);

Note, the other issue is that the onAuth function in the app.js function is not working.

How should I clean up my code? What am I doing wrong? I am using a bunch of tutorials etc and I don't think the right way.

2
I tested it even after resetting my password and using the password in the reset link for that user that Firebase gave me. Still same error. - Dhruv Ghulati

2 Answers

1
votes

I have figured out the issue.

$rootScope.userEmail = user.email;

I was calling this line when user is actually undefined as a variable (though $scope.user has been defined).

0
votes

login controller code

  function ($scope, $stateParams,  $firebaseAuth, $state) {

        $scope.user = {
            'email': '',
            'password': ''
        };

        $scope.signIn = function(){
            $scope.errorBox = '';
            const promise = firebase.auth().signInWithEmailAndPassword($scope.user.email, $scope.user.password);
            promise.then(resp => {

                $state.go('zazzycoinsActivities');
            })
            .catch(err => {
              $scope.$apply(function(){
                 $scope.errorBox = err.message;
              });
            });
        };

    }

this might work for you too it worked for me......