1

we have the following factory to retrieve data from firebase:

    .factory('UserInfo', ["$firebase", "$q",
    function($firebase, $q) {
        //initialize firebase
        var ref = new Firebase("https://xxx.firebaseio.com/users/data");
        var dataRef = $firebase(ref).$asArray();

        //$q for synchronous method call
        var deferred = $q.defer();
        var promise = deferred.promise;

        return {
            getProfile: function(ID) {
                console.log(ID);
                dataRef.$loaded()
                    .then(function(data) {
                        var record = data.$getRecord(ID);
                        var profileData = {
                            "profileID": record.profileID,
                            "displayName": record.displayName,
                            "email": record.email,
                            "picture": record.picture,
                            "birthdate": record.birthdate,
                            "age": record.age,
                            "hobby": record.hobby,
                            "gender": record.gender,
                            "firstname": record.firstname,
                            "lastname": record.lastname,
                            "numberHuggs": record.numberHuggs,
                            "rating": record.rating
                        };
                        //console.log(profileData);
                        deferred.resolve(profileData);
                        //return profileData;

                    }) // end then

                .catch(function(error) {
                    console.error("Error getting UserInfo:", error);
                    deferred.reject("Error getting UserInfo: " + error)
                }); // end catch

                return deferred.promise;
            } // end function(ID)
        };
    } // end function
]) //end factory

in our controller, we access this factory using

$scope.chatList.$loaded().then(function() {
    for (var i = 0; i < ($scope.chatList).length; i++) {
                                        console.log($scope.chatList[i].otherProfileID);

        UserInfo.getProfile($scope.chatList[i].otherProfileID).then(function(value) {
                            console.log(value);

        });
    };

});

essentially, it takes profileIDs of users, sends them to UserInfo.getProfile() and getProfile then returns an object with our data. sadly this doesn't work. the console.log() in our controller code indicate, that different profileIDs are handled in the factory, but in the end, it returns (console.log(value)) the first userprofile 3 times (we have 3 different profileIDs in the array) any hints?

2 Answers2

3

You should create a new deferred object for each call to getProfile. Your code creates it once therefore the resolve always happens for the same object.

Try moving this block :

//$q for synchronous method call
var deferred = $q.defer();
var promise = deferred.promise;

Into the getProfile function body

Variant
  • 17,279
  • 4
  • 40
  • 65
1

dataRef.$loaded() already returns a thenable, therefore you don't need to create/resolve your own deferred - moreover, it's actually bad practice to do so (aka the Deferred Anti-pattern).

Instead, return the result of your dataRef.$loaded().then() chain, having made suitable returns in then's callbacks.

With further tidying, the whole thing should simplify as follows :

.factory('UserInfo', ["$firebase", "$q", function($firebase, $q) {
    var ref = new Firebase("https://xxx.firebaseio.com/users/data"),
        dataRef = $firebase(ref).$asArray();
    return {
        getProfile: function(ID) {
            return dataRef.$loaded().then(function(data) {
                return angular.extend({}, data.$getRecord(ID));//much shorter than transcribing properties manually
            }).catch(function(error) {
                console.error("Error getting UserInfo: ", error.message);
                return $q.reject(error);
            });
        }
    };
}]);
Community
  • 1
  • 1
Roamer-1888
  • 19,138
  • 5
  • 33
  • 44