3

I was looking at Emberjs recently and found this useful article written by one of its main contributors: Advice on & Instruction in the Use Of Ember.js

It walked me through an example which fetch a list of user data from a server and render them on screen. I'll briefly explain how it worked:

  1. The app contacts the server to fetch a list of user data though ajax call.
  2. At the end of the ajax call an empty enumerable is returned immediately, which is later used as a property of a controller.
  3. Once the ajax call is completed, it populates the enum with data which in turns update the controller's property, and finally triggers an automatic re-rendering.

This works fine as long as the list is not revisited. As a user revisit the list, say he/she navigates to another state and then comes back, the logic will be triggered again, fetching the data from server and populates the list. However, the list this time is not empty! Thus we have a list of duplicated data. I would like to resolve this by clearing the content of the list when the ajax call is successful. Below is the code for the ajax call:

allAwesomebergs: [],
fetch: function(){
    $.ajax({
        url: 'https://api.github.com/repos/emberjs/ember.js/contributors',
        dataType: 'jsonp',
        context: this,
        success: function(response) {
            response.data.forEach(function(awesomeberg){
                this.allAwesomebergs.addObject(App.Awesomeberg.create(awesomeberg))
            }, this);
        }
    });
    return this.allAwesomebergs;
},

The above code does not clear the content of the list. I tried adding a line "allAwesomebergs = []" at the beginning of the success function, but what I got was just a blank screen. I thought I may not be doing this correctly, but I looked at the document from Ember and didn't see anything about clearing the content of an Enumerable.

Thus the question is: what is the easiest way to resolve this duplicate loading issue? Clearing the content before hand seems the most obvious but I can't make it work.

Xavier_Ex
  • 8,432
  • 11
  • 39
  • 55

2 Answers2

4

You can call clear() before you start adding the new objects. See this documentation.

New code would be:

allAwesomebergs: [],
fetch: function(){
    $.ajax({
        url: 'https://api.github.com/repos/emberjs/ember.js/contributors',
        dataType: 'jsonp',
        context: this,
        success: function(response) {
            this.allAwesomebergs.clear();
            response.data.forEach(function(awesomeberg){
                this.allAwesomebergs.addObject(App.Awesomeberg.create(awesomeberg))
            }, this);
        }
    });
    return this.allAwesomebergs;
},
CraigTeegarden
  • 8,173
  • 8
  • 38
  • 43
  • I think this wont work since allAwesomebergs is a plain iavascript array. – mavilein Jan 04 '13 at 22:50
  • 1
    I believe ember automatically applies some of it's additional functionality to the Array class. – CraigTeegarden Jan 04 '13 at 23:17
  • 1
    Thanks for the anwser! @mavilein yes by default ember will wrap native javascript objects into their ember versions. By all means I tried this and it worked. As long as I am working with the same array that I used to work with and clearing that very same array won't mess up the binding. – Xavier_Ex Jan 07 '13 at 15:20
-2

I think your approach was ok, but it should have been:

this.allAwesomebergs = []

It is all about the this in front of it. So clear is not needed here.

mavilein
  • 11,648
  • 4
  • 43
  • 48
  • 1
    I believe this creates a new javascript array, which would ruin the ember.js bindings. See this question: http://stackoverflow.com/questions/1232040/how-to-empty-an-array-in-javascript – CraigTeegarden Jan 04 '13 at 23:14
  • Thanks for answering, but as @c4p pointed out that this won't work. The code snippet I gave was in an ajax call and I had set the context to "this" which means the "this" pointer makes no difference in this case. – Xavier_Ex Jan 07 '13 at 15:18