1

I'm working on a blog like structured web app In AngularJS. Im trying to retrieve the user which is an other of a post and retrieve their display name dynamically as it loops through all the posts but I cant seem to retrieve data correctly.. This is what I have done so far.

Blog Controller:

uno.controller('newsCtrl', function($scope, $http, adbFactory){
    $scope.derp = 'derp!!!!!';
    adbFactory.get($http, 'get users 1', false).success(function(data){
        $scope.user = data;
    }).error(function(){
        console.log('Errorrr');
    });

    $scope.init = function(){
        adbFactory.get($http, 'get all blog_posts', true).success(function(data){
            $scope.posts = data;
            console.log($scope.posts);
        });
    };

    $scope.getAuthor = function(_id) {
        adbFactory.get($http, 'get users id ' +_id+ ' spec', false).success(function(data){
            //$scope.author = data;
            //console.log($scope.author);
            return data;
        });
    };
});

If I console.log the data it shows the users perfectly given the author id which is in the database, but when i attempt to call the getAuthor function using the '{{ }}' scope i get a collage of errors... heres my blog template below.

Blog Template:

<div class="large-12 small-12 columns" ng-init="init()">
    <div class="row">
        <div class="large-12 small-12 columns" ng-repeat="topic in posts" style="margin-bottom:20px;">
            <div id="news-post" class="panel animated fadeInUp">
                <div class="row" ng-init="getAuthor(topic.author_id)">
                    <div class="large-2 small-2 columns"> 
                        <img src="{{ topic['thumb'] }}" alt="" style="border-radius:50%; height:100px; width: 150px;" />
                    </div>
                    <div class="left large-10 small-10 columns">
                        <div class="row">
                            <h2 class="post-title"><a href="#/news/post/{{ topic['id'] }}">{{topic['title']}}</a> <p>Posted By, {{ getAuthor(topic.author_id).email }}</p></h2>
                            <p>{{ topic['body'] }}</p> 
                        </div>
                    </div>
                </div>
            </div>
        </div>
        <hr>
    </div>
</div>

not quite sure what the problem can be.. Any thing I'm missing?

UPDATE:: I recently updated my controller and factories to get a better scope of handling my data flow, my Controller now looks like this:

uno.controller('newsCtrl', function($scope, $http, adbFactory, $cacheFactory, unoFunctions){
    $scope.init = function(){
        adbFactory.get($http, 'get all blog_posts', true).success(function(data){
            $scope.posts = data;

            $scope.getUser = function(_id) {
            $scope.userData = unoFunctions.getUser(_id);
                //console.log($scope.userData);

                return $scope.userData;
            };
        });

        $scope.getTags = function(_id) {
            var post = unoFunctions.getPost(_id);
            var _tags = post.tags.split(',');
            for(var i = 0; i < _tags.length; i++)
            {
                _tags[i] = _tags[i].trim();
            }

            return _tags;
        };

        $scope.getUserName = function(_id) {
            $scope.userData = unoFunctions.getUser(_id);
            return $scope.userData.display_name;
        };

        $scope.getUser = function(_id) {
            $scope.userData = unoFunctions.getUser(_id);
            //console.log($scope.userData);
            return $scope.userData;
        };

        $scope.getUserName = function(_id) {
            $scope.userData = unoFunctions.getUser(_id);
            return $scope.userData.display_name;
        };
    };
});

the unoFunctions factory is wht I use now to handle certain requests from my database, and that is shown below.

uno.factory('unoFunctions', function(adbFactory, $http, $cacheFactory){ var fact = {};

var user = $cacheFactory('user');
var post = $cacheFactory('post');

fact.getUser = function(_id) {
    if(!user.get(_id)){
        adbFactory.get($http, 'get users id '+_id+' spec', false).success(function(data){
            user.put(_id, data);
        });
    }

    return user.get(_id);
};
fact.getPost = function(_id) {
    if(!post.get(_id))
    {
        adbFactory.get($http, 'get blog_posts id '+_id+' spec', false).success(function(data){
            post.put(_id, data);
        });
    }

    return post.get(_id);
};

fact.loggedIn = function()
{
    console.log('gfdg');
};

/*------------------------------*/
return fact;

});

