Trying to authenticate an user using firebase. Started my app using firebase 2.xx but even after upgrading to Firebase 3.xx, throwing
error "onAuthStateChanged is not a function".
This is how my login function looks like-
.controller('HomeCtrl', ['$scope','$location','CommonProp','$firebaseAuth', '$firebaseObject',function($scope,$location,CommonProp,$firebaseAuth,$firebaseObject) {
var firebaseObj = $firebaseObject(rootRef);
var loginObj = $firebaseAuth(firebaseObj);
$scope.SignIn = function($scope, user) {
event.preventDefault(); // To prevent form refresh
var username = user.email;
var password = user.password;
loginObj.$signInWithEmailAndPassword({
email: username,
password: password
})
.then(function(user) {
// Success callback
console.log('Authentication successful');
$location.path("/welcome");
CommonProp.setUser(user.password.email);
}, function(error) {
// Failure callback
console.log(error);
});
}
}]);
Your problem is that you are passing a $firebaseObject to $firebaseAuth().
So make sure you are initializing your [$firebaseAuth][1] object like the following and then your code should work properly.
var loginObj = $firebaseAuth();
Working jsFiddle for demonstrating.
You can check here the documentation for AngularFire2
Related
I am relatively new to Ionic and I'm having issues doing a Facebook login with ionic framework on the android platform. It does work perfectly on browser (sometimes when I try to do the login the first attempt doesn't work) but when I run the project on Android it just redirects and doesn't pass to the next page.
I think that the issue could be that the first login attempt doesn't fetch the Facebook user data.
Here is my code:
.controller('LoginCtrl', function (Backand, $state, $rootScope, $scope, LoginService, ID, name) {
$scope.bgs = ["img/welcome-bg.jpg"];
$scope.firebaseFacebookLogIn = function(){
var provider = new firebase.auth.FacebookAuthProvider();
provider.addScope('user_birthday');
provider.addScope('public_profile');
firebase.auth().signInWithRedirect(provider);
firebase.auth().getRedirectResult().then(function(result) {
if (result.credential) {
// This gives you a Facebook Access Token. You can use it to access the Facebook API.
var token = result.credential.accessToken;
var user = result.user;
var uid = user.providerData[0].uid;
var nombre = user.providerData[0].displayName;
localStorage.setItem("Usuario", user);
localStorage.setItem("ID", uid);
localStorage.setItem("Nombre", nombre);
$state.go('app.feed');
}
//var user = firebase.auth().currentUser;
}).catch(function(error) {
// Handle Errors here.
var errorCode = error.code;
alert(errorCode);
var errorMessage = error.message;
alert(errorMessage);
// The email of the user's account used.
var email = error.email;
alert(email);
// The firebase.auth.AuthCredential type that was used.
var credential = error.credential;
alert(credential);
// ...
});
};
$scope.ID = localStorage.getItem("ID");
$scope.name = localStorage.getItem("name");
$scope.facebookLogOut = function(token){
firebase.auth().signOut().then(function() {
// Sign-out successful.
$state.go('auth.walkthrough');
}, function(error) {
// An error happened.
});
};
})
Solved it!
Turns out that I was just missing a firebase tag inside config.xml of the project.. Pretty dumb to be honest, hope it helps to somebody with the same issue.
I'm making a single page app in AngularJS using Firebase and using the side nav bar on index.html.
And after login, I want the username should be on the side nav bar but the $scope is working for the current page on the controller is working.
scotchApp.controller('mainController', function($scope) {
$scope.validateLogin = function()
{
var email = $scope.login.userName + "#xyz.co";
var password = $scope.login.password;
firebase.auth().signInWithEmailAndPassword(email, password).catch(function(error) {
$scope.message = "please enter the correct details";
});
firebase.auth().onAuthStateChanged(function(user)
{
if(user)
{
$scope.usermobile = $scope.login.userName;
window.location.assign("/#/equipment");
}
});
}
$scope.message = '';
});
The current user is available in firebase.auth().currentUser as described in the docs so in your mainController you don't need to listen for auth changes.
In your code you are attaching a new listener each time the user tries to login, but what you actually want is to respond to one successful login, so just add a then to your sign in call:
firebase.auth().signInWithEmailAndPassword(email, password)
.then(function (user) {
console.log('the logged in user: ', user);
// Go to the other route here.
// It is recommended to use the router instead of "manually" changing `window.location`
})
.catch(function(error) {
$scope.message = "please enter the correct details";
});
I am just trying to create a simple social login (e.g.: google, Facebook,...) inside a Ionic App and using Firebase V3 as backend. Unfortunately all the example and tutorial that I found on the internet seems to be broken and do not work with the new API v3.
For example I tried to follow this tutorial (https://firebase.googleblog.com/2016/01/social-login-with-ionic_77.html?showComment=1465144743780#c7688518627861813273)
but apparently I am not able to access the global variable Firebase that was previously available and therefore from this snippet of my app.js
angular.module('starter', ['ionic', 'starter.controllers', 'starter.services', 'firebase'])
.constant('FirebaseUrl', 'https://ionicle.firebaseio.com/')
.service('rootRef', ['FirebaseUrl', Firebase])
I get the following error
ReferenceError: Can't find variable: Firebase, http://localhost:8103/js/app.js, Line: 12
facebookAuth: function () {
ngFB.login({ scope: 'email' }).then(
function (response) {
if (response.status === 'connected') {
console.log('Facebook login succeeded', response);
var credential = firebase.auth.FacebookAuthProvider.credential(
response.authResponse.accessToken);
firebase.auth().signInWithCredential(credential).catch(function (error) {
// Handle Errors here.
var errorCode = error.code;
var errorMessage = error.message;
// The email of the user's account used.
var email = error.email;
// The firebase.auth.AuthCredential type that was used.
var credential = error.credential;
// ...
});
} else {
alert('Facebook login failed');
}
});
},
more details here: http://www.clearlyinnovative.com/firebase-3-0-ionic-facebook-login
My intention is to update the navigation bar after the user login. Basically, it should change Login to Hi, {{usr.username}} right after the login.
However, it does not update after logging in and I have to click on Login again to trigger the change. However, in the console, the user info is logged right after the login.
In the index.html, the part of the code looks like:
<div class="item" ng-click="loginmodal()" ng-hide="loggedIn">Log in</div>
<div class="item" ng-show="loggedIn">Hi, {{usr.username}}</div>
where $scope.loggedIn is initialized as false and $scope.usr as null. I am using firebase for authentication:
FirebaseRef.authWithPassword({
"email" : email,
"password" : password
}, function(error, authData) {
if (error) {
console.log('Login Failed!', error);
} else {
console.log('Authenticated successfully with payload:', authData);
FirebaseRef.child("users").child(authData.uid).once('value', function(dataSnapshot) {
$scope.usr = dataSnapshot.val();
});
$scope.loggedIn = true;
console.log($scope.usr);
console.log($scope.loggedIn);
}
});
In console, I have $scope.loggedIn as true, but have $scope.usras null.
Is it wrong how I am using the authWithPassword() function or can I force the change to be updated?
AngularJS won't update the view if any changes to the $scope object are done outside of its $digest loop.
But worry not, Firebase is such a popular tool it has a AngularJS service. It's called AngularFire and you should be using it instead of global Firebase object.
So your code will be something similar to:
var auth = $firebaseAuth(FirebaseRef);
auth.$authWithPassword({
email: email,
password: password
}).then(function (authData) {
console.log('Authenticated successfully with payload:', authData);
var sync = $firebase(FirebaseRef.child("users").child(authData.uid));
var syncObject = sync.$asObject();
syncObject.$bindTo($scope, "usr");
}).catch(function (error) {
console.error('Login Failed!', error);
});
Read more in the documentation of AngularFire
Try calling $scope.$digest() right after changing $scope.usr value.
Anyway, notice that you call to Firebase to get the user is asynchronous, so I wouldn't put dependent code after this call, but inside the callback.
Call $scope.$apply();
FirebaseRef.child("users").child(authData.uid).once('value', function(dataSnapshot) {
$scope.$apply(function(){
$scope.usr = dataSnapshot.val();
});
});
I am using a separate server that authenticates my angular app. As part of that process the server has already authenticated the user with firebase and has received an auth_token back. Once the angular app is served, I re-request the token from my server and now I want to issue an angularFireAuth.login().
I have tried this but get a "Reference Error unrecognized auth". Am I missing something very fundamental? Shouldn't I be able to login with a pre-existing firebase auth_token??
Here is the code:
var profileController = function ($rootScope, $scope, $log, $location, angularFire, angularFireAuth, profileService) {
init();
function init() {
$scope.profile = {};
profileService.getFirebaseToken(function success(data) {
$scope.auths = data;$
$scope.auth = $rootScope.auth;
var id = {'id': data['_id']};
auth=angularFireAuth.login(data['access_token'],id);
$scope.auth = auth;
}, function error(err) {
console.log('error', err);
});
** Note: data['_id'] = string id that is the userid in my firebase and used as auth.id in my security rules
data['access_token'] = string token. this is not a dictionary or object. just the string token returned from: token = create_token(SECRET, custom_data, options). Which runs successfully on my python tornado server using the: firebase_token_generator module.
Ok. I figured it out. The error I was receiving because the login request is asynchronous. So the "Reference Error: auth" was because the variable auth was referenced before assigned.
I did not ultimately use this exact code above. So I do not know if it was/would work. Instead I switched to the construct that is on the firebase site:
fbLoginService.getFirebaseToken(function success(data) {
var dataRef = new Firebase('xxxxxx.firebaseio.com')
dataRef.auth(data['firebase']['access_token'], function(error) {
if(error) {
console.log("Login Failed!", error);
alert("Login Failure. Unable to login to database(firebase)");
} else {
console.log("Firebase Login Succeeded!");
$rootScope.firebaseAuth=true;
}
});
}, function error(err) {
console.log('error', err);
alert('error', err);
});
I have now created a loginController and loginService that I fire on initial load of index.html with the inclusion of the ng-controller="fbLoginController". All looks good so far.