2012-08-13 28 views
21

Próbuję użyć Backbone z interfejsem API.Przesłanianie funkcji analizy szkieletu

Domyślny format odpowiedzi API:

{ 
somemetadatas:xxx , 
results:yyy 
} 

Czy to sprowadzić do jednego modelu lub kolekcji.

Więc o ile wiem, że mogę zastąpić funkcję Backbone parse z:

parse: function (response) { 
    return response.results; 
}, 

Ale widziałem w the documentation:

analizowaniacollection.parse(response)

parse jest wywoływana przez Backbone, gdy tylko ac Modele ollection są zwracane przez serwer podczas pobierania. Funkcja jest przekazywana do surowego obiektu response i powinna zwracać tablicę atrybutów modelu, która ma zostać dodana do kolekcji. Domyślna implementacja nie jest opcją, po prostu przechodząc przez odpowiedź JSON. Zastąp to, jeśli chcesz pracować z istniejącym API lub lepiej przestrzeni nazw swoich odpowiedzi. Zauważ, że później, jeśli Twoja klasa modelu ma już funkcję parse, zostanie ona uruchomiona względem każdego pobranego modelu .

Więc jeśli mam odpowiedź dla kolekcji sprowadzić tak:

{ 
somemetadatas:xxx , 
results:[user1,user2] 
} 

Pierwszy parse funkcja na zbiorze rozpakuje [user1,user2].

Ale doc mówi:

Zauważ, że potem, jeśli klasa modelu ma już parse funkcję, to będzie działać przeciwko sobie pobrane model.

więc będzie starał się znaleźć response.results; na user1 i user2

muszę obie funkcje analizowania modelu i kolekcji, ponieważ oba modele i zbierania dane osobowe będą pod atrybutem wynikowej.

Ale jeśli pobieram kolekcję, nie chcę, aby funkcja analizowania modelu była używana z pojedynczym elementem tablicy.


Czy istnieje rozwiązanie tego problemu?

myślę roztworu gdzie moja kolekcja funkcja parse zmieni coś takiego:

{ 
somemetadatas:xxx , 
results:[user1,user2] 
} 

w coś takiego:

[ {results.user1} , {results.user2} ] 

więc, że funkcja modelu parse nie zawiedzie na zasadzie pobieranie kolekcji. Ale jest trochę hacky ... czy istnieje jakieś eleganckie rozwiązanie tego problemu?


Nawiasem mówiąc, jak moje API będzie zawsze przynosi rezultaty tej postaci, jest to możliwe, aby zastąpić domyślnie funkcję parse wszystkich moich modeli i kolekcji? (Niestety, jestem JS noob ...)

Odpowiedz

27

Możesz sprawdzić, czy otrzymane dane są opakowane przez członka results i odpowiednio zareagować. Na przykład,

var M = Backbone.Model.extend({ 
    parse: function (data) { 
     if (_.isObject(data.results)) { 
      return data.results; 
     } else { 
      return data; 
     } 
    } 
}); 

A Fiddle http://jsfiddle.net/9rCH3/

Jeśli chcesz uogólniać ten problem, albo wywodzą się wszystkie klasy model z tej klasy bazowej lub zmodyfikować prototyp szkieletowej do świadczenia tej funkcji:

Backbone.Model.prototype.parse = function (data) { 
    if (_.isObject(data.results)) { 
     return data.results; 
    } else { 
     return data; 
    } 
}; 

http://jsfiddle.net/9rCH3/1/

+0

dzięki spróbuje że –

+0

Mam zwyczaj 'parse' nazywa, ale nie ma wpływu - wartości w modelu są tylko początkowy identyfikator, który został dostarczony w konstruktorze ... Wszelkie pomysły? – Dor

+0

Jeśli próbujesz coś zrobić z identyfikatorami modelu, nie możesz od wersji 1.1.0. http://backbonejs.org/#changelog Jeśli to nie jest to, musisz zadać pytanie. – nikoshr

1

Parsować należy również w Collecti na.

var EgCollection = Backbone.Collection.extend({ 
    parse: function (data) { 
     if (_.isObject(data.results)) { 
      return data.results; 
     } else { 
      return data; 
     } 
    } 
}); 

http://backbonejs.org/#Collection-parse