mauritslamers / Thoth

A Node-based communications hub for multi-user SproutCore applications, serving as a unified database interface and automating distribution of data changes
http://devmt.hku.nl/~maurits/doku.php?id=thoth:start
43 stars 4 forks source link

Update record fails using DiskStore #2

Open ralfschimmel opened 13 years ago

ralfschimmel commented 13 years ago

Scenario, record in SC.READY state is edited and saved / committed. Thoth is using a DiskStore.

Client sends:

{"updateRecord":{"bucket":"customer","primaryKey":"id","key":"@64JXA9I7FZorkac5LzQ2f9BvbaIuG0K3","application":"Bw","properties":[{"key":"name","type":"String"}],"relations":[{"type":"toMany","isMaster":true,"bucket":"address","primaryKey":"id","propertyName":"addresses","oppositeType":"toMany"},{"type":"toMany","isMaster":true,"bucket":"person","primaryKey":"id","propertyName":"persons","oppositeType":"toMany"},{"type":"toMany","isMaster":true,"bucket":"assignment","primaryKey":"id","propertyName":"assignments","oppositeType":"toMany"}],"combineReturnCalls":true,"record":{"name":"tetststasdasdasd","id":"@64JXA9I7FZorkac5LzQ2f9BvbaIuG0K3"},"returnData":{"requestCacheKey":"JemnH73QCwHQezB3zrxK5tFQtyOqEf3C"}}}

Server does not respond and displays the following error:

29 Jun 21:09:08 - ThothServer: Caught an exception which was not caught elsewhere: TypeError: Cannot call method 'copy' of undefined 29 Jun 21:09:08 - stack trace: TypeError: Cannot call method 'copy' of undefined at /Users/ralf/Projects/Thoth/lib/core/mixins/junctionrelations.js:244:43 at [object Object].fetchDBRecords (/Users/ralf/Projects/Thoth/lib/core/MemStore.js:119:18) at [object Object].updateRelation (/Users/ralf/Projects/Thoth/lib/core/mixins/junctionrelations.js:242:12) at [object Object].updateRecord (/Users/ralf/Projects/Thoth/lib/core/Store.js:344:18) at /Users/ralf/Projects/Thoth/lib/core/mixins/store_actions.js:196:20 at [object Object].checkPolicy (/Users/ralf/Projects/Thoth/lib/core/Policies.js:129:8) at [object Object].onUpdate (/Users/ralf/Projects/Thoth/lib/core/Server.js:1103:23) at [object Object]. (/Users/ralf/Projects/Thoth/lib/core/Server.js:165:42) at [object Object].emit (events.js:67:17) at [object Object]._onClientMessage (/Users/ralf/Projects/Thoth/lib/core/SocketListener.js:315:35)

mauritslamers commented 13 years ago

Problem is caused by two factors: Thoth assumes the presence of a keys array in the relation data, which isn't there in the case of this request. ThothSC should always send a keys array, even if empty. Thoth however should not crash by the property not being present. The Thoth side has already been fixed, the ThothSC side will be done later.

ralfschimmel commented 13 years ago

Now there still is a problem, though of another nature:

Trying to send message: {"updateRecord":{"bucket":"person","primaryKey":"id","key":"@RegS2hy8mcQhRUh2mEKldmmDIydpCkR","application":"Bw","properties":[{"key":"isActor","type":"Boolean"},{"key":"isActive","type":"Boolean"},{"key":"firstName","type":"String"},{"key":"suffix","type":"String"},{"key":"surName","type":"String"},{"key":"gender","type":"String"},{"key":"birthDate","type":"Date"},{"key":"email","type":"String"},{"key":"homePhone","type":"String"},{"key":"workPhone","type":"String"},{"key":"mobilePhone","type":"String"},{"key":"username","type":"String"},{"key":"password","type":"String"}],"relations":[{"type":"toOne","isMaster":true,"bucket":"customer","primaryKey":"id","propertyName":"customer","oppositeType":"toMany","keys":"@fPWxG37t4INmJTpJXGO0f3fiC8kkNw"},{"type":"toMany","isMaster":true,"bucket":"address","primaryKey":"id","propertyName":"addresses","oppositeType":"toMany"},{"type":"toMany","isMaster":true,"bucket":"assignmentactor","primaryKey":"id","propertyName":"assignments","oppositeType":"toMany"}],"combineReturnCalls":true,"record":{"id":"@RegS2hy8mcQhRUh2mEKldmmDIydpCkR","isActor":false,"password":"","mobilePhone":"","workPhone":"","homePhone":"","email":"","gender":"","surName":"","suffix":"","firstName":"test23"},"returnData":{"requestCacheKey":"m73ZTBQK8gZA3NOidcoORqVvf5yW7H4Xi"}}}

30 Jun 08:43:21 - ThothServer: Caught an exception which was not caught elsewhere: TypeError: Object @fPWxG37t4INmJTpJXGO0f3fiC8kkNw has no method 'copy' 30 Jun 08:43:21 - stack trace: TypeError: Object @fPWxG37t4INmJTpJXGO0f3fiC8kkNw has no method 'copy' at /Users/ralf/Projects/Thoth/lib/core/mixins/junctionrelations.js:244:58 at [object Object].fetchDBRecords (/Users/ralf/Projects/Thoth/lib/core/MemStore.js:119:18) at [object Object].updateRelation (/Users/ralf/Projects/Thoth/lib/core/mixins/junctionrelations.js:242:12) at [object Object].updateRecord (/Users/ralf/Projects/Thoth/lib/core/Store.js:344:18) at /Users/ralf/Projects/Thoth/lib/core/mixins/store_actions.js:196:20 at [object Object].checkPolicy (/Users/ralf/Projects/Thoth/lib/core/Policies.js:129:8) at [object Object].onUpdate (/Users/ralf/Projects/Thoth/lib/core/Server.js:1103:23) at [object Object]. (/Users/ralf/Projects/Thoth/lib/core/Server.js:165:42) at [object Object].emit (events.js:67:17) at [object Object]._onClientMessage (/Users/ralf/Projects/Thoth/lib/core/SocketListener.js:315:35)

ralfschimmel commented 13 years ago

Fix:

if (relation.keys) {
                if (!relation.keys.constructor.toString().indexOf("Array") == -1) {
                        var relationKeys = relation.keys.copy();
                } else {
                        var relationKeys = [relation.keys];
                }
} else {
                var relationKeys = [];
}
ralfschimmel commented 13 years ago

Well had to hassle a bit but I created a pull request :-) Now i have a clean setup so I can do this more often (for Thoth and Thoth-SC)

mauritslamers commented 13 years ago

Thanks a lot for noticing this issue. The reason it surfaced at all turned out to be a very severe oversight in the recent rewrite of ThothSC, in which relational data was stripped from the record without being put back on the relations graph. I found it while writing the tests for ThothSC. While this is now fixed in ThothSC, I'll leave it open for the moment to later fix this vulnerability in Thoth.