The user registers with username, email, and password. I authenticate using FirebaseSimpleLogin with the email, take the user id, and then load my user using the user id:
var ref = new Firebase(FIREBASE_URL + 'users'); // data containing user information
var users = $firebase(ref);
$rootScope.$on('$firebaseSimpleLogin:login', function (e, authUser) { // wait until authenticated
var query = $firebase(ref.startAt(authUser.uid).endAt(authUser.uid)); // find user by uid
query.$on('loaded', function () {
setCurrentUser(query.$getIndex()[0]); // get username from query
});
});
function setCurrentUser (username) {
$rootScope.currentUser = User.findByUsername(username);
}
Now, my problem is that I would like to redirect to the user profile page if I am logged in in my HomeCtrl:
app.controller('HomeCtrl', function ($rootScope, $scope, $location, Auth, User) {
// wait for current user to be set
// if signed in
// location.path('/user/' + currentUser.username);
});
Unfortunately, I am not sure how to wait until the setCurrentUser function is completed before I redirect. Is there a way I can have a function in my controller wait until this other function is completed?
I have a workaround, but I'm pretty sure this is not the right way to do it. Right now, I am watching for my user variable to be updated, and then calling all functions after it changes to a user, as in:
$scope.$watch(
function() { return $rootScope.currentUser }, // watch for variable to change
function() {
if ($rootScope.currentUser) { // if the current user is defined, change path
$location.path('/users/' + $rootScope.currentUser.username);
}
}
)
Try resolving the route for your users. Take the plunker demo below for example.
The app is just a simple login page to a profile page. It has a HomeCtrl
that navigates to a ResolveCtrl
(which is the profile page) after a login.
The HomeCtrl
just manages a login view. When a user is successfully logged in we navigate to the profile page. (The Auth object is a custom wrapper I made available in the Plunker).
.controller('HomeCtrl', function($scope, Auth, $window) {
$scope.user = {
email: '[email protected]',
password: 'password'
};
$scope.login = function() {
Auth.login('password', $scope.user);
};
Auth.onLogin(function(e, user) {
console.log('logged in!');
$window.location.href = '#/resolve';
});
})
Now that we're logged in we'll go the ResolveCtrl
. This controller resolves the current user before it has been loaded. That's the data
parameter.
.controller('ResolveCtrl', function($scope, $route, data) {
$scope.user = data;
})
But where is that parameter coming from? We can set a resolve object in our $routeProvider. This tells the ResolveCtrl
it can't load until we've resolved this promise. Since the Auth.getCurrentUser() returns a promise we just need to return that and it will get resolved for us.
.config(['$routeProvider',
function($routeProvider) {
$routeProvider
.when('/', {
templateUrl: '_home.html',
controller: 'HomeCtrl',
})
.when('/resolve', {
templateUrl: '_resolve.html',
controller: 'ResolveCtrl',
resolve: {
data: function(Auth) {
// load the user before the view is loaded
return Auth.getCurrentUser();
}
}
})
.otherwise({
redirectTo: '/'
});
}
])
Now when the page gets loaded we know that the user will be there.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With