Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Developing Cloud9 in Cloud9

Developing Cloud9 in Cloud9

Cloud9 is entirely built on Node.js and can be used to debug and develop other Node.js applications. This fun recursive fact we used to very quickly use the tool we built to refine and develop the tool we are building. The opensource version of Cloud9 can be pulled from Github and the app is served from a single Node.js process. Built on Socket.IO and Connect for the server, Cloud9 has a full WebDAV implementation in Node.js, and can start other Node.js processes and connect to its debugport to control the application. In this talk, Rik will go through the overall architecture of Cloud9, touching on many design choices made for writing the system in Node.js, dealing with Asynchronous code, and what scaling characteristics that came up.

B083b8207ccd0744a5abb18c8e75d24d?s=128

Sergi Mansilla

October 02, 2011
Tweet

More Decks by Sergi Mansilla

Other Decks in Programming

Transcript

  1. Developing  Cloud9  in  Cloud9 Sergi  Mansilla Brescia,  24  September  2011

    Sunday, October 2, 11
  2. @sergimansilla Developer  -­‐  Ajax.org hEp://github.com/sergi Language  programming  geek Sunday, October

    2, 11
  3. What  is  it? It  is  to  Eclipse  what  Google  Docs

     is  to  Office Easiest  way  to  create  Nodejs  apps  (including  Windows) Free  for  public  projects Open  Source Fully  funcXonal  IDE Sunday, October 2, 11
  4. Developers  carry  too  much  weight  nowadays Sunday, October 2, 11

  5. Developers  carry  too  much  weight  nowadays Sunday, October 2, 11

  6. and  someXmes  too  liEle debugging? code analysis? deployment? source control?

    Sunday, October 2, 11
  7. Other  advantages Runs  on  any  computer  with  a  modern  browser

    No  configuraXon  needed Deployment  in  the  cloud Share  by  URL You  can  use  your  own Sunday, October 2, 11
  8. So  why  not  let  the  IDE  wait  for  you  in

     the  Clouds? Sunday, October 2, 11
  9. 1  year  ago Sunday, October 2, 11

  10. We  build  Cloud9  IDE  with  Cloud9  IDE Sunday, October 2,

    11
  11. Today Sunday, October 2, 11

  12. What  the  eye  doesn’t  meet Sunday, October 2, 11

  13. Proxy  servers What  the  eye  doesn’t  meet Sunday, October 2,

    11
  14. Proxy  servers File  servers  (webDAV  based) What  the  eye  doesn’t

     meet Sunday, October 2, 11
  15. Proxy  servers File  servers  (webDAV  based) Database  interacXon  (redis) What

     the  eye  doesn’t  meet Sunday, October 2, 11
  16. Proxy  servers File  servers  (webDAV  based) Database  interacXon  (redis) Hosted

     running/debugging What  the  eye  doesn’t  meet Sunday, October 2, 11
  17. Proxy  servers File  servers  (webDAV  based) Database  interacXon  (redis) Hosted

     running/debugging Deployment  to  cloud  services What  the  eye  doesn’t  meet Sunday, October 2, 11
  18. Proxy  servers File  servers  (webDAV  based) Database  interacXon  (redis) Hosted

     running/debugging Deployment  to  cloud  services GitHub  /  BitBucket  /  FTP  hardcore  acXon What  the  eye  doesn’t  meet Sunday, October 2, 11
  19. Sunday, October 2, 11

  20. Full  nodejs  stack  (except  for  redis  and  nginx) 50000+  users

    Big  producXon  system  in  nodejs 100+  concurrent  users  and  growing Fast. 1  main  server  4Gb 1  staXc  server 2  runVm Sunday, October 2, 11
  21. Ide Server reverse proxy NGINX project.user.c9.io *.c9.io run VM control

    node process control Client static.c9.io Sunday, October 2, 11
  22. IDE Server Client Connect JSDav Socket IO Sunday, October 2,

    11
  23. Foundations APF - High performance UI library Socket.io - Realtime

    socket networking jsDAV - Filesystem layer ACE - Source code editor in JS Sunday, October 2, 11
  24. The best stuff That thing is fast Never blocks As

    low-level as you want, and makes it easy Running multiple servers in one process is awesome Sunday, October 2, 11
  25. It hasn’t been a bed of roses Sunday, October 2,

    11
  26. Requires discipline Sunday, October 2, 11

  27. High learning curve Sunday, October 2, 11

  28.                    

                                                                               db.isCommercialProject(pid,  function(err,  isCommercial)                                                                                                        if  (isCommercial)  {                                                                                                                var  transactionData  =  {                                                                                                                        members:  members,                                                                                                                        extensions:  extensions                                                                                                                };                                                                                                                _self.setProjectTransactions(db,  type,  id,  tran                                                                                                                        if  (err)                                                                                                                                return  cleanup(err);                                                                                                                        end();                                                                                                                });                                                                                                        }                                                                                                        else  {                                                                                                                app.get('/index',  function(req,  res,  next)  {                                                                                                                        User.get(req.params.userId,  function(err,  u                                                                                                                                if(err)  next(err);                                                                                                                                db.find({user:  user.name},  function(err                                                                                                                                        if(err)  next(err);                                                                                                                                        cursor.toArray(function(err,  items)                                                                                                                                                if(err)  next(err);                                                                                                                                                res.send(items);                                                                                                                                        });                                                                                                                                });                                                                                                                        });                                                                                                                });                                                                                                        }                                                                                                        function  end()  {                                                                                                                db.getProject(pid,  function(err,  project)  {                                                                                                                        if  (err)                                                                                                                                return  cleanup(err);                                                                                                                        callback(null,  project);                                                                                                                });                                                                                                        }                                                                                                });                                                                                        });                                                                                });                                                                        });                                                                });                                                        });                                                });                                        });                                });                        });                });        }; “Christmas  tree”  code (also  known  as  callbacks  from  hell) looks  familiar? Sunday, October 2, 11
  29.                    

                                                                               db.isCommercialProject(pid,  function(err,  isCommercial)                                                                                                        if  (isCommercial)  {                                                                                                                var  transactionData  =  {                                                                                                                        members:  members,                                                                                                                        extensions:  extensions                                                                                                                };                                                                                                                _self.setProjectTransactions(db,  type,  id,  tran                                                                                                                        if  (err)                                                                                                                                return  cleanup(err);                                                                                                                        end();                                                                                                                });                                                                                                        }                                                                                                        else  {                                                                                                                app.get('/index',  function(req,  res,  next)  {                                                                                                                        User.get(req.params.userId,  function(err,  u                                                                                                                                if(err)  next(err);                                                                                                                                db.find({user:  user.name},  function(err                                                                                                                                        if(err)  next(err);                                                                                                                                        cursor.toArray(function(err,  items)                                                                                                                                                if(err)  next(err);                                                                                                                                                res.send(items);                                                                                                                                        });                                                                                                                                });                                                                                                                        });                                                                                                                });                                                                                                        }                                                                                                        function  end()  {                                                                                                                db.getProject(pid,  function(err,  project)  {                                                                                                                        if  (err)                                                                                                                                return  cleanup(err);                                                                                                                        callback(null,  project);                                                                                                                });                                                                                                        }                                                                                                });                                                                                        });                                                                                });                                                                        });                                                                });                                                        });                                                });                                        });                                });                        });                });        }; “Christmas  tree”  code (also  known  as  callbacks  from  hell) looks  familiar? Sunday, October 2, 11
  30. Error handling is hard Never EVER throw Sunday, October 2,

    11
  31. Learn (and maintain) conventions Sunday, October 2, 11

  32. Don’t mix sync/async (unless you know what you’re doing) streamline.js

    stratified JavaScript Common Node But if you do be sure to check those Sunday, October 2, 11
  33. Clean after yourself and minimize side-effects Sunday, October 2, 11

  34. No CI = it’s not gonna work Sunday, October 2,

    11
  35. Modules Sunday, October 2, 11

  36. Get your hands dirty Sunday, October 2, 11

  37. Get your hands dirty Everything is new Or under heavy

    development Or sucks Manual digging often necessary Fix it yourself Authors love pull requests Sunday, October 2, 11
  38. Roll your own Sunday, October 2, 11

  39. Roll your own Node.js is still young Some modules are

    still missing Be prepared to write your own Contribute back! Sunday, October 2, 11
  40. Cloud9 OSS side-effects Cloud9 IDE (github.com/ajaxorg/cloud9) jsDAV (github.com/ajaxorg/jsdav) jsFTP (github.com/ajaxorg/jsftp)

    node-github (github.com/ajaxorg/node-github) ACE (github.com/ajaxorg/node-github) async.js (github.com/ajaxorg/async.js) ... Sunday, October 2, 11
  41. Demo time! Sunday, October 2, 11

  42. What’s coming Sunday, October 2, 11

  43. What’s coming Collaboration Sunday, October 2, 11

  44. Sunday, October 2, 11

  45. What’s coming Moar languages Sunday, October 2, 11

  46. What’s coming Code analysis Code completion Refactoring Sunday, October 2,

    11
  47. What’s coming Git UI Sunday, October 2, 11

  48. Sunday, October 2, 11

  49. Is node.js ready for production? Sunday, October 2, 11

  50. Is node.js ready for production? YES! (But you will have

    to work at it) Sunday, October 2, 11
  51. Questions? Sunday, October 2, 11

  52. Thanks! Rate  my  talk:    hEp://joind.in/talk/view/3710 Twitter: @sergimansilla Email: sergi@ajax.org

    http://c9.io or http://cloud9ide.com We are hiring!!! Sunday, October 2, 11
  53. Images • http://www.flickr.com/photos/earlg/280538938/sizes/o/in/photostream/ • http://www.flickr.com/photos/imaginedreality/275853161/sizes/z/in/photostream/ • http://www.flickr.com/photos/bdewey/4965925131/sizes/o/in/photostream/ • http://www.flickr.com/photos/polanri/74381759/sizes/o/in/photostream/ Sunday,

    October 2, 11