Open azpublic opened 9 years ago
Ok so I've tracked down this issue a little further. It seems related to the lengh of the nested collection that is not modified correctly during the first call to set() on the model in my example. The length is not decremented correctly during the set() and therefore instead of having an expected lenght of 2 after the call to the first set, the nested collection has length of 4.
Here's why (warning : nasty bug ahead):
It seems that on the first call to set() (the one after fetch has successfully populated our collection), the model goes through documentModelSet() then the nested collection (jobTasksByDate in our example) is being processed and documentCollectionSet() is called which itself triggers Backbone.js regular set() method and then Backbone.js remove() is called to "// Remove nonexistent models if appropriate." (see backbone's source near line 720 ).
This remove() call iterates through the models and makes this very specific call (near line 648) which breaks backbone-documentmodel :
model = models[i] = this.get(models[i]); //(line 648)
if (!model) continue; //(line 649)
...
this.length--;
the call to this.get(models[i]); is what breaks it because it returns undefined whereas it should return the model / attribute that preexisted in our nested collection. Since it is undefined the collection's length is not decremented appropriately by backbone hence our wrong collection length during our seccond call to set() on our model.
I have yet to figure out how to fix this and if it is only related to primitive arrays turned into documentmodel collections or not.
Any hints appreciated.
P.S. this project does not seem very active lately. Is anyone still supporting it ?
Ok so here's the final test that actually reproduces the problem. It had nothing to do with fetch() or with a parent DocumentColelction. The problem was actually with DocumentModels containing arrays of primitives. My pull request with fix will follow.
var json1 = {
"objectId": "545c8659e7e0a59538543a79",
"jobTasksByDate": [
"task1"
]
};
var json2 = {
"objectId": "545c8659e7e0a59538543a79",
"jobTasksByDate": [
"task2"
]
};
var json3 = {
"objectId": "545c8659e7e0a59538543a79",
"jobTasksByDate": [
"task3"
]
};
var j = new Job10(json1);
j.set(json2);
j.set(json3);
Hmmm... I think I may have found the same issue. Here's my workaround:
https://github.com/icereval/backbone-documentmodel/pull/25
Also includes a good test written if you want to check your solution. Here's an additional test that fails right now:
https://github.com/odbol/backbone-documentmodel/commit/90574963e1bac1c0af3ee4eb532c936a1db8caef
When calling fetch() to populate a DocumentCollection, then calling set() 2 times on one of the models of the collection triggers an exception if the model data contains an array.
example :
content of the json :
The error is thrown durin the 2nd call to set() on the model that is inside the collection and throws :
Uncaught TypeError: Cannot read property 'cid' of undefined
It seems only to happen when fetch is used and only when the underlying model has a member array.
I am having a hard time figuring out why.