And my template to output the result is this:

<div class="large-12 small-12 columns" ng-init="init()">
    <div class="row">
        <div class="large-12 small-12 columns" ng-repeat="topic in posts | filter:postTitle | orderBy:'-time' " style="margin-bottom:20px;">
            <div id="news-post" class="panel animated fadeInUp" ng-init="getTags(topic.id)">
                <div class="row" style="padding-bottom:0px;">
                    <div class="large-2 small-2 columns">
                        <img src="{{ topic['thumb'] }}" alt="" style="border-radius:50%; height:120px; width: 200px;" />
                    </div>
                    <div class="left large-10 small-10 columns">
                        <div class="row" style="padding-bottom:0px;">
                            <h2 class="post-title">
                            <a href="#/news/post/{{ topic['id'] }}">
                            {{topic['title']}} 
                            </a> 
                            <p style="font-size:13px; font-style:italic; color:#a5a5a5" class="right">{{ topic.time | timeago }} {{  }}</p>
                            <p style="font-weight:bold; font-style:italic; color:#aaa">Posted By, {{ getUser(topic.author_id).display_name }}</p></h2>
                            <p>{{ topic['body'] }}</p> 
                            <div ng-repeat="tag in getTags(topic.id)"><span style="background:#ccc; margin:7px; padding:4px; border-radius:5px; font-size:12px" class="left">{{ tag }}</span></div>
                            <p class="right" style="background:#dedede; font-size:13px; padding:7px; border-radius:6px; color:#1985A1;">{{ topic.category }}</p
                        </div>
                    </div>
                </div>
            </div>
        </div>
    </div>
</div>

This works fine and returns the required results I'm looking for but I wish to get rid of the countless Error: [$rootScope:infdig] errors and keep my console clean.. I researched the error and it seems to be because when I call functions from the unoFunctions factory like, getUser, or getPost. it returns a new array each time or something like that which I guess throws things out of scope. I'm not entirely sure, and reason for this?

3
  • what's your data? the structure of your data? Commented Sep 4, 2015 at 7:39
  • Its ins JSON Format. Like an array Commented Sep 4, 2015 at 7:56
  • 1
    Your question is not clear. what errors are you getting? Commented Sep 4, 2015 at 8:29

1 Answer 1

1

This binding

<p>Posted By, {{ getAuthor(topic.author_id).email }}</p>

assumes that getAuthor returns an object, but it doesn't, even with proper return statement - because asynchronous request takes place, and adbFactory chain will apparently return a promise, not an object. And doing adbFactory.get every time getAuthor bindings are being watched would be bad performance-wise - json result has to be parsed constantly, even with $http cache.

A suitable solution for caching and binding service results to the scope (and a precursor to full-blown model) is

var authors = $cacheFactory('authors');
$scope.getAuthor = function(_id) {
    if (!authors.get(_id)) {
        authors.put(_id, {});
        adbFactory.get($http, 'get users id ' +_id+ ' spec', false).success(function(data){
            authors.put(_id, data);
        });
    }

    return authors.get(_id);
};
Sign up to request clarification or add additional context in comments.

6 Comments

but then wht is the cache factory?
A built-in service that provides application-wide data storage docs.angularjs.org/api/ng/service/$cacheFactory , inject it into the controller.
would it be best to use? wht if the cache is cleared?
Yes, it is a good option, you can store data objects from requests by your own, but $cacheFactory keeps you from reinventing the wheel. You have full control over the cache, it won't be cleared unless you want it to.
Im now getting a Error: [$rootScope:infdig] error, from creaating a new array of objects from everything the getAuthor is called in a loop, anyway to get beside that?
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.