2012-04-18 14 views
27

Podczas przesłonięcia synchronizacji szkieletu, zarówno model/collection .save()/fetch() używa tej samej metody synchronizacji szkieletu, więc jaki jest najlepszy sposób sprawdzenia, czy co otrzymuje Backbone.sync to model lub kolekcja modeli?Sprawdź, czy coś jest modelem lub kolekcją w szkielecie js

Jako przykład:

Backbone.sync = function(method, model, options){ 
    //Model here can be both a collection or a single model so 
if(model.isModel()) // there is no isModel or isCollection method 
} 

Chyba szukam „bezpiecznej” najlepszych praktyk, mogłem czeku oczywiście dla niektórych atrybutów lub metod, które tylko model lub zbiór mają, ale wydaje hackish, czy nie powinien istnieć lepszy oczywisty sposób? I prawdopodobnie nie mogę go znaleźć.

Dzięki!

Odpowiedz

56

Można też spróbować instanceof tak:

Backbone.sync = function(method, model, options) { 
    if (model instanceof Backbone.Model) { 
    ... 
    } else if (model instanceof Backbone.Collection) { 
    ... 
    } 
} 
2

Jest to równie hackowate, ale kolekcja kręgosłupa ma właściwość modelu, a model nie - jest sam w sobie modelem.

Być może bezpieczniejszą metodą jest model.toJSON() i zobacz, czy wynik jest obiektem lub tablicą. Prawdopodobnie użyjesz metody model.toJSON() w niestandardowym Backbone.sync, więc jest to dość kosztowne pod względem obliczeniowym, ale i tak by się to zdarzyło.

+0

upvote bo sprawdzania własność 'length' (tylko Collection ...?!?) wczoraj w szybkim kodowaniu! Sprawdzanie "modelu" jest genialne w porównaniu. Ha ha. – eightyfive

+3

Nie powinniście liczyć na takie rzeczy, ponieważ mogą się zmienić w przyszłości i złamać kod. Użyj słowa kluczowego instanceof zgodnie z opisem :) –

0

Możesz zrobić coś takiego.

Backbone.Model.prototype.getType = function() { 
    return "Model"; 
} 

Backbone.Collection.prototype.getType = function() { 
    return "Collection"; 
} 

if(model.getType() == "Model") {} 
if(model.getType() == "Collection"){} 
+4

To bardzo zły pomysł, prawie niemożliwy do utrzymania, gdy aplikacja staje się bardziej skomplikowana. A co się stanie, jeśli obiekt potrzebuje metody getType(), która mówi o typie samochodu zamiast typu obiektu szkieletowego? –

+0

@NicolasZozol nie zgadzam się. Nie rozumiem, jak trudno jest to utrzymać, a drugi punkt jest po prostu niesprawiedliwy. Możesz wywołać powyższe metody, jak tylko chcesz. Na przykład 'getBackboneObjectType', który z pewnością nie spowoduje konfliktów nazw. –

+0

Powód, dla którego jest to złe, wymaga od realizatora śledzenia typów obiektów zawartych w bibliotece trzeciej strony i tworzenia nowego prototypu getType za każdym razem, gdy nowy typ zostanie wprowadzony do przyszłych wersji szkieletu. Dodatkowo narażasz się na błędy w pisowni typów bez łatwej do wykrycia metody (ponieważ wszystko odbywa się za pomocą porównań ciągów znaków). Użycie instancji instanceof pozwala kompilatorom JavaScript (takim jak node.js) wykryć błędy pisowni, a kompilacja nie powiedzie się. zmiana nazwy w zaktualizowanej wersji Szkieletu, ułatwiając identyfikację przełomowych zmian. –

10

@ odpowiedź fiskers7 za współpracuje z głębokim rozszerzenia:

 var Item = Backbone.Model.extend({ 
      className : 'Item', 
      size :10 
     }); 

     var VerySmallItem = Item.extend({ 
      size :0.1 
     }); 

     var item = new Item(); 
     var verySmall = new VerySmallItem(); 

     alert("item is Model ?" + (item instanceof Backbone.Model)); //true 
     alert("verySmall is Model ?" + (verySmall instanceof Backbone.Model)); //true 
0

Nie jestem do końca pewien, jak czuję się o to, ponieważ wydaje się nieco hackish, ale nie mogę dokładnie myśleć, dlaczego byłoby to super złe w tej chwili.

Zdecydowanie proste i szybciej niż „instancją” check (jestem zakładając, że nie będzie wymienić jakieś inne funkcje „isBBModel/Collection” na swoich obiektach?)

Backbone.Model.prototype.isBBCollection = function() { return false; } 
Backbone.Model.prototype.isBBModel = function() { return true; } 
Backbone.Collection.prototype.isBBCollection = function() { return true; } 
Backbone.Collection.prototype.isBBModel = function() { return false; } 
Powiązane problemy