Nodejs - A performance que eu sempre quis ter

8.298 visualizações

Publicada em

Palestra apresentada no evento DevInSampa - www.devinsampa.com.br

Publicada em: Tecnologia

Nodejs - A performance que eu sempre quis ter

  1. 1. A performance que eu sempre quis ter Emerson Macedo @emerleite http://codificando.com http://visaoagil.wordpress.com/author/emerleite/
  2. 2. #whoami
  3. 3. 2000
  4. 4. 360 milhões de usuários de internet em todo mundo
  5. 5. 9,8 milhões de usuários
  6. 6. 9,8 milhões de usuários 4,8 milhões são ativos
  7. 7. Com poucos usuários qualquer tecnologia funciona
  8. 8. 2010
  9. 9. ~ 2 bilhões de usuários de internet em todo mundo
  10. 10. 68 milhões de usuários
  11. 11. 68 milhões de usuários 37 milhões são ativos
  12. 12. Com muitos usuários nem toda tecnologia funciona
  13. 13. Tecnologias atuais
  14. 14. Todas essas tecnologias tem algo em comum
  15. 15. PHP 1995
  16. 16. PHP 1995 Java EE 1998
  17. 17. PHP 1995 Java EE 1998 ASP.Net 2002
  18. 18. PHP 1995 Java EE 1998 ASP.Net 2002 Ruby on Rails 2005
  19. 19. PHP 1995 Java EE 1998 ASP.Net 2002 Ruby on Rails 2005 Django 2005
  20. 20. Por que então mais uma tecnologia ?
  21. 21. Usuários de Internet no Mundo (em milhões) 2.000 milhões 2000 1500 1000 500 360 milhões 0 2000 2010
  22. 22. Usuários de Internet no Brasil (em milhões) 70 milhões 70 52,5 35 17,5 10 milhões 0 2000 2010
  23. 23. Mas já escalamos muito bem nossos sites
  24. 24. Estrutura física de servidores para escalar
  25. 25. Escalando na vertical
  26. 26. Escalando na vertical
  27. 27. Escalando na horizontal
  28. 28. Escalando na horizontal
  29. 29. Escalando na horizontal
  30. 30. Escalando na horizontal
  31. 31. Escalando DB na horizontal re ad ad re write write write
  32. 32. Escalando DB na horizontal Shard Shard Shard Shard Shard Shard Database Database Database Database Database Database
  33. 33. Arquitetura pra fazer o software escalar
  34. 34. Pattern para atender muitos requests
  35. 35. Pattern para atender muitos requests Finalize a requisição o mais rápido possível
  36. 36. HTTP GET
  37. 37. HTTP POST
  38. 38. Pattern para atender muitos requests Finalize a requisição o mais rápido possível
  39. 39. Por que então mais uma tecnologia ?
  40. 40. 2014
  41. 41. ~ 70% dos adultos serão usuários regulares de redes sociais
  42. 42. Como manter conectados 10, 20 ou 30 mil usuários simultâneos ?
  43. 43. Escalando na horizontal
  44. 44. Escalando na horizontal
  45. 45. Evented, non-blocking I/O Google V8 Engine
  46. 46. Qual é o problema das tecnologias atuais ?
  47. 47. Como manter conectados 10, 20 ou 30 mil usuários simultâneos ?
  48. 48. Nosso código costuma ser escrito assim
  49. 49. Nosso código costuma ser escrito assim O que o software está fazendo enquanto a querie executa ?
  50. 50. Na maioria dos casos está travado esperando a resposta
  51. 51. Rails ou Django HTTPD Database
  52. 52. Rails ou Django HTTPD Database
  53. 53. Rails ou Django HTTPD Database
  54. 54. Rails ou Django RUNTIME PROCESS HTTPD Database
  55. 55. Rails ou Django RUNTIME BLOCK PROCESS HTTPD Database
  56. 56. Rails ou Django RUNTIME BLOCK PROCESS RUNTIME BLOCK PROCESS HTTPD Database RUNTIME BLOCK PROCESS RUNTIME PROCESS BLOCK
  57. 57. Java Servlet Container HTTPD Servlet Database
  58. 58. Java Servlet Container HTTPD Servlet Database
  59. 59. Java Servlet Container HTTPD Servlet Database
  60. 60. Java Servlet Container Thread HTTPD Servlet Database
  61. 61. Java Servlet Container Thread BLOCK HTTPD Servlet Database
  62. 62. Java Servlet Container Thread BLOCK Thread BLOCK Thread BLOCK HTTPD Servlet Database Thread BLOCK Thread BLOCK Thread BLOCK Thread BLOCK
  63. 63. Apenas um processo abrindo uma thread para cada request
  64. 64. Produtividade do programador mais que performance da tecnologia
  65. 65. Apenas um processo abrindo uma thread para cada request
  66. 66. Parece bom mas ...
  67. 67. Como manter conectados 10, 20 ou 30 mil usuários simultâneos ?
  68. 68. Como manter conectados 10, 20 ou 30 mil usuários simultâneos ? 30 mil threads ?
  69. 69. concurrency × reqs/sec Apache vs NGINX concurrency × reqs/sec http://blog.webfaction.com/a-little-holiday-present http://blog.webfaction.com/a-little-holiday-present
  70. 70. concurrency × reqs/sec Apache vs NGINX concurrency × memory http://blog.webfaction.com/a-little-holiday-present http://blog.webfaction.com/a-little-holiday-present
  71. 71. Apache cria uma thread por request
  72. 72. Troca de contexto entre theads tem um custo
  73. 73. Cada OS Thread cria uma pilha de execução nova
  74. 74. Não devemos usar uma thread por request quando precisamos suportar alta concorrência
  75. 75. Como manter conectados 10, 20 ou 30 mil usuários simultâneos ?
  76. 76. Pattern para atender muitos requests Finalize a requisição o mais rápido possível
  77. 77. Pattern para atender alta concorrência
  78. 78. Pattern para atender alta concorrência Não crie threads
  79. 79. Pattern para atender alta concorrência Não crie threads Use um Event Loop
  80. 80. Produtividade do programador mais que performance da tecnologia
  81. 81. Performance != Escalabilidade
  82. 82. Performance != Escalabilidade mas ...
  83. 83. Uma performance melhor ajuda a escalar com menos recursos
  84. 84. Precisamos fazer I/O de outra maneira
  85. 85. Latência de I/O
  86. 86. Latência de I/O L1 3 ciclos
  87. 87. Latência de I/O L1 3 ciclos L2 14 ciclos
  88. 88. Latência de I/O L1 3 ciclos L2 14 ciclos RAM 250 ciclos
  89. 89. Latência de I/O L1 3 ciclos L2 14 ciclos RAM 250 ciclos Disco 41.000.000 ciclos
  90. 90. Latência de I/O L1 3 ciclos L2 14 ciclos RAM 250 ciclos Disco 41.000.000 ciclos Rede 240.000.000 ciclos
  91. 91. Latência de I/O L1 3 ciclos L2 14 ciclos RAM 250 ciclos Disco 41.000.000 ciclos Rede 240.000.000 ciclos
  92. 92. I/O não bloqueante
  93. 93. I/O não bloqueante L1 3 ciclos L2 14 ciclos RAM 250 ciclos
  94. 94. I/O não bloqueante L1 3 ciclos L2 14 ciclos RAM 250 ciclos I/O bloqueante
  95. 95. I/O não bloqueante L1 3 ciclos L2 14 ciclos RAM 250 ciclos I/O bloqueante Disco 41.000.000 ciclos Rede 240.000.000 ciclos
  96. 96. Infraestrutura não bloqueante, puramente baseada em eventos, para desenvolver software de alta concorrência
  97. 97. Servidor TCP simples em NodeJS O código acima faz com que a execução retorne imediatamente ao event loop
  98. 98. Por que já não faziamos dessa forma ?
  99. 99. POSIX Assync I/O não suportado por todos os S.Os
  100. 100. POSIX Assync I/O não suportado por todos os S.Os libmysql_client não permite query async
  101. 101. Filosofia do NodeJS
  102. 102. Filosofia do NodeJS Todo I/O deveria ser feito desta forma
  103. 103. Para qualquer operação que acesse o disco ou a rede deve existir um callback
  104. 104. Arquitetura Javascript Node standard library C Node Bindings thread event pool loop V8 (libeio) (libev)
  105. 105. Pilha de execução ev_loop() I/O em disco (bloqueante)
  106. 106. Pilha de execução socket_readdable(1) ev_loop() I/O em disco (bloqueante)
  107. 107. Pilha de execução http_parse(1) socket_readdable(1) ev_loop() I/O em disco (bloqueante)
  108. 108. Pilha de execução load(“index.html”) http_parse(1) socket_readdable(1) ev_loop() I/O em disco (bloqueante)
  109. 109. Pilha de execução http_parse(1) socket_readdable(1) ev_loop() I/O em disco (bloqueante)
  110. 110. Pilha de execução socket_readdable(1) ev_loop() I/O em disco (bloqueante)
  111. 111. Pilha de execução ev_loop() I/O em disco (bloqueante)
  112. 112. Pilha de execução ev_loop() I/O em RAM (não bloqueante)
  113. 113. Pilha de execução socket_readdable(2) ev_loop() I/O em RAM (não bloqueante)
  114. 114. Pilha de execução http_parse(2) socket_readdable(2) ev_loop() I/O em RAM (não bloqueante)
  115. 115. Pilha de execução http_respond(2) http_parse(2) socket_readdable(2) ev_loop() I/O em RAM (não bloqueante)
  116. 116. Pilha de execução http_parse(2) socket_readdable(2) ev_loop() I/O em RAM (não bloqueante)
  117. 117. Pilha de execução socket_readdable(2) ev_loop() I/O em RAM (não bloqueante)
  118. 118. Pilha de execução ev_loop() I/O em RAM (não bloqueante)
  119. 119. Pilha de execução ev_loop() Arquivo carregou do disco
  120. 120. Pilha de execução file_loaded() ev_loop() Arquivo carregou do disco
  121. 121. Pilha de execução http_respond(1) file_loaded() ev_loop() Arquivo carregou do disco
  122. 122. Pilha de execução file_loaded() ev_loop() Arquivo carregou do disco
  123. 123. Pilha de execução ev_loop() Arquivo carregou do disco
  124. 124. Arquitetura Web
  125. 125. Arquitetura Web Nginx
  126. 126. Arquitetura Web Nginx Ruby Ruby Ruby Ruby Ruby or or or or or Python Python Python Python Python
  127. 127. Arquitetura Web Nginx Ruby Ruby Ruby Ruby Ruby or or or or or NodeJS Python Python Python Python Python
  128. 128. Arquitetura Web Nginx
  129. 129. Arquitetura Web Nginx NodeJS
  130. 130. Arquitetura Web NodeJS
  131. 131. Arquitetura Web NodeJS Quando NodeJS estiver bem maduro, a idéia de Ryan é que ele seja a porta de entrada. Será ?
  132. 132. Por que Javascript ?
  133. 133. Não é burocrático, assim como Ruby ou Python
  134. 134. Não é burocrático, assim como Ruby ou Python Especialistas Javascript Client-Side já pensam assíncrono
  135. 135. Instalação
  136. 136. Instalação http://nodejs.org/#download
  137. 137. Instalação http://nodejs.org/#download $ ./configure $ make $ make install
  138. 138. Desenvolvendo aplicações web
  139. 139. Express JS http://expressjs.com/
  140. 140. Express JS http://expressjs.com/ Sinatra ???
  141. 141. Express JS #múltiplos ambientes
  142. 142. Express JS #markup
  143. 143. Express JS #markup
  144. 144. Express JS #stylesheet
  145. 145. Express JS #comportamento
  146. 146. Express JS #comportamento
  147. 147. Database
  148. 148. Database http://wiki.github.com/ry/node/modules#database
  149. 149. Database http://wiki.github.com/ry/node/modules#database MongoDB CouchDB MySQL Assíncrono Sqlite Redis Postgres
  150. 150. Test driven development #vows - http://vowsjs.org/
  151. 151. Test driven development
  152. 152. Test driven development #http://github.com/visionmedia/expresso/
  153. 153. Node package manager http://github.com/isaacs/npm
  154. 154. Node package manager http://github.com/isaacs/npm #instalação $ curl http://npmjs.org/install.sh | sh
  155. 155. Node package manager http://github.com/isaacs/npm #instalação $ curl http://npmjs.org/install.sh | sh #utilização $ npm install pacote
  156. 156. Node package manager http://github.com/isaacs/npm #instalação $ curl http://npmjs.org/install.sh | sh #utilização $ npm install pacote #desinstalação $ npm uninstall npm
  157. 157. Node package manager http://github.com/isaacs/npm
  158. 158. Node package manager http://github.com/isaacs/npm #stable - expressjs $ npm install express
  159. 159. Node package manager http://github.com/isaacs/npm #stable - expressjs $ npm install express #unstable - hamljs $ npm install hamljs@latest
  160. 160. Node package manager http://github.com/isaacs/npm #stable - expressjs $ npm install express #unstable - hamljs $ npm install hamljs@latest #versão - vows $ npm install vows@0.4.6
  161. 161. Node package manager
  162. 162. Node package manager http://github.com/isaacs/npm
  163. 163. Node package manager http://github.com/isaacs/npm #listando $ npm list
  164. 164. Node package manager http://github.com/isaacs/npm #listando $ npm list #instalado $ npm list @installed
  165. 165. Node package manager http://github.com/isaacs/npm #listando $ npm list #instalado $ npm list @installed #autor $ npm list =ry
  166. 166. Node package manager
  167. 167. Node package manager http://github.com/isaacs/npm
  168. 168. Node package manager http://github.com/isaacs/npm #atualizando $ npm update
  169. 169. Node package manager http://github.com/isaacs/npm #atualizando $ npm update #porpacote $ npm update pacote
  170. 170. Node package manager http://github.com/isaacs/npm #atualizando $ npm update #porpacote $ npm update pacote #ondefica ~/.node_libraries
  171. 171. Deployment em produção
  172. 172. Spark + Nginx http://github.com/senchalabs/spark
  173. 173. Spark + Nginx http://github.com/senchalabs/spark #instalação $ npm install spark@latest
  174. 174. Spark + Nginx http://github.com/senchalabs/spark #instalação $ npm install spark@latest #utilização $ spark -p [port] -n [processes]
  175. 175. Spark + Nginx
  176. 176. Spark + Nginx #config.js
  177. 177. Spark + Nginx #config.js #nginx
  178. 178. Oportunidades
  179. 179. Upload de arquivos
  180. 180. Upload de arquivos Streaming de vídeo
  181. 181. Upload de arquivos Real-time web applications Streaming de vídeo
  182. 182. Alternativas
  183. 183. Status atual
  184. 184. Status atual Versão 0.1.103
  185. 185. Status atual Versão 0.1.103 Javascript ~ 6000 linhas
  186. 186. Status atual Versão 0.1.103 Javascript ~ 6000 linhas C++ ~ 11000 linhas
  187. 187. Status atual Versão 0.1.103 Javascript ~ 6000 linhas C++ ~ 11000 linhas Mailin list ~ 1200 pessoas
  188. 188. Status atual Versão 0.1.103 Javascript ~ 6000 linhas C++ ~ 11000 linhas Mailin list ~ 1200 pessoas Contribuidores ~ 70 pessoas
  189. 189. Conclusão
  190. 190. I/O não deve ser feito da forma que fazemos hoje em dia
  191. 191. Muito promissor
  192. 192. Muito promissor Podemos usar já !!!
  193. 193. Produtividade do programador mais que performance da tecnologia
  194. 194. Obrigado !!! Emerson Macedo @emerleite http://codificando.com
  195. 195. Referências http://www.internetworldstats.com/emarketing.htm http://en.wikipedia.org/wiki/Event_loop http://lse.sourceforge.net/io/aio.html http://code.google.com/p/v8/ http://opengroup.org/onlinepubs/007908775/xsh/select.html http://en.wikipedia.org/wiki/Thread_pool_pattern http://www.commonjs.org/specs/modules/1.0/ http://en.wikipedia.org/wiki/File_descriptor

×