balderdashy / sails

Realtime MVC Framework for Node.js
https://sailsjs.com
MIT License
22.83k stars 1.95k forks source link

[Serious issue] Update wrong record during high traffic requests #2130

Closed parnurzeal closed 10 years ago

parnurzeal commented 10 years ago

Salis-version: 0.10.0-rc7 Connector: sails-mysql

I now encounter a problem that sails gets update into the "WRONG" record. What I tried to do was just sending lots of normal GET requests to sails and tried to update 5-6 different records at the same time. What happened was data that got update in other field got update into other records. This is serious issue.

Follows are my cutting part of related schema and custom controllers I am using:

ServerController.js (controller)

'update': function(req,res,next){
     // [UPDATE]
     // curl localhost:1337/server/update -i -X POST -H 'Content-Type: application/json' -d '{"serial_no":"QTFC9S3060011"}'
     alldata = req.params.all();
     delete alldata.id;
     alldata.serial_no && delete alldata.serial_no;
     serial_no = req.param('serial_no');
     Server.findOne({serial_no:serial_no}).exec(function(err, theServer){
       if (err) return next(err);
       if (!theServer) return res.send(400, "Server not found.");
       for(key in alldata){
         theServer[key] = alldata[key];
       }
       theServer.save(function(err, updatedServer){
         if(err) return next(err);
         else {
           Server.publishUpdate(updatedServer.id, updatedServer);
           res.json(updatedServer);
         }
       });
     });
  },

Server.js (model)

module.exports = {
    autosubscribe: ['create','update','destroy'],
    schema:true,
  attributes: {
        serial_no: {
            type: 'string',
            required: true,
            unique: true
        },
        prov_state: {
            model: 'Prov_state',
            required: true,
        },
        prov_process_status: {
            type: 'string',
            required: true,
            enum: ['passed', 'processing', 'failed']
        },
    },
}

Prov_state.js

module.exports = {
  schema:true,
  attributes: {
    desc: 'string',
    servers:{
      collection: 'server',
      via: 'prov_state'
    }
  }
};

What I did is just looping curl GET to url http://localhost:1337/server

And also running update on 4 records to change prov_state number from 1-4 ( increasing 1 number per second and change back to 1 if it is already 4) curl localhost:1337/server/update -i -X POST -H 'Content-Type: application/json' -d '{"serial_no":"QTFC9S3060011", "prov_state":"[number 1->4]"}'

but updating 1 record to change prov_state number from 5-12 ( increasing 1 number per second and change back to 5 if it is already 12) curl localhost:1337/server/update -i -X POST -H 'Content-Type: application/json' -d '{"serial_no":"QTFC9S3060011", "prov_state":"[number 5->12]"}'

What happened was other 4 records got update to some different number like 5 - 12 !!!

I don't think I am implementing anything weird in my custom controller. Please do help if I use the version that having the problem and need to upgrade to other version.

parnurzeal commented 10 years ago

More information about DB. I have tried both mysql-5.6.15-osx10.7-x86_64 on mac os x. And using MariaDB10 on CentOS6.3

They both have the problem.

edy commented 10 years ago

prefix all your variables with var: var alldata = req.params.all(); var serial_no = ...

and try again

parnurzeal commented 10 years ago

Hi @edy,

What a dumb I am! Thanks very much! This solved my problem.

albertosouza commented 10 years ago

@parnurzeal use .jshint that warns you that kind of thing The Sublime text 3 has the sublime linter and have to grunt and npm modules for jshint

parnurzeal commented 10 years ago

@albertosouza Very useful. Thank you very much! I am using it now.