forked from amejiarosario/amejiarosario.github.io
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathatom.xml
3343 lines (2962 loc) · 459 KB
/
atom.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"?>
<feed xmlns="http://www.w3.org/2005/Atom">
<title>Adrian Mejia Blog</title>
<subtitle>var life = ['work_smart', 'have_fun', 'make_history'];</subtitle>
<link href="/atom.xml" rel="self"/>
<link href="http://adrianmejia.com/"/>
<updated>2016-08-24T21:54:42.000Z</updated>
<id>http://adrianmejia.com/</id>
<author>
<name>Adrian Mejia</name>
</author>
<generator uri="http://hexo.io/">Hexo</generator>
<entry>
<title>Building a Node.js static file server (files over HTTP) using ES6+</title>
<link href="http://adrianmejia.com/blog/2016/08/24/Building-a-Node-js-static-file-server-files-over-HTTP-using-ES6/"/>
<id>http://adrianmejia.com/blog/2016/08/24/Building-a-Node-js-static-file-server-files-over-HTTP-using-ES6/</id>
<published>2016-08-24T21:54:42.000Z</published>
<updated>2016-08-24T21:54:42.000Z</updated>
<content type="html"><![CDATA[<p>We are going to do a <strong>static file server</strong> in Node.js. This web server is going to respond with the content of the file in a given path. While we are doing this exercise we are going to cover more about <code>http</code> module. Also, use some utilities from other core modules such as <code>path</code>, <code>url</code> and <code>fs</code>.</p>
<a id="more"></a>
<h1 id="HTTP-Web-Servers">HTTP Web Servers<a href="#HTTP-Web-Servers" class="headerlink" title="HTTP Web Servers"></a></h1><p>Node’s HTTP module is versatile. You can use it as a client, to grab content from websites or as a server. We are going to use it server files from our file system.</p>
<p>If you are familiar with Ruby or Python or http-server package. It’s the equivalent of this:</p>
<figure class="highlight bash"><figcaption><span>Existing HTTP Servers Implementations</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># python HTTP server</span></div><div class="line">python -m SimpleHTTPServer 9000</div><div class="line"></div><div class="line"><span class="comment"># ruby HTTP server</span></div><div class="line">ruby -run <span class="_">-e</span> httpd . -p 9000</div><div class="line"></div><div class="line"><span class="comment"># Node HTTP server (npm install http-server)</span></div><div class="line">http-server . -p 9000</div></pre></td></tr></table></figure>
<p>Let’s do our own. It’s not that hard.</p>
<h1 id="Simple-HTTP-Server">Simple HTTP Server<a href="#Simple-HTTP-Server" class="headerlink" title="Simple HTTP Server"></a></h1><p>One of the simplest servers that you can create in Node, looks like this:</p>
<figure class="highlight javascript"><figcaption><span>Simple server.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">const</span> http = <span class="built_in">require</span>(<span class="string">'http'</span>);</div><div class="line"></div><div class="line">http.createServer(<span class="function"><span class="keyword">function</span> (<span class="params">req, res</span>) </span>{</div><div class="line"> <span class="comment">// server code</span></div><div class="line"> <span class="built_in">console</span>.log(<span class="string">`<span class="subst">${req.method}</span> <span class="subst">${req.url}</span>`</span>);</div><div class="line"> res.end(<span class="string">'hello world!'</span>);</div><div class="line">}).listen(<span class="number">9000</span>);</div><div class="line"></div><div class="line"><span class="built_in">console</span>.log(<span class="string">'Server listening on port 9000'</span>);</div></pre></td></tr></table></figure>
<p>To test it out, save the code in a file called <code>server.js</code> and run:</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line">node server.js</div></pre></td></tr></table></figure>
<p>Then open the browser on <code>http://localhost:9000</code> and you will see the “hello world!” message.</p>
<p>Let’s explain what’s going on in the code. We are using the function <code>http.createServer</code> with a callback. This callback function is going to be called every time a client connects to the server. You can see that it takes two parameters: <code>req</code>uest and <code>res</code>ponse.</p>
<p>The request contains the client’s information. For instance: requested URL, path, headers, HTTP method, and so forth.</p>
<p>The response object is used to reply to the client. You can set what you want to send back to the client. For instance, data, headers, etc.</p>
<p>Finally, the listening part. It allows you to set the port that you want your server to run on. In this case, we are using <code>9000</code>.</p>
<h1 id="Node-js-HTTP-static-file-server-with-ES6">Node.js HTTP static file server with ES6+<a href="#Node-js-HTTP-static-file-server-with-ES6" class="headerlink" title="Node.js HTTP static file server with ES6+"></a></h1><p>Let’s now proceed to do the static web server. We want to parse the URL path and get the file matching that path. For instance, if we get a request like <code>localhost:9000/example/server.js</code>. We want to look for a file in <code>./example/server.js</code>.</p>
<p>Browsers don’t rely on the extension to render a file. Instead, they use the header <code>Content-type</code>. For instance, if we serve an HTML file with a content type <code>text/plain</code> it will show the HTML code (plain text). But, if you use a content type <code>text/html</code> then it will render the HTML as such.</p>
<p>For now, we can infer the file content type based on the file extension. The content types are represented in MIME formmat. MIME stands for Multipurpose Internet Mail Extensions. You can see the MIME types according to file extentions in the following code:</p>
<figure class="highlight javascript"><figcaption><span>static_server.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div><div class="line">15</div><div class="line">16</div><div class="line">17</div><div class="line">18</div><div class="line">19</div><div class="line">20</div><div class="line">21</div><div class="line">22</div><div class="line">23</div><div class="line">24</div><div class="line">25</div><div class="line">26</div><div class="line">27</div><div class="line">28</div><div class="line">29</div><div class="line">30</div><div class="line">31</div><div class="line">32</div><div class="line">33</div><div class="line">34</div><div class="line">35</div><div class="line">36</div><div class="line">37</div><div class="line">38</div><div class="line">39</div><div class="line">40</div><div class="line">41</div><div class="line">42</div><div class="line">43</div><div class="line">44</div><div class="line">45</div><div class="line">46</div><div class="line">47</div><div class="line">48</div><div class="line">49</div><div class="line">50</div><div class="line">51</div><div class="line">52</div><div class="line">53</div><div class="line">54</div><div class="line">55</div><div class="line">56</div><div class="line">57</div><div class="line">58</div><div class="line">59</div><div class="line">60</div><div class="line">61</div><div class="line">62</div><div class="line">63</div><div class="line">64</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">const</span> http = <span class="built_in">require</span>(<span class="string">'http'</span>);</div><div class="line"><span class="keyword">const</span> url = <span class="built_in">require</span>(<span class="string">'url'</span>);</div><div class="line"><span class="keyword">const</span> fs = <span class="built_in">require</span>(<span class="string">'fs'</span>);</div><div class="line"><span class="keyword">const</span> path = <span class="built_in">require</span>(<span class="string">'path'</span>);</div><div class="line"><span class="comment">// you can pass the parameter in the command line. e.g. node static_server.js 3000</span></div><div class="line"><span class="keyword">const</span> port = process.argv[<span class="number">2</span>] || <span class="number">9000</span>;</div><div class="line"></div><div class="line">http.createServer(<span class="function"><span class="keyword">function</span> (<span class="params">req, res</span>) </span>{</div><div class="line"> <span class="built_in">console</span>.log(<span class="string">`<span class="subst">${req.method}</span> <span class="subst">${req.url}</span>`</span>);</div><div class="line"></div><div class="line"> <span class="comment">// parse URL</span></div><div class="line"> <span class="keyword">const</span> parsedUrl = url.parse(req.url);</div><div class="line"> <span class="comment">// extract URL path</span></div><div class="line"> <span class="keyword">let</span> pathname = <span class="string">`.<span class="subst">${parsedUrl.pathname}</span>`</span>;</div><div class="line"> <span class="comment">// based on the URL path, extract the file extention. e.g. .js, .doc, ...</span></div><div class="line"> <span class="keyword">const</span> ext = path.parse(pathname).ext;</div><div class="line"> <span class="comment">// maps file extention to MIME types</span></div><div class="line"> <span class="keyword">const</span> mimeType = {</div><div class="line"> <span class="string">'.ico'</span>: <span class="string">'image/x-icon'</span>,</div><div class="line"> <span class="string">'.html'</span>: <span class="string">'text/html'</span>,</div><div class="line"> <span class="string">'.js'</span>: <span class="string">'text/javascript'</span>,</div><div class="line"> <span class="string">'.json'</span>: <span class="string">'application/json'</span>,</div><div class="line"> <span class="string">'.css'</span>: <span class="string">'text/css'</span>,</div><div class="line"> <span class="string">'.png'</span>: <span class="string">'image/png'</span>,</div><div class="line"> <span class="string">'.jpg'</span>: <span class="string">'image/jpeg'</span>,</div><div class="line"> <span class="string">'.wav'</span>: <span class="string">'audio/wav'</span>,</div><div class="line"> <span class="string">'.mp3'</span>: <span class="string">'audio/mpeg'</span>,</div><div class="line"> <span class="string">'.svg'</span>: <span class="string">'image/svg+xml'</span>,</div><div class="line"> <span class="string">'.pdf'</span>: <span class="string">'application/pdf'</span>,</div><div class="line"> <span class="string">'.doc'</span>: <span class="string">'application/msword'</span>,</div><div class="line"> <span class="string">'.eot'</span>: <span class="string">'appliaction/vnd.ms-fontobject'</span>,</div><div class="line"> <span class="string">'.ttf'</span>: <span class="string">'aplication/font-sfnt'</span></div><div class="line"> };</div><div class="line"></div><div class="line"> fs.exists(pathname, <span class="function"><span class="keyword">function</span> (<span class="params">exist</span>) </span>{</div><div class="line"> <span class="keyword">if</span>(!exist) {</div><div class="line"> <span class="comment">// if the file is not found, return 404</span></div><div class="line"> res.statusCode = <span class="number">404</span>;</div><div class="line"> res.end(<span class="string">`File <span class="subst">${pathname}</span> not found!`</span>);</div><div class="line"> <span class="keyword">return</span>;</div><div class="line"> }</div><div class="line"></div><div class="line"> <span class="comment">// if is a directory, then look for index.html</span></div><div class="line"> <span class="keyword">if</span> (fs.statSync(pathname).isDirectory()) {</div><div class="line"> pathname += <span class="string">'/index.html'</span>;</div><div class="line"> }</div><div class="line"></div><div class="line"> <span class="comment">// read file from file system</span></div><div class="line"> fs.readFile(pathname, <span class="function"><span class="keyword">function</span>(<span class="params">err, data</span>)</span>{</div><div class="line"> <span class="keyword">if</span>(err){</div><div class="line"> res.statusCode = <span class="number">500</span>;</div><div class="line"> res.end(<span class="string">`Error getting the file: <span class="subst">${err}</span>.`</span>);</div><div class="line"> } <span class="keyword">else</span> {</div><div class="line"> <span class="comment">// if the file is found, set Content-type and send data</span></div><div class="line"> res.setHeader(<span class="string">'Content-type'</span>, mimeType[ext] || <span class="string">'text/plain'</span> );</div><div class="line"> res.end(data);</div><div class="line"> }</div><div class="line"> });</div><div class="line"> });</div><div class="line"></div><div class="line"></div><div class="line">}).listen(<span class="built_in">parseInt</span>(port));</div><div class="line"></div><div class="line"><span class="built_in">console</span>.log(<span class="string">`Server listening on port <span class="subst">${port}</span>`</span>);</div></pre></td></tr></table></figure>
<p>We are using Node.js core <code>path.parse</code> libraries to get the extensions from the URL path. Similarly, we are using <code>url.parse</code> to break down the <code>request.url</code> into its components. Then, we extract the extension from the file. Finally, we use <code>fs.readFile</code> to get the content from the file system. If any error occurs related to the file path, we return a 404 and otherwise return the file content.</p>
<p>Give it a try with:</p>
<figure class="highlight bash"><figcaption><span>Command lines to test the server</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># run server</span></div><div class="line">node server.js</div><div class="line"></div><div class="line"><span class="comment"># get the javascript file with</span></div><div class="line">curl -i localhost:9000/server.js</div><div class="line"></div><div class="line"><span class="comment"># testing with non-existing file</span></div><div class="line">curl -i localhost:9000/invalid-file.doc</div></pre></td></tr></table></figure>
<p>For the first one, you will get a 200 OK response, while for the 2nd one you will get a 404 not found error, as expected.</p>
<p>You can also download the code from this repo and try out with the test files:</p>
<figure class="highlight bash"><figcaption><span>Testing with different file types</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># Get Repository</span></div><div class="line">git <span class="built_in">clone</span> https://github.com/amejiarosario/meanshop.git</div><div class="line"><span class="built_in">cd</span> meanshop</div><div class="line"><span class="comment"># Load the specific version</span></div><div class="line">git checkout 4add350fb27a7e72115fb16237f52a5b316709b3</div><div class="line"></div><div class="line"><span class="comment"># start the server (requires Node 4+)</span></div><div class="line">npm start</div><div class="line"></div><div class="line"><span class="comment"># test it in your browser with the following paths:</span></div><div class="line">open http://localhost:9000/</div><div class="line">open http://localhost:9000/index.html</div><div class="line">open http://localhost:9000/<span class="built_in">test</span>/meanshop-book.png</div></pre></td></tr></table></figure>
<h1 id="Summary">Summary<a href="#Summary" class="headerlink" title="Summary"></a></h1><p>In this post, we went through the basics about <code>http</code> module to create a server. We talk about the MIME types and how the help the browser to render properly. Finally, we put all together to accomplish our static file server with Node.js!</p>
]]></content>
<summary type="html">
<p>We are going to do a <strong>static file server</strong> in Node.js. This web server is going to respond with the content of the file in a given path. While we are doing this exercise we are going to cover more about <code>http</code> module. Also, use some utilities from other core modules such as <code>path</code>, <code>url</code> and <code>fs</code>.</p>
</summary>
<category term="Programming" scheme="http://adrianmejia.com/categories/Programming/"/>
<category term="Web Development" scheme="http://adrianmejia.com/categories/Programming/Web-Development/"/>
<category term="javascript" scheme="http://adrianmejia.com/tags/javascript/"/>
<category term="nodejs" scheme="http://adrianmejia.com/tags/nodejs/"/>
</entry>
<entry>
<title>Node Package Manager (NPM) Tutorial</title>
<link href="http://adrianmejia.com/blog/2016/08/19/Node-Package-Manager-NPM-Tutorial/"/>
<id>http://adrianmejia.com/blog/2016/08/19/Node-Package-Manager-NPM-Tutorial/</id>
<published>2016-08-19T20:18:32.000Z</published>
<updated>2016-08-19T20:18:32.000Z</updated>
<content type="html"><![CDATA[<p>This tutorial goes from how to install NPM to manage packages dependencies. While we are doing this, we will use practical examples to drive the concepts home.</p>
<a id="more"></a>
<p>Node Package Manager (NPM) is a CLI tool to manage dependencies. It also allows you to publish packages to the NPM website and find new modules.</p>
<p>In this section, we are going to get hands on NPM. We will cover from how to install it to how to download, uninstall and manage packages. While we are doing this we will use practical examples to drive the concepts home.</p>
<h1 id="How-to-install-update-NPM">How to install/update NPM?<a href="#How-to-install-update-NPM" class="headerlink" title="How to install/update NPM?"></a></h1><p><abbr title="Node Package Manager">NPM</abbr> is bundle into the Node installation. So, if you have Node, then you have <abbr title="Node Package Manager">NPM</abbr> already. But, <abbr title="Node Package Manager">NPM</abbr> gets updated more often than Node. So, from time to time you need to get the latest version.</p>
<p>You can check the NPM version and install latest by running:</p>
<figure class="highlight bash"><figcaption><span>Installing NPM</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># get version</span></div><div class="line">npm -v</div><div class="line"></div><div class="line"><span class="comment"># update NPM to latest and greatest</span></div><div class="line">npm install -g npm</div></pre></td></tr></table></figure>
<p>You can also use the shortcut for <code>npm install</code> like <code>npm i</code>.</p>
<h1 id="How-to-start-a-NodeJs-project">How to start a NodeJs project?<a href="#How-to-start-a-NodeJs-project" class="headerlink" title="How to start a NodeJs project?"></a></h1><p>Node projects and packages use a special file called <code>package.json</code>. It contains dependencies and more information to run the project. Let’s start by creating that using the <code>npm init</code> command. We are going to call our project <code>meanshop2</code>, but call it whatever you want ;)</p>
<figure class="highlight bash"><figcaption><span>initializing a Node project/package</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div></pre></td><td class="code"><pre><div class="line">mkdir meanshop2 && <span class="built_in">cd</span> meanshop2</div><div class="line">npm init --yes</div></pre></td></tr></table></figure>
<p>This set of commands created a new folder called <code>meanshop2</code>. The <code>init</code> command will create <code>package.json</code> file for us. The <code>--yes</code> option go with the defaults. Otherwise, it will ask us to fill out every property in package.json.</p>
<figure class="highlight javascript"><figcaption><span>package.json</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div></pre></td><td class="code"><pre><div class="line">{</div><div class="line"> <span class="string">"name"</span>: <span class="string">"meanshop2"</span>,</div><div class="line"> <span class="string">"version"</span>: <span class="string">"1.0.0"</span>,</div><div class="line"> <span class="string">"description"</span>: <span class="string">""</span>,</div><div class="line"> <span class="string">"main"</span>: <span class="string">"index.js"</span>,</div><div class="line"> <span class="string">"scripts"</span>: {</div><div class="line"> <span class="string">"test"</span>: <span class="string">"echo \"Error: no test specified\" && exit 1"</span></div><div class="line"> },</div><div class="line"> <span class="string">"keywords"</span>: [],</div><div class="line"> <span class="string">"author"</span>: <span class="string">""</span>,</div><div class="line"> <span class="string">"license"</span>: <span class="string">"ISC"</span></div><div class="line">}</div></pre></td></tr></table></figure>
<p>Feel free to edit any of the properties values, such as author, description. Notice, that version starts with <code>1.0.0</code>. We are going to talk more about versioning later on this tutorial.</p>
<h1 id="How-to-download-NPM-packages">How to download NPM packages?<a href="#How-to-download-NPM-packages" class="headerlink" title="How to download NPM packages?"></a></h1><p>You can download <abbr title="Node Package Manager">NPM</abbr> packages using <code>npm install <package_name></code>. By default, npm will grap the latest version, but you can also expecify an exact verision.</p>
<p>Let’s install two packages <code>lodash</code> and <code>express</code> as follows:</p>
<figure class="highlight bash"><figcaption><span>Installing NPM packages</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># install latest and save on package.json</span></div><div class="line">npm install lodash --save</div><div class="line"></div><div class="line"><span class="comment"># install specific version and save dep on package.json</span></div><div class="line">npm install [email protected] --save</div></pre></td></tr></table></figure>
<p><code>npm install</code> is going to create a new folder called <code>node_modules</code>. This is where all the dependencies live.</p>
<p>Notice that for the second package we are specifying the exact version. You can use the <code>@</code> symbol and then the version number.</p>
<p>Go to your <code>package.json</code> and verify that they both are listed as dependencies. You can install all the dependencies by running this command:</p>
<figure class="highlight bash"><figcaption><span>Install all dependencies from a package.json</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line">npm install</div></pre></td></tr></table></figure>
<p><abbr title="Node Package Manager">NPM</abbr> will add packages to dependencies if you use the <code>--save</code> flag. Otherwise <code>npm</code> won’t include it. To automate the process you can run:</p>
<figure class="highlight bash"><figcaption><span>Smarter NPM's defaults</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div></pre></td><td class="code"><pre><div class="line">npm config <span class="built_in">set</span> save=<span class="literal">true</span></div><div class="line">npm config <span class="built_in">set</span> save-exact=<span class="literal">true</span></div></pre></td></tr></table></figure>
<p>The <code>save=true</code> will make that the packages get auto-installed. <code>save-exact=true</code> will lock the current version and prevent automatic updates and break the project.</p>
<p>To sum up, here are the commands</p>
<figure class="highlight bash"><figcaption><span>NPM install commands</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># install a package globally</span></div><div class="line">npm install -g <package_name></div><div class="line"></div><div class="line"><span class="comment"># install a package locally (node_modules)</span></div><div class="line">npm install <package_name></div><div class="line"></div><div class="line"><span class="comment"># install a package locally and save it as dependency (package.json)</span></div><div class="line">npm install <package_name> --save-dev</div><div class="line"></div><div class="line"><span class="comment"># install package locally, save it as dependency with the exact version</span></div><div class="line">npm install <package_name> --save --save-exact</div><div class="line"></div><div class="line"><span class="comment"># install all dependencies listed on package.json</span></div><div class="line">npm install</div></pre></td></tr></table></figure>
<p>Usually, you use <code>--save-dev</code> vs <code>--save</code> when you need use package that is not part of the project. For instance, testing libraries, building assets tools, etc.</p>
<p>You can search for all NPM modules on <a href="https://www.npmjs.com/browse/star" target="_blank" rel="external">npmjs.com</a></p>
<h1 id="How-to-view-my-installed-NPM-packages">How to view my installed NPM packages?<a href="#How-to-view-my-installed-NPM-packages" class="headerlink" title="How to view my installed NPM packages?"></a></h1><p>Sometimes is useful to see the list of packages that you have installed on your system. You can do that with the following commands:</p>
<figure class="highlight bash"><figcaption><span>List packages</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># list all installed dependencies</span></div><div class="line">npm ls --depth=0</div><div class="line"></div><div class="line"><span class="comment"># list all installed globally dependencies</span></div><div class="line">npm ls -g --depth=0</div></pre></td></tr></table></figure>
<p>You can use <code>--depth=0</code> to prevent listing the dependencies’ dependencies.</p>
<h1 id="What-is-SemVer">What is SemVer?<a href="#What-is-SemVer" class="headerlink" title="What is SemVer?"></a></h1><p>Semantic Versioning (<abbr title="Semantic Versioning">SemVer</abbr>) is versioning convention composed of three numbers: <code>Major.Minor.Patch</code> or also <code>Breaking.Feature.Patch</code>:</p>
<ul>
<li><strong>Major releases: breaking changes.</strong> Major changes that change (breaks) how the API worked before. For instance, removed functions.</li>
<li><strong>Minor releases: new features</strong>. Changes that keeps the API working as before and adds new functionality.</li>
<li><strong>Patch releases: bug fixes</strong>. Patches doesn’t add functionality nor removes/changes functionality. It’s scope only to bug fixes.</li>
</ul>
<p>You can specify on the <code>package.json</code> how packages can be updated. You can use <code>~</code> for updating patches. <code>^</code> for upgrading minor releases and <code>*</code> for major releases.</p>
<p><img src="/images/semver-major-minor-patch-breaking-feature-fix.png" alt="SemVer Breaking.Feature.Fix"></p>
<p>Like this:</p>
<ul>
<li>Patch releases: <code>~1.0.7</code>, or <code>1.0.x</code> or just <code>1.0</code>.</li>
<li>Minor releases: <code>^1.0.7</code>, or <code>1.x</code> or just <code>1</code>.</li>
<li>Major releases: <code>*</code> or <code>x</code>.</li>
</ul>
<p>As you could imagine, not all developers respect the Semantic Version rules. Try to follow the rules yourself, but don’t trust that all will do. You can have your project working well with a <code>1.0.8</code> version and all in a sudden it breaks with <code>1.0.9</code>. It happened to me before, so I prefer to use: <code>--save-exact</code>, when makes sense.</p>
<h1 id="How-to-uninstall-NPM-packages">How to uninstall NPM packages?<a href="#How-to-uninstall-NPM-packages" class="headerlink" title="How to uninstall NPM packages?"></a></h1><p>You can uninstall <abbr title="Node Package Manager">NPM</abbr> packages using the following commands:</p>
<figure class="highlight bash"><figcaption><span>Uninstalling NPM packages</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># uninstall package and leave it listed as dep</span></div><div class="line">npm uninstall lodash</div><div class="line"></div><div class="line"><span class="comment"># uninstall and remove from dependencies</span></div><div class="line">npm uninstall --save lodash</div><div class="line"></div><div class="line"><span class="comment"># uninstall global package</span></div><div class="line">npm uninstall -g <package_name></div><div class="line"></div><div class="line"><span class="comment"># remove uninstalled packages from node_modules</span></div><div class="line">npm prune <span class="comment"># remove extranous</span></div></pre></td></tr></table></figure>
<h1 id="Summary">Summary<a href="#Summary" class="headerlink" title="Summary"></a></h1><p><abbr title="Node Package Manager">NPM</abbr> is a powerful tool. It helps us to create Node projects/modules, manage its dependencies and much more. In this section, we covered the main commands that you would most often.</p>
<p>Furthermore, we cover <abbr title="Semantic Versioning">SemVer</abbr>. It is used in many systems (Ruby Gems, etc.) not just in the Node community. SemVer is three-part number versioning system: Major.Minor.Patch. You can also think as Breaking.Feature.Patch.</p>
]]></content>
<summary type="html">
<p>This tutorial goes from how to install NPM to manage packages dependencies. While we are doing this, we will use practical examples to drive the concepts home.</p>
</summary>
<category term="Programming" scheme="http://adrianmejia.com/categories/Programming/"/>
<category term="Web Development" scheme="http://adrianmejia.com/categories/Programming/Web-Development/"/>
<category term="javascript" scheme="http://adrianmejia.com/tags/javascript/"/>
<category term="nodejs" scheme="http://adrianmejia.com/tags/nodejs/"/>
<category term="npm" scheme="http://adrianmejia.com/tags/npm/"/>
</entry>
<entry>
<title>Getting started with Node.js modules: require, exports, imports and beyond</title>
<link href="http://adrianmejia.com/blog/2016/08/12/Getting-started-with-Node-js-modules-require-exports-imports-npm-and-beyond/"/>
<id>http://adrianmejia.com/blog/2016/08/12/Getting-started-with-Node-js-modules-require-exports-imports-npm-and-beyond/</id>
<published>2016-08-12T20:30:23.000Z</published>
<updated>2016-08-12T20:30:23.000Z</updated>
<content type="html"><![CDATA[<p>Modules are a key concept to understand Node.js projects. We cover Node modules: require, exports and the future import.</p>
<a id="more"></a>
<p>Node modules allow you to write reusable code. You can include your own modules into another module. Using Node Package Manager (NPM), you can publish your module to the community. Also, NPM enables you to reuse modules made by other developers using.</p>
<p>In this section, we are going to cover how to create Node modules and each one of its components:</p>
<ul>
<li>Require</li>
<li>Exports</li>
<li>Module.exports</li>
</ul>
<blockquote>
<p>We are using Node 6+ for the examples and ES6 syntax. But the concepts are true for any version.</p>
</blockquote>
<h1 id="Require">Require<a href="#Require" class="headerlink" title="Require"></a></h1><p><code>require</code> are used to consume modules. It allows you to include modules into your programs. You can include built-in core Node.js modules, community-based modules (node_modules) and local modules.</p>
<p>Let’s say we want to read a file from the filesystem. Node has a core module called ‘fs’:</p>
<figure class="highlight js"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div></pre></td><td class="code"><pre><div class="line marked"><span class="keyword">const</span> fs = <span class="built_in">require</span>(<span class="string">'fs'</span>);</div><div class="line"></div><div class="line">fs.readFile(<span class="string">'./file.txt'</span>, <span class="string">'utf-8'</span>, (err, data) => {</div><div class="line"> <span class="keyword">if</span>(err) { <span class="keyword">throw</span> err; }</div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'data: '</span>, data);</div><div class="line">});</div></pre></td></tr></table></figure>
<p>As you can see, we imported the “fs” module into our program. It allows us to any function attached to it, like “readFile”.</p>
<p>Require will look for files in the following order:</p>
<ol>
<li>Built-in core Node.js modules (like <code>fs</code>)</li>
<li>Modules in <code>node_modules</code> folder.</li>
<li>If the module name has a <code>./</code>, <code>/</code> or <code>../</code>, it will look for the directory/file in the given path. It matches the extensions: <code>*.js</code>, <code>*.json</code> and <code>*.node</code>.</li>
</ol>
<h1 id="Exports">Exports<a href="#Exports" class="headerlink" title="Exports"></a></h1><p><code>exports</code> are used to create modules. It allows you to export your own objects and functions. Let’s do an example:</p>
<figure class="highlight javascript"><figcaption><span>circle.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">const</span> PI = <span class="number">3.14159265359</span>;</div><div class="line">exports.area = (radius) => <span class="built_in">Math</span>.pow(radius, <span class="number">2</span>) * PI;</div><div class="line">exports.circunference = (radius) => <span class="number">2</span> * radius * PI;</div></pre></td></tr></table></figure>
<p>In the code below, we are exporting the <code>area</code> function. We defined the constant PI but this is only accessible within the module. Only the elements associated to <code>exports</code> are accessible outside the module.</p>
<p>So, we can consume it using <code>require</code> in another file like follows:</p>
<figure class="highlight javascript"><figcaption><span>main.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">const</span> circle = <span class="built_in">require</span>(<span class="string">'./circle'</span>);</div><div class="line"></div><div class="line"><span class="keyword">let</span> r = <span class="number">3</span>;</div><div class="line"><span class="built_in">console</span>.log(<span class="string">`Circle with radius <span class="subst">${r}</span> has</span></div><div class="line"> area: <span class="subst">${circle.area(r)}</span>;</div><div class="line"> circunference: <span class="subst">${circle.circunference(r)}</span>`);</div></pre></td></tr></table></figure>
<p>Noticed that this time we prefix the module name with ‘./‘. That indicates that the module is a local file.</p>
<h1 id="Module-Wrapper">Module Wrapper<a href="#Module-Wrapper" class="headerlink" title="Module Wrapper"></a></h1><p>You can think of each module as self-contained function like the following one:</p>
<figure class="highlight javascript"><figcaption><span>Module Wrapper</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div></pre></td><td class="code"><pre><div class="line">(<span class="function"><span class="keyword">function</span> (<span class="params">exports, require, module, __filename, __dirname</span>) </span>{</div><div class="line"> <span class="built_in">module</span>.exports = exports = {};</div><div class="line"></div><div class="line"> <span class="comment">// Your module code ...</span></div><div class="line"></div><div class="line">});</div></pre></td></tr></table></figure>
<p>We have already covered <code>exports</code> and <code>require</code>. Notice the relationship between <code>module.exports</code> and <code>exports</code>. They points to the same reference. However, if you assign something directly to <code>exports</code> you will break its link to <code>module.exports</code>. More on that in the next section.</p>
<p>For our convenience <code>__filename</code> and <code>__dirname</code> are defined. They provide the full path to the current file and directory. The latter excludes the filename and just print out the directory path.</p>
<p>For instance, for our <code>./circle.js</code> module, it would be something like this:</p>
<ul>
<li><p><code>__filename</code>: <code>/User/adrian/code/circle.js</code></p>
</li>
<li><p><code>__dirname</code>: <code>/User/adrian/code</code></p>
</li>
</ul>
<p>Ok, we have covered <code>exports</code>, <code>require</code>, <code>__filename</code>, and <code>__dirname</code>. The only one we haven’t cover is <code>module</code>. Let’s go for it!</p>
<h1 id="Module-exports-vs-Exports">Module.exports vs Exports<a href="#Module-exports-vs-Exports" class="headerlink" title="Module.exports vs Exports"></a></h1><p>Module is not a global, it is local for each module. It contains metadata about a module, such as module id, exports, parent, children, …</p>
<p><code>exports</code> is an alias of <code>module.exports</code>. So, whatever you assign to <code>exports</code> is also available on <code>module.exports</code>. However, if you assign something directly to exports, then you lose the shortcut to <code>module.exports</code>. E.g.</p>
<figure class="highlight javascript"><figcaption><span>cat.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div></pre></td><td class="code"><pre><div class="line"><span class="class"><span class="keyword">class</span> <span class="title">Cat</span> </span>{</div><div class="line"> makeSound() {</div><div class="line"> <span class="keyword">return</span> <span class="string">'Meowww'</span>;</div><div class="line"> }</div><div class="line">}</div><div class="line"></div><div class="line"><span class="comment">// exports = Cat; // It will not work</span></div><div class="line"><span class="built_in">module</span>.exports = Cat;</div></pre></td></tr></table></figure>
<p>Try the following example with <code>exports</code> and then with <code>module.exports</code>.</p>
<figure class="highlight javascript"><figcaption><span>main.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">const</span> Cat = <span class="built_in">require</span>(<span class="string">'./cat'</span>);</div><div class="line"><span class="keyword">var</span> cat = <span class="keyword">new</span> Cat();</div><div class="line"><span class="built_in">console</span>.log(cat.makeSound());</div></pre></td></tr></table></figure>
<p>To sum up, when to use <code>module.exports</code> vs <code>exports</code>:</p>
<p>Use <code>exports</code> to:</p>
<ul>
<li>Export named function. e.g. <code>exports.area</code>, <code>exports.circunference</code>.</li>
</ul>
<p>Use <code>module.exports</code> to:</p>
<ol>
<li><p>If you want to export an object, class, function at the root level (e.g. <code>module.exports = Cat</code></p>
</li>
<li><p>If you want to return a single object that exposes multiple assignments. e.g.<code>module.exports = {area: area, circumference: circunference};</code></p>
</li>
</ol>
<h1 id="Imports">Imports<a href="#Imports" class="headerlink" title="Imports"></a></h1><p>Imports are not available in Node as the version 6. However, it might come in future versions.</p>
<figure class="highlight javascript"><figcaption><span>future of modules in javascript</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">import</span> circle <span class="keyword">from</span> <span class="string">'./circle'</span>;</div><div class="line"><span class="keyword">import</span> {area, circumference} <span class="keyword">from</span> <span class="string">'./circle'</span>;</div></pre></td></tr></table></figure>
<p>You can use it today, using transpilers such as Traceur Compiler, Babel or Rollup. But, that will be for another post.</p>
<h1 id="Summary">Summary<a href="#Summary" class="headerlink" title="Summary"></a></h1><p>We learned about how to create Node.js modules and use it in our code. Modules allow us to reuse code easily. They provide functionality that is isolated from other modules. Required is used to load modules. Export and module exports allow defining what parts of our code we want to expose. We also explored the difference between module.exports and exports. Finally, we took a quick pick about what’s coming up for modules using <code>imports</code>.</p>
]]></content>
<summary type="html">
<p>Modules are a key concept to understand Node.js projects. We cover Node modules: require, exports and the future import.</p>
</summary>
<category term="Programming" scheme="http://adrianmejia.com/categories/Programming/"/>
<category term="Web Development" scheme="http://adrianmejia.com/categories/Programming/Web-Development/"/>
<category term="javascript" scheme="http://adrianmejia.com/tags/javascript/"/>
<category term="NodeJS" scheme="http://adrianmejia.com/tags/NodeJS/"/>
</entry>
<entry>
<title>List tasks in NPM, Grunt, Gulp and Rake</title>
<link href="http://adrianmejia.com/blog/2016/06/25/List-tasks-in-npm-grunt-gulp-and-rake/"/>
<id>http://adrianmejia.com/blog/2016/06/25/List-tasks-in-npm-grunt-gulp-and-rake/</id>
<published>2016-06-25T19:14:49.000Z</published>
<updated>2016-08-14T19:12:25.000Z</updated>
<content type="html"><![CDATA[<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div></pre></td><td class="code"><pre><div class="line">npm run</div><div class="line">grunt --help</div><div class="line">gulp --tasks</div><div class="line">rake --tasks</div></pre></td></tr></table></figure>
]]></content>
<summary type="html">
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div
</summary>
<category term="Programming" scheme="http://adrianmejia.com/categories/Programming/"/>
<category term="Web Development" scheme="http://adrianmejia.com/categories/Programming/Web-Development/"/>
<category term="javascript" scheme="http://adrianmejia.com/tags/javascript/"/>
<category term="gruntjs" scheme="http://adrianmejia.com/tags/gruntjs/"/>
<category term="gulpjs" scheme="http://adrianmejia.com/tags/gulpjs/"/>
</entry>
<entry>
<title>Creating custom AngularJS directives for beginners</title>
<link href="http://adrianmejia.com/blog/2016/04/08/creating-custom-angularjs-directives-for-beginners/"/>
<id>http://adrianmejia.com/blog/2016/04/08/creating-custom-angularjs-directives-for-beginners/</id>
<published>2016-04-08T20:41:32.000Z</published>
<updated>2016-04-08T20:41:32.000Z</updated>
<content type="html"><![CDATA[<p>Directives are one of the most important concepts to understand Angular. This tutorial takes through the basics and beyond. We will cover how to build your own HTML extensions through directives.</p>
<a id="more"></a>
<p>Angular framework relies heavily on them to teach the browser new HTML tags. Directives are a powerful tool to create reusable web components. Directives not only could be defined as new HTML tags but also as attributes, CSS classes or even HTML comments. Angular comes with many built-in (core) directives that offer numerous functionalities to your web applications right away. Furthermore, it also allows us to define our own through custom directives. We are going to focus on the later.</p>
<p>Let’s say we want to create a new HTML component that the browsers doesn’t support yet, like a To-do list:</p>
<figure class="highlight html"><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line"><span class="tag"><<span class="name">my-todo</span> <span class="attr">list</span>=<span class="string">"todo"</span> <span class="attr">title</span>=<span class="string">"Angular Todo"</span>></span><span class="tag"></<span class="name">my-todo</span>></span></div></pre></td></tr></table></figure>
<p>If you paste that code in any browser, it will not do much. We need to use Angular to teach the browser how to interpret this new HTML element called “my-todo”. We do this by defining a new directive with its attributes.</p>
<p>Let’s initialize our app and define our new directive:</p>
<p>Create a new file called “script.js”</p>
<figure class="highlight javascript"><figcaption><span>script.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">var</span> app = angular.module(<span class="string">'myApp'</span>, []);</div><div class="line"></div><div class="line">app.directive(<span class="string">'myTodo'</span>, <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> <span class="keyword">return</span> {</div><div class="line"> restrict: <span class="string">'EA'</span>,</div><div class="line"> templateUrl: <span class="string">'todo.tpl.html'</span>,</div><div class="line"> scope: {</div><div class="line"> list: <span class="string">'='</span>,</div><div class="line"> title: <span class="string">'@'</span></div><div class="line"> }</div><div class="line"> };</div><div class="line"> });</div></pre></td></tr></table></figure>
<p>Don’t get scared if you don’t understand what’s going on right now. By the end of this tutorial, you will be able to know what each line is doing.</p>
<p>In the first line, we initialize an angular module called “myApp”. That will return an “app” instance where we can start defining our Angular app.</p>
<p>We start by adding a directive called “myTodo”, notice that is different from “my-todo” that we used in the HTML code above. That’s because, by convention in HTML, tags names words are separated by a hyphen like “my-todo”. On the other hand, in Angular they match the same element with words joint together and capitalizing the beginning of each word, except the first one “myTodo”. This style of joining words is known as “camelCase”.</p>
<p>You will notice that a directive, takes a name “myTodo” and function. The later returns an object with a number of attributes depending on what we would like to accomplish. In our case, we have three attributes: restrict, templateUrl, and scope. Let’s explain each one in that exact order.</p>
<h1 id="Restrict">Restrict<a href="#Restrict" class="headerlink" title="Restrict"></a></h1><p>The “restrict” attribute tells Angular, with one letter, how are we going to create our new directive. It can take four different values ‘E’, ‘A’, ‘C’, ‘M’ or combination of them like ‘EA’. Each one has it’s own meaning:</p>
<table>
<thead>
<tr>
<th>Restrict</th>
<th>Meaning</th>
<th>Example</th>
</tr>
</thead>
<tbody>
<tr>
<td>E</td>
<td>Implies we are going to use our directive as a new HTML element.</td>
<td><code><my-todo list="todo" title="Element"> </my-todo></code></td>
</tr>
<tr>
<td>A</td>
<td>Means that our directive is going to take over any HTML element that has an attribute that matches our directive name.</td>
<td><code><div my-todo list="todo" title="Attr"> </div></code></td>
</tr>
<tr>
<td>C</td>
<td>Indicates that our directive will be found in CSS classes.</td>
<td><code><div class="my-todo" list="todo" title="Class"> </div></code></td>
</tr>
<tr>
<td>M</td>
<td>Matches HTML comments.</td>
<td><code><!--directive:my-todo attributes goes here--></code></td>
</tr>
</tbody>
</table>
<p>Taking our To-do example, with the combined value ‘EA’, means that will match any element with our directive as an attribute, and also, it will match any element defined as “<my-todo>”</my-todo></p>
<p>It is a good practice only to use restrict to either ‘E’ or ‘A’ or both. Classes ‘C’ and comments ‘M’ could be easily misinterpreted. That’s why we are using just EA.</p>
<h1 id="Template">Template<a href="#Template" class="headerlink" title="Template"></a></h1><p>Templates are just HTML code that could be reuse multiple times with different values or text. In order to be generic enough, they use placeholders tied to variables that could be easily replaced. Let’s create the “todo.tpl.html” with the following content:</p>
<figure class="highlight html"><figcaption><span>todo.tpl.html</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div></pre></td><td class="code"><pre><div class="line"><span class="tag"><<span class="name">h1</span>></span>{{title}}<span class="tag"></<span class="name">h1</span>></span></div><div class="line"><span class="tag"><<span class="name">div</span> <span class="attr">ng-repeat</span>=<span class="string">"todo in list"</span>></span></div><div class="line"> <span class="tag"><<span class="name">input</span> <span class="attr">type</span>=<span class="string">"checkbox"</span> <span class="attr">ng-model</span>=<span class="string">"todo.completed"</span>></span> {{todo.name}}</div><div class="line"><span class="tag"></<span class="name">div</span>></span></div></pre></td></tr></table></figure>
<p>Notice that our template contains placeholders with a variable such as Creating custom AngularJS directives for beginners, which is going, to be replaced by real title text. Similarly, is going to be replaced with a task name.</p>
<p>We just used our first built-in Angular directive, in this tutorial, “ng-repeat”. This directive is going to take an array of elements, like our list and repeat itself for each one of elements and refer to them as “todo”. In other words, if the list contains 4 tasks, we are going to see 4 checkboxes each one with the name of the individual tasks. We are going to explain where “title” and “list” comes in the next section.</p>
<p>Going back to our directive definition, we could have used “template” attribute instead of “templateUrl” and take inline html code directly, but often is hard to read and we would prefer to use “templateUrl” and defined as a separated file.</p>
<p>As you might figure it out, “templateUrl” takes the name of the file containing the template. If all templates and code are in the same directory just the name of the file will do. If they are in a different folder you will need to specify the full path to reach it. To keep it simple, we are going to have all files in a single directory.</p>
<h1 id="Scope">Scope<a href="#Scope" class="headerlink" title="Scope"></a></h1><p>Scopes are key concept to understand Angular. Scope is what glues JavaScript code with HTML and allow us to replace placeholders from templates with real values.</p>
<p>In our directive definition, we are creating a new “isolated scope” with two elements:</p>
<figure class="highlight javascript"><figcaption><span>Isolated scope</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div></pre></td><td class="code"><pre><div class="line">scope: {</div><div class="line"> list: <span class="string">'='</span>,</div><div class="line"> title: <span class="string">'@'</span></div><div class="line">}</div></pre></td></tr></table></figure>
<p>If you remember from our template, these are exactly the two placeholders that we had “title” and “list”. The symbols = and @ looks a little mysterious but they are not too cryptic once we know what they mean.</p>
<ul>
<li><code>@</code> Implies that the value of the attribute with the same name in the HTML element will be passed as a string. For instance, <my-todo title="The Directive"></my-todo>, will replace Creating custom AngularJS directives for beginners in our template for “The Directive”.</li>
<li><code>=</code> Binds to the value of the expression and to the literal value. This means that if we have an attribute list=“todo” and “todo” is equal to 5, then it will be replaced to 5 and not to the literal text “todo”. In our case, “todo” is going to be an array of tasks.</li>
</ul>
<p>Bear in mind, that in Angular we can have multiple scopes. So, our directives could be influenced by outer scopes. For instance, another scope could define “todo” as an array of elements. Here is where we introduce another important concept: controllers.</p>
<h1 id="Controllers">Controllers<a href="#Controllers" class="headerlink" title="Controllers"></a></h1><p>The main purpose of controllers is to set initial values the scope and also add behavior through functions. We are going to use a controller to define the “todo” list that we want to render with our newly created directive.</p>
<p>The way we create controllers is by attaching the controller to our Angular app instance. Let’s go back to script.js and append the following:</p>
<figure class="highlight javascript"><figcaption><span>script.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div></pre></td><td class="code"><pre><div class="line">app.controller(<span class="string">'main'</span>, <span class="function"><span class="keyword">function</span>(<span class="params">$scope</span>)</span>{</div><div class="line"> $scope.todo = [</div><div class="line"> {name: <span class="string">'Create a custom directive'</span>, completed: <span class="literal">true</span>},</div><div class="line"> {name: <span class="string">'Learn about restrict'</span>, completed: <span class="literal">true</span>},</div><div class="line"> {name: <span class="string">'Master scopes'</span>, completed: <span class="literal">false</span>}</div><div class="line"> ];</div><div class="line">});</div></pre></td></tr></table></figure>
<p>Noticed that we defined our controller with the name “main” and pass along a function with the “$scope” parameter. This is important since, whatever we attach to the “$scope” variable it will become available in templates and other directives. We just defined our todo list as an array of objects with two properties name and completed.</p>
<h1 id="To-do-directive">To-do directive<a href="#To-do-directive" class="headerlink" title="To-do directive"></a></h1><p>So far, we have been preparing the grounds for our directive. We have created:</p>
<ul>
<li>“myApp” module</li>
<li>“myTodo” directive</li>
<li>“todo.tpl.html” template</li>
<li>“main” controller</li>
</ul>
<p>Now, is the time to put everything together and make it work!</p>
<p>Let’s create an index.html page with the following:</p>
<figure class="highlight html"><figcaption><span>index.html</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div><div class="line">15</div><div class="line">16</div></pre></td><td class="code"><pre><div class="line"><span class="meta"><!DOCTYPE html></span></div><div class="line"><span class="tag"><<span class="name">html</span>></span></div><div class="line"></div><div class="line"> <span class="tag"><<span class="name">head</span>></span></div><div class="line"> <span class="tag"><<span class="name">script</span> <span class="attr">data-require</span>=<span class="string">"[email protected]"</span> <span class="attr">data-semver</span>=<span class="string">"1.5.0"</span> <span class="attr">src</span>=<span class="string">"https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.js"</span>></span><span class="undefined"></span><span class="tag"></<span class="name">script</span>></span></div><div class="line"> <span class="tag"><<span class="name">script</span> <span class="attr">src</span>=<span class="string">"script.js"</span>></span><span class="undefined"></span><span class="tag"></<span class="name">script</span>></span></div><div class="line"> <span class="tag"></<span class="name">head</span>></span></div><div class="line"></div><div class="line"> <span class="tag"><<span class="name">body</span> <span class="attr">ng-app</span>=<span class="string">"myApp"</span>></span></div><div class="line"></div><div class="line"> <span class="tag"><<span class="name">div</span> <span class="attr">ng-controller</span>=<span class="string">"main"</span>></span></div><div class="line"> <span class="tag"><<span class="name">my-todo</span> <span class="attr">list</span>=<span class="string">"todo"</span> <span class="attr">title</span>=<span class="string">"Angular To-do"</span>></span><span class="tag"></<span class="name">my-todo</span>></span></div><div class="line"> <span class="tag"></<span class="name">div</span>></span></div><div class="line"></div><div class="line"> <span class="tag"></<span class="name">body</span>></span></div><div class="line"><span class="tag"></<span class="name">html</span>></span></div></pre></td></tr></table></figure>
<p>We add the AngularJS library first and then initialize the app using the built-in directive “ng-app”. Notice that this must match to module that we created “myApp” or it won’t work.</p>
<p>Later, we reference our controller using another core directive called “ng-controller”. Similarly to ng-app, it also takes a value that should match the one we defined, in this case “main” controller. This main controller defines our “todo” as an array of tasks with names and whether they have been completed or not.</p>
<p>Finally, we start using our new directive! It takes two attributes the title and a list. If you remember, we defined a template inside the directive definition, so it knows how to render the content.</p>
<p>That’s all you need to make it work. Now try it!</p>
<iframe style="width: 100%; height: 400px;" src="//embed.plnkr.co/7ZDRclRJaJyTtRBKjIa3/" frameborder="0" allowfullscren="allowfullscren"></iframe>
<h1 id="Next-steps">Next steps<a href="#Next-steps" class="headerlink" title="Next steps"></a></h1><p>By now you should be looking at our new To-do list. We can reuse this new directive with new to-do lists as many times as we want. Just passing different values to “list” in our “my-todo” the browser will be able to render it for us. We can also define another controller with a different $scope.todo and our directive will respond accordantly.</p>
<p>We just walked through the main attributes to create directives and discuss how to use them. We learnt how to isolate the scope of our directive and just allow certain parameters into our templates such as “list” and “title”. Also, used the “restrict” attribute to allow our directive be created either as a new HTML element or as an attribute. Finally, we explore how to use templates and bind it with our scope variables.</p>
<h2 id="Related-Posts">Related Posts<a href="#Related-Posts" class="headerlink" title="Related Posts"></a></h2><ul>
<li><a href="/blog/2014/09/28/angularjs-tutorial-for-beginners-with-nodejs-expressjs-and-mongodb/">AngularJS Tutorial for Beginners</a></li>
<li><a href="/blog/2014/10/03/mean-stack-tutorial-mongodb-expressjs-angularjs-nodejs/">Angular and Node tutorial</a></li>
</ul>
]]></content>
<summary type="html">
<p>Directives are one of the most important concepts to understand Angular. This tutorial takes through the basics and beyond. We will cover how to build your own HTML extensions through directives.</p>
</summary>
<category term="Technologies" scheme="http://adrianmejia.com/categories/Technologies/"/>
<category term="Web Development" scheme="http://adrianmejia.com/categories/Technologies/Web-Development/"/>
<category term="javascript" scheme="http://adrianmejia.com/tags/javascript/"/>
<category term="angularjs" scheme="http://adrianmejia.com/tags/angularjs/"/>
</entry>
<entry>
<title>How to scale a Nodejs app based on number of users</title>
<link href="http://adrianmejia.com/blog/2016/03/23/how-to-scale-a-nodejs-app-based-on-number-of-users/"/>
<id>http://adrianmejia.com/blog/2016/03/23/how-to-scale-a-nodejs-app-based-on-number-of-users/</id>
<published>2016-03-23T21:34:11.000Z</published>
<updated>2016-03-23T21:34:11.000Z</updated>
<content type="html"><![CDATA[<p>Massive success is the best that could happen to any application. But, it could be a blessing and a curse for developers. Dealing with downtime, high availability and trying to scale. The following is a guideline on how to scale the web applications as the number of users grows.</p>
<a id="more"></a>
<p>One of the most dreaded questions is: ‘Would that scale?’. The following is a guideline on how to grow the web applications as the number of users grows. Scaling an application too early is more painful than beneficial. This guide provides a way how to start simple and scale as the number of users grows.</p>
<p><strong>Common Server Setups For Scaling Your Web Application</strong></p>
<p>The examples and solutions will be as practical as possible. We might use references to Amazon Web Services (AWS), Digital Ocean or other cloud solutions. Also, there are some NodeJS/Nginx references, but they could easily be translated to other technologies.</p>
<p>You may notice, that the measurement we are using is “concurrent user”, which means all users are hitting the web app at the same time. It’s different from the number of users supported (which might be higher) since it’s unlikely that all users are hitting the app at the same time. However, we are going to use “concurrent user” since it’s easier to explain.</p>
<h1 id="Local-host-1-concurrent-users">Local host (1 concurrent users)<a href="#Local-host-1-concurrent-users" class="headerlink" title="Local host (1 concurrent users)"></a></h1><p>You are the only one using your app on your localhost.</p>
<p>There is no need to worry about scale.</p>
<h1 id="Single-Server-2-9-concurrent-users">Single Server (2 - 9 concurrent users)<a href="#Single-Server-2-9-concurrent-users" class="headerlink" title="Single Server (2 - 9 concurrent users)"></a></h1><p>You deployed your app to the wild! 👏🏻 You and your colleges (and maybe close friends) are the only users so far.</p>
<p>Everything is great on a single server as long as you are using a web server that uses an event model like Nginx. NodeJS by nature uses an event-driven and non-blocking I/O model. It means that it won’t block with a single request, rather it will handle all the request and reply as data from database or services comes available in a callback/promise. Your Node app will spend most of the time waiting for the database or file system to respond. In the meantime, it can take multiple requests.</p>
<p>Your app should be a monolith (single app) right now, and it’s fine. No need to complicate your life for just a few users yet.If people are reporting bugs, unfortunately, as you make changes, you will need to take it down the app while updating the server. Using AWS t2.micro/t2.nano or equivalent (1 CPU/ 1 GB RAM) will do.</p>
<img src="/images/10_users.png" title="Single Server Setup">
<p>The “Single Server Setup” is the simplest. Web application and database share the same resources (CPU, Memory RAM, I/O).</p>
<h1 id="Vertical-Scaling-10-99-concurrent-users">Vertical Scaling (10 - 99 concurrent users)<a href="#Vertical-Scaling-10-99-concurrent-users" class="headerlink" title="Vertical Scaling (10 - 99 concurrent users)"></a></h1><p>You decided to talk about your app in your social networks 👍🏻. Your friends from Facebook and other social network start clicking the link to your web app at once and you are getting around 100 users.</p>
<p>Requests might start to take longer, and things start to become slower. You need a bigger box! This is called <strong>vertical scaling</strong>. Vertical scale means upgrading a single server hardware with more resources such as higher/faster CPU, RAM, HDD, and I/O.</p>
<p>If you are using AWS, you might upgrade to a t2.medium or equivalent (2 CPU / 4 GB RAM). An additional benefit of having multi CPU cores. We can run two instances of your NodeJS and load balance it with Nginx. Multiple instances of your app mean that you could achieve zero-downtime deployment/updates. You can upgrade one server while the other keeps serving the requests. For example, take down server #1, while server #2 continues serving the request. Then, bring up server #1 and take down server #2 to update it. In the end, no request will be dropped, and your app is fully updated.</p>
<img src="/images/100_users.png" title="Scaling a Single Server">
<p>This setup has several improvements over the previous one:</p>
<ul>
<li>Nginx takes care of users requests and accomplish two functions: static filers server and reverse proxy. It serve by itself all static files (CSS, JS, Images) without touching the web app. The request that needs the app to resolve are redirected it, this is called reverse proxy.</li>
<li>Zero-downtime upgrades.</li>
</ul>
<h1 id="Horizontal-Scaling-100-999-concurrent-users">Horizontal Scaling (100 - 999 concurrent users)<a href="#Horizontal-Scaling-100-999-concurrent-users" class="headerlink" title="Horizontal Scaling (100 - 999 concurrent users)"></a></h1><p>Looks like the hard work has paid off and your app continue growing to around 1,000 users! 🙌🏻</p>
<p>After some time, the app is becoming slow again. Probably, the bottleneck is on the I/O. Database is taking longer to respond. We could keep upgrading to m4.xlarge or equivalent (4 CPU / 16 GB RAM). 4 CPU means that you could have also have multiple instances of the database/app. This is called <strong>horizontal scaling</strong>.</p>
<p>There is a point where vertical scaling is not cost/effective anymore especially. For instance, on look at this comparison and prices from Digital Ocean:</p>
<img src="/images/vertical_vs_horizontal_scaling.png" title="Vertical vs Horizontal Scaling">
<p>On AWS will a little bit more wider the price range: $37.44/mo vs $172.08/mo.</p>
<p>Vertical scaling has another issue: all your eggs are in one basket. If the server goes down, you’re screwed! On the other hand, horizontal scaling will give you redundancy and failover capabilities if done right.</p>
<p>At this point, it’s better to start scaling horizontally rather than vertically. The bottleneck is most likely on the database. So, we can:</p>
<ul>
<li>Move the database to a different server and scale it independently</li>
<li>Add replica set if the database hits its limit and db caching if it makes sense.</li>
</ul>
<p>Since the Node is very efficient, it will spend most of the time waiting for the database to return data. So, the main limitation will be dictated by the network limits. You might need to play also with <code>/etc/security/limits.d</code> and <code>/etc/sysctl.conf</code> based on your needs. For instance the maximum number of requests queued are determined by <code>net.core.somaxconn</code>, which defaults to 128. Change it to <code>1024</code> so we can meet the 100 - 999 range of users. From now on, let’s handle 1000 users per application server.</p>
<h1 id="Multi-servers-1-000-concurrent-users">Multi-servers (1,000+ concurrent users)<a href="#Multi-servers-1-000-concurrent-users" class="headerlink" title="Multi-servers (1,000+ concurrent users)"></a></h1><p>The app keeps growing and now we need to prepare to support around 10k users!</p>
<p>We can improve our previous setup, as follows:</p>
<ul>
<li>Add load balancer (e.g. ELB) and add app units.</li>
<li>Use multiple availability zones (AZ) in a region (e.g. us-east-1, us-west-1), which one are connected through low latency links.</li>
<li>Split static files to different server/service for easier maintenance. (e.g. AWS S3 and CloudFront CDN). Add CDN for static files for optimizing cross-origin performance and lower the latency. You can store assets such as Javascript, CSS, images, videos, and so on.</li>
</ul>
<p>Using Elastic Load Balancer (ELB) with Route 53 is Amazon AWS specific, but there are similar solutions for other clouds providers. ELB is a load balancer managed by AWS and is available in all existing AZ. ELB has health checks so it won’t route to a failing host. It also can manage around 1000s instances.</p>
<img src="/images/10k_users.png" title="Horizontal Scaling">
<p>In this server setup, we started growing horizontally rather than vertically. In other words, we separated web application from database and scale each one with multiple instances. There are several advantages of having the database in a different server than the app:</p>
<ul>
<li>Application and database doesn’t fight for the same resources.</li>
<li>We can scale each tier (app, db) independently to as many as we need.</li>
</ul>
<p>The cons is that getting this setup is more complicated. Furthermore, since app and db are not in the same server performance issues might arise due to network latency or bandwidth limits. It maximize performance, it’s recommended to use private networks with low latency and high speed links.</p>
<h1 id="Microservices-100-000-concurrent-users">Microservices (100,000+ concurrent users)<a href="#Microservices-100-000-concurrent-users" class="headerlink" title="Microservices (100,000+ concurrent users)"></a></h1><p>This is it! We need to plan the infrastructure to allow us to grow to infinity! ∞</p>
<p>So far, we have been leveraging vertical and horizontal scaling, we have separated web apps from databases instances, and deploy them to multiple regions. However, we have been a single code based that handles all the work in our application. We can break it down into smaller pieces and scale them as needed. Going from monolith to microservices.</p>
<p>It’s time to take down our web app monolith and break it down into multiple smaller and independent components (microservices/SOA) that we can scale independently. We don’t have to do the break down all at once. We can have the monolith keep doing what it was doing and start writing small client apps performs some of the task that the main app used to do. Later, we can use the load balancer to redirect the traffic to the new small service instead of the main app. Eventually, we can remove the code from the monolith since the new microservice has fully replaced it. Repeat this process as many time as needed to create new microservices. It should looks something like this:</p>
<img src="/images/1m_users.png" title="Microservices Setup">
<p>If you notice, we have three new components that can scale independently as needed: Users, Products Catalog, and Orders for instance. Another advantages of having microservices is that we can have split the database as well.</p>
<h1 id="Automate-Chores-1-000-000-concurrent-users">Automate Chores (1,000,000+ concurrent users)<a href="#Automate-Chores-1-000-000-concurrent-users" class="headerlink" title="Automate Chores (1,000,000+ concurrent users)"></a></h1><p>OMG! That’s so many people, get you champagne bottle out and celebrate 🎉after you automate!</p>
<p><strong>Automate</strong> as much as you can. The infrastructure is getting fat. We have db replicas and sharding, horizontal scaling, multiple regions and multi-AZ, autoscaling.</p>
<p><strong>Highly Available, Multi-Region</strong> At this point, to scale we just keep adding instances and spreading across availability zones and regions based on the source of the traffic. If you notice that a significant amount of traffic is coming from Australia and Germany maybe it’s the time to make your app available there (e.g. ap-southeast-2, eu-central-1). Bear in mind that regions doesn’t provide low latency links between them. One way to work around this issue is sharding the database.</p>
<p><strong>Autoscaling</strong> It would be a waste if you always allocate servers for peak capacity. User traffic has peaks (e.g. Black Friday) and valleys (e.g. 4 am.). That said, it’s better to put in place an autoscaling option that allows the network to adjust to the traffic conditions. There are multiple strategies to autoscale such as CPU utilization, scale based on latency or based on network traffic.</p>
<p><strong>Metrics</strong> You will also need metrics, monitoring and centralize logging. Measure everything that can be measured. Server nodes might start to fail randomly, and you don’t want to login/SSH into each one to determine the cause. You can avoid that by having a centralized logging solution such as the ELK stack (Elasticsearch, Logstash, and Kibana). For monitoring, you can try DataDog, it has very nice visualization about the servers and CPU/RAM stats. Actully, in DataDog you can aggregate any data that you want.</p>
<p><strong>Customization</strong> Databases might still be a headache to scale. If you identify that your use case it’s better solved with a different NoSQL solution, go for it. Try always to not reinvent the wheel, but if there’s no solution out there for your particular need, consider doing your own.</p>
<p>For more general guidelines <a href="/blog/2016/01/09/how-to-build-scalable-apps/">read my previous post</a>.</p>
]]></content>
<summary type="html">
<p>Massive success is the best that could happen to any application. But, it could be a blessing and a curse for developers. Dealing with downtime, high availability and trying to scale. The following is a guideline on how to scale the web applications as the number of users grows.</p>
</summary>
<category term="Technologies" scheme="http://adrianmejia.com/categories/Technologies/"/>
<category term="production" scheme="http://adrianmejia.com/tags/production/"/>
<category term="scalability" scheme="http://adrianmejia.com/tags/scalability/"/>
</entry>
<entry>
<title>How to build scalable apps?</title>
<link href="http://adrianmejia.com/blog/2016/01/09/how-to-build-scalable-apps/"/>
<id>http://adrianmejia.com/blog/2016/01/09/how-to-build-scalable-apps/</id>
<published>2016-01-09T15:43:27.000Z</published>
<updated>2016-01-09T15:43:27.000Z</updated>
<content type="html"><![CDATA[<p>Scaling application is not an easy topic to cover in one post. So in this first post, you can find “the mindset” to build scalable apps using the 12-factor principles. In the <a href="/blog/2016/03/23/how-to-scale-a-nodejs-app-based-on-number-of-users/">next post</a>, you will find more down to earth examples one how to scale based on the number of users.</p>
<p>The Twelve steps are a compilation of guidelines to ensure apps can scale up without significant changes and tooling. These are very suitable for cloud platforms and continuous deployment. Furthermore, these principles are language agnostic, so it will work with any framework.</p>
<a id="more"></a>
<p><strong>The Twelve Factor Principles</strong></p>
<h1 id="One-codebase-per-app-multiple-deployments">One codebase per app, multiple deployments<a href="#One-codebase-per-app-multiple-deployments" class="headerlink" title="One codebase per app, multiple deployments"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>One codebase to rule all deployment environments: production, staging, local and so on and differentiate them from config files (see #3).</li>
</ul>
<p><i class="fa fa-thumbs-o-down" aria-hidden="true"></i> <em>DON’T</em></p>
<ul>
<li>Multiple apps sharing the same code. INSTEAD the common code should be extracted from a library and included through a dependency manager.</li>
</ul>
<h1 id="Declare-and-isolate-dependencies">Declare and isolate dependencies<a href="#Declare-and-isolate-dependencies" class="headerlink" title="Declare and isolate dependencies"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>Have a dependency declaration manifest (e.g. packages.json, Gemfile)</li>
<li>Execute dependencies in isolation per app (e.g. bundle exec).</li>
</ul>
<p><i class="fa fa-thumbs-o-down" aria-hidden="true"></i> <em>DON’T</em></p>
<ul>
<li>Rely on implicit existence of system-wide packages (e.g. curl, ImageMagik). INSTEAD vendor them into the app.</li>
</ul>
<h1 id="Store-the-config-in-the-environment">Store the config in the environment<a href="#Store-the-config-in-the-environment" class="headerlink" title="Store the config in the environment"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>Separate app’s config (AWS S3, passwords, Google/Fb/Tw/APIs credentials, deployment hostname) from the code.</li>
<li>Keep the code ready in a way that if were open source, it wouldn’t compromise any credentials.</li>
<li>Use/commit ‘config’ files with sensitive information into repository. INSTEAD use environmental variables (env, env vars) which are easily changed between deployments and without changing code.</li>
</ul>
<p><i class="fa fa-thumbs-o-down" aria-hidden="true"></i> <em>DON’T</em></p>
<ul>
<li>Group config variables by environment (e.g. AWS_S3_PRODUCTION, AWS_S3_TEST, AWS_S3_QA, AWS_S3_STAGING, AWS_S3_JOE…). INSTEAD use clean environment variables (e.g. AWS_S3) that are managed individually per deploy.</li>
</ul>
<h1 id="Swappable-local-and-third-party-services">Swappable local and third party services<a href="#Swappable-local-and-third-party-services" class="headerlink" title="Swappable local and third party services"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>Services like databases (e.g. MongoDB, PostgreSQL), message queues (e.g. RabbitMQ, Beanstalkd) should be accessed via URL or locator/credential stored in config.</li>
<li>Swapping local to production services should be done without any code changes.</li>
</ul>
<h1 id="Build-and-runtime">Build and runtime<a href="#Build-and-runtime" class="headerlink" title="Build and runtime"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>Code changes flows in one direction only development -> build -> run time environments.</li>
</ul>
<h1 id="Execute-the-app-as-share-nothing-stateless-processes">Execute the app as share-nothing stateless processes<a href="#Execute-the-app-as-share-nothing-stateless-processes" class="headerlink" title="Execute the app as share-nothing stateless processes"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>Store any persistent data in external services (such as databases)</li>
</ul>
<p><i class="fa fa-thumbs-o-down" aria-hidden="true"></i> <em>DON’T</em></p>
<ul>
<li>Use the filesystem/memory to save states. INSTEAD any instance of the app should be able to handle requests.</li>
</ul>
<h1 id="Export-services-via-port-binding">Export services via port binding<a href="#Export-services-via-port-binding" class="headerlink" title="Export services via port binding"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>App is completely self-contained and communicates with other processes through port binding.</li>
</ul>
<h1 id="Scale-out-the-app-horizontally">Scale out the app horizontally<a href="#Scale-out-the-app-horizontally" class="headerlink" title="Scale out the app horizontally"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>Scale app horizontally since the app is a stateless and share-nothing model.</li>
</ul>
<p><i class="fa fa-thumbs-o-down" aria-hidden="true"></i> <em>DON’T</em></p>
<ul>
<li>Daemonize. INSTEAD use operating system manager such as Upstart or init and Foreman in development.</li>
</ul>
<h1 id="Fast-startup-and-shutdown">Fast startup and shutdown<a href="#Fast-startup-and-shutdown" class="headerlink" title="Fast startup and shutdown"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>app start in few seconds to serve requests or jobs.</li>
<li>shut down gracefully after receiving SIGTERM signal (stop receiving new request/jobs, finish processing current request/job before stopping).</li>
</ul>
<h1 id="Keep-development-staging-and-production-as-similar-as-possible">Keep development, staging, and production as similar as possible<a href="#Keep-development-staging-and-production-as-similar-as-possible" class="headerlink" title="Keep development, staging, and production as similar as possible"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>design app for continuous deployment keeping the tools gaps and deployment times as minimum as possible.</li>
<li>code from development to production should take few hours or just few minutes.</li>
<li>developers who wrote the code should be able to deploy it to production.</li>
<li>keep production and development tool the same as possible</li>
</ul>
<p><i class="fa fa-thumbs-o-down" aria-hidden="true"></i> <em>DON’T</em></p>
<ul>
<li>use different services on production and development (e.g. development using SQLite and production ProtgreSQL).</li>
</ul>
<h1 id="Logs-goes-to-stdout">Logs goes to stdout<a href="#Logs-goes-to-stdout" class="headerlink" title="Logs goes to stdout"></a></h1><p><i class="fa fa-thumbs-o-down" aria-hidden="true"></i> <em>DON’T</em></p>
<ul>
<li>write logs to a particular location in the filesystem. INSTEAD send them to STDOUT, so they can be routed as will depending the environment (e.g. output to terminal in development and output to log file in production)</li>
</ul>
<h1 id="Admin-processes">Admin processes<a href="#Admin-processes" class="headerlink" title="Admin processes"></a></h1><p><i class="fa fa-thumbs-o-up" aria-hidden="true"></i> <em>DO</em></p>
<ul>
<li>favor languages/frameworks that use REPL shell out of the box to do admin tasks such as migrating databases, running consoles or running one-time scripts.</li>
</ul>
<p>This is just the beginning follow up with <a href="/blog/2016/03/23/how-to-scale-a-nodejs-app-based-on-number-of-users/">this next post</a>.</p>
]]></content>
<summary type="html">
<p>Scaling application is not an easy topic to cover in one post. So in this first post, you can find “the mindset” to build scalable apps using the 12-factor principles. In the <a href="/blog/2016/03/23/how-to-scale-a-nodejs-app-based-on-number-of-users/">next post</a>, you will find more down to earth examples one how to scale based on the number of users.</p>
<p>The Twelve steps are a compilation of guidelines to ensure apps can scale up without significant changes and tooling. These are very suitable for cloud platforms and continuous deployment. Furthermore, these principles are language agnostic, so it will work with any framework.</p>
</summary>
<category term="Technologies" scheme="http://adrianmejia.com/categories/Technologies/"/>
<category term="production" scheme="http://adrianmejia.com/tags/production/"/>
<category term="scalability" scheme="http://adrianmejia.com/tags/scalability/"/>
</entry>
<entry>
<title>Grunt JS tutorial from Beginner to Ninja</title>
<link href="http://adrianmejia.com/blog/2014/10/07/grunt-js-tutorial-from-beginner-to-ninja/"/>
<id>http://adrianmejia.com/blog/2014/10/07/grunt-js-tutorial-from-beginner-to-ninja/</id>
<published>2014-10-07T14:41:13.000Z</published>
<updated>2014-10-07T14:41:13.000Z</updated>
<content type="html"><![CDATA[<p>Sometimes you find yourself doing the same tasks again and again, especially during web development. It is time to automate repetitive tasks and use that time in more creative activities. This is where Grunt comes in. Grunt is a popular task runner that runs on NodeJS. It can minify CSS/JavaScript, run linting tools (JSHint, JSlint, CSSlint), deploy to server, and run test cases when you change a file to name a few. All the information I found about Grunt and similar Javascript test runners were too verbose and not very helpful to get started quickly. So, I decided to make this tutorial.</p>
<a id="more"></a>
<h1 id="Beginner-Grunt-js-101">Beginner: Grunt.js 101<a href="#Beginner-Grunt-js-101" class="headerlink" title="Beginner: Grunt.js 101"></a></h1><p>Grunt.js is a Javascript task runner. At its bare core it does file manipulation (mkdir, reads, write, copy), print messages and helper methods to organize and configure multiple tasks. It takes care of differences among Operating Systems for you. However, the real power comes in with the number of available plugins ready to use. Usually named <code>grunt-contrib-*</code>. Let’s start from scratch!</p>
<h1 id="Hello-Wold-from-GruntJS">Hello Wold from GruntJS<a href="#Hello-Wold-from-GruntJS" class="headerlink" title="Hello Wold from GruntJS"></a></h1><p>You need to <a href="/blog/2014/10/01/creating-a-restful-api-tutorial-with-nodejs-and-mongodb/#nodejs">install Node.js and NPM</a> to follow along with this example.</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div></pre></td><td class="code"><pre><div class="line">mkdir grunt101 && <span class="built_in">cd</span> grunt101</div><div class="line"></div><div class="line"><span class="comment"># start Node.js project and answer the questions (or leave it in blank)</span></div><div class="line">npm init</div><div class="line"></div><div class="line"><span class="comment"># add Grunt as a dependency</span></div><div class="line">npm install grunt --save-dev</div></pre></td></tr></table></figure>
<p>If you run the grunt command you will get a message like this:</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div></pre></td><td class="code"><pre><div class="line">grunt</div><div class="line"><span class="comment"># A valid Gruntfile could not be found. Please see the getting started guide for more information on how to configure grunt: http://gruntjs.com/getting-started</span></div><div class="line"><span class="comment"># Fatal error: Unable to find Gruntfile.</span></div></pre></td></tr></table></figure>
<p>So, let’s create the <code>Gruntfile.js</code> file:</p>
<figure class="highlight javascript"><figcaption><span>Gruntfile.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">var</span> grunt = <span class="built_in">require</span>(<span class="string">'grunt'</span>);</div><div class="line"></div><div class="line">grunt.registerTask(<span class="string">'default'</span>, <span class="string">'default task description'</span>, <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'hello world'</span>);</div><div class="line">});</div></pre></td></tr></table></figure>
<p>If you run <code>grunt</code> again, you will see a message. The default task is run when nothing else it is specified. We are going to create a 2nd task called ‘hello’ and it is going to accept a parameter that we can pass along with the task name separated with a colon. As follows: <code>grunt hello:adrian</code>. We can handle errors using <code>grunt.warn</code>. Every time a <code>grunt.warn</code> is found the task will stop executing, and it will give its warning message.. You can override using <code>--force</code>. Try all this commands and noticed the different effects: <code>grunt</code>, <code>grunt hello</code>, <code>grunt hello --force</code>, <code>grunt hello:adrian</code>.</p>
<figure class="highlight javascript"><figcaption><span>Gruntfile.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">var</span> grunt = <span class="built_in">require</span>(<span class="string">'grunt'</span>);</div><div class="line"></div><div class="line">grunt.registerTask(<span class="string">'default'</span>, <span class="string">'default task description'</span>, <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'hello world'</span>);</div><div class="line">});</div><div class="line"></div><div class="line">grunt.registerTask(<span class="string">'hello'</span>, <span class="string">'say hello'</span>, <span class="function"><span class="keyword">function</span>(<span class="params">name</span>)</span>{</div><div class="line"> <span class="keyword">if</span>(!name || !name.length)</div><div class="line"> grunt.warn(<span class="string">'you need to provide a name.'</span>);</div><div class="line"></div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'hello '</span> + name);</div><div class="line">});</div></pre></td></tr></table></figure>
<p>We can chain multiple grunt tasks by using and array. Change the <code>Gruntfile.js</code> for the following and see what will happen when you type <code>grunt</code>.</p>
<figure class="highlight javascript"><figcaption><span>Gruntfile.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">var</span> grunt = <span class="built_in">require</span>(<span class="string">'grunt'</span>);</div><div class="line"></div><div class="line">grunt.registerTask(<span class="string">'world'</span>, <span class="string">'world task description'</span>, <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'hello world'</span>);</div><div class="line">});</div><div class="line"></div><div class="line">grunt.registerTask(<span class="string">'hello'</span>, <span class="string">'say hello'</span>, <span class="function"><span class="keyword">function</span>(<span class="params">name</span>)</span>{</div><div class="line"> <span class="keyword">if</span>(!name || !name.length)</div><div class="line"> grunt.warn(<span class="string">'you need to provide a name.'</span>);</div><div class="line"></div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'hello '</span> + name);</div><div class="line">});</div><div class="line"></div><div class="line">grunt.registerTask(<span class="string">'default'</span>, [<span class="string">'world'</span>, <span class="string">'hello:adrian'</span>]);</div></pre></td></tr></table></figure>
<h1 id="Reference-1-Grunt-tasks-config-and-warnings">Reference 1: Grunt tasks, config and warnings<a href="#Reference-1-Grunt-tasks-config-and-warnings" class="headerlink" title="Reference 1: Grunt tasks, config and warnings"></a></h1><p>Here are some of the methods that we have used so far and some more that we will use in the next examples:</p>
<h2 id="Grunt-config">Grunt config<a href="#Grunt-config" class="headerlink" title="Grunt config"></a></h2><ul>
<li><p><a href="http://gruntjs.com/api/grunt.config#grunt.config.init" target="_blank" rel="external">grunt.initConfig(configObject)</a>: Initialize a configuration object. It can be accessed by <code>grunt.config.get</code>.</p>
</li>
<li><p><a href="http://gruntjs.com/api/grunt.config#grunt.config.get" target="_blank" rel="external">grunt.config.get([prop])</a>: get the prop value from the <code>grunt.initConfig</code>. The property could be deeply nested (e.g. <code>concat.options.dest</code>) and the values inside <code><% %></code> are expanded.</p>
</li>
</ul>
<h2 id="Grunt-tasks">Grunt tasks<a href="#Grunt-tasks" class="headerlink" title="Grunt tasks"></a></h2><ul>
<li><a href="http://gruntjs.com/api/grunt.task#grunt.task.registertask" target="_blank" rel="external">grunt.registerTask(taskName[, description], taskFunction)</a>: register a task.<ul>
<li><strong>taskName</strong>: required to register the task and it allows the task to be e executed with <code>grunt taskName</code> or called by other grunt task.</li>
<li><strong>description</strong>: (optional) string describing task.</li>
<li><strong>taskFunction</strong>: function which can accept parameters separated by colons (:). E.g. <code>grunt taskName:arg1:arg2</code></li>
</ul>
</li>
</ul>
<ul>
<li><a href="http://gruntjs.com/api/grunt.task#grunt.task.registertask" target="_blank" rel="external">grunt.task.registerTask(taskName, taskList)</a>: register task.<ul>
<li><strong>taskName</strong>: required to register the task and it allows the task to be e executed with <code>grunt taskName</code> or called by other grunt task.</li>
<li><strong>taskList</strong>: array of taskNames to be executed, in the order specified, when the taskName is called. E.g.: <code>grunt.registerTask('concatAll', ['concat:templates', 'concat:javascripts', 'concat:stylesheets']);</code></li>
</ul>
</li>
</ul>
<ul>
<li><a href="http://gruntjs.com/api/grunt.task#grunt.task.registermultitask" target="_blank" rel="external">grunt.registerMultiTask(taskName[, description], taskFunction)</a>: multi-tasks accepts the same parameters as <code>grunt.registerTask</code>. However, it reads <code>grunt.initConfig</code> parameters differently:<ol>
<li>Grunt looks for a config that matches the taskName.</li>
<li>MultiTask can have multiple configurations referred as <code>this.target</code> and the value as <code>this.data</code>.</li>
<li>All the “targets” are run if it is not specified otherwise.</li>
</ol>
</li>
</ul>
<figure class="highlight javascript"><figcaption><span>registerMultiTask Example</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div></pre></td><td class="code"><pre><div class="line">grunt.initConfig({</div><div class="line"> print: {</div><div class="line"> target1: [<span class="string">'index.html'</span>, <span class="string">'src/styles.css'</span>, <span class="number">2</span>],</div><div class="line"> target2: <span class="string">'data'</span>,</div><div class="line"> hello: <span class="string">'world'</span></div><div class="line"> }</div><div class="line">});</div><div class="line"></div><div class="line">grunt.registerMultiTask(<span class="string">'print'</span>, <span class="string">'print targets'</span>, <span class="function"><span class="keyword">function</span>(<span class="params"></span>) </span>{</div><div class="line"> grunt.log.writeln(<span class="keyword">this</span>.target + <span class="string">': '</span> + <span class="keyword">this</span>.data);</div><div class="line">});</div></pre></td></tr></table></figure>
<p>You can specify one target <code>grunt print:hello</code> or run all them <code>grunt print</code> which will produce this output:</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div></pre></td><td class="code"><pre><div class="line">Running "print:target1" (print) task</div><div class="line">target1: index.html,src/styles.css,2</div><div class="line"></div><div class="line">Running "print:target2" (print) task</div><div class="line">target2: data</div><div class="line"></div><div class="line">Running "print:hello" (print) task</div><div class="line">hello: world</div></pre></td></tr></table></figure>
<h2 id="Grunt-Errors-and-Warnings">Grunt Errors and Warnings<a href="#Grunt-Errors-and-Warnings" class="headerlink" title="Grunt Errors and Warnings"></a></h2><ul>
<li><p><a href="http://gruntjs.com/api/grunt.fail#grunt.fail.warn" target="_blank" rel="external">grunt.fail.warn(error [, errorcode])</a>: prints to STDOUT a message and abort grunt executions. It can be override using <code>--force</code> and it can show the stack trace if <code>--stack</code> is given. e.g. <code>grunt taskName --force --stack</code>.</p>
</li>
<li><p><a href="http://gruntjs.com/api/grunt.fail#grunt.fail.fatal" target="_blank" rel="external">grunt.fail.fatal(error [, errorcode])</a>: similar to <code>warn</code>, displays message to STDOUT and terminate Grunt. Cannot be <code>--force</code>ed and it emits a beep unless <code>--no-color</code> parameter is passed. It also accepts <code>--stack</code>. E.g. <code>grunt taskName --no-color --stack</code>.</p>
</li>
</ul>
<h1 id="Example-Forex-and-grunt-multiple-async-calls-handling">Example: Forex and grunt multiple async calls handling<a href="#Example-Forex-and-grunt-multiple-async-calls-handling" class="headerlink" title="Example: Forex and grunt multiple async calls handling"></a></h1><p>The idea is get conversion rates from a base currency (e.g. USD) to a target currency (e.g. EUR). We are using a <code>registerMultiTask</code>, so the taskName ‘currency’ matches its property in the <code>config.init</code>. Notice that we can has additional arbitrary data such as endpoint URL.</p>
<p>Async calls can be a little tricky in Javascript. We are going to do multiple HTTP request. Since <code>http.get</code> is async Grunt will finish the task before even receiving any response. <code>this.async()</code> solves the issue, we just need to call it when we are done.</p>
<figure class="highlight javascript"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div><div class="line">15</div><div class="line">16</div><div class="line">17</div><div class="line">18</div><div class="line">19</div><div class="line">20</div><div class="line">21</div><div class="line">22</div><div class="line">23</div><div class="line">24</div><div class="line">25</div><div class="line">26</div><div class="line">27</div><div class="line">28</div><div class="line">29</div><div class="line">30</div><div class="line">31</div><div class="line">32</div><div class="line">33</div><div class="line">34</div><div class="line">35</div><div class="line">36</div><div class="line">37</div><div class="line">38</div><div class="line">39</div><div class="line">40</div><div class="line">41</div><div class="line">42</div><div class="line">43</div><div class="line">44</div><div class="line">45</div><div class="line">46</div><div class="line">47</div><div class="line">48</div><div class="line">49</div></pre></td><td class="code"><pre><div class="line"><span class="built_in">module</span>.exports = <span class="function"><span class="keyword">function</span>(<span class="params">grunt</span>)</span>{</div><div class="line"> grunt.config.init({</div><div class="line"> currency: {</div><div class="line"> USD: [<span class="string">'EUR'</span>, <span class="string">'GBP'</span>, <span class="string">'DOP'</span>],</div><div class="line"> DOP: [<span class="string">'USD'</span>]</div><div class="line"> },</div><div class="line"></div><div class="line"> endpoint: {</div><div class="line"> host: <span class="string">'http://www.freecurrencyconverter3api.com'</span>,</div><div class="line"> path: <span class="string">'/api/v2/convert?compact=y&q='</span></div><div class="line"> }</div><div class="line"> });</div><div class="line"></div><div class="line"> grunt.registerMultiTask(<span class="string">'currency'</span>, <span class="string">'Fetches currency exchange rates'</span>, <span class="function"><span class="keyword">function</span>(<span class="params"></span>) </span>{</div><div class="line"> <span class="keyword">var</span> http = <span class="built_in">require</span>(<span class="string">'http'</span>),</div><div class="line"> done = <span class="keyword">this</span>.async(),</div><div class="line"> responses = <span class="number">0</span>;</div><div class="line"></div><div class="line"> <span class="keyword">var</span> baseCurrency = <span class="keyword">this</span>.target;</div><div class="line"> <span class="keyword">var</span> targetCurrencies = <span class="keyword">this</span>.data;</div><div class="line"></div><div class="line"> grunt.config.requires(<span class="string">'endpoint'</span>);</div><div class="line"></div><div class="line"> targetCurrencies.forEach(<span class="function"><span class="keyword">function</span>(<span class="params">targetCurrency, i, arr</span>)</span>{</div><div class="line"> <span class="keyword">var</span> convertTo = baseCurrency + <span class="string">'_'</span> + targetCurrency,</div><div class="line"> body = [];</div><div class="line"> url = grunt.config.get(<span class="string">'endpoint.host'</span>);</div><div class="line"></div><div class="line"> url += grunt.config.get(<span class="string">'endpoint.path'</span>) + convertTo;</div><div class="line"></div><div class="line"> http.get(url, <span class="function"><span class="keyword">function</span>(<span class="params">res</span>) </span>{</div><div class="line"> res.on(<span class="string">'data'</span>, <span class="function"><span class="keyword">function</span>(<span class="params">data</span>)</span>{</div><div class="line"> body.push(data);</div><div class="line"> });</div><div class="line"></div><div class="line"> res.on(<span class="string">'end'</span>, <span class="function"><span class="keyword">function</span> (<span class="params"></span>) </span>{</div><div class="line"> <span class="keyword">var</span> conversion = <span class="built_in">JSON</span>.parse(body.join());</div><div class="line"> grunt.log.ok(baseCurrency + <span class="string">'/'</span> + targetCurrency + <span class="string">' => '</span> + conversion[convertTo].val);</div><div class="line"> <span class="comment">// if got all responses: done!</span></div><div class="line"> <span class="keyword">if</span>(responses++ == arr.length - <span class="number">1</span>)</div><div class="line"> done();</div><div class="line"> });</div><div class="line"> }).on(<span class="string">'error'</span>, <span class="function"><span class="keyword">function</span> (<span class="params">err</span>) </span>{</div><div class="line"> grunt.warn(<span class="string">'Please verify endpoint host and path: <'</span>+ url +<span class="string">'>. It might be incorrect or down.'</span>);</div><div class="line"> done(err);</div><div class="line"> });</div><div class="line"> });</div><div class="line"> });</div><div class="line">}</div></pre></td></tr></table></figure>
<h1 id="Reference-2-Grunt-Files-and-logs">Reference 2: Grunt Files and logs<a href="#Reference-2-Grunt-Files-and-logs" class="headerlink" title="Reference 2: Grunt Files and logs"></a></h1><h2 id="Grunt-logs">Grunt logs<a href="#Grunt-logs" class="headerlink" title="Grunt logs"></a></h2><p>All them stars with the prefix <code>grunt.log</code> and accepts a <code>msg</code> which is displayed to STDOUT (usually the screen). Here are the differences between them:</p>
<ul>
<li><a href="http://gruntjs.com/api/grunt.log#grunt.log.writeln-grunt.verbose.writeln" target="_blank" rel="external">writeln([msg]), write(msg) and subhead(msg)</a>: writes message to STDOUT. <code>grunt.log.writeln</code> will do the same as <code>grunt.log.write</code> but without trailing newline. <code>subhead(msg)</code> will print the message in bold and proceeded by a newline and a trailing newline as well.</li>
</ul>
<p>The following methods adds a “>>” before the message in the screen which could be of different colors depending on the method:</p>
<ul>
<li><code>grunt.log.error([msg])</code>: print message prefixed with a RED “>>”.</li>
<li><code>grunt.log.ok([msg])</code>: print message prefixed with a GREEN “>>”.</li>
</ul>
<h2 id="Grunt-files">Grunt files<a href="#Grunt-files" class="headerlink" title="Grunt files"></a></h2><p><strong>Files</strong></p>
<p>All has an optional attributes <code>options</code> that could be <code>encoding</code> among others.</p>
<ul>
<li><a href="http://gruntjs.com/api/grunt.file#grunt.file.write" target="_blank" rel="external">grunt.file.write(filepath, contents [, options])</a>: writes contents to file, creates path if necessary.</li>
<li><a href="http://gruntjs.com/api/grunt.file#grunt.file.read" target="_blank" rel="external">grunt.file.read(filepath [, options])</a>: returns file content.</li>
<li><a href="http://gruntjs.com/api/grunt.file#grunt.file.readjson" target="_blank" rel="external">grunt.file.readJSON(filepath [, options])</a>: reads file content and parse it to JSON.</li>
<li><a href="http://gruntjs.com/api/grunt.file#grunt.file.delete" target="_blank" rel="external">grunt.file.delete(filepath [, options])</a>: deletes files recursively.</li>
<li><a href="http://gruntjs.com/api/grunt.file#grunt.file.copy" target="_blank" rel="external">grunt.file.copy(srcpath, destpath [, options])</a>: copy file from <code>srcpath</code> to <code>destpath</code>.</li>
</ul>
<p><strong>Directories</strong></p>
<ul>
<li><a href="http://gruntjs.com/api/grunt.file#grunt.file.mkdir" target="_blank" rel="external">grunt.file.mkdir(dirpath [, mode])</a>: creates directory and any intermediary. Like <code>mkdir -p</code>.</li>
<li><a href="http://gruntjs.com/api/grunt.file#grunt.file.expand" target="_blank" rel="external">grunt.file.expand([options, ] patterns)</a>: returns an array with all the files matching a pattern. It can also accept and array of patterns. Preceding a patter with <code>!</code> will negate them. E.g. <code>['**/*.js', !**/*spec.js]</code> => get all javascript (including subdirectories) but NOT the ones that ends with spec.js.</li>
<li><a href="http://gruntjs.com/api/grunt.file#grunt.file.recurse" target="_blank" rel="external">grunt.file.recurse(rootdir, callback)</a>: expand path and return a callback function with the following signature <code>callback(abspath, rootdir, subdir, filename)</code>.</li>
</ul>
<h1 id="Example-2-Gruntfile-for-files-manipulation">Example 2: Gruntfile for files manipulation<a href="#Example-2-Gruntfile-for-files-manipulation" class="headerlink" title="Example 2: Gruntfile for files manipulation"></a></h1><p>GruntJS comes with built-in functions for basic <a href="https://github.com/gruntjs/grunt/blob/master/lib/grunt/file.js" target="_blank" rel="external">file system handling</a>. To see the function in action. Create four directories: <code>stylesheets</code>, <code>javascripts</code>, <code>templates</code> and put files on first three. The idea is to concatenate all the files into one index.html and placed it a newly created <code>public</code> folder.</p>
<p>Here’s the grunt file that will copy and concatenate all the files for us:</p>
<figure class="highlight javascript"><figcaption><span>Gruntfile.js</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div><div class="line">15</div><div class="line">16</div><div class="line">17</div><div class="line">18</div><div class="line">19</div><div class="line">20</div><div class="line">21</div><div class="line">22</div><div class="line">23</div><div class="line">24</div><div class="line">25</div><div class="line">26</div><div class="line">27</div><div class="line">28</div><div class="line">29</div><div class="line">30</div><div class="line">31</div><div class="line">32</div><div class="line">33</div><div class="line">34</div><div class="line">35</div><div class="line">36</div><div class="line">37</div><div class="line">38</div><div class="line">39</div><div class="line">40</div><div class="line">41</div></pre></td><td class="code"><pre><div class="line"><span class="built_in">module</span>.exports = <span class="function"><span class="keyword">function</span>(<span class="params">grunt</span>)</span>{</div><div class="line"> grunt.config.init({</div><div class="line"> concat: {</div><div class="line"> options: {</div><div class="line"> dest: <span class="string">'tmp'</span>,</div><div class="line"> templates: [<span class="string">'templates/header.html'</span>, <span class="string">'templates/footer.html'</span>],</div><div class="line"> javascripts: [<span class="string">'javascripts/*.js'</span>],</div><div class="line"> stylesheets: [<span class="string">'stylesheets'</span>]</div><div class="line"> }</div><div class="line"> }</div><div class="line"> });</div><div class="line"></div><div class="line"> <span class="keyword">var</span> recursiveConcat = <span class="function"><span class="keyword">function</span>(<span class="params">source, result</span>)</span>{</div><div class="line"> grunt.file.expand(source).forEach(<span class="function"><span class="keyword">function</span>(<span class="params">file</span>)</span>{</div><div class="line"> <span class="keyword">if</span>(grunt.file.isDir(file)){</div><div class="line"> grunt.file.recurse(file, <span class="function"><span class="keyword">function</span>(<span class="params">f</span>)</span>{</div><div class="line"> result = recursiveConcat(f, result);</div><div class="line"> });</div><div class="line"> } <span class="keyword">else</span> {</div><div class="line"> grunt.log.writeln(<span class="string">'Concatenating '</span> + file + <span class="string">' to other '</span> + result.length + <span class="string">' characters.'</span>);</div><div class="line"> result += grunt.file.read(file);</div><div class="line"> }</div><div class="line"> });</div><div class="line"> <span class="keyword">return</span> result;</div><div class="line"> };</div><div class="line"></div><div class="line"> grunt.registerTask(<span class="string">'concat'</span>, <span class="string">'concatenates files'</span>, <span class="function"><span class="keyword">function</span>(<span class="params">type</span>)</span>{</div><div class="line"> grunt.config.requires(<span class="string">'concat.options.'</span> + type); <span class="comment">// fail the task if this propary is missing.</span></div><div class="line"> grunt.config.requires(<span class="string">'concat.options.dest'</span>);</div><div class="line"></div><div class="line"> <span class="keyword">var</span> files = grunt.config.get(<span class="string">'concat.options.'</span> + type),</div><div class="line"> dest = grunt.config.get(<span class="string">'concat.options.dest'</span>),</div><div class="line"> concatenated = recursiveConcat(files, <span class="string">''</span>);</div><div class="line"></div><div class="line"> grunt.log.writeln(<span class="string">'Writing '</span> + concatenated.length + <span class="string">' chars to '</span> + <span class="string">'tmp/'</span> + type);</div><div class="line"> grunt.file.write(dest + <span class="string">'/'</span> + type, concatenated);</div><div class="line"> });</div><div class="line"></div><div class="line"> grunt.registerTask(<span class="string">'concatAll'</span>, [<span class="string">'concat:templates'</span>, <span class="string">'concat:javascripts'</span>, <span class="string">'concat:stylesheets'</span>]);</div><div class="line"> grunt.registerTask(<span class="string">'default'</span>, [<span class="string">'concatAll'</span>]);</div><div class="line">}</div></pre></td></tr></table></figure>
<p>A more complete example can be found in the repository where we have the join and open function as well.</p>
<h2 id="Reference-3-Inside-Grunt-tasks">Reference 3: Inside Grunt tasks<a href="#Reference-3-Inside-Grunt-tasks" class="headerlink" title="Reference 3: Inside Grunt tasks"></a></h2><p>Inside all Grunt task there are number of functions available through <code>this</code>:</p>
<ul>
<li><a href="http://gruntjs.com/inside-tasks#this.async" target="_blank" rel="external">this.async</a>: designed for async tasks. Grunt will normally end the task without waiting for the callback to be executed. If you need Grunt to wait use <code>done()</code>.</li>
</ul>
<figure class="highlight javascript"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div></pre></td><td class="code"><pre><div class="line"><span class="keyword">var</span> done = <span class="keyword">this</span>.async();</div><div class="line"></div><div class="line">http.get(<span class="string">'http://adrianmejia.com'</span>, <span class="function"><span class="keyword">function</span>(<span class="params">res</span>)</span>{</div><div class="line"> res.on(<span class="string">'data'</span>, <span class="function"><span class="keyword">function</span>(<span class="params">data</span>)</span>{</div><div class="line"> <span class="comment">// ... process data ...</span></div><div class="line"> done(); <span class="comment">// forces Grunt to wait until data is received.</span></div><div class="line"> })</div><div class="line">}).on(<span class="function"><span class="keyword">function</span>(<span class="params">err</span>)</span>{</div><div class="line"> done(err); <span class="comment">// or an error is received.</span></div><div class="line">});</div></pre></td></tr></table></figure>
<ul>
<li><p><a href="http://gruntjs.com/inside-tasks#this.requires" target="_blank" rel="external">this.requires</a>: list of taskNames that should executed successfully first. E.g. <code>this.requires(['concat', 'jshint'])</code>.</p>
</li>
<li><p><a href="http://gruntjs.com/inside-tasks#this.name" target="_blank" rel="external">this.name</a>: this is the name of the task. E.g. <code>grunt hello</code>, then <code>this.name === 'name'</code>.</p>
</li>
<li><p><a href="http://gruntjs.com/inside-tasks#this.args" target="_blank" rel="external">this.args</a>: returns an array with the parameters. E.g. <code>grunt hello:crazy:world</code>, then <code>this.args</code> will return <code>['crazy', 'world']</code>.</p>
</li>
<li><p><a href="http://gruntjs.com/inside-tasks#this.options" target="_blank" rel="external">this.options([defaultsObj])</a>: it gets options values from the <code>config.init</code>, optionally you can also pass an object containing the default values. Notice in the example bellow that even though console.log has a <code>this.options({gzip: true})</code> it gets override by the options parameters. If not one it is specified in the <code>config.init</code> then it will use the default gzip: true.</p>
</li>
</ul>
<p><strong>Inside MultiTasks</strong></p>
<p>Consider this <code>grunt.config.init</code> example:</p>
<figure class="highlight javascript"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div><div class="line">15</div><div class="line">16</div><div class="line">17</div><div class="line">18</div><div class="line">19</div><div class="line">20</div><div class="line">21</div><div class="line">22</div><div class="line">23</div><div class="line">24</div><div class="line">25</div><div class="line">26</div></pre></td><td class="code"><pre><div class="line"><span class="built_in">module</span>.exports = <span class="function"><span class="keyword">function</span>(<span class="params">grunt</span>)</span>{</div><div class="line"> grunt.config.init({</div><div class="line"> multiTaskName: {</div><div class="line"> options: {</div><div class="line"> gzip: <span class="literal">false</span></div><div class="line"> },</div><div class="line"> target1: {</div><div class="line"> src: <span class="string">'stylesheets/*.css'</span>,</div><div class="line"> dest: <span class="string">'public'</span>,</div><div class="line"> ext: <span class="string">'.min.css'</span></div><div class="line"> },</div><div class="line"> target2: {</div><div class="line"> src: <span class="string">'*.js'</span>,</div><div class="line"> dest: <span class="string">'public'</span>,</div><div class="line"> ext: <span class="string">'.min.js'</span></div><div class="line"> }</div><div class="line"> }</div><div class="line"> });</div><div class="line"></div><div class="line"> grunt.registerMultiTask(<span class="string">'multiTaskName'</span>, <span class="string">'example'</span>, <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'this.options'</span>, <span class="keyword">this</span>.options({gzip: <span class="literal">true</span>}));</div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'this.data'</span>, <span class="keyword">this</span>.data);</div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'this.files'</span>, <span class="keyword">this</span>.files);</div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'this.filesSrc'</span>, <span class="keyword">this</span>.filesSrc);</div><div class="line"> });</div><div class="line">}</div></pre></td></tr></table></figure>
<figure class="highlight bash"><figcaption><span>Output example</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div><div class="line">15</div><div class="line">16</div><div class="line">17</div><div class="line">18</div></pre></td><td class="code"><pre><div class="line">grunt multiTaskName</div><div class="line"><span class="comment"># Running "multiTaskName:target1" (multiTaskName) task</span></div><div class="line"><span class="comment"># this.options { gzip: false }</span></div><div class="line"><span class="comment"># this.data { src: 'stylesheets/*.css', dest: 'public', ext: '.min.css' }</span></div><div class="line"><span class="comment"># this.files [ { src: [Getter],</span></div><div class="line"><span class="comment"># dest: 'public',</span></div><div class="line"><span class="comment"># ext: '.min.css',</span></div><div class="line"><span class="comment"># orig: { src: [Object], dest: 'public', ext: '.min.css' } } ]</span></div><div class="line"><span class="comment"># this.filesSrc [ 'stylesheets/h1.css', 'stylesheets/h2.css' ]</span></div><div class="line"><span class="comment">#</span></div><div class="line"><span class="comment"># Running "multiTaskName:target2" (multiTaskName) task</span></div><div class="line"><span class="comment"># this.options { gzip: false }</span></div><div class="line"><span class="comment"># this.data { src: '*.js', dest: 'public', ext: '.min.js' }</span></div><div class="line"><span class="comment"># this.files [ { src: [Getter],</span></div><div class="line"><span class="comment"># dest: 'public',</span></div><div class="line"><span class="comment"># ext: '.min.js',</span></div><div class="line"><span class="comment"># orig: { src: [Object], dest: 'public', ext: '.min.js' } } ]</span></div><div class="line"><span class="comment"># this.filesSrc [ 'Gruntfile.js' ]</span></div></pre></td></tr></table></figure>
<ul>
<li><p><a href="http://gruntjs.com/inside-tasks#this.target" target="_blank" rel="external">this.target</a>: name of the target current target. If you call it <code>grunt multiTaskName</code>, it will run like multiple tasks calling each target one at a time. <code>this.target</code> will be equal to <code>target1</code> and then <code>target2</code>.</p>
</li>
<li><p><a href="http://gruntjs.com/inside-tasks#this.files" target="_blank" rel="external">this.files</a>: return a (single) array that has all the properties for the current target. Take a look the the output above.</p>
</li>
<li><p><a href="http://gruntjs.com/inside-tasks#this.filessrc" target="_blank" rel="external">this.filesSrc</a>: it expands files and paths against <code>src</code> and return an array with them.</p>
</li>
<li><p><a href="http://gruntjs.com/inside-tasks#this.data" target="_blank" rel="external">this.data</a>: contains the raw data of the target parameters.</p>
</li>
</ul>
<h1 id="Intermediate-Using-Grunt-js-plugins">Intermediate: Using Grunt.js plugins<a href="#Intermediate-Using-Grunt-js-plugins" class="headerlink" title="Intermediate: Using Grunt.js plugins"></a></h1><p>Chances are that there is a plugin for most of your needs. Last time I checked there were 3,638 plugins for grunt. This are the 10 most popular:</p>
<h2 id="Installing-a-grunt-plugin">Installing a grunt plugin<a href="#Installing-a-grunt-plugin" class="headerlink" title="Installing a grunt plugin"></a></h2><p>Let’s say we want to install jshint.</p>
<ol>
<li>Get the plugin module</li>
</ol>
<p>Download it from npm:</p>
<p><code>npm install grunt-contrib-jshint --save-dev</code></p>
<p>or from github:</p>
<p><code>npm install https://github.com/YOUR_USERNAME/grunt-contrib-YOUR-PLUGIN --save-dev</code></p>
<ol>
<li>Load it in your Gruntfile</li>
</ol>
<p><code>grunt.loadNpmTasks('grunt-contrib-jshint');</code></p>
<p>or</p>
<p><code>grunt.loadNpmTasks('grunt-contrib-YOUR-PLUGIN');</code></p>
<h2 id="10-most-popular-grunt-plugins">10 most popular grunt plugins<a href="#10-most-popular-grunt-plugins" class="headerlink" title="10 most popular grunt plugins"></a></h2><p>1- <a href="https://github.com/gruntjs/grunt-contrib-jshint" target="_blank" rel="external">jshint</a>: Validate files with JSHint. Uses <code>.jshintrc</code> to settings.</p>
<figure class="highlight javascript"><figcaption><span>.jshintrc (example)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div></pre></td><td class="code"><pre><div class="line">{</div><div class="line"> <span class="string">"curly"</span>: <span class="literal">true</span>,</div><div class="line"> <span class="string">"eqnull"</span>: <span class="literal">true</span>,</div><div class="line"> <span class="string">"eqeqeq"</span>: <span class="literal">true</span>,</div><div class="line"> <span class="string">"undef"</span>: <span class="literal">true</span>,</div><div class="line"> <span class="string">"globals"</span>: {</div><div class="line"> <span class="string">"jQuery"</span>: <span class="literal">true</span></div><div class="line"> }</div><div class="line">}</div></pre></td></tr></table></figure>
<p>2- <a href="https://github.com/gruntjs/grunt-contrib-watch" target="_blank" rel="external">watch</a>: Run predefined tasks whenever watched file patterns are added, changed or deleted. Spawn runs task in a child process but having set to <code>spawn: false</code> is faster.</p>
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div></pre></td><td class="code"><pre><div class="line">watch: {</div><div class="line"> scripts: {</div><div class="line"> files: [<span class="string">'**/*.js'</span>],</div><div class="line"> tasks: [<span class="string">'jshint'</span>],</div><div class="line"> options: {</div><div class="line"> spawn: <span class="literal">false</span>,</div><div class="line"> },</div><div class="line"> },</div><div class="line">},</div></pre></td></tr></table></figure>
<p>3- <a href="https://github.com/gruntjs/grunt-contrib-uglify" target="_blank" rel="external">uglify</a>: minifies javascript files.
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div></pre></td><td class="code"><pre><div class="line">uglify: {</div><div class="line"> my_target: {</div><div class="line"> files: {</div><div class="line"> <span class="string">'dest/output.min.js'</span>: [<span class="string">'src/input1.js'</span>, <span class="string">'src/input2.js'</span>]</div><div class="line"> }</div><div class="line"> }</div><div class="line">}</div></pre></td></tr></table></figure></p>
<p>4- <a href="https://github.com/gruntjs/grunt-contrib-clean" target="_blank" rel="external">clean</a>: Clean files and folders.
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div></pre></td><td class="code"><pre><div class="line">clean: {</div><div class="line"> <span class="comment">// Deletes all .js files, but skips min.js files</span></div><div class="line"> js: [<span class="string">"path/to/dir/*.js"</span>, <span class="string">"!path/to/dir/*.min.js"</span>]</div><div class="line"></div><div class="line"> <span class="comment">// delete all files and directories here</span></div><div class="line"> build: [<span class="string">"path/to/dir/one"</span>, <span class="string">"path/to/dir/two"</span>],</div><div class="line">}</div></pre></td></tr></table></figure></p>
<p>5- <a href="https://github.com/gruntjs/grunt-contrib-concat" target="_blank" rel="external">concat</a>: Concatenate files.
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example simple)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div></pre></td><td class="code"><pre><div class="line">concat: {</div><div class="line"> options: {</div><div class="line"> separator: <span class="string">';'</span>,</div><div class="line"> },</div><div class="line"> dist: {</div><div class="line"> src: [<span class="string">'src/intro.js'</span>, <span class="string">'src/project.js'</span>, <span class="string">'src/outro.js'</span>],</div><div class="line"> dest: <span class="string">'dist/built.js'</span>,</div><div class="line"> },</div><div class="line">}</div></pre></td></tr></table></figure></p>
<figure class="highlight javascript"><figcaption><span>grunt.config.init (adding banners and multiple targets)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div></pre></td><td class="code"><pre><div class="line">pkg: grunt.file.readJSON(<span class="string">'package.json'</span>),</div><div class="line">concat: {</div><div class="line"> options: {</div><div class="line"> stripBanners: <span class="literal">true</span>,</div><div class="line"> banner: <span class="string">'/*! <%= pkg.name %> - v<%= pkg.version %> - '</span> +</div><div class="line"> <span class="string">'<%= grunt.template.today("yyyy-mm-dd") %> */'</span>,</div><div class="line"> },</div><div class="line"> dist: {</div><div class="line"> <span class="string">'dist/with_extras.js'</span>: [<span class="string">'src/main.js'</span>, <span class="string">'src/extras.js'</span>],</div><div class="line"> },</div><div class="line">},</div></pre></td></tr></table></figure>
<p>6- <a href="https://github.com/gruntjs/grunt-contrib-cssmin" target="_blank" rel="external">cssmin</a>: Compress CSS files.
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div></pre></td><td class="code"><pre><div class="line">cssmin: {</div><div class="line"> combine: {</div><div class="line"> files: {</div><div class="line"> <span class="string">'path/to/output.css'</span>: [<span class="string">'path/to/input_one.css'</span>, <span class="string">'path/to/input_two.css'</span>]</div><div class="line"> }</div><div class="line"> }</div><div class="line">}</div></pre></td></tr></table></figure></p>
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example with banner and adding .min.css extension)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div></pre></td><td class="code"><pre><div class="line">cssmin: {</div><div class="line"> add_banner: {</div><div class="line"> options: {</div><div class="line"> banner: <span class="string">'/* My minified css file */'</span></div><div class="line"> },</div><div class="line"> files: [{</div><div class="line"> expand: <span class="literal">true</span>,</div><div class="line"> cwd: <span class="string">'release/css/'</span>,</div><div class="line"> src: [<span class="string">'*.css'</span>, <span class="string">'!*.min.css'</span>],</div><div class="line"> dest: <span class="string">'release/css/'</span>,</div><div class="line"> ext: <span class="string">'.min.css'</span></div><div class="line"> }]</div><div class="line"> }</div><div class="line">}</div></pre></td></tr></table></figure>
<p>7- <a href="https://github.com/gruntjs/grunt-contrib-connect" target="_blank" rel="external">connect</a>: runs server as long as Grunt is running. It can be persistent passing <code>keepalive</code> like this <code>grunt connect:keepalive</code>.</p>
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div></pre></td><td class="code"><pre><div class="line">connect: {</div><div class="line"> server: {</div><div class="line"> options: {</div><div class="line"> port: <span class="number">9001</span>,</div><div class="line"> base: <span class="string">'www-root'</span></div><div class="line"> }</div><div class="line"> }</div><div class="line">}</div></pre></td></tr></table></figure>
<p>8- <a href="https://github.com/karma-runner/grunt-karma" target="_blank" rel="external">karma</a>: runs karma testing tool.</p>
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div></pre></td><td class="code"><pre><div class="line">karma: {</div><div class="line"> unit: {</div><div class="line"> options: {</div><div class="line"> files: [<span class="string">'test/**/*.js'</span>]</div><div class="line"> }</div><div class="line"> }</div><div class="line">}</div></pre></td></tr></table></figure>
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example referencing karma.conf and overriding parameters)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div></pre></td><td class="code"><pre><div class="line">karma: {</div><div class="line"> unit: {</div><div class="line"> configFile: <span class="string">'karma.conf.js'</span>,</div><div class="line"> runnerPort: <span class="number">9999</span>,</div><div class="line"> singleRun: <span class="literal">true</span>,</div><div class="line"> browsers: [<span class="string">'PhantomJS'</span>],</div><div class="line"> logLevel: <span class="string">'ERROR'</span></div><div class="line"> }</div><div class="line">}</div></pre></td></tr></table></figure>
<p>9- <a href="https://github.com/gruntjs/grunt-contrib-less" target="_blank" rel="external">less</a>: Compile LESS files to CSS.
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div><div class="line">15</div><div class="line">16</div><div class="line">17</div><div class="line">18</div><div class="line">19</div><div class="line">20</div><div class="line">21</div><div class="line">22</div><div class="line">23</div></pre></td><td class="code"><pre><div class="line">less: {</div><div class="line"> development: {</div><div class="line"> options: {</div><div class="line"> paths: [<span class="string">"assets/css"</span>]</div><div class="line"> },</div><div class="line"> files: {</div><div class="line"> <span class="string">"path/to/result.css"</span>: <span class="string">"path/to/source.less"</span></div><div class="line"> }</div><div class="line"> },</div><div class="line"> production: {</div><div class="line"> options: {</div><div class="line"> paths: [<span class="string">"assets/css"</span>],</div><div class="line"> cleancss: <span class="literal">true</span>,</div><div class="line"> modifyVars: {</div><div class="line"> imgPath: <span class="string">'"http://mycdn.com/path/to/images"'</span>,</div><div class="line"> bgColor: <span class="string">'red'</span></div><div class="line"> }</div><div class="line"> },</div><div class="line"> files: {</div><div class="line"> <span class="string">"path/to/result.css"</span>: <span class="string">"path/to/source.less"</span></div><div class="line"> }</div><div class="line"> }</div><div class="line">}</div></pre></td></tr></table></figure></p>
<p>10- <a href="https://github.com/sindresorhus/grunt-concurrent" target="_blank" rel="external">concurrent</a>: Run grunt tasks concurrently.</p>
<figure class="highlight javascript"><figcaption><span>grunt.config.init (example)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div></pre></td><td class="code"><pre><div class="line">concurrent: {</div><div class="line"> target1: [<span class="string">'coffee'</span>, <span class="string">'sass'</span>],</div><div class="line"> target2: [<span class="string">'jshint'</span>, <span class="string">'mocha'</span>],</div><div class="line"> target3: {</div><div class="line"> tasks: [<span class="string">'nodemon'</span>, <span class="string">'watch'</span>],</div><div class="line"> options: {</div><div class="line"> logConcurrentOutput: <span class="literal">true</span></div><div class="line"> }</div><div class="line"> }</div><div class="line">}</div></pre></td></tr></table></figure>
<p>In the next blog post, we will continue the tutorial with using GruntJS in a web application, making your own plugins and a comparison between other task runners tools such as Gulp, Gulp, Brunch, Rake::Pipeline and Broccoli.</p>
]]></content>
<summary type="html">
<p>Sometimes you find yourself doing the same tasks again and again, especially during web development. It is time to automate repetitive tasks and use that time in more creative activities. This is where Grunt comes in. Grunt is a popular task runner that runs on NodeJS. It can minify CSS/JavaScript, run linting tools (JSHint, JSlint, CSSlint), deploy to server, and run test cases when you change a file to name a few. All the information I found about Grunt and similar Javascript test runners were too verbose and not very helpful to get started quickly. So, I decided to make this tutorial.</p>
</summary>
<category term="Technologies" scheme="http://adrianmejia.com/categories/Technologies/"/>
<category term="Web Development" scheme="http://adrianmejia.com/categories/Technologies/Web-Development/"/>
<category term="javascript" scheme="http://adrianmejia.com/tags/javascript/"/>
<category term="gruntjs" scheme="http://adrianmejia.com/tags/gruntjs/"/>
<category term="nodejs" scheme="http://adrianmejia.com/tags/nodejs/"/>
</entry>
<entry>
<title>MEAN Stack Tutorial MongoDB ExpressJS AngularJS NodeJS (Part III)</title>
<link href="http://adrianmejia.com/blog/2014/10/03/mean-stack-tutorial-mongodb-expressjs-angularjs-nodejs/"/>
<id>http://adrianmejia.com/blog/2014/10/03/mean-stack-tutorial-mongodb-expressjs-angularjs-nodejs/</id>
<published>2014-10-03T10:59:34.000Z</published>
<updated>2016-08-07T01:47:53.000Z</updated>
<content type="html"><![CDATA[<p>We are going to build a full stack Todo App using the MEAN (MongoDB, ExpressJS, AngularJS and NodeJS). This is the last part of <a href="/tags/Tutorial-MEAN-Stack/">three-post series tutorial</a>.</p>
<a id="more"></a>
<p>Before completing the app, let’s cover some background about the this stack. If you rather jump to the hands-on part click here to <a href="#start">get started</a>.</p>
<h1 id="Why-MEAN-stack">Why MEAN stack?<a href="#Why-MEAN-stack" class="headerlink" title="Why MEAN stack?"></a></h1><p><a href="#start">TL; DR</a>: NodeJS has been built from bottom up a non-blocking I/O paradigm, which gives you more efficiency per CPU core than using threads in other languages like <a href="http://strongloop.com/strongblog/node-js-is-faster-than-java/" target="_blank" rel="external">Java</a>.</p>
<p>LAMP (Linux-Apache-MySQL-PHP) has dominated web application stack for many years now. Well-known platforms such as Wikipedia, Wordpress, and even Facebook uses it or started with it. Enterprise, usually, used go down the Java path: Hibernate, Spring, Struts, JBoss. More agile frameworks also have been used such as Ruby on Rails and for Python Django and Pylon.</p>
<img src="/images/mean_vs_lamp_stack.png" title="LAMP vs MEAN stack">
<p><strong>Ubiquitous</strong></p>
<p>Well, it turns out, that JavaScript it is everywhere. It used to be limited to browsers. But, now you can found it in smartphones, servers, robots, Arduino, RaspberryPi… Thus, it does not matter what technology you use to build web applications, you need to be familiar with Javascript. In that case, then, it is a time saver to use wherever it fits, especially for building web applications. MEAN stack is embracing that, using Javascript to create end-to-end web applications.
<strong>Non-blocking architecture</strong></p>
<p>JavaScript is a dynamic, object-oriented, and functional scripting language. One of the features that make it win over Java Applets decades ago, it was its lightness and non-blocking event loop.
Blocking means that when one line of code is executing, the rest of it is locked waiting to finish. On the other hand, non-blocking gives to each line of code a shot and then through callbacks it can come back when an event happens.
Programming languages that are blocking (Java, Ruby, Python, PHP, …) overcomes concurrency using many threads of execution while JavaScript handles it using non-blocking event loop in a single thread.</p>
<img src="/images/blocking_vs_non_blocking_io.png">
<p>As you can see, a single thread of execution in Node can handle perform multiple tasks vs a non-blocking style that execute each one sequentially. You can read more about it in <a href="[strongloop.com](http://strongloop.com/strongblog/node-js-is-faster-than-java/)" target="_blank">NodeJS faster than Java</a> article.</p>
<p>Some companies like <a href="https://www.paypal-engineering.com/2013/11/22/node-js-at-paypal/" target="_blank" rel="external">Paypal</a> moved from Java backend to NodeJS and reported a increased performance, lower average response times, and development speed gains. Similarly happens to <a href="https://engineering.groupon.com/2013/misc/i-tier-dismantling-the-monoliths/" target="_blank" rel="external">Groupon</a> that came from Java/Rails monoliths.</p>
<p><strong>Agile and vibrant community</strong></p>
<p>The community behind Javascript is quite vibrant. It has permeated in almost all the fields of technology: data visualization, server-side, databases, robotics, building tools and many more.</p>
<p><a id="start"></a></p>
<h1 id="TODO-app-with-MEAN">TODO app with MEAN<a href="#TODO-app-with-MEAN" class="headerlink" title="TODO app with MEAN"></a></h1><p>In this section are going to put together everything that we learnt in the <a href="/blog/2014/09/28/angularjs-tutorial-for-beginners-with-nodejs-expressjs-and-mongodb/">two</a> <a href="/blog/2014/10/01/creating-a-restful-api-tutorial-with-nodejs-and-mongodb/">previous</a> tutorials.</p>
<h2 id="MEAN-Backend-with-MongoDB-ExpressJS-and-NodeJS">MEAN Backend with MongoDB, ExpressJS and NodeJS<a href="#MEAN-Backend-with-MongoDB-ExpressJS-and-NodeJS" class="headerlink" title="MEAN Backend with MongoDB, ExpressJS and NodeJS"></a></h2><p>In the <a href="/blog/2014/10/01/creating-a-restful-api-tutorial-with-nodejs-and-mongodb/">previous post</a>, we have gone through the process of building a RESTful API and we are going to be building on top of that. <a href="https://github.com/amejiarosario/todoAPIjs" target="_blank" rel="external">Repository here</a>.</p>
<figure class="highlight bash"><figcaption><span>Getting the back-end code build on Part II</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line">git <span class="built_in">clone</span> https://github.com/amejiarosario/todoAPIjs.git</div></pre></td></tr></table></figure>
<h2 id="MEAN-stack-front-end-with-AngularJS">MEAN stack front-end with AngularJS<a href="#MEAN-stack-front-end-with-AngularJS" class="headerlink" title="MEAN stack front-end with AngularJS"></a></h2><p>Similarly, we have build a very lean todoApp in the <a href="/blog/2014/09/28/angularjs-tutorial-for-beginners-with-nodejs-expressjs-and-mongodb/">first part</a> of this tutorial. You can <a href="https://gist.githubusercontent.com/amejiarosario/068143b53e54db43ef38/raw/ngTodo.html" target="_blank" rel="external">download the file</a> to follow along and see it in action <a href="https://cdn.rawgit.com/amejiarosario/068143b53e54db43ef38/raw/ngTodo.html" target="_blank" rel="external">here</a>. You might notice the angularJS app is very simple and even it is entirely in one file for simplicity sake. In further tutorials, we are going to make it more modular, split in files, add tests and stylesheets.</p>
<p>Let’s go first to the ExpressJS app (todoAPIjs) and review the default routing system:</p>
<ol>
<li><code>app.js</code> loads the all the routes.</li>
<li>The root path (<code>/</code>) is mounted on the <code>routes/index.js</code></li>
<li><code>routes/index.js</code> sets the variable title and renders <code>index.ejs</code>.</li>
</ol>
<figure class="highlight javascript"><figcaption><span>Tracing ExpressJS index route</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div></pre></td><td class="code"><pre><div class="line"><span class="comment">// app.js</span></div><div class="line"><span class="keyword">var</span> routes = <span class="built_in">require</span>(<span class="string">'./routes/index'</span>);</div><div class="line">app.use(<span class="string">'/'</span>, routes);</div><div class="line"></div><div class="line"><span class="comment">// ./routes/index.js</span></div><div class="line">router.get(<span class="string">'/'</span>, <span class="function"><span class="keyword">function</span>(<span class="params">req, res</span>) </span>{</div><div class="line"> res.render(<span class="string">'index'</span>, { title: <span class="string">'Express'</span> });</div><div class="line">});</div><div class="line"></div><div class="line"><span class="comment">// ./views/index.ejs</span></div><div class="line"> <h1><span class="xml"><span class="tag"><<span class="name">%=</span> <span class="attr">title</span> %></span><span class="tag"></<span class="name">h1</span>></span></span></div><div class="line"> <p>Welcome to <%= title %><span class="xml"><span class="tag"></<span class="name">p</span>></span></span></div></pre></td></tr></table></figure>
<p>The best place to load our <code>./views/index.ejs</code>. So let’s copy the body content from ngTodo.html content in there and change in <code>./routes/index.js</code> title to “ngTodo App”. Don’t forget to add ng-app on the top. <code><html ng-app="app"></code>.</p>
<p><a href="https://github.com/amejiarosario/todoAPIjs/commit/ebf20f4093aa20c867777b4b3db825429b54a20d" target="_blank" rel="external">diff</a></p>
<h1 id="Wiring-up-the-App">Wiring up the App<a href="#Wiring-up-the-App" class="headerlink" title="Wiring up the App"></a></h1><h2 id="AngularJS-Read-with-http">AngularJS Read with $http<a href="#AngularJS-Read-with-http" class="headerlink" title="AngularJS Read with $http"></a></h2><p>As you might notice, in the factory, we have a fixed array. We need to change it to communicate with the API that we just build.</p>
<p><code>$http</code> is Anguar core sevice that allow to make <code>XMLHttpRequest</code> or <code>jsonp</code> request. You can either pass an object with http verb and url or call call $http.verb (<code>$http.get</code>, <code>$http.post</code>).</p>
<p><code>$http</code> returns a promise which has a <code>success</code> and <code>error</code> function.</p>
<figure class="highlight javascript"><figcaption><span>AngularJS $HTTP Usage Example</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div></pre></td><td class="code"><pre><div class="line">$http({method: <span class="string">'GET'</span>, url: <span class="string">'/todos'</span>}).</div><div class="line"> success(<span class="function"><span class="keyword">function</span>(<span class="params">data, status, headers, config</span>) </span>{</div><div class="line"> <span class="comment">// this callback will be called asynchronously</span></div><div class="line"> <span class="comment">// when the response is available.</span></div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'todos: '</span>, data );</div><div class="line"> }).</div><div class="line"> error(<span class="function"><span class="keyword">function</span>(<span class="params">data, status, headers, config</span>) </span>{</div><div class="line"> <span class="comment">// called asynchronously if an error occurs</span></div><div class="line"> <span class="comment">// or server returns response with an error status.</span></div><div class="line"> <span class="built_in">console</span>.log(<span class="string">'Oops and error'</span>, data);</div><div class="line"> });</div></pre></td></tr></table></figure>
<p>Let’s try it out in our app. Go to <code>views/index.ejs</code> and do this changes:</p>
<figure class="highlight javascript"><figcaption><span>Using $http to retrieve data from database</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div></pre></td><td class="code"><pre><div class="line"><span class="comment">// Service</span></div><div class="line">.factory(<span class="string">'Todos'</span>, [<span class="string">'$http'</span>, <span class="function"><span class="keyword">function</span>(<span class="params">$http</span>)</span>{</div><div class="line"> <span class="keyword">return</span> $http.get(<span class="string">'/todos'</span>);</div><div class="line">}])</div><div class="line"></div><div class="line"><span class="comment">// Controller</span></div><div class="line">.controller(<span class="string">'TodoController'</span>, [<span class="string">'$scope'</span>, <span class="string">'Todos'</span>, <span class="function"><span class="keyword">function</span> (<span class="params">$scope, Todos</span>) </span>{</div><div class="line"> Todos.success(<span class="function"><span class="keyword">function</span>(<span class="params">data</span>)</span>{</div><div class="line"> $scope.todos = data;</div><div class="line"> }).error(<span class="function"><span class="keyword">function</span>(<span class="params">data, status</span>)</span>{</div><div class="line"> <span class="built_in">console</span>.log(data, status);</div><div class="line"> $scope.todos = [];</div><div class="line"> });</div><div class="line">}])</div></pre></td></tr></table></figure>
<p><a href="https://github.com/amejiarosario/todoAPIjs/commit/0221aebd62e88445629debe4f132684686cf48ec" target="_blank" rel="external">diff</a></p>
<p><code>$http.get</code> will request data using the <code>GET</code> method.</p>
<blockquote>
<p>Try it in your browser!s If you have data from the <a href="http://adrianmejia.com/blog/2014/10/01/creating-a-restful-api-tutorial-with-nodejs-and-mongodb/#browser-and-postman">previous tutorial</a> you should be able to see it.</p>
</blockquote>
<p>To <strong>start the server</strong>, you can use
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line">npm start</div></pre></td></tr></table></figure></p>
<p>or if you have it installed</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line">nodemon</div></pre></td></tr></table></figure>
<h2 id="AngularJS-Read-with-resource">AngularJS Read with $resource<a href="#AngularJS-Read-with-resource" class="headerlink" title="AngularJS Read with $resource"></a></h2><p>If you click in one of the Todo elements and get redirected to the detail page, you will not see anything yet. We need to update the <code>TodoDetailCtrl</code> first. Even though we already have the GET verb working. We have a different URL requirement for <code>/todos/:id</code> for the other methods. There’s an Angular service that has a higher level of abstraction of $http to deal with RESTful requests. It is called <code>$resource</code>.</p>
<p>Initialize as:
<code>$resource(url, [paramDefaults], [actions], options);</code></p>
<p>It comes with the following actions already defined; it is missing one though… Can you tell?</p>
<figure class="highlight javascript"><figcaption><span>$resource actions</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div></pre></td><td class="code"><pre><div class="line">{ <span class="string">'get'</span>: {method:<span class="string">'GET'</span>}, <span class="comment">// get individual record</span></div><div class="line"> <span class="string">'save'</span>: {method:<span class="string">'POST'</span>}, <span class="comment">// create record</span></div><div class="line"> <span class="string">'query'</span>: {method:<span class="string">'GET'</span>, isArray:<span class="literal">true</span>}, <span class="comment">// get list all records</span></div><div class="line"> <span class="string">'remove'</span>: {method:<span class="string">'DELETE'</span>}, <span class="comment">// remove record</span></div><div class="line"> <span class="string">'delete'</span>: {method:<span class="string">'DELETE'</span>} }; <span class="comment">// same, remove record</span></div></pre></td></tr></table></figure>
<p>The instances are used in the following way (examples will come later):</p>
<ul>
<li>GET: <code>Resource.get([parameters], [success], [error])</code></li>
<li>Non-GET: <code>Resource.action([parameters], postData, [success], [error])</code></li>
<li>Non-GET: <code>resourceInstance.$action([parameters], [success], [error])</code></li>
</ul>
<p><code>$resource</code> is not part of the Angular core, so it requires to <code>ngResource</code> and the dependency. We can get it from the CDN:</p>
<figure class="highlight html"><figcaption><span>ngResource dependency</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line"><span class="tag"><<span class="name">script</span> <span class="attr">src</span>=<span class="string">"https://ajax.googleapis.com/ajax/libs/angularjs/1.2.25/angular-resource.min.js"</span>></span><span class="undefined"></span><span class="tag"></<span class="name">script</span>></span></div></pre></td></tr></table></figure>
<p>This is what need to set it up:</p>
<figure class="highlight javascript"><figcaption><span>$resource.query()</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div></pre></td><td class="code"><pre><div class="line"> <span class="comment">// add ngResource dependency</span></div><div class="line"> angular.module(<span class="string">'app'</span>, [<span class="string">'ngRoute'</span>, <span class="string">'ngResource'</span>])</div><div class="line"></div><div class="line"> <span class="comment">// ...</span></div><div class="line"></div><div class="line"> .factory(<span class="string">'Todos'</span>, [<span class="string">'$resource'</span>, <span class="function"><span class="keyword">function</span>(<span class="params">$resource</span>)</span>{</div><div class="line"> <span class="keyword">return</span> $resource(<span class="string">'/todos/:id'</span>, <span class="literal">null</span>, {</div><div class="line"> <span class="string">'update'</span>: { method:<span class="string">'PUT'</span> }</div><div class="line"> });</div><div class="line"> }])</div><div class="line"><span class="comment">// ...</span></div><div class="line"> .controller(<span class="string">'TodoController'</span>, [<span class="string">'$scope'</span>, <span class="string">'Todos'</span>, <span class="function"><span class="keyword">function</span> (<span class="params">$scope, Todos</span>) </span>{</div><div class="line"> $scope.todos = Todos.query();</div><div class="line"> }])</div></pre></td></tr></table></figure>
<p>Angular will render an empty <code>$scope.todos</code>. but, when <code>Todos.query()</code> comes with the data from the server it will re-render the UI.</p>
<p><a href="https://github.com/amejiarosario/todoAPIjs/commit/2aff6fe004bf7f7b2cd1b91d53e6958c3b158a20" target="_blank" rel="external">diff</a></p>
<h2 id="AngularJS-Create">AngularJS Create<a href="#AngularJS-Create" class="headerlink" title="AngularJS Create"></a></h2><p>We will need to create a new text box, a button to send a <code>POST</code> request to server and add it to the <code>$scope</code>.</p>
<blockquote>
<p>We are using inline templates with <code>id="/todos.html"</code> and <code>id="/todoDetails.html"</code>. They are not physical files. Just <code>ng-template</code> that we create in the <a href="/blog/2014/09/28/angularjs-tutorial-for-beginners-with-nodejs-expressjs-and-mongodb/">part I</a> of these <a href="/tags/Tutorial-MEAN-Stack/">tutorial series</a>.</p>
</blockquote>
<p>Add this code at the bottom of the <code>id="/todos.html"</code> template:</p>
<figure class="highlight html"><figcaption><span>New textbox for adding Todos</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line">New task <span class="tag"><<span class="name">input</span> <span class="attr">type</span>=<span class="string">"text"</span> <span class="attr">ng-model</span>=<span class="string">"newTodo"</span>></span><span class="tag"><<span class="name">button</span> <span class="attr">ng-click</span>=<span class="string">"save()"</span>></span>Create<span class="tag"></<span class="name">button</span>></span></div></pre></td></tr></table></figure>
<p>Notice that we are using a new directive <code>ng-click</code>, this one executes a function when it clicked. Angular makes sure that the behaviour is consistent across different browsers.</p>
<figure class="highlight javascript"><figcaption><span>Save function $resource.$save(...)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div></pre></td><td class="code"><pre><div class="line">.controller(<span class="string">'TodoController'</span>, [<span class="string">'$scope'</span>, <span class="string">'Todos'</span>, <span class="function"><span class="keyword">function</span> (<span class="params">$scope, Todos</span>) </span>{</div><div class="line"> $scope.todos = Todos.query();</div><div class="line"></div><div class="line"> $scope.save = <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> <span class="keyword">if</span>(!$scope.newTodo || $scope.newTodo.length < <span class="number">1</span>) <span class="keyword">return</span>;</div><div class="line"> <span class="keyword">var</span> todo = <span class="keyword">new</span> Todos({ name: $scope.newTodo, completed: <span class="literal">false</span> });</div><div class="line"></div><div class="line"> todo.$save(<span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> $scope.todos.push(todo);</div><div class="line"> $scope.newTodo = <span class="string">''</span>; <span class="comment">// clear textbox</span></div><div class="line"> });</div><div class="line"> }</div><div class="line">}])</div></pre></td></tr></table></figure>
<p><a href="https://github.com/amejiarosario/todoAPIjs/commit/46dd14023e2d9eff72d1366dbba9c9c8c872e07b" target="_blank" rel="external">diff</a></p>
<h2 id="Show-Todo-details">Show Todo details<a href="#Show-Todo-details" class="headerlink" title="Show Todo details"></a></h2><p>Every time you click a todo link, it is showing an empty fields. Let’s fix that. First we need set the real <code>_id</code> to the links instead of <code>$index</code>.</p>
<figure class="highlight html"><figcaption><span>Change the ID link in the `id="/todos.html"` template (fragment)</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div></pre></td><td class="code"><pre><div class="line"><span class="tag"><<span class="name">li</span> <span class="attr">ng-repeat</span>=<span class="string">"todo in todos | filter: search"</span>></span></div><div class="line"> <span class="tag"><<span class="name">input</span> <span class="attr">type</span>=<span class="string">"checkbox"</span> <span class="attr">ng-model</span>=<span class="string">"todo.completed"</span>></span></div><div class="line"> <span class="tag"><<span class="name">a</span> <span class="attr">href</span>=<span class="string">"#/{{todo._id}}"</span>></span>{{todo.name}}<span class="tag"></<span class="name">a</span>></span></div><div class="line"><span class="tag"></<span class="name">li</span>></span></div></pre></td></tr></table></figure>
<figure class="highlight javascript"><figcaption><span>Update TodoDetailCtrl with $resource.get</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div></pre></td><td class="code"><pre><div class="line">.controller(<span class="string">'TodoDetailCtrl'</span>, [<span class="string">'$scope'</span>, <span class="string">'$routeParams'</span>, <span class="string">'Todos'</span>, <span class="function"><span class="keyword">function</span> (<span class="params">$scope, $routeParams, Todos</span>) </span>{</div><div class="line"> $scope.todo = Todos.get({id: $routeParams.id });</div><div class="line">}])</div></pre></td></tr></table></figure>
<p>Notice the change from
<code>$scope.todo = Todos[$routeParams.id];</code>
to
<code>$scope.todo = Todos.get({id: $routeParams.id });</code></p>
<p>Now you should be able to see the details :)</p>
<p><a href="https://github.com/amejiarosario/todoAPIjs/commit/2484107294163a25621fba3785601adb32229ae9" target="_blank" rel="external">diff</a></p>
<h2 id="AngularJS-Update-in-line-editing">AngularJS Update (in-line editing)<a href="#AngularJS-Update-in-line-editing" class="headerlink" title="AngularJS Update (in-line editing)"></a></h2><p>This is going to be a very cool feature. Let’s meet these new directives:</p>
<ul>
<li><p><strong>ng-show</strong>: this directive shows the element if the expression evaluates to true. Otherwise, the content is hidden.</p>
</li>
<li><p><strong>ng-change</strong>: directive for input elements that evaluates the expression after any change.</p>
</li>
</ul>
<p>Replace the template with <code>id="/todos.html"</code> with the following:</p>
<figure class="highlight html"><figcaption><span>Template todos.html</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div><div class="line">15</div><div class="line">16</div></pre></td><td class="code"><pre><div class="line"><span class="comment"><!-- Template --></span></div><div class="line"><span class="tag"><<span class="name">script</span> <span class="attr">type</span>=<span class="string">"text/ng-template"</span> <span class="attr">id</span>=<span class="string">"/todos.html"</span>></span><span class="xml"></span></div><div class="line"> Search: <span class="tag"><<span class="name">input</span> <span class="attr">type</span>=<span class="string">"text"</span> <span class="attr">ng-model</span>=<span class="string">"search.name"</span>></span></div><div class="line"> <span class="tag"><<span class="name">ul</span>></span></div><div class="line"> <span class="tag"><<span class="name">li</span> <span class="attr">ng-repeat</span>=<span class="string">"todo in todos | filter: search"</span>></span></div><div class="line"> <span class="tag"><<span class="name">input</span> <span class="attr">type</span>=<span class="string">"checkbox"</span> <span class="attr">ng-model</span>=<span class="string">"todo.completed"</span> <span class="attr">ng-change</span>=<span class="string">"update($index)"</span>></span></div><div class="line"> <span class="tag"><<span class="name">a</span> <span class="attr">ng-show</span>=<span class="string">"!editing[$index]"</span> <span class="attr">href</span>=<span class="string">"#/{{todo._id}}"</span>></span>{{todo.name}}<span class="tag"></<span class="name">a</span>></span></div><div class="line"> <span class="tag"><<span class="name">button</span> <span class="attr">ng-show</span>=<span class="string">"!editing[$index]"</span> <span class="attr">ng-click</span>=<span class="string">"edit($index)"</span>></span>edit<span class="tag"></<span class="name">button</span>></span></div><div class="line"></div><div class="line"> <span class="tag"><<span class="name">input</span> <span class="attr">ng-show</span>=<span class="string">"editing[$index]"</span> <span class="attr">type</span>=<span class="string">"text"</span> <span class="attr">ng-model</span>=<span class="string">"todo.name"</span>></span></div><div class="line"> <span class="tag"><<span class="name">button</span> <span class="attr">ng-show</span>=<span class="string">"editing[$index]"</span> <span class="attr">ng-click</span>=<span class="string">"update($index)"</span>></span>Update<span class="tag"></<span class="name">button</span>></span></div><div class="line"> <span class="tag"><<span class="name">button</span> <span class="attr">ng-show</span>=<span class="string">"editing[$index]"</span> <span class="attr">ng-click</span>=<span class="string">"cancel($index)"</span>></span>Cancel<span class="tag"></<span class="name">button</span>></span></div><div class="line"> <span class="tag"></<span class="name">li</span>></span></div><div class="line"> <span class="tag"></<span class="name">ul</span>></span></div><div class="line"> New task <span class="tag"><<span class="name">input</span> <span class="attr">type</span>=<span class="string">"text"</span> <span class="attr">ng-model</span>=<span class="string">"newTodo"</span>></span><span class="tag"><<span class="name">button</span> <span class="attr">ng-click</span>=<span class="string">"save()"</span>></span>Create<span class="tag"></<span class="name">button</span>></span></div><div class="line"><span class="tag"></<span class="name">script</span>></span></div></pre></td></tr></table></figure>
<p>Now let’s change the controller to handle the inline editing:</p>
<figure class="highlight javascript"><figcaption><span>Todo Controller</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div><div class="line">10</div><div class="line">11</div><div class="line">12</div><div class="line">13</div><div class="line">14</div><div class="line">15</div><div class="line">16</div><div class="line">17</div><div class="line">18</div><div class="line">19</div><div class="line">20</div><div class="line">21</div><div class="line">22</div><div class="line">23</div><div class="line">24</div><div class="line">25</div><div class="line">26</div><div class="line">27</div><div class="line">28</div><div class="line">29</div></pre></td><td class="code"><pre><div class="line">.controller(<span class="string">'TodoController'</span>, [<span class="string">'$scope'</span>, <span class="string">'Todos'</span>, <span class="function"><span class="keyword">function</span> (<span class="params">$scope, Todos</span>) </span>{</div><div class="line"> $scope.editing = [];</div><div class="line"> $scope.todos = Todos.query();</div><div class="line"></div><div class="line"> $scope.save = <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> <span class="keyword">if</span>(!$scope.newTodo || $scope.newTodo.length < <span class="number">1</span>) <span class="keyword">return</span>;</div><div class="line"> <span class="keyword">var</span> todo = <span class="keyword">new</span> Todos({ name: $scope.newTodo, completed: <span class="literal">false</span> });</div><div class="line"></div><div class="line"> todo.$save(<span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> $scope.todos.push(todo);</div><div class="line"> $scope.newTodo = <span class="string">''</span>; <span class="comment">// clear textbox</span></div><div class="line"> });</div><div class="line"> }</div><div class="line"></div><div class="line"> $scope.update = <span class="function"><span class="keyword">function</span>(<span class="params">index</span>)</span>{</div><div class="line"> <span class="keyword">var</span> todo = $scope.todos[index];</div><div class="line"> Todos.update({id: todo._id}, todo);</div><div class="line"> $scope.editing[index] = <span class="literal">false</span>;</div><div class="line"> }</div><div class="line"></div><div class="line"> $scope.edit = <span class="function"><span class="keyword">function</span>(<span class="params">index</span>)</span>{</div><div class="line"> $scope.editing[index] = angular.copy($scope.todos[index]);</div><div class="line"> }</div><div class="line"></div><div class="line"> $scope.cancel = <span class="function"><span class="keyword">function</span>(<span class="params">index</span>)</span>{</div><div class="line"> $scope.todos[index] = angular.copy($scope.editing[index]);</div><div class="line"> $scope.editing[index] = <span class="literal">false</span>;</div><div class="line"> }</div><div class="line">}])</div></pre></td></tr></table></figure>
<p>We added a new variable <code>$scope.editing</code> which shows or hides the form to edit the values. Furthermore, notice ng-click functions: edit, update and cancel.</p>
<blockquote>
<p>Let’s see what they do. Try it out!</p>
</blockquote>
<p>While were are editing notice that we copy the original todo task into the editing variable. This server for two purposes:</p>
<ol>
<li><p>It evaluates to <code>true</code> and show the forms with <code>ng-show</code></p>
</li>
<li><p>It holds a copy of the original value in case we press cancel.</p>
</li>
</ol>
<p>Now, going to the Todo Details. We would like that to be updated as well and add notes.</p>
<figure class="highlight html"><figcaption><span>Todo Details</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div></pre></td><td class="code"><pre><div class="line"><span class="tag"><<span class="name">script</span> <span class="attr">type</span>=<span class="string">"text/ng-template"</span> <span class="attr">id</span>=<span class="string">"/todoDetails.html"</span>></span><span class="xml"></span></div><div class="line"> <span class="tag"><<span class="name">h1</span>></span>{{ todo.name }}<span class="tag"></<span class="name">h1</span>></span></div><div class="line"> completed: <span class="tag"><<span class="name">input</span> <span class="attr">type</span>=<span class="string">"checkbox"</span> <span class="attr">ng-model</span>=<span class="string">"todo.completed"</span>></span><span class="tag"><<span class="name">br</span>></span></div><div class="line"> note: <span class="tag"><<span class="name">textarea</span> <span class="attr">ng-model</span>=<span class="string">"todo.note"</span>></span><span class="tag"></<span class="name">textarea</span>></span><span class="tag"><<span class="name">br</span>></span><span class="tag"><<span class="name">br</span>></span></div><div class="line"></div><div class="line"> <span class="tag"><<span class="name">button</span> <span class="attr">ng-click</span>=<span class="string">"update()"</span>></span>Update<span class="tag"></<span class="name">button</span>></span></div><div class="line"> <span class="tag"><<span class="name">a</span> <span class="attr">href</span>=<span class="string">"/"</span>></span>Cancel<span class="tag"></<span class="name">a</span>></span></div><div class="line"><span class="tag"></<span class="name">script</span>></span></div></pre></td></tr></table></figure>
<p>Similarly, we added an update method. However, this time we do not need to pass any index, since it is just one todo at a time. After it has been saved, it goes back to root path <code>/</code>.</p>
<figure class="highlight javascript"><figcaption><span>TodoDetailCtrl controller</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div></pre></td><td class="code"><pre><div class="line">.controller(<span class="string">'TodoDetailCtrl'</span>, [<span class="string">'$scope'</span>, <span class="string">'$routeParams'</span>, <span class="string">'Todos'</span>, <span class="string">'$location'</span>, <span class="function"><span class="keyword">function</span> (<span class="params">$scope, $routeParams, Todos, $location</span>) </span>{</div><div class="line"> $scope.todo = Todos.get({id: $routeParams.id });</div><div class="line"></div><div class="line"> $scope.update = <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> Todos.update({id: $scope.todo._id}, $scope.todo, <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> $location.url(<span class="string">'/'</span>);</div><div class="line"> });</div><div class="line"> }</div><div class="line">}])</div></pre></td></tr></table></figure>
<blockquote>
<p>Awesome! Time to check it out in the browser!</p>
</blockquote>
<p><code>$location.url([url])</code> is a getter/setter method that allows us to change url, thus routing/view.</p>
<p><a href="https://github.com/amejiarosario/todoAPIjs/commit/b6394448e1e1e8384815877df764507d6562dc4d" target="_blank" rel="external">diff</a></p>
<h2 id="AngularJS-Delete">AngularJS Delete<a href="#AngularJS-Delete" class="headerlink" title="AngularJS Delete"></a></h2><p>These are the changes added to perform the remove functionality:</p>
<p>A. Add removes button in the <code>li</code> element:
<figure class="highlight html"><figcaption><span>todos.html Template</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line"><span class="tag"><<span class="name">button</span> <span class="attr">ng-show</span>=<span class="string">"!editing[$index]"</span> <span class="attr">ng-click</span>=<span class="string">"remove($index)"</span>></span>remove<span class="tag"></<span class="name">button</span>></span></div></pre></td></tr></table></figure></p>
<p>Do the same for the details Template</p>
<figure class="highlight html"><figcaption><span>todoDetails.html Template</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line"><span class="tag"><<span class="name">button</span> <span class="attr">ng-click</span>=<span class="string">"remove()"</span>></span>Remove<span class="tag"></<span class="name">button</span>></span></div></pre></td></tr></table></figure>
<p>B. Add remove functionality in the controllers
<figure class="highlight javascript"><figcaption><span>TodoController</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div></pre></td><td class="code"><pre><div class="line">$scope.remove = <span class="function"><span class="keyword">function</span>(<span class="params">index</span>)</span>{</div><div class="line"> <span class="keyword">var</span> todo = $scope.todos[index];</div><div class="line"> Todos.remove({id: todo._id}, <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> $scope.todos.splice(index, <span class="number">1</span>);</div><div class="line"> });</div><div class="line">}</div></pre></td></tr></table></figure></p>
<p>And also in the details controllers</p>
<figure class="highlight javascript"><figcaption><span>todoDetails controller</span></figcaption><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div></pre></td><td class="code"><pre><div class="line">$scope.remove = <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> Todos.remove({id: $scope.todo._id}, <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>{</div><div class="line"> $location.url(<span class="string">'/'</span>);</div><div class="line"> });</div><div class="line">}</div></pre></td></tr></table></figure>
<p>When we remove elements from the todos array <code>$scope.todos.splice(index, 1)</code> they also disappear from the DOM. Very cool, huh?</p>
<p><a href="https://github.com/amejiarosario/todoAPIjs/commit/b9ff3a863c78d72e71b5cc9eb573bb3cb9d87179" target="_blank" rel="external">diff</a></p>
<blockquote>
<p><strong>Congratulations! You are now a MEAN developer!</strong></p>
</blockquote>
<h1 id="What’s-next">What’s next?<a href="#What’s-next" class="headerlink" title="What’s next?"></a></h1><p>Learn how to use GruntJS to automate repetitive tasks in your MEAN Stack workflow.</p>
<p><a href="/blog/2014/10/07/grunt-js-tutorial-from-beginner-to-ninja/">GruntJS Tutorial</a></p>
<p>Also, you can learn more about full-stack framework solutions.</p>
<h2 id="Full-Stack-Javascript-Web-Frameworks">Full-Stack Javascript Web Frameworks<a href="#Full-Stack-Javascript-Web-Frameworks" class="headerlink" title="Full-Stack Javascript Web Frameworks"></a></h2><p>What we did in these three series tutorial could have been done with just few keystrokes in the comamnd line ;). However, it’s good to know what’s going on. But at this point you do. So, I will introduce you to some frameworks that can save you a lot of time.</p>
<p><strong>Using MEAN.io</strong></p>
<p><a href="http://mean.io" target="_blank" rel="external">MeanIO</a> uses a customized CLI tool: ‘mean’. Its approach for modularity is leaned towards self-contained packages that have code for both client and server files. At moment of writing this, it has nine packages ranging from MEAN-Admin, Translation, file uploads, image crop and more.</p>
<p><strong>Using MEAN.js</strong></p>
<p><a href="http://meanjs.org/" target="_blank" rel="external">MeanJS</a> it is a fork from the creator of MEAN.IO, it uses Yeoman generators to generate Angular’s CRUD modules, routes, controllers, views, services, and more. Also has generators for Express: models, controllers, routes and tests. It has excellent documentation.</p>
<h2 id="Others-Frameworks-to-look-at">Others Frameworks to look at<a href="#Others-Frameworks-to-look-at" class="headerlink" title="Others Frameworks to look at"></a></h2><ul>
<li><a href="https://www.meteor.com/" target="_blank" rel="external">Meteor</a> - Meteor is an open-source platform for building top-quality web apps in a fraction of the time, whether you’re an expert developer or just getting started.</li>
<li><a href="http://sailsjs.org/" target="_blank" rel="external">Sails</a> - The web framework of your dreams.
for your next web application.</li>
<li><a href="https://developer.yahoo.com/cocktails/mojito/" target="_blank" rel="external">Yahoo! Mojito</a> - A JavaScript MVC framework for mobile applications, one of the Yahoo! Cocktails.</li>
<li><a href="http://towerjs.org" target="_blank" rel="external">Tower.js</a> - Small components for building apps, manipulating data, and automating a distributed infrastructure.</li>
</ul>
]]></content>
<summary type="html">
<p>We are going to build a full stack Todo App using the MEAN (MongoDB, ExpressJS, AngularJS and NodeJS). This is the last part of <a href="/tags/Tutorial-MEAN-Stack/">three-post series tutorial</a>.</p>
</summary>
<category term="Technologies" scheme="http://adrianmejia.com/categories/Technologies/"/>
<category term="Web Development" scheme="http://adrianmejia.com/categories/Technologies/Web-Development/"/>
<category term="javascript" scheme="http://adrianmejia.com/tags/javascript/"/>
<category term="Tutorial_MEAN-Stack" scheme="http://adrianmejia.com/tags/Tutorial-MEAN-Stack/"/>
<category term="angularjs" scheme="http://adrianmejia.com/tags/angularjs/"/>
<category term="mean stack" scheme="http://adrianmejia.com/tags/mean-stack/"/>
</entry>
<entry>
<title>Creating RESTful APIs with NodeJS and MongoDB Tutorial (Part II)</title>
<link href="http://adrianmejia.com/blog/2014/10/01/creating-a-restful-api-tutorial-with-nodejs-and-mongodb/"/>
<id>http://adrianmejia.com/blog/2014/10/01/creating-a-restful-api-tutorial-with-nodejs-and-mongodb/</id>
<published>2014-10-01T21:26:42.000Z</published>
<updated>2016-08-06T22:26:37.000Z</updated>
<content type="html"><![CDATA[<p>Welcome to this RESTful API using Node.js (Express.js) and MongoDB (mongoose) tutorial! We are going to learn how to install and use each component individually and then proceed to create a RESTful API.</p>
<a id="more"></a>
<h1 id="What-is-a-RESTful-API">What is a RESTful API?<a href="#What-is-a-RESTful-API" class="headerlink" title="What is a RESTful API?"></a></h1><p>REST stands for Representational State Transfer. It is an architecture that allows <code>client-server</code> communication through a uniform interface. They are also <code>stateless</code>, <code>cachable</code> and has property called <code>idempotence</code>. It means that the side effect of identical requests have the same effect as the same single request.</p>
<p>HTTP RESTful API’s are compose of:</p>
<ul>
<li>HTTP methods, e.g. GET, PUT, DELETE, PATCH, POST, …</li>
<li>Base URI, e.g. <code>http://adrianmejia.com</code></li>
<li>URL path, e.g. <code>/blog/2014/10/01/creating-a-restful-api-tutorial-with-nodejs-and-mongodb/</code></li>
<li>Media type, e.g. <code>html</code>, <code>JSON</code>, <code>XML</code>, <code>Microformats</code>, <code>Atom</code>, <code>Images</code>…</li>
</ul>
<p>Here’s is a summary what we want to implement:</p>
<table>
<thead>
<tr>
<th>Resource (URI)</th>
<th>POST (create)</th>
<th>GET (read)</th>
<th>PUT (update)</th>
<th>DELETE (destroy)</th>
</tr>
</thead>
<tbody>
<tr>
<td>/todos</td>
<td>create new task</td>
<td>list tasks</td>
<td>N/A (update all)</td>
<td>N/A (destroy all)</td>
</tr>
<tr>
<td>/todos/1</td>
<td>error</td>
<td>show task ID 1</td>
<td>update task ID 1</td>
<td>destroy task ID 1</td>
</tr>
</tbody>
</table>
<p><strong>NOTE</strong> for this tutorial:</p>
<ul>
<li>Format will be JSON.</li>
<li>Bulk updates and bulk destroys are not safe, so we will not be implementing those.</li>
<li><strong>CRUD</strong> functionality: POST == <strong>C</strong>REATE, GET == <strong>R</strong>EAD, PUT == <strong>U</strong>PDATE, DELETE == <strong>D</strong>ELETE.</li>
</ul>
<h1 id="Installing-the-MEAN-Stack-Backend">Installing the MEAN Stack Backend<a href="#Installing-the-MEAN-Stack-Backend" class="headerlink" title="Installing the MEAN Stack Backend"></a></h1><p>In this section, we are going to install the backend components of the MEAN stack: MongoDB, NodeJS and ExpressJS. If you already are familiar with them, then jump to <a href="#wiring-up-the-mean-stack">wiring the stack</a>. Otherwise, enjoy the ride!</p>
<h2 id="Installing-MongoDB">Installing MongoDB<a href="#Installing-MongoDB" class="headerlink" title="Installing MongoDB"></a></h2><p>MongoDB is a document-oriented NoSQL database (Big Data ready). It stores data in JSON-like format and allows to perform SQL-like queries against it.</p>
<p>You can installed following the <a href="http://docs.mongodb.org/manual/installation/" target="_blank">instructions here</a>.</p>
<p>If you have a <strong>Mac</strong> and <a href="http://brew.sh/" target="_blank">brew</a> it’s just:</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line">brew install mongodb && mongod</div></pre></td></tr></table></figure>
<p>In <strong>Ubuntu</strong>:</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line">sudo apt-get -y install mongodb</div></pre></td></tr></table></figure>
<p>After you have them installed, check version as follows:</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># Mac</span></div><div class="line">mongod --version</div><div class="line"><span class="comment"># => db version v2.6.4</span></div><div class="line"><span class="comment"># => 2014-10-01T19:07:26.649-0400 git version: nogitversion</span></div><div class="line"></div><div class="line"><span class="comment"># Ubuntu</span></div><div class="line">mongod --version</div><div class="line"><span class="comment"># => db version v2.0.4, pdfile version 4.5</span></div><div class="line"><span class="comment"># => Wed Oct 1 23:06:54 git version: nogitversion</span></div></pre></td></tr></table></figure>
<h2 id="Installing-NodeJS">Installing NodeJS<a href="#Installing-NodeJS" class="headerlink" title="Installing NodeJS"></a></h2><p>The Node official definition is:</p>
<blockquote><p>Node.js® is a JavaScript runtime built on Chrome’s V8 JavaScript engine. Node.js uses an event-driven, non-blocking I/O model that makes it lightweight and efficient. Node.js’ package ecosystem, npm, is the largest ecosystem of open source libraries in the world.</p>
<footer><strong>Node.js Website</strong><cite><a href="https://nodejs.org" target="_blank" rel="external">nodejs.org</a></cite></footer></blockquote>
<p>In short, NodeJS allows you to run Javascript outside the browser, in this case, on the web server. <abbr title="Node Package Manager">NPM</abbr> allows you to install/publish node packages with ease.</p>
<p>To install it, you can go to <a href="http://nodejs.org/" target="_blank">NodeJS Website</a>.</p>
<p>Since Node versions changes very often. You can use the <abbr title="Node Version Manager">NVM</abbr> (Node Version Manager) on <strong>Ubuntu</strong> and Mac with:</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># download NPM</span></div><div class="line">curl -o- https://raw.githubusercontent.com/creationix/nvm/v0.31.4/install.sh | bash</div><div class="line"></div><div class="line"><span class="comment"># load NPM</span></div><div class="line"><span class="built_in">export</span> NVM_DIR=<span class="string">"<span class="variable">$HOME</span>/.nvm"</span></div><div class="line">[ <span class="_">-s</span> <span class="string">"<span class="variable">$NVM_DIR</span>/nvm.sh"</span> ] && . <span class="string">"<span class="variable">$NVM_DIR</span>/nvm.sh"</span> <span class="comment"># This loads nvm</span></div><div class="line"></div><div class="line"><span class="comment"># Install latest stable version</span></div><div class="line">nvm install stable</div></pre></td></tr></table></figure>
<p>Check out <a href="https://github.com/creationix/nvm" target="_blank">https://github.com/creationix/nvm</a> for more details.</p>
<p>Also, on <strong>Mac</strong> and <a href="http://brew.sh" target="_blank">brew</a> you can do:</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><div class="line">1</div></pre></td><td class="code"><pre><div class="line">brew install nodejs</div></pre></td></tr></table></figure>
<p>After you got it installed, check node version and npm (node package manager) version:
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div></pre></td><td class="code"><pre><div class="line">node -v</div><div class="line"><span class="comment"># => v6.2.2</span></div><div class="line"></div><div class="line">npm -v</div><div class="line"><span class="comment"># => 3.9.5</span></div></pre></td></tr></table></figure></p>
<h2 id="Installing-ExpressJS">Installing ExpressJS<a href="#Installing-ExpressJS" class="headerlink" title="Installing ExpressJS"></a></h2><p>ExpressJS is web application framework that runs on NodeJS. Allows you to build web applications and APIs endpoints (mode details later).</p>
<p>We are going to create a project folder first, and then add <code>express</code> as a dependency.
Let’s use <abbr title="Node Package Manager">NPM</abbr> init command to get us started.</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><div class="line">1</div><div class="line">2</div><div class="line">3</div><div class="line">4</div><div class="line">5</div><div class="line">6</div><div class="line">7</div><div class="line">8</div><div class="line">9</div></pre></td><td class="code"><pre><div class="line"><span class="comment"># create project folder</span></div><div class="line">mkdir todo-app</div><div class="line"></div><div class="line"><span class="comment"># move to the folder and initialize the project</span></div><div class="line"><span class="built_in">cd</span> todo-app</div><div class="line">npm init . <span class="comment"># press enter multiple times to accept all defaults</span></div><div class="line"></div><div class="line"><span class="comment"># install express v4.14 and save it as dependency</span></div><div class="line">npm install [email protected] --save</div></pre></td></tr></table></figure>
<p>Notice that after the last command, <code>express</code> should be added to package.json with the version <code>4.14.x</code>.</p>