Running Untrusted Code in Node

F70874714f4bb31b2ab4b6c70de39b04?s=47 Dave Wasmer
February 25, 2014

Running Untrusted Code in Node

Running untrusted code in Node in a safe mode while handling the lode.

F70874714f4bb31b2ab4b6c70de39b04?s=128

Dave Wasmer

February 25, 2014
Tweet

Transcript

  1. Running untrusted code in Node in a safe mode while

    handling the lode
  2. lode?

  3. Dave Wasmer @davewasmer Developer @ Kinvey yep, this slide …

  4. Kinvey Backend as a service … and this one.

  5. What goes into backend as a service?

  6. None
  7. Lots o’ stuff • Data storage • User management •

    Twitter, Facebook, G+, LinkedIn • OAuth, LDAP, Active Directory • File storage • don’t forget CDN delivery • Push notifications • Emails • 3rd Party API Integration • Analytics • a whole lot more ..
  8. What if CRUD ain’t enough?

  9. enter: Business Logic!

  10. Run your code on our servers

  11. Custom JavaScript execution?!

  12. eval(customerCode); // Genius, mirite? NO!

  13. The Problem We needed a safe, scalable way to run

    arbitrary (possibly malicious) JavaScript on our servers.
  14. Safety • Can’t allow access to: • filesystem • shared

    memory • Kinvey internals • State is evil!
  15. Scalablity • Needs to scale horizontally • i.e. spin up

    new instances on-demand • automatically add to resource pool • Optimize for usage • not running huge computations - short, frequent bursts of activity • 2x per API request is possible!
  16. Our solution to scalability KCS KCS KCS KBL KBL KBL

    Redis Work Master Child Child Child Child
  17. Our solution to scalability KCS KCS KCS KBL KBL KBL

    Redis Work Master Child Child Child Child
  18. Our solution to scalability KCS KCS KCS KBL KBL KBL

    Redis Work Master Child Child Child Child
  19. Our solution to scalability KCS KCS KCS KBL KBL KBL

    Redis Work Master Child Child Child Child
  20. Our solution to scalability Work Master Child Child Child Child

  21. Safety Concerns • How to run arbitrary JS code? •

    Three issues • System access (filesystem, network, etc) • Application access (application state, data, etc) • Stupidity / DoS (while (true), forgot to signal async completed)
  22. System access • Filesystem • Severely limited or none •

    Network • Partially limited
  23. Our solution to system access ! // Setting things up

    ! try { script = vm.createScript(codeAsStr); } catch (e) { // syntax error! } ! sandbox = generateNewSandbox()
  24. generateNewSandbox = function(){ ! var sandbox = {}; sandbox.complete =

    function(){ runNextTask(); }; sandbox.whateverYouWant = function(){ ... } return sandbox; ! } Our solution to system access
  25. ! // Running the untrusted script try { script.runInNewContext(sandbox) }

    catch (e) { // e will be any immediate (synchronous) // runtime errors } Our solution to system access
  26. Application access • Data • Permissions

  27. Our solution to application access ! // inside generateNewSandbox() !

    sandbox.db = { find: function(query, callback) { // do db stuff callback(null, result) // <- Careful! }, ...
 }
  28. Stupidity / DoS • while (true) {} // single-threaded ftw!

    • function onPreSave(req, res, modules) {
 doSomeAsyncStuff()
 } // kthxbai • function doSomeAsyncStuff() {
 setTimeout(function(){ 
 throw new Error() 
 }, 100000); // muhahaha
 }
  29. Our solution to stupidity / DoS Work Master Child Child

    Child Child
  30. Our solution to stupidity / DoS Work Master Child Child

    Child Child
  31. Our solution to stupidity / DoS ! // For handling

    callback errors process.on(‘uncaughtException’, function(){ // handle it here });
  32. Wrap-up