-
Notifications
You must be signed in to change notification settings - Fork 0
/
rss.xml
5052 lines (4922 loc) · 960 KB
/
rss.xml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0"><channel><title><![CDATA[Reativa Tecnologia]]></title><description><![CDATA[Transformamos programadores iniciantes nos melhores programadores do mercado.]]></description><link>https://blog.reativa.dev</link><generator>GatsbyJS</generator><lastBuildDate>Sat, 27 Feb 2021 08:35:19 GMT</lastBuildDate><item><title><![CDATA[Mentoria para programadores iniciantes]]></title><description><![CDATA[Olá, eu me chamo Paulo Luan. Sou programador há 10 anos, tenista de mesa amador e apaixonado por disrupção. Fui parte de projetos como o…]]></description><link>https://blog.reativa.dev/mentoria-pauloluan/</link><guid isPermaLink="false">https://blog.reativa.dev/mentoria-pauloluan/</guid><pubDate>Fri, 08 Jan 2021 00:00:00 GMT</pubDate><content:encoded><h2>Olá, eu me chamo Paulo Luan.</h2>
<p>Sou programador há 10 anos, tenista de mesa amador e apaixonado por disrupção. Fui parte de projetos como o desenvolvimento do Internet Banking do maior banco da América Latina e diversos e-commerces das maiores varejistas mundiais como Motorola e Embraer. Centenas de milhões de reais já passaram através dos códigos que desenvolvi, além de ter contribuído com o desenvolvimento do sistema que <a href="https://bit.ly/38UQA3Q">irritou o presidente do Brasil em 2019</a> 😂</p>
<p><img src="https://media-exp1.licdn.com/dms/image/C4E12AQGAoCZCBrGP6w/article-inline_image-shrink_1000_1488/0/1605780554533?e=1615420800&#x26;v=beta&#x26;t=LQPux0ShUPX2ZVHPz08VFS-OGhCl91F3N74rRILhYQ8" alt="No alt text provided for this image"></p>
<p>já mentorei mais de 2.547 programadores: no <a href="http://bit.ly/pauloluan-insta">Instagram</a>, nas consultorias e na vida.</p>
<p>Hoje, estou iniciando uma nova etapa e colocando em prática tudo que aprendi:</p>
<h2>Ensinando todas as coisas que eu considero ter inestimável importância para ser um bom dev, para que você possa chegar muito mais longe do que eu, no menor tempo o possível.</h2>
<p>Antes de começarmos, vou deixar uma coisa bem clara: SIM eu tenho fins lucrativos, mas não sou uma daquelas páginas que te prometem dinheiro fácil.</p>
<p>Eu não vou fazer aqueles vídeos bizarros falando que “você vai enriquecer em apenas 7 dias no conforto do seu lar”. Estou te apresentando uma oportunidade para você se tornar um programador de alto nível, você pode aproveitá-la ou não.</p>
<p>Porque diabos eu começaria o texto assim, dizendo que não te prometo dinheiro fácil? Porque tenho um compromisso sério com a verdade e com a honestidade. Odeio quem tenta levar tudo na conversa, enrolando com um monte de baboseira e discursos falsos para te vender produtos de merda por 5 mil reais.</p>
<h2>Minha pegada é ir direto ao ponto. Assim economizo o meu tempo e o seu.</h2>
<p>Se você chegou até aqui é porque me conhece, e já viu pelo menos um pouco do meu trabalho. Sei disso porque não me interesso em enviar spam para desinteressados, já que essa não é minha filosofia de trabalho.</p>
<p>Como já mencionado, nos últimos anos, estruturei a engenharia por trás de diversos projetos de software, que foram usadas por milhões de pessoas ao redor do mundo.</p>
<p>Mas eu não fiz estas coisas sozinho, eu sempre contei com equipes fantásticas e pessoas talentosíssimas, e Isso me ajudou a entender como o mercado funciona, o que dá certo e principalmente: O que não dá.</p>
<p>“Então onde você quer chegar?”, você deve estar se perguntando.</p>
<p>Quero dizer que sou competente, e sei exatamente daquilo que estou falando. Nada que eu disser nessa página, ou colocar em meus cursos, não foi feito por mim antes. Todas as teses, ideias e propostas foram testadas pelo menos uma vez, com meu próprio tempo e dedicação nos diversos lugares que passei durante a última década desenvolvendo código.</p>
<p>Ou seja:</p>
<h2>EU SEMPRE MANTENHO MINHA PELE EM RISCO.</h2>
<p>Agora eu te pergunto:</p>
<h2>“O que é que os maiores programadores do mundo têm em comum?”</h2>
<p>Eles resolvem problemas, são pragmáticos e autodidatas.</p>
<p>A essa altura você deve estar se perguntando: “O que isso tem a ver comigo e com a minha realidade?”</p>
<h2>TUDO. Qualquer pessoa pode se tornar programador, os princípios são os mesmos.</h2>
<p>Não aprendemos direito na faculdade o que é possível fazer com todo esse conhecimento. A faculdade peca em muitos aspectos, e você já deve ter reparado que tenho opiniões bastante ácidas em relação a ela. Mas ao invés de mal dissermos delas, eu resolvi fazer algo a respeito, oferencendo a minha mentoria.</p>
<p>É aqui que começa a minha grande promessa:</p>
<h2>Trazer até você as mesmas estratégias e recursos utilizadas pelos melhores programadores do mundo, Com uma diferença enorme: de maneira simples, acessível e pronta para ser colocada em prática.</h2>
<p>Se eu fosse fazer uma mentoria personalizada, com reuniões e acompanhamento, isso sairia por milhares de reais 😞 e eu só teria a oportunidade de levar esse conhecimento a pouquíssimas pessoas. Então optei por colocar a um preço extremamente barato, o conhecimento de tudo o que deu certo mentorando os outros pupilos em um único documento, para você fazer no seu tempo!</p>
<p>CHEGA DE PAPO, clique na foto para acessar os detalhes deste guia!</p>
<p><a href="http://bit.ly/guia-dev-autodidata"><img src="https://media-exp1.licdn.com/dms/image/C4E12AQGjObVVjSeOMA/article-inline_image-shrink_1000_1488/0/1605780884587?e=1615420800&#x26;v=beta&#x26;t=qVh2v-RZsIvdXVrr5LUK2wTWvQds_oDWjhYdX6BlzGo" alt="No alt text provided for this image"></a></p>
<h2><a href="https://bit.ly/guia-dev-autodidata">Lá eu abro o jogo sobre o que funciona e o que não funciona, e o caminho que eu gostaria de ter seguido.</a></h2>
<p>Absolutamente tudo que aprendi ao longo dos 11 anos que trabalhei como programador, além de dizer exatamente como funciona o mercado, e como sair da fase de programador-recém-formado-perdido-na-carreira até o sucesso que você almeja.</p>
<p>Mas pagar o preço de uma pizza por um PDF? Parece uma idéia maluca, não? Mas este conteúdo transformou a vida de milhares de pessoas (e não sou eu que estou falando, leia os comentários ali embaixo 👇👇), e você tem 7 dias para reembolso (te devolvo o dinheiro sem fazer perguntas) caso entenda que não se encaixe ao seu momento, contexto e objetivos.</p>
<p>Eu estou escrevendo isto pois recebi essa mensagem no Instagram:</p>
<p><img src="https://media-exp1.licdn.com/dms/image/C4E12AQHDZWdlYn1D-A/article-inline_image-shrink_1000_1488/0/1605781094923?e=1615420800&#x26;v=beta&#x26;t=J1_MCYWk5KagcblRnrdwSNH1Pp4C7efe62p1zwaUbeQ" alt="No alt text provided for this image"></p>
<p>Eu cobro um valor simbólico por um motivo:</p>
<blockquote>
<p>Quando você paga por algo, você tende a realizar, quando algo é gratuito você ignora e posterga</p>
</blockquote>
<p>E não estou nesse jogo por dinheiro, estou para gerar ação e resultados, então se você não tem coragem de me pagar uma pizza de calabreza, e de dar o próximo passo para colocar em prática tudo o que eu falo, eu é que não quero te mentorar, feche essa página e <a href="https://bit.ly/video-de-brigas">vá ver gente brigando no twitter</a>.</p>
<blockquote>
<p>Mas se tu quer mudar sua realidade de verdade, é esforçado, mas ainda se sente perdido e ‘não está preparado para o mercado’, cola com o pai que eu vou mover o mundo por você.</p>
</blockquote>
<p>(Se o seu problema é você ser realmente pobre e não tem condições nenhuma, me mande uma <a href="http://bit.ly/pauloluan-insta">mensagem no Instagram</a> que eu te envio de graça, 0800 na faixa, de gratis)</p>
<p>BORA CODAR.</p></content:encoded></item><item><title><![CDATA[Como fazer perguntas sobre programação na internet? (e aumentar 5x as chances de ter uma resposta)]]></title><description><![CDATA[Dicas iniciais Antes de começarmos: Você se sente perdido? Ansioso? A faculdade parece que não te formou direito? As vagas exigem milhares…]]></description><link>https://blog.reativa.dev/como-fazer-perguntas-inteligentes/</link><guid isPermaLink="false">https://blog.reativa.dev/como-fazer-perguntas-inteligentes/</guid><pubDate>Sun, 03 Jan 2021 00:00:00 GMT</pubDate><content:encoded><h3>Dicas iniciais</h3>
<p>Antes de começarmos: Você se sente perdido? Ansioso? A faculdade parece que não te formou direito? As vagas exigem milhares de coisas e você se sente um bosta? Eu posso te mentorar! diariamente faço mentoria coletiva (gratuita) para programadores iniciantes que se sentem perdidos, você será extremamente bem vindo por lá (é só clicar na imagem).</p>
<p><a href="http://bit.ly/pauloluan-insta"><img src="https://media-exp1.licdn.com/dms/image/C4E12AQF9pxdMEVTSQg/article-inline_image-shrink_1500_2232/0/1614414726929?e=1619654400&#x26;v=beta&#x26;t=ti7w8kAyqaK7PRcB9YGnRNv8ircAgThraVR-O1D4T54" alt="Mentoria Gratuita"></a></p>
<h3>Aperte <code class="language-text">ctrl+p</code> e imprima esse artigo, para que você possa fazer anotações!</h3>
<blockquote>
<p>Texto original em <a href="http://www.catb.org/esr/faqs/smart-questions.html">inglês</a></p>
</blockquote>
<blockquote>
<p>Nota sobre o texto: O autor original é um pouco ‘rude’ com alguns termos, tente ignorar esse fato e se atente aos ensinamentos principais (que são extremamente úteis), boa leitura!</p>
</blockquote>
<h2>Introdução</h2>
<p>No mundo dos <em>programadores</em>, o tipo de respostas que você obtém para suas questões técnicas depende bastante da forma que você faz as perguntas bem como da dificuldade de desenvolver a resposta. Este guia irá ensinar você como fazer perguntas de forma a obter uma resposta satisfatória.</p>
<p>A primeira coisa a entender é que os <em>programadores</em> gostam de problemas difíceis e questões boas e provocantes sobre eles. Se não fosse assim, não estaríamos aqui. Se você nos der uma questão interessante para mastigar seremos gratos; boas questões são um estímulo e um presente. Boas perguntas nos ajudam a desenvolver nosso entendimento, e geralmente revelam problemas que poderíamos não ter percebido ou pensado de outra forma. Entre os <em>programadores</em>, “Boa pergunta!” é um forte e sincero cumprimento.</p>
<p>Apesar disto, os <em>programadores</em> tem uma reputação de abordar questões simples com o que se parece com hostilidade ou arrogância. Às vezes parece que somos hostis aos novatos e ignorantes. Mas isto não é verdade.</p>
<p>O que nós somos, sem qualquer desculpa, é hostis a pessoas que parecem não estar querendo pensar ou fazer seu próprio trabalho de casa antes de fazer perguntas. Pessoas assim são como precipícios — eles pegam sem dar nada em troca, eles desperdiçam um tempo que poderíamos ter usado em outra questão mais interessante e com outra pessoa que valha mais a pena responder. Chamamos este tipo de pessoa de ”<em>losers</em>” (e por razões históricas às vezes escrevemos ”<em>lusers</em>”).</p>
<p>Somos, em grande parte, voluntários. Tomamos tempo de nossas vidas ocupadas, e às vezes somos sobrecarregados por ela. Por isto filtramos as perguntas de forma rude. Em particular, jogamos fora questões de pessoas que pareçam ser <em>losers</em> para gastar nosso tempo de responder perguntas de forma mais eficiente, com vencedores.</p>
<p>Você não quer ser um dos <em>losers</em>. Você não quer parecer com um, também. A melhor forma de conseguir respostas rápidas é fazer as perguntas como um vencedor — perguntar como uma pessoa esperta, confiante, e com dicas, que parece precisar de ajuda apenas em um problema particular.</p>
<h2>Antes de Perguntar</h2>
<p>Antes de fazer uma pergunta técnica por email, ou em um <em>newsgroup</em>, ou em um <em>chat-board</em> de um <em>website</em>, faça o seguinte:</p>
<ol>
<li>Tente encontrar uma resposta lendo o manual</li>
<li>Tente encontrar uma resposta lendo o FAQ</li>
<li>Tente encontrar uma resposta pesquisando a Web</li>
<li>Tente encontrar uma resposta perguntando a algum amigo mais preparado</li>
</ol>
<p>Quando fizer sua pergunta, mostre que você fez estas coisas primeiro, isto ajuda a estabelecer que você não está sendo uma esponja preguiçosa e desperdiçando o tempo de outras pessoas. Melhor ainda, mostre que você aprendeu alguma coisa tendo feito estas coisas. Gostamos de responder perguntas de pessoas que tenham demonstrado que podem aprender das respostas.</p>
<p>Prepare sua questão. Pense adiante. Perguntas que pareçam precipitadas recebem respostas precipitadas, ou nenhuma resposta. Quanto mais você demonstrar que dedicou pensamentos e esforços em resolver seu problema antes de pedir por ajuda, mais provável é que você vá conseguir ajuda.</p>
<p>Cuidado para não fazer a pergunta errada. Se você fizer perguntas baseadas em pressupostos falsos, <em>J. Random</em> provavelmente vai responder com uma resposta literalmente inútil ao mesmo tempo que pensa “Pergunta estúpida…”, e com a esperança de que a experiência de ganhar o que você pediu em vez do que você precisa vá lhe ensinar uma lição.</p>
<p>Por outro lado, tornar claro que você está apto e pronto a ajudar no processo de desenvolver a solução é um bom início. “Alguém pode me providenciar uma dica?”, “O que falta no meu exemplo?” e “Existe algum site que eu deveria ter procurado?” são perguntas que provavelmente vão ter respostas, em vez de “Por favor poste o procedimento que devo usar.” por que neste caso você está tornando claro que você não está disposto a completar o processo se alguém puder simplesmente apontar a direção certa para você.</p>
<p>Nunca assuma que você tem direito a uma resposta. Você não tem. Você vai conquistar uma resposta se puder conquistar a mesma, fazendo uma pergunta que seja substancial, interessante, estimulante — uma que implicitamente contribua à experiência da comunidade em vez de meramente exigir passivamente por conhecimentos dos outros.</p>
<h2>Quando Perguntar</h2>
<h3>Escolha seu fórum cuidadosamente</h3>
<p>Seja perceptivo ao escolher onde fazer sua pergunta. Você tem mais chances de ser ignorado, ou chamado de <em>loser</em>, se:</p>
<ul>
<li>postar sua pergunta em um fórum no qual ela seja <em>off topic</em></li>
<li>postar uma pergunta muito elementar onde sejam esperadas questões técnicas avançadas, ou vice-versa</li>
<li>fizer <em>cross-post</em> para muitos <em>newsgroups</em> diferentes</li>
</ul>
<p>Os <em>programadores</em> detonam com perguntas que sejam feitas inapropriadamente para tentar proteger seus canais de comunicação de serem afogados em irrelevâncias. Você não vai querer que isto aconteça com você.</p>
<h3>Escreva em linguagem clara, gramática e ortograficamente correta</h3>
<p>Sabemos por experiência que pessoas que são escritores descuidados e superficiais são também geralmente pensadores descuidados e superficiais (com experiência suficiente para apostar nisto). Responder perguntas para pensadores descuidados e superficiais não traz nenhuma compensação; nós preferimos gastar nosso tempo com outras coisas.</p>
<p>Portanto, expressar sua dúvida de forma clara e correta é importante. Se você não pode se incomodar com isto, nós não podemos nos incomodar em prestar atenção. Gaste algum esforço extra para polir sua linguagem. Você não precisa ser cerimonioso ou formal — ao contrário, a cultura dos <em>programadores</em> valoriza a linguagem informal, cheia de gírias e humor, usada com precisão. Mas ela precisa ser precisa; tem que haver algum indício que você está pensando e prestando atenção.</p>
<p>Escreva corretamente. Não confunda ”<em>its</em>” com ”<em>it’s</em>”, ou ”<em>loose</em>” com ”<em>lose</em>”. Não escreva TUDO EM MAIÚSCULAS, isto é lido como um grito e considerado rude. Se você escreve como um bobo semi-analfabeto, provavelmente você será ignorado. Escrever como um <em>l33t script kiddie hax0r</em> é o beijo da morte e garante que você não receberá nada a não ser um silêncio pétreo (ou, na melhor das hipóteses, ajuda carregada de desprezo e sarcasmo).</p>
<p>Se você está fazendo perguntas em um fórum que não usa sua linguagem nativa, você vai ter uma quantia limitada de tolerância a erros ortográficos e gramaticais — mas nenhuma tolerância a prequiça mental. Além disso, a menos que você saiba a linguagem de quem vai te responder, escreva em inglês. <em>programadores</em> ocupados tendem a simplesmente ignorar questões em linguagens que eles não entendem, e o inglês é a linguagem de trabalho na Internet. Escrevendo as perguntas em inglês você minimiza as chances de que as mesmas sejam descartadas sem ser lidas.</p>
<h3>Envie questões em formatos que sejam fáceis de entender</h3>
<p>Se você faz questões artificialmente difíceis de ler, provavelmente será ignorado em favor de alguém que não faz isto. Portanto:</p>
<ul>
<li>Envie email em texto puro, não HTML</li>
<li>Não envie emails em que os parágrafos inteiros sejam linhas únicas (isto torna mais difícil responder a somente uma parte da mensagem)</li>
<li>Nunca, jamais espere que os <em>programadores</em> possam ler formatos de documentos proprietários fechados como do <em>Microsoft Word</em>. A maioria dos <em>programadores</em> reagem a estes formatos da mesma forma que você reagiria a um monte fedorento de esterco de porco jogado na tua porta.</li>
<li>Se você estiver enviando email em uma máquina Windows, retire a funcionalidade estúpida de ”<em>Smart Quotes</em>” da Microsoft. Fazendo isto você evita pingar caracteres inúteis em seu email</li>
</ul>
<h3>Utilize linhas de assunto com significado e específicas</h3>
<p>Em listas de correio ou grupos de notícias, a linha de assunto é sua oportunidade de ouro para atrair a atenção de especialistas qualificados em cerca de 50 caracteres ou menos. Não desperdice esta oportunidade com murmúrios e balbúcias, como “Por favor me ajudem” (ou então “POR FAVOR ME AJUDEM!!!!”). Não tente nos impressionar com a profundidade de tua angústia; ao invés disto, use o espaço para uma descrição super-concisa do problema.</p>
<p><strong>Estúpida:</strong></p>
<ul>
<li>SOCORRO! O vídeo não funciona no meu laptop!</li>
</ul>
<p><strong>Inteligente:</strong></p>
<ul>
<li>XFree86 4.1 mostra cursor errado, chipset de vídeo Fooware MV1005</li>
</ul>
<h3>Seja preciso e informativo sobre o seu problema</h3>
<ul>
<li>Descreva os sintomas do seu problema ou <em>bug</em> cuidadosa e claramente.</li>
<li>Descreva o ambiente em que o mesmo ocorre (máquina, SO, aplicação, o que for)</li>
<li>Descreva a pesquisa que você fez para experimenta resolver e entender o problema antes de ter feito a pergunta</li>
<li>Descreva os passos de diagnóstico que você tomou para resolver o problema por conta própria antes de ter feito a pergunta</li>
<li>Descreva qualquer alteração recente no seu computador ou configuração de software que possa ser relevante</li>
</ul>
<p>Faça o melhor que puder para antecipar as perguntas que um <em>programador</em> possa fazer, e para responder as mesmas previamente no seu pedido de ajuda.</p>
<p>Simon Tatham escreveu um excelente documento chamado <em>How to Report Bugs Effectively</em>. Eu recomendo que você leia o mesmo.</p>
<h3>Descreva os Sintomas, não suas suspeitas</h3>
<p>Não há utilidade em dizer aos <em>programadores</em> o que você pensa que está causando seu problema (se suas teorias de diagnósticos fossem tão boas, você estaria pedindo ajuda?). Assim, certifique-se de informar os sintomas exatos do que está dando errado, em vez de suas interpretações e teorias. Deixe-os fazer a interpretação e diagnóstico.</p>
<p><strong>Estúpida:</strong></p>
<ul>
<li>Estou tendo erros SIG11 quando o kernel compila, e suspeito que uma trilha da motherboard está interrompida. Qual a melhor forma de verificar isto?</li>
</ul>
<p><strong>Inteligente:</strong></p>
<ul>
<li>Meu computador feito em casa K6/233 com mobo FIC-PA2007 (chipset VIA Apollo VP2) com 256MB SDRAM Corsair PC133 começa a dar erros SIG11 frequentes cerca de 20 minutos após ser ligada, durante compilações de kernel, mas nunca nos primeiros 20 minutos. Reinicializar não reinicia o relógio, mas desligar à noite sim. Trocar toda a RAM não ajudou. O trecho relevante de um log de uma sessão de compilação típica segue abaixo.</li>
</ul>
<h3>Descreva os sintomas dos problemas em ordem cronológica</h3>
<p>As pistas mais úteis para descobrir o que está errado geralmente estão no que ocorreu um pouco antes. Por isto, descreva precisamente o que você fez, e o que a máquina fez, até a ocorrência do problema. No caso de processos de linha de comando, ter um log da sessão (por exemplo usando o utilitário script) e copiando as vinte e tantas linhas relevantes é bastante útil.</p>
<p>Se o programa que está dando problemas possui opções de diagnóstico (tipo uma opção -v para modo verboso), tente pensar com carinho em usar algumas opções que possam acrescentar alguma informação de depuração úteis ao texto transcrito.</p>
<p>Se sua mensagem for muito longa (mais que cerca de quatro parágrafos), pode ser útil descrever o problema de forma sucinta no início, e então seguir com a história cronológica. Desta forma, os <em>programadores</em> saberão o que procurar quando estiverem lendo sua crônica.</p>
<h3>Não peça para ser respondido via email privado</h3>
<p>Os <em>programadores</em> acreditam que a solução de problemas deve ser um processo público e transparente, durante o qual uma primeira tentativa de resposta pode e deve ser corrigida por alguém com mais conhecimentos que tenha percebido que a mesma está incompleta ou incorreta. Da mesma forma, eles obtém alguma recompensa por ter respondido por serem vistos como competentes e conhecedores por seus iguais.</p>
<p>Quando você pede uma resposta em private, você está interrompendo tanto o processo quanto o prêmio. Não faça isto. É escolha de quem responde se a resposta deve seguir em <em>private</em> — e se isto acontece, usualmente é por que ele pensa que a questão é muito óbvia ou mal-formada para interessar a outros.</p>
<p>Há uma exceção limitada a esta regra. Se você pensa que a questão é tal que você provavelmente vai receber muitas respostas que são muito semelhantes, então as palavras mágicas são “mandem por email que eu resumo as respostas para o grupo”. É cortês tentar proteger a lista de mail e o <em>newsgroup</em> de uma inundação de <em>posts</em> idênticos — mas você deve cumprir a promessa de mandar o resumo.</p>
<h3>Corte fora perguntas inúteis</h3>
<p>Resista a tentação de fechar seu pedido de ajuda com questões semanticamentes nulas como “Alguém pode me ajudar?” ou “Há alguma resposta?” Primeiro, se você fez sua parte da descrição do problema de forma competente, este tipo de pergunta é, na melhor hipótese, supérflua. Em segundo, pelo que a precede, esta questão beira a perturbação, convidando a respostas inúteis mas lógicamente impecáveis como “Sim” ou “Não”. Cortesia não machuca, e, às vezes, ajuda</p>
<p>Seja cortês. Use “Por favor”, e “Agradeço antecipadamente”. Torne claro que você dá valor ao tempo que as pessoas gastam tentando te ajudar gratuitamente.</p>
<p>Para ser honesto, isto não é tão importante quanto (e não é susbtituto de) ser gramaticalmente correto, claro, preciso e descritivo, evitando formatos proprietários, etc. Os <em>programadores</em> em geral perferem um relatório de bugs um tanto brusco mas técnicamente correto, que uma mensagem polidamente vaga (se isto te surpreende, lembre que damos valor a uma questão pelo que ela nos ensina).</p>
<p>Entretanto, se você tem os fatos técnicos citados coerentemente, ser polido aumenta as chances de conseguir uma resposta útil.</p>
<h3>Poste uma mensagem curta apontando a solução encontrada</h3>
<p>Envie uma nota após o problema ter sido solucionado para todos que te ajudaram; deixe-os saberem como ficou e agradeça novamente pela ajuda. Se o problema atraiu o interesse geral na lista de email ou <em>newsgroup</em>, é apropriado postar um retorno no mesmo.</p>
<p>O <em>follow-up</em> não precisa ser longo e detalhado, um simples “Feito - era um cabo de rede com problemas! Obrigado a todos - Bill” é melhor que nada. De fato, um resumo curto e simples é melhor que uma longa dissertação a menos que a resposta tenha um real valor técnico.</p>
<p>Além de ser cortês e informativo, este tipo de <em>follow-up</em> ajuda todo mundo que deu assistência a ter uma sensação de fechamento do problema. Se você não é um <em>techie</em> ou <em>programador</em>, acredite em nós que este sentimento é muito importante para os gurus e especialistas que você pediu ajuda. Narrativas de problemas que terminam em um vazio não resolvido são coisas frustrantes; os <em>programadores</em> sentem uma comichão por ver os mesmos resolvidos. O bom karma que você ganha coçando esta comichão é que será muito mais útil postar uma pergunta na próxima vez que você tiver algum problema.</p>
<h2>Como Interpretar as Respostas</h2>
<h3>RTFM e STFW: Como Saber que Você “se Ferrou”</h3>
<p>Há uma tradição antiga e respeitada: se você recebe uma resposta escrita “RTFM”, a pessoa que enviou pensa que você deve Ler O Diabo do Manual (”<em>Read The Fucking Manual</em>” - a expressão é mais “colorida” no original). E ele provavelmente está certo sobre isto. Vá ler o manual.</p>
<p>RTFM tem um parente mais jovem. Se você receber uma resposta “STFW”, a pessoa que mandou ela pensa que você deveria Procurar no Diabo da Web (”<em>Search The Fucking Web</em>”). E ele provavelmente está certo sobre isto. Vá fazer uma pesquisa.</p>
<p>Geralmente, a pessoa que envia um destas respostas tem o manual ou a página com a informação que você precisa aberta, e está olhando para ela enquanto escreve. Estas respostas significam que (a) a informação a ler é fácil de encontrar, e (b) você vai aprender mais se procurar por conta própria do que se você ganhar a mesma de mão beijada.</p>
<p>Você não deve se sentir ofendido por estas respostas - pelos padrões dos <em>programadores</em>, ele está te mostrando um pouco de respeito simplesmente por não ter te ignorado. Você deveria, ao invés, ficar agradecido pela sua bondade de vovózinha.</p>
<h3>Se você não entendeu…</h3>
<p>Se você não entendeu a resposta, não devolva imediatamente um pedido de esclarecimento. Use as mesmas ferramentas que você usou para encontrar uma resposta para sua pergunta original (manuais, FAQ, a Web, um amigo que saiba mais) para entender a resposta. Se você precisar mais esclarecimentos, mostre o que você aprendeu.</p>
<p>Por exemplo, suponha que eu tenha dito: “Parece que você tem uma zentry presa, você precisa limpar ela.” Então:</p>
<p>Eis uma pergunta ruim: “O que é uma zentry?”</p>
<p>Eis uma pergunta boa: “OK, eu li a página man e as zentries são mencionadas somente sob as opções -z e -p. Nenhuma delas esclarece nada sobre zentries. É só isto ou eu estou deixando passar alguma coisa aqui?”</p>
<h3>Não Reaja como um Perdedor</h3>
<p>Eventualmente você vai se dar mal algumas vezes em fóruns da comunidade de <em>programadores</em> — em formas detalhadas neste artigo, ou parecidas. E vai ser dito para você exatamente onde você se deu mal, possivelmente com termos coloridos. Em público.</p>
<p>Quando isto acontecer, a pior coisa que você pode fazer é se queixar da experiência, alegar ter sido verbalmente atacado, exigir que se desculpem, gritar, prender a respiração, ameaçar com processos legais, reclamar com os chefes das pessoas, deixar a tampa do vaso levantada, etc. Ao invés disso, aqui está o que você deve fazer:</p>
<ul>
<li>Supere isto. É normal. De fato, é saudável e apropriado.</li>
</ul>
<p>Os padrões da comunidade não se mantém por si mesmos: eles são mantidos por pessoas que ativamente os aplicam, visivelmente, em público. Não se queixe que toda crítica deveria ir por email privado: não é assim que isto funciona. Nem é útil insistir que você foi insultado pessoalmente quanto alguém comentar que algumas de suas alegações estão erradas, ou que ele vê de forma diferente. Estas são atitudes de perdedores.</p>
<p>Tem havido forums de <em>programadores</em> onde, por conta de algum senso de hiper-cortesia mal orientado, os participantes são banidos por postar qualquer mensagem apontando erros de outros, e ouvem um “Não diga nada se você não está a fim de ajudar o usuário”. A resultantes partida de participantes que sabiam alguma coisa para outros lugares causou a queda do grupo para uma balbúrdia sem sentido e os tornou inúteis como fóruns técnicos.</p>
<h3>Exageradamente “amigável” (daquele jeito) ou útil: escolha.</h3>
<p>Lembre-se: quando aquele <em>programador</em> te disser que você errou, e (não importa o quão rude) te diz para não fazer isto novamente, ele está agindo por preocupação (1) por ti e (2) pela comunidade. Seria mais fácil para ele ignorar você e filtrar você fora da vida dele. Se você não consegue ser grato, pelo menos tenha um pouco de dignidade, não chore, e não espere ser tratado como uma boneca frágil só por que você é um novato com uma alma teatralmente hipersensível e ilusões de merecimento.</p>
<h2>Perguntas Que Não Se Faz</h2>
<p>Aqui estão algumas perguntas estúpidas clássicas, e o que os <em>programadores</em> estão pensando quando não respondem às mesmas.</p>
<h3>P: Onde eu encontro o programa X?</h3>
<p><strong>R</strong>: No mesmo lugar em que eu encontrei ele, bobão — na outra ponta de uma pesquisa na web. D’eus, ninguém sabe usar o Google ainda?</p>
<h3>P: Estou tendo problemas com minha máquina Windows. Você pode me ajudar?</h3>
<p><strong>R</strong>: Sim. Jogue fora aquele lixo da Microsoft e instale o Linux.</p>
<h3>P: Estou tendo problemas para instalar o Linux ou o X. Você pode me ajudar?</h3>
<p><strong>R</strong>: Não. Eu preciso ter acesso à tua máquina para resolver este problema. Vá pedir ajuda no teu grupo de usuários Linux local.</p>
<h3>P: Como eu posso crackear o root/roubar privilégios de ops de canais/ler os emails de outra pessoa?</h3>
<p><strong>R</strong>: Você é uma forma de vida inferior por querer fazer este tipo de coisa e um debilóide por pedir que um <em>programador</em> te ajude.</p>
<h2>Boas e Más Perguntas</h2>
<p>Por fim, vou ilustrar como fazer perguntas de uma forma inteligente por exemplo. Pares de questões sobre o mesmo problema, uma pergunta feita de forma estúpida, e outra de forma inteligente.</p>
<p><strong>Estúpida:</strong> Onde eu posso encontrar alguma informação sobre o Foonly Flubarmatic?</p>
<ul>
<li>Esta pergunta está implorando por um “STFW” como resposta.</li>
</ul>
<p><strong>Inteligente</strong>: Eu usei o Google para pesquisar por “Foonly Flubarmatic 2600” na Web, mas não consegui nenhum link útil. Alguém sabe onde eu posso encontrar alguma informação sobre a programação deste dispositivo?</p>
<ul>
<li>Este usuário já SFTW ou, e parece que ele tem um problema real.</li>
</ul>
<p><strong>Estúpida</strong>: Não consigo compilar o projeto foo. Por quê ele está com erros?</p>
<ul>
<li>Ele está assumindo que todo mundo está errado. Arrogância da parte dele.</li>
</ul>
<p><strong>Inteligente</strong>: O código do projeto foo não compila no Nulix versão 6.2. Eu li o FAQ, mas não tem nada sobre problemas relacionados ao Nulix. Aqui tem uma transcrição de minhas tentativas de compilar o mesmo, é algo que eu fiz?</p>
<ul>
<li>Ele especificou o ambiente, ele leu o FAQ, ele está mostrando o erro, e ele não está assumindo que seu problema é por causa do erro de outra pessoa. Este cara merece alguma atenção.</li>
</ul>
<p><strong>Estúpida:</strong> Estou tendo problemas com minha motherboard. Alguém pode me ajudar?</p>
<ul>
<li>A resposta de <em>J. Random</em> é provavelmente “Certo. Precisa arrotar e trocar as fraldas também?” seguido pelo pressionar da tecla delete.</li>
</ul>
<p><strong>Inteligente:</strong> Eu tentei X, Y e Z na motherboard S2464. Quando isto não funcionou, eu tentei A, B e C. Note o sintoma curioso quando tentei C. Obviamente o florbish está gromicando, mas os resultados não são os esperados. Quais são as causas usuais de gromicamento em motherboards MP? Alguém tem idéias de testes que eu possa fazer para descobrir o problema?</p>
<ul>
<li>
<p>Esta pessoa, por outro lado, parece que vale a pena responder. Ela exibiu inteligência para resolver problemas ao invés de ficar esperando que uma solução caísse do céu. Na última questão, note a sutil mas importante diferença entre “Me dê uma resposta” e “por favor me ajude a descobrir que diagnósticos adicionais posso tentar para descobrir o problema”. De fato, a forma da última questão é baseada em um incidente real que aconteceu em agosto de 2001 na lista de correio linux-kernel. Eu era quem estava fazendo a pergunta aquela vez. Eu estava observando misteriosos travamentos em uma motherboard Tyan S2464. Os membros da lista forneceram as informações que eu precisava para resolver o problema. Fazendo a pergunta do jeito que eu fiz, eu dei algo para que as pessoas mastigassem, eu tornei fácil e atrativo o envolvimento. Eu demonstrei respeito pela habilidade de meus colegas e convidei eles a me consultarem como a um igual. Eu demonstrei respeito pelo tempo deles informando quais as ruas escuras que eu já havia tomado. Mais tarde, quando agradeci a todos e destaquei como o processo funcionou bem, um membro da lkml apontou que ele pensava que o processo funcionou não por que eu era um “nome” naquela lista, mas por que eu fiz a pergunta de forma apropriada.</p>
<p>Nós, <em>programadores</em>, estamos, de certa forma, em uma rude meritocracia: estou certo que ele está correto, e seu eu tivesse agido como uma esponja eu teria recebido <em>flames</em> ou seria ignorado, não importando quem eu era. Sua sugestão que eu escrevesse sobre o incidente como uma instrução para outros foi o que me inspirou a compor este guia.</p>
</li>
</ul>
<h2>Considerações finais</h2>
<p>Agradecimentos: texto original foi escrito por <em>Por: Eric Raymond</em> em inglês: <a href="http://www.catb.org/esr/faqs/smart-questions.html">http://www.catb.org/esr/faqs/smart-questions.html</a> <em>Tradução feita por: <a href="http://geocities.yahoo.com.br/cesarakg/">César A. K. Grossmann</a></em></p>
<p>Evelyn Mitchell contribuiu com alguns exemplos de perguntas estúpidas e inspirou a seção “Como responder perguntas de forma útil”. Mikhail Ramendik contribuiu com valiosas sugestões de aprimoramento deste guia.</p>
<h2>Como responder perguntas de forma útil</h2>
<p>Seja gentil. Stress relacionado a problemas podem fazer as pessoas parecerem rudes ou estúpidas mesmo que elas não sejam.</p>
<p>Responda à uma primeira falta offline. Não há necessidade de humilhar publicamente alguém que tenha honestamente cometido um erro. Um novato de verdade pode não saber como pesquisar o histórico da lista ou onde o FAQ está localizado.</p>
<p>Se você não tem certeza, deixe isto claro! Uma resposta errada mas cheia de autoridade é pior do que nenhuma resposta. Não indique a ninguém um caminho errado só porque é divertido falar como um expert. Seja humilde e honesto; dê um bom exemplo para os seus companheiros.</p>
<p>Se você não pode ajudar, não atrapalhe! Não faça piadas sobre procedimentos que podem bagunçar o sistema do usuário — o pobre coitado pode interpretar isto como instruções sérias.</p>
<p>Faça perguntas para levantar mais informações. Se você for bom nisso o usuário irá aprender alguma coisa — e talvez você também. Tente transformar uma pergunta ruim em uma pergunta boa; lembre-se que todos nós fomos novatos um dia.</p>
<p>Enquanto mandar um RTFM é algumas vezes justificável quando você está respondendo uma pergunta de um preguiçoso, uma indicação do local exato da documentação (ou a frase correta para pesquisar no Google) é bem melhor.</p>
<p>Se você for responder uma pergunta, responda direito. Não sugira gambiarras para fazer funcionar a ferramenta errada. Sugira a ferramenta certa. Refaça a pergunta.</p>
<p>Ajude sua comunidade a aprender com a pergunta. Quando você responder a uma pergunta pense: “Como a documentação ou o FAQ podem ser melhorados para que ninguém precise perguntar isso novamente?” E então envie um patch ao mantenedor da documentação.</p>
<p>Se você teve que pesquisar para encontrar uma resposta, demonstre como você encontrou a resposta ao invés de fazer parecer que você a tirou de dentro de uma cartola. Responder a uma boa pergunta é como dar um prato de comida a um faminto. Mas ensiná-lo a plantar o próprio alimento é lhe garantir comida para o resto da vida. == Fontes relacionadas ==</p>
<p>Se você precisa de instruções sobre o básico dos computadores, sistemas Unix e Internet consulte o HOWTO Fundamentos do Unix e da Internet. (em inglês)</p>
<p>Quando você distribuir um software ou escrever patches para um, tente seguir o guia HOWTO Software Release Practice. (em inglês)</p></content:encoded></item><item><title><![CDATA[Apostila de NodeJS 100% Gratuita]]></title><description><![CDATA[Esta apostila é o resultado de alguns meses de pesquisa, revisão e edição, foi baseada na documentação oficial (então as informações são…]]></description><link>https://blog.reativa.dev/apostila-nodejs-completa/</link><guid isPermaLink="false">https://blog.reativa.dev/apostila-nodejs-completa/</guid><pubDate>Sun, 12 Jan 2020 00:00:00 GMT</pubDate><content:encoded><p>Esta apostila é o resultado de alguns meses de pesquisa, revisão e edição, foi baseada na documentação oficial (então as informações são confiáveis). </p>
<p>Este conteúdo eu iria colocar no como adicional no <a href="https://bit.ly/guia-dev-autodidata">Guia do Dev Autodidata</a> (que é o meu guia para <strong>iniciantes</strong>). Mas resolvi deixar <strong>gratuito</strong> a toda a comunidade, então aproveite e bons estudos!</p>
<p>Se tiver qualquer dúvida (ou sugestões) me envie no <a href="http://bit.ly/pauloluan-insta">Instagram</a>, faço mentoria coletiva (gratuita) diariamente para programadores iniciantes que se sentem perdidos, você será extremamente bem vindo por lá (é só clicar na imagem).</p>
<p><a href="http://bit.ly/pauloluan-insta"><img src="https://media-exp1.licdn.com/dms/image/C4E12AQF9pxdMEVTSQg/article-inline_image-shrink_1500_2232/0/1614414726929?e=1619654400&#x26;v=beta&#x26;t=ti7w8kAyqaK7PRcB9YGnRNv8ircAgThraVR-O1D4T54" alt="Mentoria Gratuita"></a></p>
<p>Um grande abraço, Paulo Luan.</p>
<h3>Dica: Aperte <code class="language-text">ctrl+p</code> e imprima esse artigo, para que você possa fazer anotações!</h3>
<h2>Introdução ao Node.js</h2>
<p>Node.js é um ambiente de execução JavaScript open source e multiplataforma. É uma ferramenta popular para quase todo tipo de projeto!</p>
<p>Node.js roda na engine (motor) V8, o coração do Google Chrome, fora do navegador. Isso permite que o Node.js seja muito performático.</p>
<p>Uma aplicação Node.js roda em um único processo, sem criar uma nova thread para cada requisição. O Node.js provê uma série de primitivas assíncronas para I/O (input/output) em sua biblioteca nativa que previnem códigos JavaScript bloqueantes, e geralmente, bibliotecas em Node.js são escritas usando como padrão paradigmas não-bloqueantes, fazendo com que o comportamento de bloqueio seja uma exceção à regra.</p>
<p>Quando o Node.js executa operações de I/O, como ler dados da rede, acessar um banco de dados ou o sistema de arquivos, em vez de bloquear a thread em execução e gastar ciclos de CPU esperando, o Node.js vai continuar com as operações quando a resposta retornar.</p>
<p>Isso permite com que o Node.js lide com centenas de conexões paralelas em um único servidor, removendo o fardo de gerenciar concorrências em threads, que podem ser fontes significativas de bugs.</p>
<p>Node.js tem uma vantagem única poque milhões de desenvolvedores frontend que programam JavaScript para o navegador possam agora desenvolver código server-side (backend) além do client-side (frontend), sem a necessidade de aprender uma linguagem completamente diferente.</p>
<p>No Node.js os novos padrões do ECMAScript podem ser utilizados sem problemas, como você não precisa esperar todos os seus usuários atualizarem seus navegadores, você tem a liberdade de decidir qual versão do ECMAScript utilizar, bastando trocar a versão do Node.js, além de poder habilitar especificamente features experimentais, bastando executar o Node.Js com as flags apropriadas.</p>
<h2>Um número imenso de bibliotecas</h2>
<p>O npm (node package manager) com sua simples estrutura ajudou na ploriferação do ecossistema Node.js, hospedando atualmente mais de 1,000,000 de pacotes open source que podem ser utilizados gratuitamente.</p>
<h2>Um exemplo de aplicação Node.js</h2>
<p>O exemplo mais comum de Hello World no Node.js é um servidor web:</p>
<iframe
title="Hello world web server"
src="https://glitch.com/embed/#!/embed/nodejs-dev-0001-01?path=server.js&previewSize=30&attributionHidden=true&sidebarCollapsed=true"
alt="nodejs-dev-0001-01 on Glitch"
style="height: 400px; width: 100%; border: 0;">
</iframe>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> http <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'http'</span><span class="token punctuation">)</span>
<span class="token keyword">const</span> hostname <span class="token operator">=</span> <span class="token string">'127.0.0.1'</span>
<span class="token keyword">const</span> port <span class="token operator">=</span> <span class="token number">3000</span>
<span class="token keyword">const</span> server <span class="token operator">=</span> http<span class="token punctuation">.</span><span class="token function">createServer</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token parameter">req<span class="token punctuation">,</span> res</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
res<span class="token punctuation">.</span>statusCode <span class="token operator">=</span> <span class="token number">200</span>
res<span class="token punctuation">.</span><span class="token function">setHeader</span><span class="token punctuation">(</span><span class="token string">'Content-Type'</span><span class="token punctuation">,</span> <span class="token string">'text/plain'</span><span class="token punctuation">)</span>
res<span class="token punctuation">.</span><span class="token function">end</span><span class="token punctuation">(</span><span class="token string">'Hello World\n'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span>
server<span class="token punctuation">.</span><span class="token function">listen</span><span class="token punctuation">(</span>port<span class="token punctuation">,</span> hostname<span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token template-string"><span class="token template-punctuation string">`</span><span class="token string">Server running at http://</span><span class="token interpolation"><span class="token interpolation-punctuation punctuation">${</span>hostname<span class="token interpolation-punctuation punctuation">}</span></span><span class="token string">:</span><span class="token interpolation"><span class="token interpolation-punctuation punctuation">${</span>port<span class="token interpolation-punctuation punctuation">}</span></span><span class="token string">/</span><span class="token template-punctuation string">`</span></span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<p>Para executar esse trecho, salve-o como <code class="language-text">server.js</code> e rode com <code class="language-text">node server.js</code> no seu terminal.</p>
<p>Primeiramente esse código importa o módulo <a href="https://nodejs.org/api/http.html"><code class="language-text">http</code></a>.</p>
<p>O Node.js tem uma <a href="https://nodejs.org/api/">biblioteca padrão</a> fantástica, incluindo suporte de primeira classe para redes.</p>
<p>O método <code class="language-text">createServer()</code> do <code class="language-text">http</code> cria um novo servidor HTTP e o retorna.</p>
<p>É definido para o servidor escutar em uma porta e host name (nome de anfitrião, ao pé da letra) específicos. Quando o servidor está pronto, a função callback é chamada, nesse caso nos informando que o servidor está rodando.</p>
<p>Sempre que uma nova requisição é recebida, o <a href="https://nodejs.org/api/http.html#http_event_request">evento de request</a> é chamado, provendo dois objetos: uma requisição (objeto do tipo <a href="https://nodejs.org/api/http.html#http_class_http_incomingmessage"><code class="language-text">http.IncomingMessage</code></a>) e uma resposta (objeto do tipo <a href="https://nodejs.org/api/http.html#http_class_http_serverresponse"><code class="language-text">http.ServerResponse</code></a>).</p>
<p>Esses 2 objetos são essenciais para manusear a chamada HTTP.</p>
<p>O primeiro provê os detalhes da requisição. Nesse simples exemplo, ele não é utilizado, mas com ele você pode acessar os dados da request e as headers.</p>
<p>O segundo é usado para retornar dados para quem o chamou.</p>
<p>Nesse caso com:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">res<span class="token punctuation">.</span>statusCode <span class="token operator">=</span> <span class="token number">200</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>nós definimos a propriedade statusCode como 200, para indicar uma resposta bem sucedida.</p>
<p>Nós definimos a header de Content-Type (tipo de conteúdo):</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">res<span class="token punctuation">.</span><span class="token function">setHeader</span><span class="token punctuation">(</span><span class="token string">'Content-Type'</span><span class="token punctuation">,</span> <span class="token string">'text/plain'</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>e nós fechamos a resposta, adicionando o conteúdo como um argumento do <code class="language-text">end()</code>:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">res<span class="token punctuation">.</span><span class="token function">end</span><span class="token punctuation">(</span><span class="token string">'Hello World\n'</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<h2>Frameworks e ferramentas para Node.js</h2>
<p>Node.js é uma plataforma de baixo nível. Para facilitar e inspirar os desenvolvedores, milhares de bibliotecas são construidas sob o Node.js pela comunidade.</p>
<p>Muitas delas se estabaleceram como opções populares ao decorrer do tempo. Aqui está uma pequena lista com algumas que valem a pena aprender:</p>
<ul>
<li><a href="https://adonisjs.com/"><strong>AdonisJs</strong></a>: Um framework full-stack altamente focado na ergonomia, estabilidade e confiança do desenvolvedor. Adonis é um dos frameworks web Node.js mais rápidos.</li>
<li><a href="https://expressjs.com/"><strong>Express</strong></a>: Provê os meios de se criar servidores web de uma forma muito simples porém poderosa. Têm uma pegada minimalista, não opinada, focada nas funções essenciais de um servidor, que são a chave do sucesso.</li>
<li><a href="https://fastify.io/"><strong>Fastify</strong></a>: Um framework altamente focado em prover a melhor experiência ao desenvolvedor, com o mínimo de gargalos na performance e uma podesora arquitetura de extensões (plugins). Fastify é um dos mais rápidos frameworks Node.js.</li>
<li><a href="https://www.gatsbyjs.com/"><strong>Gatsby</strong></a>: Um gerador de sites estáticos baseado em <a href="https://reactjs.org/">React</a>, gerido com <a href="https://graphql.org/">GraphQL</a> e com um ecossistema de plugins e templates iniciais requíssimo.</li>
<li><a href="https://hapijs.com"><strong>hapi</strong></a>: Um rico framework para construção de aplicações e serviços que habilitam desenvolvedores a focar na escrita das lógicas de aplicação reutilizáveis em vez de perder tempo montando a infraestrutura.</li>
<li><a href="http://koajs.com/"><strong>koa</strong></a>: É mantido pelo time por trás do Express, pretende ser ainda menor e simples, construido sob muitos anos de conhecimento. O novo projeto nasceu da necessidade de criar mudanças incompatíveis sem romper com a comunidade existente.</li>
<li><a href="https://loopback.io/"><strong>Loopback.io</strong></a>: Faz com que seja fácil construir aplicações modernas que requerem integrações complexas.</li>
<li><a href="https://meteor.com"><strong>Meteor</strong></a>: Um framework full-stack incrivelmente poderoso, permite que você crie aplições Javascript com uma abordagem isomórfica, compartilhando código entre cliente e servidor. É uma ferramenta generalista que tenta fornecer tudo, que agora integra com bibliotecas frontend como <a href="https://reactjs.org/">React</a>, <a href="https://vuejs.org/">Vue</a>, e <a href="https://angular.io">Angular</a>. Também pode ser utilizado para criar aplicativos mobile.</li>
<li><a href="https://github.com/zeit/micro"><strong>Micro</strong></a>: Provê um servidor enxuto para criação de microserviços HTTP assíncronos.</li>
<li><a href="https://nestjs.com/"><strong>NestJS</strong></a>: Um framework Node.js progressivo baseado em Typescript para construção de aplicação de nível empresarial eficientes, confiáveis e escaláveis.</li>
<li><a href="https://nextjs.org/"><strong>Next.js</strong></a>: Framework <a href="https://reactjs.org">React</a> que fornce a melhor experiência de desenvolvimento, com todos os recursos que você precisa para produção: renderização híbrida entre servidor (SSR) e estáticos, suporte ao TypeScript, bundle otimizado, rotas pre-fetching, e mais.</li>
<li><a href="https://nx.dev/"><strong>Nx</strong></a>: Um conjunto de ferramentas para desenvolvimento full-stack em monorepo, utilizando NestJS, <a href="https://reactjs.org/">React</a>, <a href="https://angular.io">Angular</a>, e mais! Nx ajuda a escalar seu desenvolvimento de um time construindo uma aplicação para múltiplos times colaborando em múltiplas aplicações!</li>
<li><a href="https://sapper.svelte.dev/"><strong>Sapper</strong></a>: Sapper é um framework para construção de aplicações web de todos os tamanhos, com uma bela experiências de desenvolvimento e roteamento flexível baseado em filesystems. Oferece SSR e muito mais!</li>
<li><a href="https://socket.io/"><strong>Socket.io</strong></a>: Um motor de comunição em tempo real para construir aplicações em rede.</li>
<li><a href="https://strapi.io/"><strong>Strapi</strong></a>: Strapi é um CMS flexível, open-source e independente, que fornece aos desenvolvedores a liberdade de escolher seus frameworks e ferramentas favoritos, enquanto também permite que editores administrem e distribuam seus conteúdos de maneira fácil. Por fazer o painel administrativo uma API extensível através de um sistema de plugins, o Strapi permite que as maiores empresas do mundo acelerem a entrega de conteúdo enquanto constroem belas experiências digitais.</li>
</ul>
<h2>Uma breve história do Node.js</h2>
<p>Acredite ou não, Node.js só tem 11 anos de idade.</p>
<p>Em comparação, <a href="https://en.wikipedia.org/wiki/JavaScript#Beginnings_at_Netscape">o JavaScript tem 24 anos</a> e <a href="https://howoldistheinter.net/">a Web tem 31 anos</a>.</p>
<p>Na tecnologia, 11 anos não é um tempo muito longo, mas o Node.js parece ter existido sempre.</p>
<p>Eu tive o prazer de trabalhar com Node.js desde os primórdios quando ele só tinha 2 anos, e apesar das informações limitadas pela web, você já podia sentir que o crescimento seria enorme.</p>
<p>Nesse post, vamos dissecar a história do Node.js, para colocar as coisas em perspectiva.</p>
<h2>Um pouco de história</h2>
<p>JavaScript é uma linguagem de programação que foi criada no Netscape como uma ferramente de scripts para manipulação de páginas web dentro do browser <a href="https://en.wikipedia.org/wiki/Netscape_Navigator">Netscape Navigator</a>.</p>
<p>Parte do modelo de negócios da Netscape era vender servidores web, o que incluia um ambiente chamado <em>Netscape LiveWire</em>, que podia criar páginas dinâmicas usando JavaScript no server-side.
Infelizmente, o <em>Netscape LiveWire</em> não obteve muito sucesso e JavaScript server-side não era popular até recentemente, com a introdução do Node.js</p>
<p>Um fator chave que levou o Node.js ao topo foi o timing. Apenas alguns poucos anos antes, Javascript começou a ser mais considerado como uma linguagem séria, graças às aplicações “Web 2.0” (como Flickr, Gmail, etc.) que mostraram ao mundo como poderia ser uma experiência moderna na web.</p>
<p>Motores JavaScript (engines) também se tornaram consideravelmente melhores com a competição entre vários browsers para fornecer aos usuários a melhor performance. Times de desenvolvimento por trás dos maiores browsers trabalharam duro para oferecer melhor suporte para o JavaScript e encontrar meios que o fizesse rodar mais rápido. A engine que roda por baixo dos panos do Node.js, V8 (também conhecida como Chrome V8 por ser a engine Javascript open-source do Projeto Chromium), melhorou significamente devido a esta competição.</p>
<p>Aconteceu de o Node.js ser criado no lugar certo e na hora certa, mas sorte não é a única razão do porquê ser tão popular hoje. Ele introduz várias abordagens e estratégias inovadoras para o desenvolvimento sever-side com JavaScript que já ajudaram diversos desenvolvedores.</p>
<h2>2009</h2>
<ul>
<li>Nasce o Node.js</li>
<li>A primeira forma do <a href="https://www.npmjs.com/">npm</a> é criada</li>
</ul>
<h2>2010</h2>
<ul>
<li>Nasce o <a href="https://expressjs.com/">Express</a></li>
<li>Nasce o <a href="https://socket.io">Socket.io</a></li>
</ul>
<h2>2011</h2>
<ul>
<li>npm alcança a versão 1.0</li>
<li>Grandes empresas começam a adotar Node.js: LinkedIn, Uber, etc.</li>
<li>Nasce o <a href="https://hapijs.com">hapi</a></li>
</ul>
<h2>2012</h2>
<ul>
<li>Adoção continua muito rápida</li>
</ul>
<h2>2013</h2>
<ul>
<li>Primeira grande plataforma de blogs usando Node.js: <a href="https://ghost.org/">Ghost</a></li>
<li>Nasce o <a href="https://koajs.com/">Koa</a></li>
</ul>
<h2>2014</h2>
<ul>
<li>O Grande Fork: <a href="https://iojs.org/">io.js</a> é o maior fork do Node.js, com o objetivo de introduzir suporte ao ES6 e crescer rapidamente.</li>
</ul>
<h2>2015</h2>
<ul>
<li>Nasce a <a href="https://foundation.nodejs.org/">Node.js Foundation</a></li>
<li>IO.js é mergeado de volta ao Node.js</li>
<li>npm introduz módulos privados</li>
<li>Node.js 4 (versões 1, 2 e 3 nunca foram lançadas previamente)</li>
</ul>
<h2>2016</h2>
<ul>
<li>O incidente de <a href="https://blog.npmjs.org/post/141577284765/kik-left-pad-and-npm">leftpad</a></li>
<li>Nasce o <a href="https://yarnpkg.com/en/">Yarn</a></li>
<li>Node.js 6</li>
</ul>
<h2>2017</h2>
<ul>
<li>npm aumenta o foco em segurança</li>
<li>Node.js 8</li>
<li>HTTP/2</li>
<li>V8 introduz o Node.js em sua suite de testes, fazendo do Node.js oficialmente um alvo da engine, em adição ao Chrome</li>
<li>3 bilhões de downloads no npm toda semana</li>
</ul>
<h2>2018</h2>
<ul>
<li>Node.js 10</li>
<li><a href="https://nodejs.org/api/esm.html">ES modules</a>: suporte experimental ao .mjs</li>
<li>Node.js 11</li>
</ul>
<h2>2019</h2>
<ul>
<li>Node.js 12</li>
<li>Node.js 13</li>
</ul>
<h2>2020</h2>
<ul>
<li>Node.js 14</li>
<li>Node.js 15</li>
</ul>
<h2>Como instalar o Node.js</h2>
<p>Node.js pode ser instalado de diferentes formas. Esse post destaca as mais comuns e convenientes.</p>
<p>Pacotes oficiais para todas as principais plataformas estão disponíveis em <a href="https://nodejs.org/en/download/">https://nodejs.org/en/download/</a>.</p>
<p>Uma maneira muito conveniente de instalar o Node.js é através de um gerenciador de pacotes. Neste caso, cada sistema operacional tem sua abordagem mais adequada.</p>
<p>No macOS, <a href="https://brew.sh/">Homebrew</a> é a alternativa oficial, e - uma vez instalado - permite que a instalação do Node.js seja feita facilmente, rodando esse comando na CLI:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">brew <span class="token function">install</span> node</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Outros gerenciadores de pacote para Linux e Windows estão listados em <a href="https://nodejs.org/en/download/package-manager/">https://nodejs.org/en/download/package-manager/</a>.</p>
<p><code class="language-text">nvm</code> é um maneira muito popular de rodar Node.js. Ele permite que você troque facilmente entre versões, e instale novas versões para testar e troque de volta caso algo pare de funcionar, por exemplo.</p>
<p>Também é muito útil para testar seu código com versões antigas do Node.js</p>
<p>Veja <a href="https://github.com/creationix/nvm">https://github.com/creationix/nvm</a> para mais informações sobre essa opção.</p>
<p>Minha sugestão é utilizar o instalador oficial se você só estiver começando e não utiliza o Homebrew, caso contrário, o Homebew é a minha solução favorita.</p>
<p>Em todo caso, quando o Node.js é instalado você terá acesso ao comando executável <code class="language-text">node</code> na linha de comando.</p>
<h2>O que devo saber de Javascript para usar o Node.JS?</h2>
<p>Como um iniciante, é difícil chegar no ponto onde você é confiante o suficiente nas suas habilidades de programação.</p>
<p>Enquanto aprende a programar, você também pode ficar confuso sobre onde o JavaScript termina, e onde o Node.js começa, e vice versa.</p>
<p>Eu recomendo que você tenha um bom domínio dos principais conceitos do JavaScript antes de mergulhar no Node.js:</p>
<ul>
<li>Estrutura Léxica</li>
<li>Expressões</li>
<li>Tipos</li>
<li>Variáveis</li>
<li>Funções</li>
<li>this</li>
<li>Arrow Functions</li>
<li>Loops</li>
<li>Escopos</li>
<li>Arrays</li>
<li>Template Literals</li>
<li>Semicolons (;)</li>
<li>Strict Mode</li>
<li>ECMAScript 6, 2016, 2017</li>
</ul>
<p>Com esses conceitos em mente, você está no caminho certo para se tornar um desenvolvedor proficiente em JavaScript, tanto Browser como também Node.js.</p>
<p>Os conceitos a seguir também são essenciais para entender programação assíncrona, que é uma parte fundamental do Node.js:</p>
<ul>
<li>Programação Assíncrona e callbacks</li>
<li>Timers</li>
<li>Promises</li>
<li>Async e Await</li>
<li>Closures</li>
<li>Event Loop</li>
</ul>
<h2>Qual a diferença do Node.JS e do Browser?</h2>
<p>Ambos browser e Node.js utilizam JavaScript como sua linguagem de programação.</p>
<p>Construir aplicações que rodem no browser é uma coisa completamente diferente de construir aplicações Node.js</p>
<p>Apesar do fato que é sempre JavaScript, há fatores chave que tornam a experiência radicalmente diferente.</p>
<p>Da perspectiva de um desenvolvedor frontend que usa JavaScript extensivamente, aplicações Node.js trazem consigo uma enorme vantagem: o conforto de programar tudo - o frontend e o backend - em uma única linguagem.</p>
<p>Você tem uma grande oportunidade porque nós sabemos quão difícil é para aprender, completa e profundamente, uma nova linguagem de programação, e por usar a mesma linguagem para fazer todo o trabalho na web - tanto no servidor quanto no cliente, você está em uma posição única de vantagem.</p>
<p>O que muda é o ecossistema.</p>
<p>No browser, na maioria do tempo o que você está fazendo é interagindo com o DOM, ou outras APIs Web como Cookies. Isso não existe no Node.js, é claro. Você não tem o <code class="language-text">document</code>, <code class="language-text">window</code> e todos os outros objetos que são providos pelo browser.</p>
<p>E no browser, nós não temos as APIs legais que o Node.js provê com seus módulos, como a funcionalidade de acesso ao filesystem.</p>
<p>Outra grande diferença é que no Node.js você controla seu ambiente. A não ser que você esteja criando uma aplicação open source que qualquer um pode hospedar em qualquer lugar, você sabe em qual versão do Node.js a aplicação vai rodar. Comparado ao ambiente do browser, onde você não tem o luxo de escolher qual browser seu visitante vai utilizar, isso é muito conveniente.</p>
<p>Isso significa que você pode escrever códigos com os modernos ES6-7-8-9, se atentando ao suporte da sua versão do Node.js.</p>
<p>Visto que o JavaScript se move muito rápido, mas os browsers podem ser um pouco lentos para atualizarem, as vezes na web, você está preso em versões velhas do JavaScript / ECMAScript.</p>
<p>Você pode utilizar o Babel para transformar seu código em um formato compátivel com ES5 antes de enviar para o browser, mas no Node.js, você não precisa disso.</p>
<p>Outra diferença é que o Node.js utiliza o sistema de módulos CommonJS, enquanto que nos browsers ainda estamos vendo o inicio da implementação do padrão ES Modules.</p>
<p>Na prática, isso signifca que por enquanto você utiliza <code class="language-text">require()</code> no Node.js e <code class="language-text">import</code> no browser.</p>
<h2>O motor V8 do JAvascript</h2>
<p>V8 é o nome da engine JavaScript que roda no Google Chrome. É a coisa que pega nosso JavaScript e o executa enquanto navegamos com o Chrome.</p>
<p>V8 provê o ambiente de execução em que o JavaScript executa. O DOM, e outras APIs web são fornecidas pelo browser.</p>
<p>O legal é que a engine JavaScript é independente do browser que ela está hospedada. Essa funcionalidade chave possibilitou a ascensão do Node.js. A V8 foi escolhida como engine por trás do Node.js em 2009, e com a explosão de popularidade do Node.js, a V8 se tornou a engine que agora possibilita uma quantidade incrível de código sever-side escrito em JavaScript.</p>
<p>O ecossistema Node.js é enorme e isso graças à V8 que também possibilitou aplicações desktop, com projetos como o Electron.</p>
<h2>Outras engines JS</h2>
<p>Outros browsers têm suas própias engines:</p>
<ul>
<li>Firefox tem a <a href="https://developer.mozilla.org/en-US/docs/Mozilla/Projects/SpiderMonkey"><strong>SpiderMonkey</strong></a></li>
<li>Safari tem a <a href="https://developer.apple.com/documentation/javascriptcore"><strong>JavaScriptCore</strong></a> (também chamada de Nitro)</li>
<li>Edge foi originalmente basedo na <a href="https://github.com/Microsoft/ChakraCore"><strong>Chakra</strong></a> mas recentemente <a href="https://support.microsoft.com/en-us/help/4501095/download-the-new-microsoft-edge-based-on-chromium">foi refeito utilizando Chromium</a> e a V8.</li>
</ul>
<p>e existem muitas outras também.</p>
<p>Todas essas engines implementam o <a href="https://www.ecma-international.org/publications/standards/Ecma-262.htm">padrão ECMA ES-262</a>, também chamado de ECMAScript, o padrão utilizado pelo JavaSript.</p>
<h2>A busca por performance</h2>
<p>V8 foi escrita em C++, e é continuamente melhorada. É portável e roda no Mac, Windows, Linux e diversos outros sistemas.</p>
<p>Nessa introdução à V8, vamos ignorar os detalhes de implementação: eles podem ser encontrados em sites mais apropriados (por exemplo, o <a href="https://v8.dev/">site oficial da V8</a>), e eles mudam com o passar do tempo, frequentemente.</p>
<p>V8 está sempre evoluindo, assim como as outras engines JavaScript ao seu redor, para agilizar a Web e o ecossistema Node.js.</p>
<p>Na web, há uma corrida por performance que vem sendo travada por anos, e nós (como usuários e desenvolvedores) nos beneficiamos muito por essa competição, porque nós possuímos máquinas mais rápidas e otimizadas ano a ano.</p>
<h2>Compilação</h2>
<p>JavaScript é geralmente considerado como uma linguagem interpretada, mas engines modernas de JavaScript não o interpretam apenas, elas o compilam.</p>
<p>Isso vem acontecendo desde 2009, quando o compilador JavaScript SpiderMonkey foi adicionado no Firefox 3.5, e todo mundo seguiu essa ideia.</p>
<p>JavaScript é internamente compilado pela v8 com <strong>compilação just-in-time</strong> (JIT) para acelerar a execução.</p>
<p>Isso pode parecer contra-intuitivo, mas desde a introdução do Google Maps em 2004, o JavaScript evoluiu de uma linguagem que geralmente executava poucas dúzias de linhas de código, para aplicações completas com centenas de milhares de linhas de código executando no browser.</p>
<p>Nossas aplicações agora podem rodar por horas dentro do browser, em vez de uma simples validação de regras de formulários ou scripts banais.</p>
<p>Nesse <em>novo mundo</em>, compilar JavaScript faz total sentido porque, embora possa demorar um pouco mais para termos o código JavaScript <em>pronto</em>, uma vez concluída a compilação temos muito mais desempenho do que código puramente interpretado.</p>
<h2>Rode scripts do Node a partir da linha de comando do Linux</h2>
<p>A maneira mais usual de rodar um programa Node.js é executando o comando <code class="language-text">node</code> disponível globalmente (uma vez instalado o Node.js) e passando o nome do arquivo desejado.</p>
<p>Considerando que o arquivo principal da sua aplicação Node.js se chame <code class="language-text">app.js</code>, você pode executá-lo digitando:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">node app.js</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Enquanto executa o comando, tenha certeza de estar no mesmo diretório que contêm o arquivo <code class="language-text">app.js</code>.</p>
<h2>Como sair de um programa Node.JS</h2>
<p>Há várias maneiras de finalizar uma aplicação Node.js.</p>
<p>Com o programa rodando no console, você pode fechá-lo com <code class="language-text">ctrl-C</code>, mas o que queremos discutir aqui é a maneira programática de fazer isso.</p>
<p>Vamos começar com a maneira mais drástica, e note porque é melhor você <em>não</em> utilizá-la:</p>
<p>O módulo nativo <code class="language-text">process</code> provê um método prático que permite a você, programaticamente, sair de um programa Node.js: <code class="language-text">process.exit()</code>.</p>
<p>Quando o Node.js executa essa linha, o processo é forçado a terminar imediatamente.</p>
<p>Isso significa que qualquer callback pendente, qualquer request de rede sendo enviada, qualquer acesso ao filesystem, ou processos de escrita no <code class="language-text">stdout</code> ou <code class="language-text">stderr</code> - tudo será finalizado de imediato <em>desgraciadamente</em>.</p>
<p>Se isso está bem para você, basta passar um inteiro que sinalize o código de saída para o sistema operacional:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">process<span class="token punctuation">.</span><span class="token function">exit</span><span class="token punctuation">(</span><span class="token number">1</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Por padrão, o código de saída é <code class="language-text">0</code>, que significa sucesso. Códigos de saída diferentes tem significados diferentes, que você pode querer utilizar no seu sistema para se comunicar com outros programas.</p>
<p>Você pode ler mais sobre os códigos de saída em <a href="https://nodejs.org/api/process.html#process_exit_codes">https://nodejs.org/api/process.html#process_exit_codes</a>;</p>
<p>Você também pode definir a propriedade <code class="language-text">process.exitCode</code> como:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">process<span class="token punctuation">.</span>exitCode <span class="token operator">=</span> <span class="token number">1</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>e quando o programa for encerrado posteriormente, o Node.js retornará esse código de saída.</p>
<p>Um programa irá sair graciosamente quando todos os processos estiverem completos.</p>
<p>Muitas vezes nós iniciamos servidores Node.js, como esse servidor HTTP:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> express <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'express'</span><span class="token punctuation">)</span>
<span class="token keyword">const</span> app <span class="token operator">=</span> <span class="token function">express</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
app<span class="token punctuation">.</span><span class="token function">get</span><span class="token punctuation">(</span><span class="token string">'/'</span><span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token parameter">req<span class="token punctuation">,</span> res</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
res<span class="token punctuation">.</span><span class="token function">send</span><span class="token punctuation">(</span><span class="token string">'Hi!'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span>
app<span class="token punctuation">.</span><span class="token function">listen</span><span class="token punctuation">(</span><span class="token number">3000</span><span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=></span> console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'Server ready'</span><span class="token punctuation">)</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<p>Esse programa nunca terá um fim. Se você chamar <code class="language-text">process.exit()</code>, qualquer requisição corrente/pendente será abortada. Isso <em>não é legal</em>.</p>
<p>Nesse caso, você precisa enviar ao comando um sinal de SIGTERM, e lidar com o processo desse sinal:</p>
<blockquote>
<p>Nota: <code class="language-text">process</code> não requer importação, está disponível automaticamente.</p>
</blockquote>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> express <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'express'</span><span class="token punctuation">)</span>
<span class="token keyword">const</span> app <span class="token operator">=</span> <span class="token function">express</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
app<span class="token punctuation">.</span><span class="token function">get</span><span class="token punctuation">(</span><span class="token string">'/'</span><span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token parameter">req<span class="token punctuation">,</span> res</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
res<span class="token punctuation">.</span><span class="token function">send</span><span class="token punctuation">(</span><span class="token string">'Hi!'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span>
<span class="token keyword">const</span> server <span class="token operator">=</span> app<span class="token punctuation">.</span><span class="token function">listen</span><span class="token punctuation">(</span><span class="token number">3000</span><span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=></span> console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'Server ready'</span><span class="token punctuation">)</span><span class="token punctuation">)</span>
process<span class="token punctuation">.</span><span class="token function">on</span><span class="token punctuation">(</span><span class="token string">'SIGTERM'</span><span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
server<span class="token punctuation">.</span><span class="token function">close</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'Process terminated'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<blockquote>
<p>O que são sinais? Sinais são um sistema de intercomunicação POSIX: uma notificação enviada para um processo com o objetivo de notificar que um evento ocorreu.</p>
</blockquote>
<ul>
<li><code class="language-text">SIGKILL</code> é o sinal que diz ao processo para que finalize imediatamente, e agirá idealmente como o <code class="language-text">process.exit()</code>.</li>
<li><code class="language-text">SIGTERM</code> é o sinal que diz ao processo para que termine graciosamente. É o sinal que é enviado por generenciadores de processo como <code class="language-text">upstart</code> ou <code class="language-text">supervisord</code> e muitos outros.</li>
</ul>
<p>Você pode enviar esse sinal por dentro da aplicação, em outra função:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">process<span class="token punctuation">.</span><span class="token function">kill</span><span class="token punctuation">(</span>process<span class="token punctuation">.</span>pid<span class="token punctuation">,</span> <span class="token string">'SIGTERM'</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>ou de outro programa Node.js em execução, ou qualquer outra aplicação rodando em seu sistema que saiba o PID do processo que você deseja fianlizar.</p>
<h2>Como ler Variáveis de ambiente a partir do Node.js?</h2>
<p>O módulo nativo <code class="language-text">process</code> do Node.js fornece a propriedade <code class="language-text">env</code> que armazena todas as variáveis de ambiente que foram definidas no momento de início da aplicação.</p>
<p>Aqui vai um exemplo que acessa a variável de ambiente NODE_ENV, que é definida com o valor <code class="language-text">development</code> por padrão.</p>
<blockquote>
<p>Nota: <code class="language-text">process</code> não requer importação, está disponível automaticamente.</p>
</blockquote>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">process<span class="token punctuation">.</span>env<span class="token punctuation">.</span><span class="token constant">NODE_ENV</span> <span class="token comment">// "development"</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Defini-lá para “production” antes do script executar contará ao Node.js que é um ambiente de produção.</p>
<p>Da mesma forma, você pode acessar/definir qualquer variável de ambiente customizada.</p>
<h2>Como usar o REPL no Node</h2>
<p>Nós usamos o comando <code class="language-text">node</code> para executar scripts Node.js:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">node script.js</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Se nós omitirmos o nome do arquivo, iniciaremos o modo REPL:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">node</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<blockquote>
<p>Nota: REPL (Read Evaluate Print Loop) é um ambiente para linguagem de programação (basicamente uma aba de console) que lê instruções individuais do input do usuário e após a execução, retorna o resultado no console.</p>
</blockquote>
<p>Se você tentar isso agora no seu terminal, isto é o que vai acontecer:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">❯ node
<span class="token operator">></span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span></span></pre></div>
<p>o comando permanece em modo de espera (idle) e aguarda alguma entrada.</p>
<blockquote>
<p>Dica: se você não tem certeza de como abrir seu terminal, pesquise por “How to open terminal on &#x3C;seu SO>“.</p>
</blockquote>
<p>Para ser mais exato, o REPL está aguardando a entrada de código JavaScript.</p>
<p>Vamos começar de forma simples:</p>
<div class="gatsby-highlight" data-language="console"><pre style="counter-reset: linenumber NaN" class="language-console line-numbers"><code class="language-console">&gt; console.log(&#39;test&#39;)
test
undefined
&gt;</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span></span></pre></div>
<p>O primeiro valor, <code class="language-text">test</code>, é a saída que esperavamos do log do console, e depois tivemos um undefined, que é o retorno de rodar <code class="language-text">console.log()</code>.</p>
<p>Agora podemos inserir uma nova entrada de JavaScript.</p>
<h2>Use o tab para autocomplete</h2>
<p>O legal do REPL é que ele é interativo.</p>
<p>Conforme você escreve seu código, se você pressionar o tecla <code class="language-text">tab</code> o REPL vai tentar completar o que foi escrito para combinar com variáveis previamente definidas.</p>
<h2>Explorando objetos do JavaScript</h2>
<p>Tente digitar o nome de uma classe do JavaScript, como <code class="language-text">Number</code>, e adicione um ponto e pressione <code class="language-text">tab</code>.</p>
<p>O REPL vai listar todas as propriedades e métodos que você pode acessar naquela classe:</p>
<p><span
class="gatsby-resp-image-wrapper"
style="position: relative; display: block; margin-left: auto; margin-right: auto; max-width: 590px;"
>
<a
class="gatsby-resp-image-link"
href="/static/2b60eb9487f93b672da38e391d2e5e56/4a421/tab.png"
style="display: block"
target="_blank"
rel="noopener"
>
<span
class="gatsby-resp-image-background-image"
style="padding-bottom: 57.12979890310786%; position: relative; bottom: 0; left: 0; background-image: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAALCAYAAAB/Ca1DAAAACXBIWXMAAAsSAAALEgHS3X78AAACdklEQVQoz21SyW7aYBD2CQiqSlEVpWDCvoTFRKwxS8DYQBzWY+5Rby3Ki/QFeu+ph0RtD0gVEpA8Ql6ghySqmtBaIlKjOL+nM66CWrWWPs0wyz/ffAP37tUby6f3b19+/PzhaD47HU2n09FsNhvN53PTTiaT0cnxyegYQf7p6XxVQxbxGmuPzs7ODsfjsZ179uSpS5Elpu6rUCqVoFKpmFYUxZVPKJfL//iUr1arkMvl4ODg4OfF5UWAe76+zrfbewsqaEiN+2azqScSCd3n8+nk53M5XZIkPZ/P616vV49Go7qiKHqxWDTzOPh+0+MBVVW/3tzcBDme9/DYoFWrFcAC1mq1jLQgGKFQyFBkxSiXSka9XjcymYzh9/uMRDJpyLJs7O7uGrVajeIslUrBcDi8vry6CnIbGy/4nR1RoxUFIYVNfggEAhAOh82VKE7sQ8EgIGvY2oqbayJDiMVigKyZy+WCTqdzvVgsgpzbzfONhqw1JAmSON2D9KkRGQJOh+10GuLxuBkjRKLR3/HtbcD1KcZ4nodut3uNHzHc4AuFokYTS6JoUHMsFjUfRN0gm81AAS35OBAikYj5mw6B+gLqzWgQMTQ13PR6+U6n+wNFBdTkIZvNMkEQGE5n/X6f7asqU/f2GF6WpdNplsLcYDBg7XabYQ8TxZ0Hkgcf/GY+iBvTUZYoMqDYgAcBWoH0kWUF8CCmhkHUMIAglnhlU0eyOARIw16v913TtBBnsVjcWHSBh7hDgZd4lFtc4Rb9FfC6K/8x90fN0u123+G/48v5+XmAw8/qcDgKa2trdavVWiPYbLa/8L/YI+x2O+Ulp9NZQGK2XxcCVXBQQWM0AAAAAElFTkSuQmCC'); background-size: cover; display: block;"
></span>
<img
class="gatsby-resp-image-image"
alt="Pressionando tab as propriedades do objeto são reveladas"
title="Pressionando tab as propriedades do objeto são reveladas"
src="/static/2b60eb9487f93b672da38e391d2e5e56/799d3/tab.png"
srcset="/static/2b60eb9487f93b672da38e391d2e5e56/00d96/tab.png 148w,
/static/2b60eb9487f93b672da38e391d2e5e56/0b23c/tab.png 295w,
/static/2b60eb9487f93b672da38e391d2e5e56/799d3/tab.png 590w,
/static/2b60eb9487f93b672da38e391d2e5e56/2a3d6/tab.png 885w,
/static/2b60eb9487f93b672da38e391d2e5e56/4a421/tab.png 1094w"
sizes="(max-width: 590px) 100vw, 590px"
loading="lazy"
/>
</a>
</span></p>
<h2>Explore objetos globais</h2>
<p>Você pode inspecionar os objetos globais que você tem acesso digitando <code class="language-text">global.</code> e pressionando <code class="language-text">tab</code>:</p>
<p><span
class="gatsby-resp-image-wrapper"
style="position: relative; display: block; margin-left: auto; margin-right: auto; max-width: 590px;"
>
<a
class="gatsby-resp-image-link"
href="/static/c2bef52ca393ecb33846c54af34927a1/4a421/globals.png"
style="display: block"
target="_blank"
rel="noopener"
>
<span
class="gatsby-resp-image-background-image"
style="padding-bottom: 91.6819012797075%; position: relative; bottom: 0; left: 0; background-image: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAASCAYAAABb0P4QAAAACXBIWXMAAAsSAAALEgHS3X78AAADQklEQVQ4y32UOU8bURSFLSAWSo+CPeBlxmYz4AW8sdoztjE2AhNSUEcpGVHlb+RHpIUuSDEBIpYiBXWK9BSegMFNFInB7+bcF4ZACLF09TRv+d65595n17u1t+79D+/ffP5ysLn3aW+jXq+bBwcH5tHRkXl8fGzu7u6aW1tb5vb2trmzs2Pu7e+Zh4eHcv02NhCbJycnr+v1j89dfS+8nrWXtfbaqzWqVCpUq9VI13XKZDKUTqepUChQqVTCWKSV5WVaXFykqakpuc6RzWZpcnKS1tfXf56dnQVdgWBQ0Q2jyZOGrl9jg61pmu3xeOze3l4b83Y+l7Onp6fthYUFOx6P24qi3EVfX991T08PYa1xeXmlukKhkFIul1usAgrb+Xxe4GYRiUSEr98nMtmMwGZRMAxRKpZEOp0SgUBAqKoqgsEgj22AqVqtnp+fX6guKFGgojUxMUGxWEwMDAwQFBI2ks/no7GxMeI1zmB8fJwAIQDJ7/fL8T7w4qKpurBBgaqWns+zN3yrhEG5PMAg9jSXy1EymaQw5lVcODgwKC/G/ofAUCisIN0W0qKlalUUi0VaWlqi1doqeyqNv7VDgssoCg7TysoKxeMxVvoQqGkhBZAWgwz4lEgkiIPTjI5HCcWQQIbxPIpCExjZmn+mrKqaBPKB2dlZMTY6Sv39/dI/r9dLqVSK+DJunym0iAY7UFkJu7XnL6CmKaheCz6yEsHG394soU4vsiUzUMvzDHKK86RCw9DZdOGkwgcYyAoZxheile5ATwIdD/lQJDIiePERkF+KUZBV5Xa5D30SyMbPzMyIoaEhpx3uUmYPq5WqfGYO0InHwNAfIFd5FEUJh8MPFOIl0fz8vOzN/ymULwVqGHjFxut5/QYetlHlNjcsj1DYxpqMVCrZZgBgcp1HfN8oipeB35vNy99vGf79kM2LpkXr0MjIyJ1fnGYZ/lYWK5wB1IccZTJ4H7cRgK1Go6G5fH6/B5Bv8K+JtBrRaNQaHh62/D6fhVQsvG9rbm7OgkIrm8lYgFlQbsEOGbi0gX+lJi77enp66nfh9wwxhEggYk50dnbGurq6YvfnOjo6Ym63W4687gS+E93d3cMer9f9CwpdL1MX+qFQAAAAAElFTkSuQmCC'); background-size: cover; display: block;"
></span>
<img
class="gatsby-resp-image-image"
alt="Globals"
title="Globals"
src="/static/c2bef52ca393ecb33846c54af34927a1/799d3/globals.png"
srcset="/static/c2bef52ca393ecb33846c54af34927a1/00d96/globals.png 148w,
/static/c2bef52ca393ecb33846c54af34927a1/0b23c/globals.png 295w,
/static/c2bef52ca393ecb33846c54af34927a1/799d3/globals.png 590w,
/static/c2bef52ca393ecb33846c54af34927a1/2a3d6/globals.png 885w,
/static/c2bef52ca393ecb33846c54af34927a1/4a421/globals.png 1094w"
sizes="(max-width: 590px) 100vw, 590px"
loading="lazy"
/>
</a>
</span></p>
<h2>A variável especial _</h2>
<p>Se depois de um código você digitar <code class="language-text">_</code>, isso fará com que seja exibido o resultado da última operação.</p>
<h2>Comandos com ponto (dot commands)</h2>
<p>O REPL tem alguns comandos especiais, todos começando com um <code class="language-text">.</code>. Eles são:</p>
<ul>
<li><code class="language-text">.help</code>: exibe a guia de ajuda dos dot commands.</li>
<li><code class="language-text">.editor</code>: habilita o modo de editor, para escrever múltiplas linhas de código JavaScript com facilidade. Uma vez nesse modo, pressione ctrl-D para executar o código que foi escrito.</li>
<li><code class="language-text">.break</code>: quando estiver inserindo um código com múltiplas linhas, utilizar o comando .break fará com que a entrada seja abortada. Mesma funcionalidade de pressionar ctrl-C.</li>
<li><code class="language-text">.clear</code>: reinicia o contexto do REPL para um objeto vazio e cancela qualquer entrada corrente de múltiplas linhas.</li>
<li><code class="language-text">.load</code>: carrega um arquivo JavaScript, relativo ao diretório atual.</li>
<li><code class="language-text">.save</code>: salva todas suas entradas na sessão REPL em um arquivo (especifique um nome pro arquivo)</li>
<li><code class="language-text">.exit</code>: sai do repl (mesmo funcionamento de pressionar ctrl-C duas vezes)</li>
</ul>
<p>O REPL sabe quando você está inserindo uma entrada com múltiplas linhas sem a necessidade de utilizar o <code class="language-text">.editor</code>.</p>
<p>Por exemplo, se você começar a digitar uma iteração como essa:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">,</span> <span class="token number">2</span><span class="token punctuation">,</span> <span class="token number">3</span><span class="token punctuation">]</span><span class="token punctuation">.</span><span class="token function">forEach</span><span class="token punctuation">(</span><span class="token parameter">num</span> <span class="token operator">=></span> <span class="token punctuation">{</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>e pressionar <code class="language-text">enter</code>, o REPL irá para uma nova linha que começa com 3 pontos, indicando que você pode continuar a trabalhar naquele bloco.</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token operator">...</span> console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>num<span class="token punctuation">)</span>
<span class="token operator">...</span> <span class="token punctuation">}</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span></span></pre></div>
<p>Se você digitar <code class="language-text">.break</code> no fim de uma linha, o modo múltiplas linhas irá parar e o código não será executado.</p>
<h2>O Node.JS aceita argumentos a partir da linha de comando.</h2>
<p>Você pode passar qualquer quantidade de argumentos quando está invocando uma aplicação Node.js, usando:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">node app.js</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Argumentos podem ser com chave e valor ou diretos (sem chave).</p>
<p>Por exemplo:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">node app.js joe</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>ou</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">node app.js <span class="token assign-left variable">name</span><span class="token operator">=</span>joe</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Isso muda em como você obterá os valores no código Node.js.</p>
<p>A maneira de obtê-los é usando o objeto nativo <code class="language-text">process</code>.</p>
<p>Ele expõe uma propriedade chamada <code class="language-text">argv</code>, que é um array que contêm todos os argumentos passados na invocação.</p>
<p>O primeiro elemento é o caminho absoluto do comando <code class="language-text">node</code>.</p>
<p>O segundo é o caminho absoluto do arquivo em execução.</p>
<p>Todos os argumentos adicionais estão presentes da terceira posição em diante.</p>
<p>Você pode iterar sobre todos os argumentos (incluindo o caminho do node e o do arquivo) usando um loop:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">process<span class="token punctuation">.</span>argv<span class="token punctuation">.</span><span class="token function">forEach</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token parameter">val<span class="token punctuation">,</span> index</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token template-string"><span class="token template-punctuation string">`</span><span class="token interpolation"><span class="token interpolation-punctuation punctuation">${</span>index<span class="token interpolation-punctuation punctuation">}</span></span><span class="token string">: </span><span class="token interpolation"><span class="token interpolation-punctuation punctuation">${</span>val<span class="token interpolation-punctuation punctuation">}</span></span><span class="token template-punctuation string">`</span></span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span></span></pre></div>
<p>ou obter apenas os argumentos adicionais, criando um novo array que exclui os 2 primeiros parâmetros:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> args <span class="token operator">=</span> process<span class="token punctuation">.</span>argv<span class="token punctuation">.</span><span class="token function">slice</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Se você tem um argumento direto (sem chave), como esse:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">node app.js joe</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>você pode acessá-lo usando</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> args <span class="token operator">=</span> process<span class="token punctuation">.</span>argv<span class="token punctuation">.</span><span class="token function">slice</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">)</span>
args<span class="token punctuation">[</span><span class="token number">0</span><span class="token punctuation">]</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span></span></pre></div>
<p>Já nesse caso:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">node app.js <span class="token assign-left variable">name</span><span class="token operator">=</span>joe</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p><code class="language-text">args[0]</code> é <code class="language-text">name=joe</code>, e você precisa tratá-lo. A melhor maneira de fazer isso é usando a biblioteca <a href="https://www.npmjs.com/package/minimist"><code class="language-text">minimist</code></a>, que ajuda a lidar com argumentos:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> args <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'minimist'</span><span class="token punctuation">)</span><span class="token punctuation">(</span>process<span class="token punctuation">.</span>argv<span class="token punctuation">.</span><span class="token function">slice</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">)</span><span class="token punctuation">)</span>
args<span class="token punctuation">[</span><span class="token string">'name'</span><span class="token punctuation">]</span> <span class="token comment">//joe</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span></span></pre></div>
<p>Desta vez você você precisa usar dois traços antes do nome do argumento:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">node app.js --name<span class="token operator">=</span>joe</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<h2>Output para a linha de comando usando Node.JS</h2>
<h2>Saída (output) básico usando o módulo console</h2>
<p>O Node.js provê o <a href="https://nodejs.org/api/console.html">módulo <code class="language-text">console</code></a> que possui uma infinidade de maneiras muito úteis para interagir com a linha de comando.</p>
<p>É basicamente o mesmo objeto <code class="language-text">console</code> encontrado no browser.</p>
<p>O método mais básico e mais usado é o <code class="language-text">console.log()</code>, que imprime a string que você passar como parâmetro.</p>
<p>Se você passar um objeto, ele irá renderizá-lo como uma string.</p>
<p>Você pode passar múltiplas variáveis para o <code class="language-text">console.log</code>, por exemplo:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> x <span class="token operator">=</span> <span class="token string">'x'</span>
<span class="token keyword">const</span> y <span class="token operator">=</span> <span class="token string">'y'</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>x<span class="token punctuation">,</span> y<span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span></span></pre></div>
<p>o Node.js vai printar ambas.</p>
<p>Nós também podemos formatar mensagens mais sofisticadas passando variáveis e um formato espeficador.</p>
<p>Por exemplo:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'My %s has %d years'</span><span class="token punctuation">,</span> <span class="token string">'cat'</span><span class="token punctuation">,</span> <span class="token number">2</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<ul>
<li><code class="language-text">%s</code> formata a variável como uma string</li>
<li><code class="language-text">%d</code> formata a variável como um número</li>
<li><code class="language-text">%i</code> formata a variável como um número, porém só a parte inteira</li>
<li><code class="language-text">%o</code> formata a variável como um objeto</li>
</ul>
<p>Exemplo:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'%o'</span><span class="token punctuation">,</span> Number<span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<h2>Limpando o console</h2>
<p><code class="language-text">console.clear()</code> limpa o console (o comportamento pode mudar dependendo do console utilizado).</p>
<h2>Contando elementos</h2>
<p><code class="language-text">console.count()</code> é um método muito conveniente.</p>
<p>Dado o código:</p>
<iframe
title="Output to the command line using Node.js"
src="https://glitch.com/embed/#!/embed/nodejs-dev-0013-02?path=server.js&previewSize=40&attributionHidden=true&sidebarCollapsed=true"
alt="nodejs-dev-0013-02 on Glitch"
style="height: 400px; width: 100%; border: 0;">
</iframe>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> x <span class="token operator">=</span> <span class="token number">1</span>
<span class="token keyword">const</span> y <span class="token operator">=</span> <span class="token number">2</span>
<span class="token keyword">const</span> z <span class="token operator">=</span> <span class="token number">3</span>
console<span class="token punctuation">.</span><span class="token function">count</span><span class="token punctuation">(</span>
<span class="token string">'O valor de x é '</span> <span class="token operator">+</span> x <span class="token operator">+</span> <span class="token string">' e foi validado .. quantas vezes?'</span>
<span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">count</span><span class="token punctuation">(</span>
<span class="token string">'O valor de x é '</span> <span class="token operator">+</span> x <span class="token operator">+</span> <span class="token string">' e foi validado .. quantas vezes?'</span>
<span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">count</span><span class="token punctuation">(</span>
<span class="token string">'O valor de y é '</span> <span class="token operator">+</span> y <span class="token operator">+</span> <span class="token string">' e foi validado .. quantas vezes?'</span>
<span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<p>O que acontece é que ele vai contar o número de vezes que uma string foi impressa, e imprime o total:</p>
<p>Você pode contar maçãs e laranjas, por exemplo:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> oranges <span class="token operator">=</span> <span class="token punctuation">[</span><span class="token string">'orange'</span><span class="token punctuation">,</span> <span class="token string">'orange'</span><span class="token punctuation">]</span>
<span class="token keyword">const</span> apples <span class="token operator">=</span> <span class="token punctuation">[</span><span class="token string">'just one apple'</span><span class="token punctuation">]</span>
oranges<span class="token punctuation">.</span><span class="token function">forEach</span><span class="token punctuation">(</span><span class="token parameter">fruit</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
console<span class="token punctuation">.</span><span class="token function">count</span><span class="token punctuation">(</span>fruit<span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span>
apples<span class="token punctuation">.</span><span class="token function">forEach</span><span class="token punctuation">(</span><span class="token parameter">fruit</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
console<span class="token punctuation">.</span><span class="token function">count</span><span class="token punctuation">(</span>fruit<span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<h2>Imprimindo a pilha de execução</h2>
<p>Existem casos onde é útil imprimir a pilha de execução da função, talvez para responder a clássica pergunta <em>como você chegou nessa parte do código?</em></p>
<p>Você pode isso fazer usando <code class="language-text">console.trace()</code>:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> <span class="token function-variable function">function2</span> <span class="token operator">=</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=></span> console<span class="token punctuation">.</span><span class="token function">trace</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token keyword">const</span> <span class="token function-variable function">function1</span> <span class="token operator">=</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token function">function2</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token function">function1</span><span class="token punctuation">(</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span></span></pre></div>
<p>Isso irá imprimir a pilha de execução. Isso é o que é impresso se tentarmos usá-lo no REPL do Node.js:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash">Trace
at function2 <span class="token punctuation">(</span>repl:1:33<span class="token punctuation">)</span>
at function1 <span class="token punctuation">(</span>repl:1:25<span class="token punctuation">)</span>
at repl:1:1
at ContextifyScript.Script.runInThisContext <span class="token punctuation">(</span>vm.js:44:33<span class="token punctuation">)</span>
at REPLServer.defaultEval <span class="token punctuation">(</span>repl.js:239:29<span class="token punctuation">)</span>
at bound <span class="token punctuation">(</span>domain.js:301:14<span class="token punctuation">)</span>
at REPLServer.runBound <span class="token punctuation">[</span>as eval<span class="token punctuation">]</span> <span class="token punctuation">(</span>domain.js:314:12<span class="token punctuation">)</span>
at REPLServer.onLine <span class="token punctuation">(</span>repl.js:440:10<span class="token punctuation">)</span>
at emitOne <span class="token punctuation">(</span>events.js:120:20<span class="token punctuation">)</span>
at REPLServer.emit <span class="token punctuation">(</span>events.js:210:7<span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<h2>Calculando o tempo gasto</h2>
<p>Você pode calcular facilmente o tempo que uma função gasta para rodar, usando <code class="language-text">time()</code> e <code class="language-text">timeEnd()</code></p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> <span class="token function-variable function">doSomething</span> <span class="token operator">=</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=></span> console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'test'</span><span class="token punctuation">)</span>
<span class="token keyword">const</span> <span class="token function-variable function">measureDoingSomething</span> <span class="token operator">=</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
console<span class="token punctuation">.</span><span class="token function">time</span><span class="token punctuation">(</span><span class="token string">'doSomething()'</span><span class="token punctuation">)</span>
<span class="token comment">//faça algo, e calcule o tempo que isso levou</span>
<span class="token function">doSomething</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">timeEnd</span><span class="token punctuation">(</span><span class="token string">'doSomething()'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span>
<span class="token function">measureDoingSomething</span><span class="token punctuation">(</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<h2>stdout e stderr</h2>
<p>Como nós vimos o console.log é ótimo para imprimir mensagens no console. Isso é o que chamamos de saída padrão, ou <code class="language-text">stdout</code>.</p>
<p><code class="language-text">console.error</code> imprime na stream <code class="language-text">stderr</code>.</p>
<p>Isso não vai aparecer no console, mas vai aparecer no log de erro.</p>
<h2>Colorindo o saída</h2>
<p>Você pode colorir a saída do seu texto no console utilizando <a href="https://gist.github.com/iamnewton/8754917">escape sequences</a>, que basicamente são um conjunto de caracteres que indentificam uma cor.</p>
<p>Exemplo:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'\x1b[33m%s\x1b[0m'</span><span class="token punctuation">,</span> <span class="token string">'hi!'</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Você pode testar isso no REPL no Node.js, onde será impresso <code class="language-text">hi!</code> em amarelo.</p>
<p>Entretanto, essa é uma abordagem mais baixo nível. O jeito mais simples de colorir saídas no console é utilizando uma biblioteca. <a href="https://github.com/chalk/chalk">Chalk</a> é uma biblioteca que além de colorir, também ajuda com outras facilidades de estilização, como deixar textos em negrito, ítalico ou sublinhados.</p>
<p>Instale com <code class="language-text">npm install chalk</code>, e então use-o assim:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> chalk <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'chalk'</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>chalk<span class="token punctuation">.</span><span class="token function">yellow</span><span class="token punctuation">(</span><span class="token string">'hi!'</span><span class="token punctuation">)</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span></span></pre></div>
<p>Usando <code class="language-text">chalk.yellow</code> é muito mais conveniente do que tentar lembrar o código de cor correto, e o código fica muito mais legível.</p>
<p>Confira o link do projeto postado acima para mais exemplos de uso.</p>
<h2>Crie uma barra de progresso</h2>
<p><a href="https://www.npmjs.com/package/progress">Progress</a> é um pacote incrível para criar uma barra de progresso no console. Instale utilizando <code class="language-text">npm install progress</code>.</p>
<p>Esse trecho cria uma barra de progresso com 10 passos, e a cada 100ms um passo é completado. Quando a barra é completada nós finalizamos o contador.</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> ProgressBar <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'progress'</span><span class="token punctuation">)</span>
<span class="token keyword">const</span> bar <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">ProgressBar</span><span class="token punctuation">(</span><span class="token string">':bar'</span><span class="token punctuation">,</span> <span class="token punctuation">{</span> total<span class="token punctuation">:</span> <span class="token number">10</span> <span class="token punctuation">}</span><span class="token punctuation">)</span>
<span class="token keyword">const</span> timer <span class="token operator">=</span> <span class="token function">setInterval</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
bar<span class="token punctuation">.</span><span class="token function">tick</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token keyword">if</span> <span class="token punctuation">(</span>bar<span class="token punctuation">.</span>complete<span class="token punctuation">)</span> <span class="token punctuation">{</span>
<span class="token function">clearInterval</span><span class="token punctuation">(</span>timer<span class="token punctuation">)</span>
<span class="token punctuation">}</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">100</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<h2>Aceite inputs do terminal no Node.js</h2>
<p>Como criar um programa Node.js de CLI interativa?</p>
<p>Desde a versão 7 o Node.js possui o <a href="https://nodejs.org/api/readline.html">módulo <code class="language-text">readline</code></a> para fazer exatamente isso: obter entradas de uma stream de leitura, como a <code class="language-text">process.stdin</code>, via terminal, durante a execução de um programa Node.js, uma linha por vez.</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> readline <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'readline'</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">createInterface</span><span class="token punctuation">(</span><span class="token punctuation">{</span>
input<span class="token punctuation">:</span> process<span class="token punctuation">.</span>stdin<span class="token punctuation">,</span>
output<span class="token punctuation">:</span> process<span class="token punctuation">.</span>stdout
<span class="token punctuation">}</span><span class="token punctuation">)</span>
readline<span class="token punctuation">.</span><span class="token function">question</span><span class="token punctuation">(</span><span class="token template-string"><span class="token template-punctuation string">`</span><span class="token string">What's your name?</span><span class="token template-punctuation string">`</span></span><span class="token punctuation">,</span> <span class="token parameter">name</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token template-string"><span class="token template-punctuation string">`</span><span class="token string">Hi </span><span class="token interpolation"><span class="token interpolation-punctuation punctuation">${</span>name<span class="token interpolation-punctuation punctuation">}</span></span><span class="token string">!</span><span class="token template-punctuation string">`</span></span><span class="token punctuation">)</span>
readline<span class="token punctuation">.</span><span class="token function">close</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<p>Esse trecho de código pergunta o nome do usuário, e uma vez que o texto é inserido e o usuário pressiona enter, nós enviamos uma saudação.</p>
<p>O método <code class="language-text">question()</code> exibe o primeiro parâmetro (a pergunta) e aguarda pela entrada do usuário. A função de callback é invocada uma vez que o enter é pressionado.</p>
<p>Nessa função de callback, nós fechamos a interface do readline.</p>
<p><code class="language-text">readline</code> oferece diversos outros métodos, e você pode conferir todos na documentação linkada acima.</p>
<p>Se você precisa solicitar uma senha, o ideal é que os caracteres digitados sejam trocados pelo símbolo de <code class="language-text">*</code>.</p>
<p>A maneira mais simples de fazer isso é utilizar o <a href="https://www.npmjs.com/package/readline-sync">pacote <code class="language-text">readline-sync</code></a>, que é muito similar em termos de API.</p>
<p>Outra solução mais completa e abstrata é fornecida pelo <a href="https://github.com/SBoudrias/Inquirer.js">pacote Inquirer.js</a>.</p>
<p>Instale-o utilizando <code class="language-text">npm install inquirer</code>, e então você poderá replicar o código acima dessa forma:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> inquirer <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'inquirer'</span><span class="token punctuation">)</span>
<span class="token keyword">var</span> questions <span class="token operator">=</span> <span class="token punctuation">[</span>
<span class="token punctuation">{</span>
type<span class="token punctuation">:</span> <span class="token string">'input'</span><span class="token punctuation">,</span>
name<span class="token punctuation">:</span> <span class="token string">'name'</span><span class="token punctuation">,</span>
message<span class="token punctuation">:</span> <span class="token string">"What's your name?"</span>
<span class="token punctuation">}</span>
<span class="token punctuation">]</span>
inquirer<span class="token punctuation">.</span><span class="token function">prompt</span><span class="token punctuation">(</span>questions<span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">then</span><span class="token punctuation">(</span><span class="token parameter">answers</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token template-string"><span class="token template-punctuation string">`</span><span class="token string">Hi </span><span class="token interpolation"><span class="token interpolation-punctuation punctuation">${</span>answers<span class="token punctuation">[</span><span class="token string">'name'</span><span class="token punctuation">]</span><span class="token interpolation-punctuation punctuation">}</span></span><span class="token string">!</span><span class="token template-punctuation string">`</span></span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<p>Inquirer.js permite com que você faça diversas coisas como perguntas de múltipla escolha, ter radio buttons, confirmações e muito mais.</p>
<p>Vale a pena conhecer todas as alternativas, especialmente as nativas do Node.js, mas se você planeja levar a CLI para outro nível, Inquirer.js é ótima escolha.</p>
<h2>Expondo uma funcionalidade em um arquivo do Node.js usando exports</h2>
<p>O Node.js tem um sistema de módulos nativo.</p>
<p>Um arquivo Node.js pode importar funcionalidades expostas por outros arquivos Node.js.</p>
<p>Quando você quer importar algo você deve utilizar</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> library <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'./library'</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>para importar a funcionalidade exposta no arquivo <code class="language-text">library.js</code> que reside na pasta atual.</p>
<p>Nesse arquivo, a funcionalidade deve ser exposta antes de poder ser importada por outros arquivos.</p>
<p>Qualquer outra variável ou objeto definido no arquivo é privado por padrão e não exposto ao mundo exterior.</p>
<p>Isso é permitido por meio da API <code class="language-text">module.exports</code>, oferecida pelo <a href="https://nodejs.org/api/modules.html"><code class="language-text">module</code> system</a>.</p>
<p>Quando você atribui um objeto ou uma função como uma nova propriedade do <code class="language-text">exports</code>, isso se torna o que está sendo exposto, e como tal, pode ser importado em outras partes da sua aplicação, ou até em outras aplicações.</p>
<p>Você pode fazer isso de 2 formas.</p>
<p>A primeira é atribuir um objeto ao <code class="language-text">module.exports</code>, que é um objeto provido nativamente pelo sistema de módulos, e ele fará com que o arquivo exporte <em>apenas aquele objeto</em>:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> car <span class="token operator">=</span> <span class="token punctuation">{</span>
brand<span class="token punctuation">:</span> <span class="token string">'Ford'</span><span class="token punctuation">,</span>
model<span class="token punctuation">:</span> <span class="token string">'Fiesta'</span>
<span class="token punctuation">}</span>
module<span class="token punctuation">.</span>exports <span class="token operator">=</span> car
<span class="token comment">//..em outro arquivo</span>
<span class="token keyword">const</span> car <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'./car'</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<p>A segunda é definir o objeto exportado como propriedade do <code class="language-text">exports</code>. Essa abordagem permite que você exporte múltiplos objetos, funções ou dados:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> car <span class="token operator">=</span> <span class="token punctuation">{</span>
brand<span class="token punctuation">:</span> <span class="token string">'Ford'</span><span class="token punctuation">,</span>
model<span class="token punctuation">:</span> <span class="token string">'Fiesta'</span>
<span class="token punctuation">}</span>
exports<span class="token punctuation">.</span>car <span class="token operator">=</span> car</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<p>ou diretamente</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js">exports<span class="token punctuation">.</span>car <span class="token operator">=</span> <span class="token punctuation">{</span>
brand<span class="token punctuation">:</span> <span class="token string">'Ford'</span><span class="token punctuation">,</span>
model<span class="token punctuation">:</span> <span class="token string">'Fiesta'</span>
<span class="token punctuation">}</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span></span></pre></div>
<p>Em outro arquivo, você irá utilizá-lo referenciando a propriedade da sua importação:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> items <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'./items'</span><span class="token punctuation">)</span>
items<span class="token punctuation">.</span>car</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span></span></pre></div>
<p>ou</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> car <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'./items'</span><span class="token punctuation">)</span><span class="token punctuation">.</span>car</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Qual a diferença entre <code class="language-text">module.exports</code> e <code class="language-text">exports</code>?</p>
<p>O primeiro expõe o objeto para qual ele aponta.
O último expõe <em>as propriedades</em> do objeto que ele aponta.</p>
<h2>Uma introdução ao gerenciador de pacotes NPM</h2>
<h2>Introdução ao npm</h2>
<p><code class="language-text">npm</code> é o gerenciador de pacotes padrão do Node.js.</p>
<p>Em janeiro de 2017 mais de 350.000 pacotes foram listados no registro do npm, fazendo dele o maior repositório de código de uma única linguagem na Terra, e você pode ter certeza que existe um pacote para (quase!) tudo.</p>
<p>Ele iniciou como um meio de fazer donwload e gerenciar dependências de pacotes Node.js, mas desde então ele se tornou uma ferramenta utilizada também no frontend.</p>
<p>Há muitas coisas que o <code class="language-text">npm</code> faz.</p>
<blockquote>
<p><a href="https://yarnpkg.com/en/"><strong>Yarn</strong></a> é uma alternativa ao npm. Não deixe de conferír.</p>
</blockquote>
<h2>Downloads</h2>
<p><code class="language-text">npm</code> gerencia downloads de dependências do seu projeto.</p>
<h3>Instalando todas dependências</h3>
<p>Se o projeto tem um arquivo <code class="language-text">package.json</code>, ao rodar</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash"><span class="token function">npm</span> <span class="token function">install</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>ele vai instalar tudo que o projeto precisa, na pasta <code class="language-text">node_modules</code>, criando-a se não existir.</p>
<h3>Instalando um único pacote</h3>
<p>Você também pode instalar um pacote específico ao rodar</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash"><span class="token function">npm</span> <span class="token function">install</span> <span class="token operator">&lt;</span>package-name<span class="token operator">></span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Geralmente você verá mais flags adicionadas a esse comando:</p>
<ul>
<li><code class="language-text">--save</code> instala e adiciona uma entrada no campo <em>dependencies</em> do arquivo <code class="language-text">package.json</code></li>
<li><code class="language-text">--save-dev</code> instala e adiciona uma entrada no campo <em>devDependencies</em> do arquivo <code class="language-text">package.json</code></li>
</ul>
<p>A principal diferença é que no devDependencies ficam as ferramentas de desenvolvimento, como uma biblioteca de testes, enquanto no <code class="language-text">dependencies</code> ficam os pacotes necessários à aplicação em ambiente de produção.</p>
<h3>Atualizando pacotes</h3>
<p>Atualizar também é fácil, ao rodar</p>
<div class="gatsby-highlight" data-language="console"><pre style="counter-reset: linenumber NaN" class="language-console line-numbers"><code class="language-console">npm update</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>o <code class="language-text">npm</code> vai buscar em todos os pacotes por uma versão atualizada que satisfaça suas restrições de versionamento.</p>
<p>Você também pode especificar um único pacote para atualizar:</p>
<div class="gatsby-highlight" data-language="console"><pre style="counter-reset: linenumber NaN" class="language-console line-numbers"><code class="language-console">npm update &lt;package-name&gt;</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<h2>Versionamento</h2>
<p>Em adição aos downloads, o <code class="language-text">npm</code> também gerencia o <strong>versionamento</strong>, assim você pode especificar qualquer versão do pacote, ou uma versão maior ou menor do que você precisa.</p>
<p>Muitas vezes você vai encontrar uma biblioteca que só é compatível com a versão atual de outra biblioteca.</p>
<p>Ou um bug na versão mais atual da biblioteca, ainda não solucionado, causando um problema.</p>
<p>Especificar explicitamente a versão da biblioteca também ajuda a manter todos na exata mesma versão do pacote, assim todos do time rodam a mesma versão até que o arquivo <code class="language-text">package.json</code> seja atualizado.</p>
<p>Em todos os casos, versionar ajuda muito, e o <code class="language-text">npm</code> segue o padrão semântico de versionamento chamado semver.</p>
<h2>Executando tarefas</h2>
<p>O arquivo package.json possui um campo chamado “scripts”, que é usado para especificar tarefas de linha de comando que podem ser rodadas usando</p>
<div class="gatsby-highlight" data-language="console"><pre style="counter-reset: linenumber NaN" class="language-console line-numbers"><code class="language-console">npm run &lt;task-name&gt;</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Por exemplo:</p>
<div class="gatsby-highlight" data-language="json"><pre style="counter-reset: linenumber NaN" class="language-json line-numbers"><code class="language-json"><span class="token punctuation">{</span>
<span class="token property">"scripts"</span><span class="token operator">:</span> <span class="token punctuation">{</span>
<span class="token property">"start-dev"</span><span class="token operator">:</span> <span class="token string">"node lib/server-development"</span><span class="token punctuation">,</span>
<span class="token property">"start"</span><span class="token operator">:</span> <span class="token string">"node lib/server-production"</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span>
<span class="token punctuation">}</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<p>É muito comum usar esse recurso para rodar o Webpack:</p>
<div class="gatsby-highlight" data-language="json"><pre style="counter-reset: linenumber NaN" class="language-json line-numbers"><code class="language-json"><span class="token punctuation">{</span>
<span class="token property">"scripts"</span><span class="token operator">:</span> <span class="token punctuation">{</span>
<span class="token property">"watch"</span><span class="token operator">:</span> <span class="token string">"webpack --watch --progress --colors --config webpack.conf.js"</span><span class="token punctuation">,</span>
<span class="token property">"dev"</span><span class="token operator">:</span> <span class="token string">"webpack --progress --colors --config webpack.conf.js"</span><span class="token punctuation">,</span>
<span class="token property">"prod"</span><span class="token operator">:</span> <span class="token string">"NODE_ENV=production webpack -p --config webpack.conf.js"</span><span class="token punctuation">,</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span>
<span class="token punctuation">}</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span><span></span><span></span><span></span><span></span></span></pre></div>
<p>Então em vez de digitar esses comandos longos, que são muito fáceis de errar ou esquecer, você pode rodar</p>
<div class="gatsby-highlight" data-language="console"><pre style="counter-reset: linenumber NaN" class="language-console line-numbers"><code class="language-console">npm run watch
npm run dev
npm run prod</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span><span></span><span></span></span></pre></div>
<h2>Onde o Node instala os pacotes?</h2>
<p>Quando você instala um pacote utilizando <code class="language-text">npm</code> você pode executar 2 tipos de instalação:</p>
<ul>
<li>local</li>
<li>global</li>
</ul>
<p>Por padrão, quando você digita o comando <code class="language-text">npm install</code>, como por exemplo:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash"><span class="token function">npm</span> <span class="token function">install</span> lodash</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>o pacote será instalado na árvore de arquivos atual, em uma subpasta dentro da <code class="language-text">node_modules</code>.</p>
<p>Quando isso ocorre, o <code class="language-text">npm</code> também adiciona uma entrada do <code class="language-text">lodash</code> na propriedade <code class="language-text">dependencies</code> do arquivo <code class="language-text">package.json</code> da pasta atual.</p>
<p>Para executar uma instalação global, basta utilizar a flag <code class="language-text">-g</code>:</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash"><span class="token function">npm</span> <span class="token function">install</span> -g lodash</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Quando isso ocorre, o npm não instalará na pasta local, em vez disso, ele utilizará uma localização global.</p>
<p>Onde, exatamente?</p>
<p>O comando <code class="language-text">npm root -g</code> te dirá a localização exata na sua máquina.</p>
<p>No macOS ou Linux, essa localização costuma ser <code class="language-text">/usr/local/lib/node_modules</code>.
No Windows costuma ser <code class="language-text">C:\Users\YOU\AppData\Roaming\npm\node_modules</code></p>
<p>Todavia, se você utiliza o <code class="language-text">nvm</code> para gerenciar versões do Node.js, a localização pode ser diferente.</p>
<p>Eu por exemplo utilizo <code class="language-text">nvm</code> e a localização dos meus pacotes foi exibida como <code class="language-text">/Users/joe/.nvm/versions/node/v8.9.0/lib/node_modules</code>.</p>
<h2>Como usar ou executar um pacote instalado usando NPM?</h2>
<p>Quando você instala um pacote usando <code class="language-text">npm</code> dentro da sua pasta <code class="language-text">node_modules</code>, ou também globamente, como você o utiliza em seu código Node.js?</p>
<p>Digamos que você instale a famosa biblioteca JavaScript de utilidades chamada <code class="language-text">lodash</code>, usando</p>
<div class="gatsby-highlight" data-language="bash"><pre style="counter-reset: linenumber NaN" class="language-bash line-numbers"><code class="language-bash"><span class="token function">npm</span> <span class="token function">install</span> lodash</code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Isso irá instalar o pacote na sua pasta <code class="language-text">node_modules</code> local.</p>
<p>Para utilizá-lo em seu código, você só precisa importá-lo no seu programa utilizando <code class="language-text">require</code>:</p>
<div class="gatsby-highlight" data-language="js"><pre style="counter-reset: linenumber NaN" class="language-js line-numbers"><code class="language-js"><span class="token keyword">const</span> _ <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'lodash'</span><span class="token punctuation">)</span></code><span aria-hidden="true" class="line-numbers-rows" style="white-space: normal; width: auto; left: 0;"><span></span></span></pre></div>
<p>Mas e se o seu pacote for um executável?</p>
<p>Nesse caso, ele para a pasta <code class="language-text">node_modules/.bin/</code>.</p>
<p>Um jeito fácil de demonstrar isso é utilizando o <a href="https://www.npmjs.com/package/cowsay">cowsay</a>.</p>
<p>O pacote cowsay fornece um programa de linha de comando que faz com que uma vaca diga algo (e outros animais também 🦊).</p>
<p>Quando você instala o pacote utilizando <code class="language-text">npm install cowsay</code>, ele irá instalar a si mesmo e algumas poucas dependências na sua pasta node_modules local:</p>
<p><span
class="gatsby-resp-image-wrapper"
style="position: relative; display: block; margin-left: auto; margin-right: auto; max-width: 590px;"
>
<a
class="gatsby-resp-image-link"
href="/static/b245c50f5080dae16a2525fae0ba2c91/6e914/node_modules-content.png"
style="display: block"
target="_blank"
rel="noopener"
>
<span
class="gatsby-resp-image-background-image"
style="padding-bottom: 58.55758880516685%; position: relative; bottom: 0; left: 0; background-image: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAMCAYAAABiDJ37AAAACXBIWXMAAAsSAAALEgHS3X78AAACf0lEQVQoz6WSW08aQRTH7S3ti4BGIxFcFOQqLLssl3WvULlItWW5LaVpmzbxwc8gD/1KfTJRnmrq1tSkL7xoAPkedWdOZ5dq20SfOskvZ+ZhfvmfMzMzQ9bFl8/C+aDfGo0nteFwqF1eDrXRaETqhXZ+/l07O/tmYxin2mAw0CaTiTYej2+5urqy7tVPTk7cRPfo8Vu9YXQ/tKHZbEGno0O32wFd16Gjv4ZGowmN+hS91YF6vQ7tdhtardYttVoN9vf34fDwsGsFfFbOq6e8kgJvyHed4+NoZzeN4tEEyrIyyjICKsm7qKLUUCKaRAuLC2jRZhEtLS0ht9uNXC7XNcdx0O/331vCp6qwafAiB8GNsMlvMrhUymCGZvFmWsY5TsCqUMRFuYoVvoDpOINZmsNMIoUDgYCN1+s1JUmCo6Ojd3bCneJzQy3xEKQjpiinoN4QIc1moCBWQMrloZJ/Cc3qGxCzCiRiSeCSWSBiWFtbs8DLy8tIFEU4Pj6eCqtbBUMtToWKmgZNE2yhlCuATNjOvwKt0oEtaRtCwRB4VzxA+ShYXV29W5gXBYOXOFiPhcwcn4RyOQNMggUhqwJpGYSMCmV1B2S+AH6//ybZ/Qm3ZNEQVCKMW0IaV19k7RkSkT1DkgxrZZ3MLo0pagVbEpLO5k5hPEZ/TbM5kor7SS6Z9EbKJHvT2sciGyZFUSZp0fT5fCYRmER0i3UmwmtBEP48CkuzP5gkC8H1EITDEYgQwiGrRiFIZma16fcHftd/Ia8MHo8HFEWxvs1HS/hkdna263A6PjldzgOn09Gb4rQr+WO9ubm5e5mfn+85HI4eSX+wt7cXm/lrPfxPHliSX2DgWdzvML3rAAAAAElFTkSuQmCC'); background-size: cover; display: block;"
></span>
<img
class="gatsby-resp-image-image"
alt="O conteúdo da pasta node_modules"
title="O conteúdo da pasta node_modules"
src="/static/b245c50f5080dae16a2525fae0ba2c91/799d3/node_modules-content.png"
srcset="/static/b245c50f5080dae16a2525fae0ba2c91/00d96/node_modules-content.png 148w,
/static/b245c50f5080dae16a2525fae0ba2c91/0b23c/node_modules-content.png 295w,
/static/b245c50f5080dae16a2525fae0ba2c91/799d3/node_modules-content.png 590w,
/static/b245c50f5080dae16a2525fae0ba2c91/2a3d6/node_modules-content.png 885w,
/static/b245c50f5080dae16a2525fae0ba2c91/6e914/node_modules-content.png 929w"
sizes="(max-width: 590px) 100vw, 590px"
loading="lazy"
/>
</a>
</span></p>
<p>Há uma pasta oculta chamada .bin, que contêm links simbólicos para os binários do cowsay:</p>
<p><span
class="gatsby-resp-image-wrapper"
style="position: relative; display: block; margin-left: auto; margin-right: auto; max-width: 590px;"
>
<a
class="gatsby-resp-image-link"
href="/static/99830aefa055e247397de544ad7b7744/6e914/binary-files.png"
style="display: block"
target="_blank"
rel="noopener"
>
<span
class="gatsby-resp-image-background-image"
style="padding-bottom: 38.213132400430574%; position: relative; bottom: 0; left: 0; background-image: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAICAYAAAD5nd/tAAAACXBIWXMAAAsSAAALEgHS3X78AAABrklEQVQoz6WNv27aUBSHTV6A2EJtl95rG+wkGF8bqJuAMpBITJGwwPyxg8rQZ0iGLCAegXfpECmbpU7EHVCHKAkYnsO69/TaSlUxVB16pE9HP+l3viO8ht/Oop8P3jredeL1xn15WbubTcz3s7t8XGZEy6X7I4rciPP89OSmvfiVE8fudrvt7LY7b7VaOUI6X0ZeOP46gsFwCP61D+NxAEHggz8KoO/1wfM86PX70O12odvr8c41+EEAI94d8pvBYAC+78NisbjPhM6pHX5qmIAMJdGaJ/Tqqk4J0alVdqhDzmi91qD2xSU9tqsUYUzN5jm1Wi2qtSwq1zX64d37pFAowHQ6vQeAnKBremiZNlQMkpgVixGTMNMgjFSqfFvMKJtM03VW1DSmqiorFos8H/FcYqWjUpoTjDHM5/NUKAgNpxk2Pp+DWbYS26wxYlQzmVWpZcLyscFURWWyjJmiKHzLe/AnCULoj1DG+LuiKoDQR0AY7YEzMPBD4LK/kgpns9lDJswfHnqiKN1JknTDud1DlG5FUfwXN/l8/q7dbncmk8mB8DY5zsF/kPst+gUx2eZmkZP0+AAAAABJRU5ErkJggg=='); background-size: cover; display: block;"
></span>
<img
class="gatsby-resp-image-image"
alt="Os arquivos binários"
title="Os arquivos binários"
src="/static/99830aefa055e247397de544ad7b7744/799d3/binary-files.png"
srcset="/static/99830aefa055e247397de544ad7b7744/00d96/binary-files.png 148w,
/static/99830aefa055e247397de544ad7b7744/0b23c/binary-files.png 295w,
/static/99830aefa055e247397de544ad7b7744/799d3/binary-files.png 590w,
/static/99830aefa055e247397de544ad7b7744/2a3d6/binary-files.png 885w,
/static/99830aefa055e247397de544ad7b7744/6e914/binary-files.png 929w"
sizes="(max-width: 590px) 100vw, 590px"
loading="lazy"
/>
</a>
</span></p>
<p>Como você executa isso?</p>