-
Notifications
You must be signed in to change notification settings - Fork 36
/
Copy pathmodeling-users.html
2092 lines (1326 loc) · 218 KB
/
modeling-users.html
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
<!DOCTYPE html>
<html>
<head>
<title>modeling-users</title>
<link rel="stylesheet" href="pygments.css" type="text/css" />
<link rel="stylesheet" href="polytexnic.css" type="text/css" />
</head>
<body>
<div id="book">
<h1 class="title">Ruby on Rails Tutorial </h1>
<h1 class="subtitle"> Learn Web Development with Rails</h1>
<h2 class="author">Michael Hartl</h2>
<h2 class="contents">Contents</h2>
<div id="table_of_contents"><ol><li class="chapter"><a href="beginning.html#top"><span class="number">Chapter 1</span> From zero to deploy</a></li><li><ol><li class="section"><a href="beginning.html#sec-introduction"><span class="number">1.1</span> Introduction</a></li><li><ol><li class="subsection"><a href="beginning.html#sec-comments_for_various_readers"><span class="number">1.1.1</span> Comments for various readers</a></li><li class="subsection"><a href="beginning.html#sec-1_1_2"><span class="number">1.1.2</span> “Scaling” Rails</a></li><li class="subsection"><a href="beginning.html#sec-conventions"><span class="number">1.1.3</span> Conventions in this book</a></li></ol></li><li class="section"><a href="beginning.html#sec-up_and_running"><span class="number">1.2</span> Up and running</a></li><li><ol><li class="subsection"><a href="beginning.html#sec-development_tools"><span class="number">1.2.1</span> Development environments</a></li><li><ol><li class="subsubsection"><a href="beginning.html#sec-1_2_1_1">IDEs</a></li><li class="subsubsection"><a href="beginning.html#sec-1_2_1_2">Text editors and command lines</a></li><li class="subsubsection"><a href="beginning.html#sec-1_2_1_3">Browsers</a></li><li class="subsubsection"><a href="beginning.html#sec-1_2_1_4">A note about tools</a></li></ol></li><li class="subsection"><a href="beginning.html#sec-rubygems"><span class="number">1.2.2</span> Ruby, RubyGems, Rails, and Git</a></li><li><ol><li class="subsubsection"><a href="beginning.html#sec-rails_installer_windows">Rails Installer (Windows)</a></li><li class="subsubsection"><a href="beginning.html#sec-install_git">Install Git</a></li><li class="subsubsection"><a href="beginning.html#sec-install_ruby">Install Ruby</a></li><li class="subsubsection"><a href="beginning.html#sec-install_rubygems">Install RubyGems</a></li><li class="subsubsection"><a href="beginning.html#sec-install_rails">Install Rails</a></li></ol></li><li class="subsection"><a href="beginning.html#sec-the_first_application"><span class="number">1.2.3</span> The first application</a></li><li class="subsection"><a href="beginning.html#sec-bundler"><span class="number">1.2.4</span> Bundler</a></li><li class="subsection"><a href="beginning.html#sec-rails_server"><span class="number">1.2.5</span> <tt>rails server</tt></a></li><li class="subsection"><a href="beginning.html#sec-mvc"><span class="number">1.2.6</span> Model-view-controller (MVC)</a></li></ol></li><li class="section"><a href="beginning.html#sec-version_control"><span class="number">1.3</span> Version control with Git</a></li><li><ol><li class="subsection"><a href="beginning.html#sec-git_setup"><span class="number">1.3.1</span> Installation and setup</a></li><li><ol><li class="subsubsection"><a href="beginning.html#sec-1_3_1_1">First-time system setup</a></li><li class="subsubsection"><a href="beginning.html#sec-1_3_1_2">First-time repository setup</a></li></ol></li><li class="subsection"><a href="beginning.html#sec-adding_and_committing"><span class="number">1.3.2</span> Adding and committing</a></li><li class="subsection"><a href="beginning.html#sec-1_3_3"><span class="number">1.3.3</span> What good does Git do you?</a></li><li class="subsection"><a href="beginning.html#sec-github"><span class="number">1.3.4</span> GitHub</a></li><li class="subsection"><a href="beginning.html#sec-git_commands"><span class="number">1.3.5</span> Branch, edit, commit, merge</a></li><li><ol><li class="subsubsection"><a href="beginning.html#sec-git_branch">Branch</a></li><li class="subsubsection"><a href="beginning.html#sec-git_edit">Edit</a></li><li class="subsubsection"><a href="beginning.html#sec-git_commit">Commit</a></li><li class="subsubsection"><a href="beginning.html#sec-git_merge">Merge</a></li><li class="subsubsection"><a href="beginning.html#sec-git_push">Push</a></li></ol></li></ol></li><li class="section"><a href="beginning.html#sec-deploying"><span class="number">1.4</span> Deploying</a></li><li><ol><li class="subsection"><a href="beginning.html#sec-heroku_setup"><span class="number">1.4.1</span> Heroku setup</a></li><li class="subsection"><a href="beginning.html#sec-heroku_step_one"><span class="number">1.4.2</span> Heroku deployment, step one</a></li><li class="subsection"><a href="beginning.html#sec-1_4_3"><span class="number">1.4.3</span> Heroku deployment, step two</a></li><li class="subsection"><a href="beginning.html#sec-heroku_commands"><span class="number">1.4.4</span> Heroku commands</a></li></ol></li><li class="section"><a href="beginning.html#sec-beginning_conclusion"><span class="number">1.5</span> Conclusion</a></li></ol></li><li class="chapter"><a href="a-demo-app.html#top"><span class="number">Chapter 2</span> A demo app</a></li><li><ol><li class="section"><a href="a-demo-app.html#sec-planning_the_application"><span class="number">2.1</span> Planning the application</a></li><li><ol><li class="subsection"><a href="a-demo-app.html#sec-modeling_demo_users"><span class="number">2.1.1</span> Modeling demo users</a></li><li class="subsection"><a href="a-demo-app.html#sec-modeling_demo_microposts"><span class="number">2.1.2</span> Modeling demo microposts</a></li></ol></li><li class="section"><a href="a-demo-app.html#sec-demo_users_resource"><span class="number">2.2</span> The Users resource</a></li><li><ol><li class="subsection"><a href="a-demo-app.html#sec-a_user_tour"><span class="number">2.2.1</span> A user tour</a></li><li class="subsection"><a href="a-demo-app.html#sec-mvc_in_action"><span class="number">2.2.2</span> MVC in action</a></li><li class="subsection"><a href="a-demo-app.html#sec-weaknesses_of_this_users_resource"><span class="number">2.2.3</span> Weaknesses of this Users resource</a></li></ol></li><li class="section"><a href="a-demo-app.html#sec-microposts_resource"><span class="number">2.3</span> The Microposts resource</a></li><li><ol><li class="subsection"><a href="a-demo-app.html#sec-a_micropost_microtour"><span class="number">2.3.1</span> A micropost microtour</a></li><li class="subsection"><a href="a-demo-app.html#sec-putting_the_micro_in_microposts"><span class="number">2.3.2</span> Putting the <em>micro</em> in microposts</a></li><li class="subsection"><a href="a-demo-app.html#sec-demo_user_has_many_microposts"><span class="number">2.3.3</span> A user <tt>has_many</tt> microposts</a></li><li class="subsection"><a href="a-demo-app.html#sec-inheritance_hierarchies"><span class="number">2.3.4</span> Inheritance hierarchies</a></li><li class="subsection"><a href="a-demo-app.html#sec-deploying_the_demo_app"><span class="number">2.3.5</span> Deploying the demo app</a></li></ol></li><li class="section"><a href="a-demo-app.html#sec-2_4"><span class="number">2.4</span> Conclusion</a></li></ol></li><li class="chapter"><a href="static-pages.html#top"><span class="number">Chapter 3</span> Mostly static pages</a></li><li><ol><li class="section"><a href="static-pages.html#sec-static_pages"><span class="number">3.1</span> Static pages</a></li><li><ol><li class="subsection"><a href="static-pages.html#sec-truly_static_pages"><span class="number">3.1.1</span> Truly static pages</a></li><li class="subsection"><a href="static-pages.html#sec-static_pages_with_rails"><span class="number">3.1.2</span> Static pages with Rails</a></li></ol></li><li class="section"><a href="static-pages.html#sec-first_tests"><span class="number">3.2</span> Our first tests</a></li><li><ol><li class="subsection"><a href="static-pages.html#sec-TDD"><span class="number">3.2.1</span> Test-driven development</a></li><li class="subsection"><a href="static-pages.html#sec-adding_a_page"><span class="number">3.2.2</span> Adding a page</a></li><li><ol><li class="subsubsection"><a href="static-pages.html#sec-red">Red</a></li><li class="subsubsection"><a href="static-pages.html#sec-green">Green</a></li><li class="subsubsection"><a href="static-pages.html#sec-refactor">Refactor</a></li></ol></li></ol></li><li class="section"><a href="static-pages.html#sec-slightly_dynamic_pages"><span class="number">3.3</span> Slightly dynamic pages</a></li><li><ol><li class="subsection"><a href="static-pages.html#sec-testing_a_title_change"><span class="number">3.3.1</span> Testing a title change</a></li><li class="subsection"><a href="static-pages.html#sec-passing_title_tests"><span class="number">3.3.2</span> Passing title tests</a></li><li class="subsection"><a href="static-pages.html#sec-embedded_ruby"><span class="number">3.3.3</span> Embedded Ruby</a></li><li class="subsection"><a href="static-pages.html#sec-layouts"><span class="number">3.3.4</span> Eliminating duplication with layouts</a></li></ol></li><li class="section"><a href="static-pages.html#sec-static_pages_conclusion"><span class="number">3.4</span> Conclusion</a></li><li class="section"><a href="static-pages.html#sec-static_pages_exercises"><span class="number">3.5</span> Exercises</a></li><li class="section"><a href="static-pages.html#sec-advanced_setup"><span class="number">3.6</span> Advanced setup</a></li><li><ol><li class="subsection"><a href="static-pages.html#sec-eliminating_bundle_exec"><span class="number">3.6.1</span> Eliminating <tt>bundle exec</tt></a></li><li><ol><li class="subsubsection"><a href="static-pages.html#sec-rvm_bundler_integration">RVM Bundler integration</a></li><li class="subsubsection"><a href="static-pages.html#sec-binstubs">binstubs</a></li></ol></li><li class="subsection"><a href="static-pages.html#sec-guard"><span class="number">3.6.2</span> Automated tests with Guard</a></li><li class="subsection"><a href="static-pages.html#sec-spork"><span class="number">3.6.3</span> Speeding up tests with Spork</a></li><li><ol><li class="subsubsection"><a href="static-pages.html#sec-spork_and_guard">Guard with Spork</a></li></ol></li><li class="subsection"><a href="static-pages.html#sec-tests_inside_sublime_text"><span class="number">3.6.4</span> Tests inside Sublime Text</a></li></ol></li></ol></li><li class="chapter"><a href="rails-flavored-ruby.html#top"><span class="number">Chapter 4</span> Rails-flavored Ruby</a></li><li><ol><li class="section"><a href="rails-flavored-ruby.html#sec-motivation"><span class="number">4.1</span> Motivation</a></li><li class="section"><a href="rails-flavored-ruby.html#sec-strings_and_methods"><span class="number">4.2</span> Strings and methods</a></li><li><ol><li class="subsection"><a href="rails-flavored-ruby.html#sec-comments"><span class="number">4.2.1</span> Comments</a></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-strings"><span class="number">4.2.2</span> Strings</a></li><li><ol><li class="subsubsection"><a href="rails-flavored-ruby.html#sec-printing">Printing</a></li><li class="subsubsection"><a href="rails-flavored-ruby.html#sec-single_quoted_strings">Single-quoted strings</a></li></ol></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-objects_and_message_passing"><span class="number">4.2.3</span> Objects and message passing</a></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-method_definitions"><span class="number">4.2.4</span> Method definitions</a></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-back_to_the_title_helper"><span class="number">4.2.5</span> Back to the title helper</a></li></ol></li><li class="section"><a href="rails-flavored-ruby.html#sec-other_data_structures"><span class="number">4.3</span> Other data structures</a></li><li><ol><li class="subsection"><a href="rails-flavored-ruby.html#sec-arrays_and_ranges"><span class="number">4.3.1</span> Arrays and ranges</a></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-blocks"><span class="number">4.3.2</span> Blocks</a></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-hashes_and_symbols"><span class="number">4.3.3</span> Hashes and symbols</a></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-css_revisited"><span class="number">4.3.4</span> CSS revisited</a></li></ol></li><li class="section"><a href="rails-flavored-ruby.html#sec-ruby_classes"><span class="number">4.4</span> Ruby classes</a></li><li><ol><li class="subsection"><a href="rails-flavored-ruby.html#sec-constructors"><span class="number">4.4.1</span> Constructors</a></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-a_class_of_our_own"><span class="number">4.4.2</span> Class inheritance</a></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-modifying_built_in_classes"><span class="number">4.4.3</span> Modifying built-in classes</a></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-a_controller_class"><span class="number">4.4.4</span> A controller class</a></li><li class="subsection"><a href="rails-flavored-ruby.html#sec-a_user_class"><span class="number">4.4.5</span> A user class</a></li></ol></li><li class="section"><a href="rails-flavored-ruby.html#sec-conclusion"><span class="number">4.5</span> Conclusion</a></li><li class="section"><a href="rails-flavored-ruby.html#sec-exercises"><span class="number">4.6</span> Exercises</a></li></ol></li><li class="chapter"><a href="filling-in-the-layout.html#top"><span class="number">Chapter 5</span> Filling in the layout</a></li><li><ol><li class="section"><a href="filling-in-the-layout.html#sec-structure"><span class="number">5.1</span> Adding some structure</a></li><li><ol><li class="subsection"><a href="filling-in-the-layout.html#sec-adding_to_the_layout"><span class="number">5.1.1</span> Site navigation</a></li><li class="subsection"><a href="filling-in-the-layout.html#sec-custom_css"><span class="number">5.1.2</span> Bootstrap and custom CSS</a></li><li class="subsection"><a href="filling-in-the-layout.html#sec-partials"><span class="number">5.1.3</span> Partials</a></li></ol></li><li class="section"><a href="filling-in-the-layout.html#sec-sass_and_the_asset_pipeline"><span class="number">5.2</span> Sass and the asset pipeline</a></li><li><ol><li class="subsection"><a href="filling-in-the-layout.html#sec-the_asset_pipeline"><span class="number">5.2.1</span> The asset pipeline</a></li><li><ol><li class="subsubsection"><a href="filling-in-the-layout.html#sec-5_2_1_1">Asset directories</a></li><li class="subsubsection"><a href="filling-in-the-layout.html#sec-5_2_1_2">Manifest files</a></li><li class="subsubsection"><a href="filling-in-the-layout.html#sec-5_2_1_3">Preprocessor engines</a></li><li class="subsubsection"><a href="filling-in-the-layout.html#sec-5_2_1_4">Efficiency in production</a></li></ol></li><li class="subsection"><a href="filling-in-the-layout.html#sec-sass"><span class="number">5.2.2</span> Syntactically awesome stylesheets</a></li><li><ol><li class="subsubsection"><a href="filling-in-the-layout.html#sec-5_2_2_1">Nesting</a></li><li class="subsubsection"><a href="filling-in-the-layout.html#sec-5_2_2_2">Variables</a></li></ol></li></ol></li><li class="section"><a href="filling-in-the-layout.html#sec-layout_links"><span class="number">5.3</span> Layout links</a></li><li><ol><li class="subsection"><a href="filling-in-the-layout.html#sec-route_tests"><span class="number">5.3.1</span> Route tests</a></li><li class="subsection"><a href="filling-in-the-layout.html#sec-rails_routes"><span class="number">5.3.2</span> Rails routes</a></li><li class="subsection"><a href="filling-in-the-layout.html#sec-named_routes"><span class="number">5.3.3</span> Named routes</a></li><li class="subsection"><a href="filling-in-the-layout.html#sec-pretty_rspec"><span class="number">5.3.4</span> Pretty RSpec</a></li></ol></li><li class="section"><a href="filling-in-the-layout.html#sec-user_signup"><span class="number">5.4</span> User signup: A first step</a></li><li><ol><li class="subsection"><a href="filling-in-the-layout.html#sec-users_controller"><span class="number">5.4.1</span> Users controller</a></li><li class="subsection"><a href="filling-in-the-layout.html#sec-signup_url"><span class="number">5.4.2</span> Signup URI</a></li></ol></li><li class="section"><a href="filling-in-the-layout.html#sec-layout_conclusion"><span class="number">5.5</span> Conclusion</a></li><li class="section"><a href="filling-in-the-layout.html#sec-layout_exercises"><span class="number">5.6</span> Exercises</a></li></ol></li><li class="chapter"><a href="modeling-users.html#top"><span class="number">Chapter 6</span> Modeling users</a></li><li><ol><li class="section"><a href="modeling-users.html#sec-user_model"><span class="number">6.1</span> User model</a></li><li><ol><li class="subsection"><a href="modeling-users.html#sec-database_migrations"><span class="number">6.1.1</span> Database migrations</a></li><li class="subsection"><a href="modeling-users.html#sec-the_model_file"><span class="number">6.1.2</span> The model file</a></li><li><ol><li class="subsubsection"><a href="modeling-users.html#sec-model_annotation">Model annotation</a></li><li class="subsubsection"><a href="modeling-users.html#sec-accessible_attributes">Accessible attributes</a></li></ol></li><li class="subsection"><a href="modeling-users.html#sec-creating_user_objects"><span class="number">6.1.3</span> Creating user objects</a></li><li class="subsection"><a href="modeling-users.html#sec-finding_user_objects"><span class="number">6.1.4</span> Finding user objects</a></li><li class="subsection"><a href="modeling-users.html#sec-updating_user_objects"><span class="number">6.1.5</span> Updating user objects</a></li></ol></li><li class="section"><a href="modeling-users.html#sec-user_validations"><span class="number">6.2</span> User validations</a></li><li><ol><li class="subsection"><a href="modeling-users.html#sec-initial_user_tests"><span class="number">6.2.1</span> Initial user tests</a></li><li class="subsection"><a href="modeling-users.html#sec-presence_validation"><span class="number">6.2.2</span> Validating presence</a></li><li class="subsection"><a href="modeling-users.html#sec-length_validation"><span class="number">6.2.3</span> Length validation</a></li><li class="subsection"><a href="modeling-users.html#sec-format_validation"><span class="number">6.2.4</span> Format validation</a></li><li class="subsection"><a href="modeling-users.html#sec-uniqueness_validation"><span class="number">6.2.5</span> Uniqueness validation</a></li><li><ol><li class="subsubsection"><a href="modeling-users.html#sec-the_caveat">The uniqueness caveat</a></li></ol></li></ol></li><li class="section"><a href="modeling-users.html#sec-adding_a_secure_password"><span class="number">6.3</span> Adding a secure password</a></li><li><ol><li class="subsection"><a href="modeling-users.html#sec-an_encrypted_password"><span class="number">6.3.1</span> An encrypted password</a></li><li class="subsection"><a href="modeling-users.html#sec-password_and_confirmation"><span class="number">6.3.2</span> Password and confirmation</a></li><li class="subsection"><a href="modeling-users.html#sec-user_authentication"><span class="number">6.3.3</span> User authentication</a></li><li class="subsection"><a href="modeling-users.html#sec-has_secure_password"><span class="number">6.3.4</span> User has secure password</a></li><li class="subsection"><a href="modeling-users.html#sec-creating_a_user"><span class="number">6.3.5</span> Creating a user</a></li></ol></li><li class="section"><a href="modeling-users.html#sec-6_4"><span class="number">6.4</span> Conclusion</a></li><li class="section"><a href="modeling-users.html#sec-6_5"><span class="number">6.5</span> Exercises</a></li></ol></li><li class="chapter"><a href="sign-up.html#top"><span class="number">Chapter 7</span> Sign up</a></li><li><ol><li class="section"><a href="sign-up.html#sec-showing_users"><span class="number">7.1</span> Showing users</a></li><li><ol><li class="subsection"><a href="sign-up.html#sec-rails_environments"><span class="number">7.1.1</span> Debug and Rails environments</a></li><li class="subsection"><a href="sign-up.html#sec-a_users_resource"><span class="number">7.1.2</span> A Users resource</a></li><li class="subsection"><a href="sign-up.html#sec-tests_with_factories"><span class="number">7.1.3</span> Testing the user show page (with factories)</a></li><li class="subsection"><a href="sign-up.html#sec-a_gravatar_image"><span class="number">7.1.4</span> A Gravatar image and a sidebar</a></li></ol></li><li class="section"><a href="sign-up.html#sec-signup_form"><span class="number">7.2</span> Signup form</a></li><li><ol><li class="subsection"><a href="sign-up.html#sec-tests_for_user_signup"><span class="number">7.2.1</span> Tests for user signup</a></li><li class="subsection"><a href="sign-up.html#sec-using_form_for"><span class="number">7.2.2</span> Using <tt>form_for</tt></a></li><li class="subsection"><a href="sign-up.html#sec-the_form_html"><span class="number">7.2.3</span> The form HTML</a></li></ol></li><li class="section"><a href="sign-up.html#sec-signup_failure"><span class="number">7.3</span> Signup failure</a></li><li><ol><li class="subsection"><a href="sign-up.html#sec-a_working_form"><span class="number">7.3.1</span> A working form</a></li><li class="subsection"><a href="sign-up.html#sec-signup_error_messages"><span class="number">7.3.2</span> Signup error messages</a></li></ol></li><li class="section"><a href="sign-up.html#sec-signup_success"><span class="number">7.4</span> Signup success</a></li><li><ol><li class="subsection"><a href="sign-up.html#sec-the_finished_signup_form"><span class="number">7.4.1</span> The finished signup form</a></li><li class="subsection"><a href="sign-up.html#sec-the_flash"><span class="number">7.4.2</span> The flash</a></li><li class="subsection"><a href="sign-up.html#sec-the_first_signup"><span class="number">7.4.3</span> The first signup</a></li><li class="subsection"><a href="sign-up.html#sec-deploying_to_production_with_ssl"><span class="number">7.4.4</span> Deploying to production with SSL</a></li></ol></li><li class="section"><a href="sign-up.html#sec-7_5"><span class="number">7.5</span> Conclusion</a></li><li class="section"><a href="sign-up.html#sec-signup_exercises"><span class="number">7.6</span> Exercises</a></li></ol></li><li class="chapter"><a href="sign-in-sign-out.html#top"><span class="number">Chapter 8</span> Sign in, sign out</a></li><li><ol><li class="section"><a href="sign-in-sign-out.html#sec-signin_failure"><span class="number">8.1</span> Sessions and signin failure</a></li><li><ol><li class="subsection"><a href="sign-in-sign-out.html#sec-sessions_controller"><span class="number">8.1.1</span> Sessions controller</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-signin_tests"><span class="number">8.1.2</span> Signin tests</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-signin_form"><span class="number">8.1.3</span> Signin form</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-reviewing_form_submission"><span class="number">8.1.4</span> Reviewing form submission</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-rendering_with_a_flash_message"><span class="number">8.1.5</span> Rendering with a flash message</a></li></ol></li><li class="section"><a href="sign-in-sign-out.html#sec-signin_success"><span class="number">8.2</span> Signin success</a></li><li><ol><li class="subsection"><a href="sign-in-sign-out.html#sec-remember_me"><span class="number">8.2.1</span> Remember me</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-a_working_sign_in_method"><span class="number">8.2.2</span> A working <tt>sign_in</tt> method</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-current_user"><span class="number">8.2.3</span> Current user</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-changing_the_layout_links"><span class="number">8.2.4</span> Changing the layout links</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-signin_upon_signup"><span class="number">8.2.5</span> Signin upon signup</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-signing_out"><span class="number">8.2.6</span> Signing out</a></li></ol></li><li class="section"><a href="sign-in-sign-out.html#sec-cucumber"><span class="number">8.3</span> Introduction to Cucumber (optional)</a></li><li><ol><li class="subsection"><a href="sign-in-sign-out.html#sec-installation_and_setup"><span class="number">8.3.1</span> Installation and setup</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-features_and_steps"><span class="number">8.3.2</span> Features and steps</a></li><li class="subsection"><a href="sign-in-sign-out.html#sec-rspec_custom_matchers"><span class="number">8.3.3</span> Counterpoint: RSpec custom matchers</a></li></ol></li><li class="section"><a href="sign-in-sign-out.html#sec-8_4"><span class="number">8.4</span> Conclusion</a></li><li class="section"><a href="sign-in-sign-out.html#sec-sign_in_out_exercises"><span class="number">8.5</span> Exercises</a></li></ol></li><li class="chapter"><a href="updating-showing-and-deleting-users.html#top"><span class="number">Chapter 9</span> Updating, showing, and deleting users</a></li><li><ol><li class="section"><a href="updating-showing-and-deleting-users.html#sec-updating_users"><span class="number">9.1</span> Updating users</a></li><li><ol><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-edit_form"><span class="number">9.1.1</span> Edit form</a></li><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-unsuccessful_edits"><span class="number">9.1.2</span> Unsuccessful edits</a></li><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-successful_edits"><span class="number">9.1.3</span> Successful edits</a></li></ol></li><li class="section"><a href="updating-showing-and-deleting-users.html#sec-authorization"><span class="number">9.2</span> Authorization</a></li><li><ol><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-requiring_signed_in_users"><span class="number">9.2.1</span> Requiring signed-in users</a></li><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-requiring_the_right_user"><span class="number">9.2.2</span> Requiring the right user</a></li><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-friendly_forwarding"><span class="number">9.2.3</span> Friendly forwarding</a></li></ol></li><li class="section"><a href="updating-showing-and-deleting-users.html#sec-showing_all_users"><span class="number">9.3</span> Showing all users</a></li><li><ol><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-user_index"><span class="number">9.3.1</span> User index</a></li><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-sample_users"><span class="number">9.3.2</span> Sample users</a></li><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-pagination"><span class="number">9.3.3</span> Pagination</a></li><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-partial_refactoring"><span class="number">9.3.4</span> Partial refactoring</a></li></ol></li><li class="section"><a href="updating-showing-and-deleting-users.html#sec-destroying_users"><span class="number">9.4</span> Deleting users</a></li><li><ol><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-administrative_users"><span class="number">9.4.1</span> Administrative users</a></li><li><ol><li class="subsubsection"><a href="updating-showing-and-deleting-users.html#sec-revisiting_attr_accessible">Revisiting <tt>attr_accessible</tt></a></li></ol></li><li class="subsection"><a href="updating-showing-and-deleting-users.html#sec-the_destroy_action"><span class="number">9.4.2</span> The <tt>destroy</tt> action</a></li></ol></li><li class="section"><a href="updating-showing-and-deleting-users.html#sec-updating_and_deleting_users_conclusion"><span class="number">9.5</span> Conclusion</a></li><li class="section"><a href="updating-showing-and-deleting-users.html#sec-updating_deleting_exercises"><span class="number">9.6</span> Exercises</a></li></ol></li><li class="chapter"><a href="user-microposts.html#top"><span class="number">Chapter 10</span> User microposts</a></li><li><ol><li class="section"><a href="user-microposts.html#sec-a_micropost_model"><span class="number">10.1</span> A Micropost model</a></li><li><ol><li class="subsection"><a href="user-microposts.html#sec-the_basic_model"><span class="number">10.1.1</span> The basic model</a></li><li class="subsection"><a href="user-microposts.html#sec-accessible_attribute"><span class="number">10.1.2</span> Accessible attributes and the first validation</a></li><li class="subsection"><a href="user-microposts.html#sec-user_micropost_associations"><span class="number">10.1.3</span> User/Micropost associations</a></li><li class="subsection"><a href="user-microposts.html#sec-ordering_and_dependency"><span class="number">10.1.4</span> Micropost refinements</a></li><li><ol><li class="subsubsection"><a href="user-microposts.html#sec-default_scope">Default scope</a></li><li class="subsubsection"><a href="user-microposts.html#sec-dependent_destroy">Dependent: destroy</a></li></ol></li><li class="subsection"><a href="user-microposts.html#sec-micropost_validations"><span class="number">10.1.5</span> Content validations</a></li></ol></li><li class="section"><a href="user-microposts.html#sec-showing_microposts"><span class="number">10.2</span> Showing microposts</a></li><li><ol><li class="subsection"><a href="user-microposts.html#sec-augmenting_the_user_show_page"><span class="number">10.2.1</span> Augmenting the user show page</a></li><li class="subsection"><a href="user-microposts.html#sec-sample_microposts"><span class="number">10.2.2</span> Sample microposts</a></li></ol></li><li class="section"><a href="user-microposts.html#sec-manipulating_microposts"><span class="number">10.3</span> Manipulating microposts</a></li><li><ol><li class="subsection"><a href="user-microposts.html#sec-access_control"><span class="number">10.3.1</span> Access control</a></li><li class="subsection"><a href="user-microposts.html#sec-creating_microposts"><span class="number">10.3.2</span> Creating microposts</a></li><li class="subsection"><a href="user-microposts.html#sec-a_proto_feed"><span class="number">10.3.3</span> A proto-feed</a></li><li class="subsection"><a href="user-microposts.html#sec-destroying_microposts"><span class="number">10.3.4</span> Destroying microposts</a></li></ol></li><li class="section"><a href="user-microposts.html#sec-10_4"><span class="number">10.4</span> Conclusion</a></li><li class="section"><a href="user-microposts.html#sec-micropost_exercises"><span class="number">10.5</span> Exercises</a></li></ol></li><li class="chapter"><a href="following-users.html#top"><span class="number">Chapter 11</span> Following users</a></li><li><ol><li class="section"><a href="following-users.html#sec-the_relationship_model"><span class="number">11.1</span> The Relationship model</a></li><li><ol><li class="subsection"><a href="following-users.html#sec-a_problem_with_the_data_model"><span class="number">11.1.1</span> A problem with the data model (and a solution)</a></li><li class="subsection"><a href="following-users.html#sec-relationship_user_associations"><span class="number">11.1.2</span> User/relationship associations</a></li><li class="subsection"><a href="following-users.html#sec-relationship_validations"><span class="number">11.1.3</span> Validations</a></li><li class="subsection"><a href="following-users.html#sec-following"><span class="number">11.1.4</span> Followed users</a></li><li class="subsection"><a href="following-users.html#sec-followers"><span class="number">11.1.5</span> Followers</a></li></ol></li><li class="section"><a href="following-users.html#sec-a_web_interface_for_following_and_followers"><span class="number">11.2</span> A web interface for following users</a></li><li><ol><li class="subsection"><a href="following-users.html#sec-sample_following_data"><span class="number">11.2.1</span> Sample following data</a></li><li class="subsection"><a href="following-users.html#sec-stats_and_a_follow_form"><span class="number">11.2.2</span> Stats and a follow form</a></li><li class="subsection"><a href="following-users.html#sec-following_and_followers_pages"><span class="number">11.2.3</span> Following and followers pages</a></li><li class="subsection"><a href="following-users.html#sec-a_working_follow_button_the_standard_way"><span class="number">11.2.4</span> A working follow button the standard way</a></li><li class="subsection"><a href="following-users.html#sec-a_working_follow_button_with_ajax"><span class="number">11.2.5</span> A working follow button with Ajax</a></li></ol></li><li class="section"><a href="following-users.html#sec-the_status_feed"><span class="number">11.3</span> The status feed</a></li><li><ol><li class="subsection"><a href="following-users.html#sec-motivation_and_strategy"><span class="number">11.3.1</span> Motivation and strategy</a></li><li class="subsection"><a href="following-users.html#sec-a_first_feed_implementation"><span class="number">11.3.2</span> A first feed implementation</a></li><li class="subsection"><a href="following-users.html#sec-scopes_subselects_and_a_lambda"><span class="number">11.3.3</span> Subselects</a></li><li class="subsection"><a href="following-users.html#sec-the_new_status_feed"><span class="number">11.3.4</span> The new status feed</a></li></ol></li><li class="section"><a href="following-users.html#sec-following_conclusion"><span class="number">11.4</span> Conclusion</a></li><li><ol><li class="subsection"><a href="following-users.html#sec-extensions_to_the_sample_application"><span class="number">11.4.1</span> Extensions to the sample application</a></li><li><ol><li class="subsubsection"><a href="following-users.html#sec-replies">Replies</a></li><li class="subsubsection"><a href="following-users.html#sec-messaging">Messaging</a></li><li class="subsubsection"><a href="following-users.html#sec-follower_notifications">Follower notifications</a></li><li class="subsubsection"><a href="following-users.html#sec-password_reminders">Password reminders</a></li><li class="subsubsection"><a href="following-users.html#sec-signup_confirmation">Signup confirmation</a></li><li class="subsubsection"><a href="following-users.html#sec-rss_feed">RSS feed</a></li><li class="subsubsection"><a href="following-users.html#sec-rest_api">REST API</a></li><li class="subsubsection"><a href="following-users.html#sec-search">Search</a></li></ol></li><li class="subsection"><a href="following-users.html#sec-guide_to_further_resources"><span class="number">11.4.2</span> Guide to further resources</a></li></ol></li><li class="section"><a href="following-users.html#sec-following_exercises"><span class="number">11.5</span> Exercises</a></li></ol></li><li class="chapter"><a href="supplement.html#top"><span class="number">Chapter 12</span> Rails 4.0 supplement</a></li><li><ol><li class="section"><a href="supplement.html#sec-upgrading_from_rails_3_2_to_4_0"><span class="number">12.1</span> Upgrading from Rails 3.2 to 4.0</a></li><li><ol><li class="subsection"><a href="supplement.html#sec-rails_4_0_setup"><span class="number">12.1.1</span> Rails 4.0 setup</a></li><li class="subsection"><a href="supplement.html#sec-getting_to_green"><span class="number">12.1.2</span> Getting to green</a></li><li class="subsection"><a href="supplement.html#sec-some_specific_issues"><span class="number">12.1.3</span> Some specific issues</a></li><li><ol><li class="subsubsection"><a href="supplement.html#sec-models">Models</a></li><li class="subsubsection"><a href="supplement.html#sec-controllers_and_views">Controllers and views</a></li></ol></li><li class="subsection"><a href="supplement.html#sec-finishing_up"><span class="number">12.1.4</span> Finishing up</a></li><li class="subsection"><a href="supplement.html#sec-additional_resources"><span class="number">12.1.5</span> Additional resources</a></li></ol></li><li class="section"><a href="supplement.html#sec-strong_parameters"><span class="number">12.2</span> Strong parameters</a></li><li class="section"><a href="supplement.html#sec-security_updates"><span class="number">12.3</span> Security updates</a></li><li><ol><li class="subsection"><a href="supplement.html#sec-secret_key"><span class="number">12.3.1</span> Secret key</a></li><li class="subsection"><a href="supplement.html#sec-encrypted_remember_tokens"><span class="number">12.3.2</span> Hashed remember tokens</a></li></ol></li></ol></li></ol></div>
<div id="main_content"></div>
<p> <span class="preamble">
<span id="foreword">
<strong> Foreword</strong> <br />
</span>
</span></p>
<p>My former company (CD Baby) was one of the first to loudly switch to Ruby on Rails, and then even more loudly switch back to PHP (Google me to read about the drama). This book by Michael Hartl came so highly recommended that I had to try it, and the <em>Ruby on Rails Tutorial</em> is what I used to switch back to Rails again.</p>
<p>Though I’ve worked my way through many Rails books, this is the one that finally made me “get” it. Everything is done very much “the Rails way”—a way that felt very unnatural to me before, but now after doing this book finally feels natural. This is also the only Rails book that does test-driven development the entire time, an approach highly recommended by the experts but which has never been so clearly demonstrated before. Finally, by including Git, GitHub, and Heroku in the demo examples, the author really gives you a feel for what it’s like to do a real-world project. The tutorial’s code examples are not in isolation.</p>
<p>The linear narrative is such a great format. Personally, I powered through the <em>Rails Tutorial</em> in three long days, doing all the examples and challenges at the end of each chapter. Do it from start to finish, without jumping around, and you’ll get the ultimate benefit.</p>
<p>Enjoy!</p>
<p><a href="http://sivers.org/">Derek Sivers</a> (<a href="http://sivers.org/">sivers.org</a>) <br />
<em>Founder, CD Baby</em> <br /></p>
<p> <span class="preamble">
<strong> Acknowledgments</strong> <br />
</span></p>
<p>The <em>Ruby on Rails Tutorial</em> owes a lot to my previous Rails book, <em>RailsSpace</em>, and hence to my coauthor <a href="http://aure.com/">Aurelius Prochazka</a>. I’d like to thank Aure both for the work he did on that book and for his support of this one. I’d also like to thank Debra Williams Cauley, my editor on both <em>RailsSpace</em> and the <em>Ruby on Rails Tutorial</em>; as long as she keeps taking me to baseball games, I’ll keep writing books for her.</p>
<p>I’d like to acknowledge a long list of Rubyists who have taught and inspired me over the years: David Heinemeier Hansson, Yehuda Katz, Carl Lerche, Jeremy Kemper, Xavier Noria, Ryan Bates, Geoffrey Grosenbach, Peter Cooper, Matt Aimonetti, Gregg Pollack, Wayne E. Seguin, Amy Hoy, Dave Chelimsky, Pat Maddox, Tom Preston-Werner, Chris Wanstrath, Chad Fowler, Josh Susser, Obie Fernandez, Ian McFarland, Steven Bristol, Pratik Naik, Sarah Mei, Sarah Allen, Wolfram Arnold, Alex Chaffee, Giles Bowkett, Evan Dorn, Long Nguyen, James Lindenbaum, Adam Wiggins, Tikhon Bernstam, Ron Evans, Wyatt Greene, Miles Forrest, the good people at Pivotal Labs, the Heroku gang, the thoughtbot guys, and the GitHub crew. Finally, many, many readers—far too many to list—have contributed a huge number of bug reports and suggestions during the writing of this book, and I gratefully acknowledge their help in making it as good as it can be. <br /></p>
<p> <span class="preamble">
<span id="author">
<strong> About the author</strong> <br />
</span>
</span></p>
<p><a href="http://michaelhartl.com/">Michael Hartl</a> is the author of the <a href="http://ruby.railstutorial.org/"><em>Ruby on Rails Tutorial</em></a>, the leading introduction to web development with <a href="http://rubyonrails.org/">Ruby on Rails</a>. His prior experience includes writing and developing <em>RailsSpace</em>, an extremely obsolete Rails tutorial book, and developing Insoshi, a once-popular and now-obsolete social networking platform in Ruby on Rails. In 2011, Michael received a <a href="http://rubyheroes.com/heroes">Ruby Hero Award</a> for his contributions to the Ruby community. He is a graduate of <a href="http://college.harvard.edu/">Harvard College</a>, has a <a href="http://resolver.caltech.edu/CaltechETD:etd-05222003-161626">Ph.D. in Physics</a> from <a href="http://www.caltech.edu/">Caltech</a>, and is an alumnus of the <a href="http://ycombinator.com/">Y Combinator</a> entrepreneur program. <br /></p>
<p> <span id="license" class="preamble">
<strong> Copyright and license</strong> <br />
</span></p>
<p><em>Ruby on Rails Tutorial: Learn Web Development with Rails</em>. Copyright © 2012 by Michael Hartl. All source code in the <em>Ruby on Rails Tutorial</em> is available jointly under the <a href="http://www.opensource.org/licenses/mit-license.php">MIT License</a> and the <a href="http://people.freebsd.org/~phk/">Beerware License</a>.</p>
<div class="code"><div class="highlight"><pre>The MIT License
Copyright (c) 2012 Michael Hartl
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
</pre></div>
</div>
<div class="code"><div class="highlight"><pre>/*
* ----------------------------------------------------------------------------
* "THE BEER-WARE LICENSE" (Revision 42):
* Michael Hartl wrote this code. As long as you retain this notice you
* can do whatever you want with this stuff. If we meet some day, and you think
* this stuff is worth it, you can buy me a beer in return.
* ----------------------------------------------------------------------------
*/
</pre></div>
</div>
<div id="top"></div>
<h1 class="chapter"><a id="sec-6" href="modeling-users.html#top" class="heading"><span class="number">Chapter 6</span> Modeling users</a></h1>
<p>In <a class="ref" href="filling-in-the-layout.html#top">Chapter 5</a>, we ended with a stub page for creating new users (<a class="ref" href="filling-in-the-layout.html#sec-user_signup">Section 5.4</a>); over the course of the next four chapters, we’ll fulfill the promise implicit in this incipient signup page. The first critical step is to create a <em>data model</em> for users of our site, together with a way to store that data. In <a class="ref" href="sign-up.html#top">Chapter 7</a>, we’ll give users the ability to sign up for our site and create a user profile page. Once users can sign up, we’ll let them sign in and sign out as well (<a class="ref" href="sign-in-sign-out.html#top">Chapter 8</a>), and in <a class="ref" href="updating-showing-and-deleting-users.html#top">Chapter 9</a> (<a class="ref" href="updating-showing-and-deleting-users.html#sec-requiring_signed_in_users">Section 9.2.1</a>) we’ll learn how to protect pages from improper access. Taken together, the material in <a class="ref" href="modeling-users.html#top">Chapter 6</a> through <a class="ref" href="updating-showing-and-deleting-users.html#top">Chapter 9</a> develops a full Rails login and authentication system. As you may know, there are various pre-built authentication solutions for Rails; <a class="ref" href="modeling-users.html#sidebar-roll_your_own">Box 6.1</a> explains why, at least at first, it’s probably a better idea to roll your own.</p>
<p>This is a long and action-packed chapter, and you may find it unusually challenging, especially if you are new to data modeling. By the end of it, though, we will have created an industrial-strength system for validating, storing, and retrieving user information.</p>
<div class="label" id="sidebar-roll_your_own"></div>
<div class="sidebar"><span class="title"><span class="header">Box 6.1.</span><span class="description">Roll your own authentication system</span></span>
<p>Virtually all web applications require a login and authentication system of some sort. As a result, most web frameworks have a plethora of options for implementing such systems, and Rails is no exception. Examples of authentication and authorization systems include <a href="http://github.com/thoughtbot/clearance">Clearance</a>, <a href="http://github.com/binarylogic/authlogic">Authlogic</a>, <a href="http://github.com/plataformatec/devise">Devise</a>, and <a href="http://railscasts.com/episodes/192-authorization-with-cancan">CanCan</a> (as well as non-Rails-specific solutions built on top of <a href="http://en.wikipedia.org/wiki/OpenID">OpenID</a> or <a href="http://en.wikipedia.org/wiki/Oauth">OAuth</a>). It’s reasonable to ask why we should reinvent the wheel. Why not just use an off-the-shelf solution instead of rolling our own?</p>
<p>For one, practical experience shows that authentication on most sites requires extensive customization, and modifying a third-party product is often more work than writing the system from scratch. In addition, off-the-shelf systems can be “black boxes”, with potentially mysterious innards; when you write your own system, you are far more likely to understand it. Moreover, recent additions to Rails (<a class="ref" href="modeling-users.html#sec-adding_a_secure_password">Section 6.3</a>) make it easy to write a custom authentication system. Finally, if you <em>do</em> end up using a third-party system later on, you’ll be in a much better position to understand and modify it if you’ve first built one yourself.</p>
</div>
<p>As usual, if you’re following along using Git for version control, now would be a good time to make a topic branch for modeling users:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> git checkout master
<span class="gp">$</span> git checkout -b modeling-users
</pre></div>
</div>
<p>(The first line here is just to make sure that you start on the master branch, so that the <code>modeling-users</code> topic branch is based on <code>master</code>. You can skip that command if you’re already on the master branch.)</p>
<div class="label" id="sec-user_model"></div>
<h2><a id="sec-6_1" href="modeling-users.html#sec-user_model" class="heading"><span class="number">6.1</span> User model</a></h2>
<p>Although the ultimate goal of the next three chapters is to make a signup page for our site (mocked up in <a class="ref" href="modeling-users.html#fig-signup_mockup_preview">Figure 6.1</a>), it would do little good now to accept information for new users: we don’t currently have any place to put it. Thus, the first step in signing up users is to make a data structure to capture and store their information.</p>
<div class="label" id="fig-signup_mockup_preview"></div>
<div class="figure"><div class="center"><span class="graphic"><img src="images/figures/signup_mockup_bootstrap.png" alt="signup_mockup_bootstrap" /></span></div><div class="caption"><span class="header">Figure 6.1: </span><span class="description">A mockup of the user signup page. <a href="http://railstutorial.org/images/figures/signup_mockup_bootstrap-full.png">(full size)</a></span></div></div>
<p>In Rails, the default data structure for a data model is called, naturally enough, a <em>model</em> (the M in MVC from <a class="ref" href="beginning.html#sec-mvc">Section 1.2.6</a>). The default Rails solution to the problem of persistence is to use a <em>database</em> for long-term data storage, and the default library for interacting with the database is called <em>Active Record</em>.<sup class="footnote" id="fnref-6_1"><a href="#fn-6_1">1</a></sup> Active Record comes with a host of methods for creating, saving, and finding data objects, all without having to use the structured query language (SQL)<sup class="footnote" id="fnref-6_2"><a href="#fn-6_2">2</a></sup> used by <a href="http://en.wikipedia.org/wiki/Relational_database">relational databases</a>. Moreover, Rails has a feature called <em>migrations</em> to allow data definitions to be written in pure Ruby, without having to learn an SQL data definition language (DDL). The effect is that Rails insulates you almost entirely from the details of the data store. In this book, by using SQLite for development and PostgreSQL (via Heroku) for deployment (<a class="ref" href="beginning.html#sec-deploying">Section 1.4</a>), we have developed this theme even further, to the point where we barely ever have to think about how Rails stores data, even for production applications.</p>
<div class="label" id="sec-database_migrations"></div>
<h3><a id="sec-6_1_1" href="modeling-users.html#sec-database_migrations" class="heading"><span class="number">6.1.1</span> Database migrations</a></h3>
<p>You may recall from <a class="ref" href="rails-flavored-ruby.html#sec-a_user_class">Section 4.4.5</a> that we have already encountered, via a custom-built <code>User</code> class, user objects with <code>name</code> and <code>email</code> attributes. That class served as a useful example, but it lacked the critical property of <em>persistence</em>: when we created a User object at the Rails console, it disappeared as soon as we exited. Our goal in this section is to create a model for users that won’t disappear quite so easily.</p>
<p>As with the User class in <a class="ref" href="rails-flavored-ruby.html#sec-a_user_class">Section 4.4.5</a>, we’ll start by modeling a user with two attributes, a <code>name</code> and an <code>email</code> address, the latter of which we’ll use as a unique username.<sup class="footnote" id="fnref-6_3"><a href="#fn-6_3">3</a></sup> (We’ll add an attribute for passwords in <a class="ref" href="modeling-users.html#sec-adding_a_secure_password">Section 6.3</a>.) In <a class="ref" href="rails-flavored-ruby.html#code-example_user">Listing 4.9</a>, we did this with Ruby’s <code>attr_accessor</code> method:</p>
<div class="code"><div class="highlight"><pre><span class="k">class</span> <span class="nc">User</span>
<span class="kp">attr_accessor</span> <span class="ss">:name</span><span class="p">,</span> <span class="ss">:email</span>
<span class="o">.</span>
<span class="o">.</span>
<span class="o">.</span>
<span class="k">end</span>
</pre></div>
</div>
<p>In contrast, when using Rails to model users we don’t need to identify the attributes explicitly. As noted briefly above, to store data Rails uses a relational database by default, which consists of <em>tables</em> composed of data <em>rows</em>, where each row has <em>columns</em> of data attributes. For example, to store users with names and email addresses, we’ll create a <code>users</code> table with <code>name</code> and <code>email</code> columns (with each row corresponding to one user). By naming the columns in this way, we’ll let Active Record figure out the User object attributes for us.</p>
<p>Let’s see how this works. (If this discussion gets too abstract for your taste, be patient; the console examples starting in <a class="ref" href="modeling-users.html#sec-creating_user_objects">Section 6.1.3</a> and the database browser screenshots in <a class="ref" href="modeling-users.html#fig-sqlite_database_browser">Figure 6.3</a> and <a class="ref" href="modeling-users.html#fig-sqlite_user_row">Figure 6.6</a> should make things clearer.) You may recall from <a class="ref" href="filling-in-the-layout.html#code-generate_users_controller">Listing 5.28</a> that we created a Users controller (along with a <code>new</code> action) using the command</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> rails generate controller Users new --no-test-framework
</pre></div>
</div>
<p>There is an analogous command for making a model: <code>generate model</code>. <a class="ref" href="modeling-users.html#code-generate_user_model">Listing 6.1</a> shows the command to generate a User model with two attributes, <code>name</code> and <code>email</code>.</p>
<div class="label" id="code-generate_user_model"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.1.</span> <span class="description">Generating a User model.</span> </div>
<div class="code"><div class="highlight"><pre>$ rails generate model User name:string email:string
invoke active_record
create db/migrate/[timestamp]_create_users.rb
create app/models/user.rb
invoke rspec
create spec/models/user_spec.rb
</pre></div>
</div></div>
<p>(Note that, in contrast to the plural convention for controller names, model names are singular: a Users controller, but a User model.) By passing the optional parameters <code>name:string</code> and <code>email:string</code>, we tell Rails about the two attributes we want, along with what types those attributes should be (in this case, <code>string</code>). Compare this with including the action names in <a class="ref" href="static-pages.html#code-generating_pages">Listing 3.4</a> and <a class="ref" href="filling-in-the-layout.html#code-generate_users_controller">Listing 5.28</a>.</p>
<p>One of the results of the <code>generate</code> command in <a class="ref" href="modeling-users.html#code-generate_user_model">Listing 6.1</a> is a new file called a <em>migration</em>. Migrations provide a way to alter the structure of the database incrementally, so that our data model can adapt to changing requirements. In the case of the User model, the migration is created automatically by the model generation script; it creates a <code>users</code> table with two columns, <code>name</code> and <code>email</code>, as shown in <a class="ref" href="modeling-users.html#code-users_migration">Listing 6.2</a>. (We’ll see in <a class="ref" href="modeling-users.html#sec-uniqueness_validation">Section 6.2.5</a> and again in <a class="ref" href="modeling-users.html#sec-adding_a_secure_password">Section 6.3</a> how to make a migration from scratch.)</p>
<div class="label" id="code-users_migration"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.2.</span> <span class="description">Migration for the User model (to create a <code>users</code> table). <br /> <code>db/migrate/[timestamp]_create_users.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="k">class</span> <span class="nc">CreateUsers</span> <span class="o"><</span> <span class="ss">ActiveRecord::Migration</span>
<span class="k">def</span> <span class="nf">change</span>
<span class="n">create_table</span> <span class="ss">:users</span> <span class="k">do</span> <span class="o">|</span><span class="n">t</span><span class="o">|</span>
<span class="n">t</span><span class="o">.</span><span class="n">string</span> <span class="ss">:name</span>
<span class="n">t</span><span class="o">.</span><span class="n">string</span> <span class="ss">:email</span>
<span class="n">t</span><span class="o">.</span><span class="n">timestamps</span>
<span class="k">end</span>
<span class="k">end</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>Note that the name of the migration file is prefixed by a <em>timestamp</em> based on when the migration was generated. In the early days of migrations, the filenames were prefixed with incrementing integers, which caused conflicts for collaborating teams if multiple programmers had migrations with the same number. Barring the improbable scenario of migrations generated the same second, using timestamps conveniently avoids such collisions.</p>
<p>The migration itself consists of a <code>change</code> method that determines the change to be made to the database. In the case of <a class="ref" href="modeling-users.html#code-users_migration">Listing 6.2</a>, <code>change</code> uses a Rails method called <code>create_table</code> to create a <em>table</em> in the database for storing users. The <code>create_table</code> method accepts a block (<a class="ref" href="rails-flavored-ruby.html#sec-blocks">Section 4.3.2</a>) with one block variable, in this case called <code>t</code> (for “table”). Inside the block, the <code>create_table</code> method uses the <code>t</code> object to create <code>name</code> and <code>email</code> columns in the database, both of type <code>string</code>.<sup class="footnote" id="fnref-6_4"><a href="#fn-6_4">4</a></sup> Here the table name is plural (<code>users</code>) even though the model name is singular (User), which reflects a linguistic convention followed by Rails: a model represents a single user, whereas a database table consists of many users. The final line in the block, <code>t.timestamps</code>, is a special command that creates two <em>magic columns</em> called <code>created_at</code> and <code>updated_at</code>, which are timestamps that automatically record when a given user is created and updated. (We’ll see concrete examples of the magic columns starting in <a class="ref" href="modeling-users.html#sec-creating_user_objects">Section 6.1.3</a>.) The full data model represented by this migration is shown in <a class="ref" href="modeling-users.html#fig-user_model_initial">Figure 6.2</a>.</p>
<div class="label" id="fig-user_model_initial"></div>
<div class="figure"><div class="center"><span class="graphic"><img src="images/figures/user_model_initial.png" alt="user_model_initial" /></span></div><div class="caption"><span class="header">Figure 6.2: </span><span class="description">The users data model produced by <a class="ref" href="modeling-users.html#code-users_migration">Listing 6.2</a>.</span></div></div>
<p>We can run the migration, known as “migrating up”, using the <code>rake</code> command (<a class="ref" href="a-demo-app.html#sidebar-rake">Box 2.1</a>) as follows:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> bundle <span class="nb">exec </span>rake db:migrate
</pre></div>
</div>
<p>(You may recall that we ran this command once before, in <a class="ref" href="a-demo-app.html#sec-demo_users_resource">Section 2.2</a>.) The first time <code>db:migrate</code> is run, it creates a file called <code>db/development.sqlite3</code>, which is an <a href="http://sqlite.org/">SQLite</a><sup class="footnote" id="fnref-6_5"><a href="#fn-6_5">5</a></sup> database. We can see the structure of the database using the excellent <a href="http://sourceforge.net/projects/sqlitebrowser/">SQLite Database Browser</a> to open the <code>db/development.sqlite3</code> file (<a class="ref" href="modeling-users.html#fig-sqlite_database_browser">Figure 6.3</a>); compare with the diagram in <a class="ref" href="modeling-users.html#fig-user_model_initial">Figure 6.2</a>. You might note that there’s one column in <a class="ref" href="modeling-users.html#fig-sqlite_database_browser">Figure 6.3</a> not accounted for in the migration: the <code>id</code> column. As noted briefly in <a class="ref" href="a-demo-app.html#sec-demo_users_resource">Section 2.2</a>, this column is created automatically, and is used by Rails to identify each row uniquely.</p>
<div class="label" id="fig-sqlite_database_browser"></div>
<div class="figure"><div class="center"><span class="graphic"><img src="images/figures/sqlite_database_browser.png" alt="sqlite_database_browser" /></span></div><div class="caption"><span class="header">Figure 6.3: </span><span class="description">The <a href="http://sqlitebrowser.sourceforge.net/">SQLite Database Browser</a> with our new <code>users</code> table. <a href="http://railstutorial.org/images/figures/sqlite_database_browser-full.png">(full size)</a></span></div></div>
<p>Most migrations, including all the ones in the <em>Rails Tutorial</em>, are <em>reversible</em>, which means we can “migrate down” and undo them with a single Rake task, called <code>db:rollback</code>:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> bundle <span class="nb">exec </span>rake db:rollback
</pre></div>
</div>
<p>(See <a class="ref" href="static-pages.html#sidebar-undoing_things">Box 3.1</a> for another technique useful for reversing migrations.) Under the hood, this command executes the <code>drop_table</code> command to remove the users table from the database. The reason this works is that the <code>change</code> method knows that <code>drop_table</code> is the inverse of <code>create_table</code>, which means that the rollback migration can be easily inferred. In the case of an irreversible migration, such as one to remove a database column, it is necessary to define separate <code>up</code> and <code>down</code> methods in place of the single <code>change</code> method. Read about <a href="http://guides.rubyonrails.org/migrations.html">migrations in the Rails Guides</a> for more information.</p>
<p>If you rolled back the database, migrate up again before proceeding:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> bundle <span class="nb">exec </span>rake db:migrate
</pre></div>
</div>
<div class="label" id="sec-the_model_file"></div>
<h3><a id="sec-6_1_2" href="modeling-users.html#sec-the_model_file" class="heading"><span class="number">6.1.2</span> The model file</a></h3>
<p>We’ve seen how the User model generation in <a class="ref" href="modeling-users.html#code-generate_user_model">Listing 6.1</a> generated a migration file (<a class="ref" href="modeling-users.html#code-users_migration">Listing 6.2</a>), and we saw in <a class="ref" href="modeling-users.html#fig-sqlite_database_browser">Figure 6.3</a> the results of running this migration: it updated a file called <code>development.sqlite3</code> by creating a table <code>users</code> with columns <code>id</code>, <code>name</code>, <code>email</code>, <code>created_at</code>, and <code>updated_at</code>. <a class="ref" href="modeling-users.html#code-generate_user_model">Listing 6.1</a> also created the model itself; the rest of this section is dedicated to understanding it.</p>
<p>We begin by looking at the code for the User model, which lives in the file <code>user.rb</code> inside the <code>app/models/</code> directory. It is, to put it mildly, very compact (<a class="ref" href="modeling-users.html#code-raw_user_model">Listing 6.3</a>). (<em>Note</em>: The <code>attr_accessible</code> line will not appear if you are using Rails 3.2.2 or earlier. In this case, you should add it in <a class="ref" href="modeling-users.html#sec-accessible_attributes">Section 6.1.2.2</a>.)</p>
<div class="label" id="code-raw_user_model"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.3.</span> <span class="description">The brand new User model. <br /> <code>app/models/user.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="k">class</span> <span class="nc">User</span> <span class="o"><</span> <span class="ss">ActiveRecord::Base</span>
<span class="n">attr_accessible</span> <span class="ss">:name</span><span class="p">,</span> <span class="ss">:email</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>Recall from <a class="ref" href="rails-flavored-ruby.html#sec-a_class_of_our_own">Section 4.4.2</a> that the syntax <code>class User < ActiveRecord::Base</code> means that the <code>User</code> class <em>inherits</em> from <code>ActiveRecord::Base</code>, so that the User model automatically has all the functionality of the <code>ActiveRecord::Base</code> class. Of course, knowledge of this inheritance doesn’t do any good unless we know what <code>ActiveRecord::Base</code> contains, and we’ll get a first look momentarily. Before we move on, though, there are two tasks to complete.</p>
<div class="label" id="sec-model_annotation"></div>
<h4><a id="sec-6_1_2_1" href="modeling-users.html#sec-model_annotation" class="heading">Model annotation</a></h4>
<p>Although it’s not strictly necessary, you might find it convenient to <em>annotate</em> your Rails models using the <code>annotate</code> gem (<a class="ref" href="modeling-users.html#code-gemfile_annotate">Listing 6.4</a>).</p>
<div class="label" id="code-gemfile_annotate"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.4.</span> <span class="description">Adding the <code>annotate</code> gem to the <code>Gemfile</code>.</span> </div>
<div class="code"><div class="highlight"><pre><span class="n">source</span> <span class="s1">'https://rubygems.org'</span>
<span class="o">.</span>
<span class="o">.</span>
<span class="o">.</span>
<span class="n">group</span> <span class="ss">:development</span><span class="p">,</span> <span class="ss">:test</span> <span class="k">do</span>
<span class="n">gem</span> <span class="s1">'sqlite3'</span><span class="p">,</span> <span class="s1">'1.3.5'</span>
<span class="n">gem</span> <span class="s1">'rspec-rails'</span><span class="p">,</span> <span class="s1">'2.11.0'</span>
<span class="k">end</span>
<span class="n">group</span> <span class="ss">:development</span> <span class="k">do</span>
<span class="n">gem</span> <span class="s1">'annotate'</span><span class="p">,</span> <span class="s1">'2.5.0'</span>
<span class="k">end</span>
<span class="n">group</span> <span class="ss">:test</span> <span class="k">do</span>
<span class="o">.</span>
<span class="o">.</span>
<span class="o">.</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>(We place the <code>annotate</code> gem in a <code>group :development</code> block (analogous to <code>group :test</code>) because the annotations aren’t needed in production applications.) We next install it with <code>bundle install</code>:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> bundle install
</pre></div>
</div>
<p>This gives us a command called <code>annotate</code>, which simply adds comments containing the data model to the model file:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> bundle <span class="nb">exec </span>annotate
<span class="go">Annotated (1): User</span>
</pre></div>
</div>
<p>The results appear in <a class="ref" href="modeling-users.html#code-annotated_user_model">Listing 6.5</a>.</p>
<div class="label" id="code-annotated_user_model"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.5.</span> <span class="description">The annotated User model. <br /> <code>app/models/user.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="c1"># == Schema Information</span>
<span class="c1">#</span>
<span class="c1"># Table name: users</span>
<span class="c1">#</span>
<span class="c1"># id :integer not null, primary key</span>
<span class="c1"># name :string(255)</span>
<span class="c1"># email :string(255)</span>
<span class="c1"># created_at :datetime</span>
<span class="c1"># updated_at :datetime</span>
<span class="c1">#</span>
<span class="k">class</span> <span class="nc">User</span> <span class="o"><</span> <span class="ss">ActiveRecord::Base</span>
<span class="n">attr_accessible</span> <span class="ss">:name</span><span class="p">,</span> <span class="ss">:email</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>I find that having the data model visible in the model files helps remind me which attributes the model has, but future code listings will omit the annotations for brevity. (Note that, if you want your annotations to be up-to-date, you’ll have to run <code>annotate</code> again any time the data model changes.)</p>
<div class="label" id="sec-accessible_attributes"></div>
<h4><a id="sec-6_1_2_2" href="modeling-users.html#sec-accessible_attributes" class="heading">Accessible attributes</a></h4>
<p>Let’s revisit the User model, focusing now on the <code>attr_accessible</code> line (<a class="ref" href="modeling-users.html#code-attr_accessible">Listing 6.6</a>). This line tells Rails which attributes of the model are <em>accessible</em>, i.e., which attributes can be modified automatically by outside users (such as users submitting requests with web browsers).</p>
<div class="label" id="code-attr_accessible"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.6.</span> <span class="description">Making the <code>name</code> and <code>email</code> attributes accessible. <br /> <code>app/models/user.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="k">class</span> <span class="nc">User</span> <span class="o"><</span> <span class="ss">ActiveRecord::Base</span>
<span class="n">attr_accessible</span> <span class="ss">:name</span><span class="p">,</span> <span class="ss">:email</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>The code in <a class="ref" href="modeling-users.html#code-attr_accessible">Listing 6.6</a> doesn’t do quite what you might think. By default, <em>all</em> model attributes are accessible. What <a class="ref" href="modeling-users.html#code-attr_accessible">Listing 6.6</a> does is to ensure that the <code>name</code> and <code>email</code> attributes—and <em>only</em> the <code>name</code> and <code>email</code> attributes—are automatically accessible to outside users. We’ll see why this is important in <a class="ref" href="updating-showing-and-deleting-users.html#top">Chapter 9</a>: using <code>attr_accessible</code> is important for preventing a <em>mass assignment</em> vulnerability, a distressingly common and often serious security hole in many Rails applications.</p>
<div class="label" id="sec-creating_user_objects"></div>
<h3><a id="sec-6_1_3" href="modeling-users.html#sec-creating_user_objects" class="heading"><span class="number">6.1.3</span> Creating user objects</a></h3>
<p>We’ve done some good prep work, and now it’s time to cash in and learn about Active Record by playing with our newly created User model. As in <a class="ref" href="rails-flavored-ruby.html#top">Chapter 4</a>, our tool of choice is the Rails console. Since we don’t (yet) want to make any changes to our database, we’ll start the console in a <em>sandbox</em>:</p>
<div class="code"><div class="highlight"><pre><span class="go">$ rails console --sandbox</span>
<span class="go">Loading development environment in sandbox</span>
<span class="go">Any modifications you make will be rolled back on exit</span>
<span class="go">>></span>
</pre></div>
</div>
<p>As indicated by the helpful message “Any modifications you make will be rolled back on exit”, when started in a sandbox the console will “roll back” (i.e., undo) any database changes introduced during the session.</p>
<p>In the console session in <a class="ref" href="rails-flavored-ruby.html#sec-a_user_class">Section 4.4.5</a>, we created a new user object with <code>User.new</code>, which we had access to only after requiring the example user file in <a class="ref" href="rails-flavored-ruby.html#code-example_user">Listing 4.9</a>. With models, the situation is different; as you may recall from <a class="ref" href="rails-flavored-ruby.html#sec-a_controller_class">Section 4.4.4</a>, the Rails console automatically loads the Rails environment, which includes the models. This means that we can make a new user object without any further work:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="no">User</span><span class="o">.</span><span class="n">new</span>
<span class="go">=> #<User id: nil, name: nil, email: nil, created_at: nil, updated_at: nil></span>
</pre></div>
</div>
<p>We see here the default console representation of a user object, which prints out the same attributes shown in <a class="ref" href="modeling-users.html#fig-user_model_initial">Figure 6.2</a> and <a class="ref" href="modeling-users.html#code-annotated_user_model">Listing 6.5</a>.</p>
<p>When called with no arguments, <code>User.new</code> returns an object with all <code>nil</code> attributes. In <a class="ref" href="rails-flavored-ruby.html#sec-a_user_class">Section 4.4.5</a>, we designed the example User class to take an <em>initialization hash</em> to set the object attributes; that design choice was motivated by Active Record, which allows objects to be initialized in the same way:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">user</span> <span class="o">=</span> <span class="no">User</span><span class="o">.</span><span class="n">new</span><span class="p">(</span><span class="nb">name</span><span class="p">:</span> <span class="s2">"Michael Hartl"</span><span class="p">,</span> <span class="ss">email:</span> <span class="s2">"[email protected]"</span><span class="p">)</span>
<span class="go">=> #<User id: nil, name: "Michael Hartl", email: "[email protected]",</span>
<span class="go">created_at: nil, updated_at: nil></span>
</pre></div>
</div>
<p>Here we see that the name and email attributes have been set as expected.</p>
<p>If you’ve been tailing the development log, you may have noticed that no new lines have shown up yet. This is because calling <code>User.new</code> doesn’t touch the database; it simply creates a new Ruby object in memory. To save the user object to the database, we call the <code>save</code> method on the <code>user</code> variable:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">save</span>
<span class="go">=> true</span>
</pre></div>
</div>
<p>The <code>save</code> method returns <code>true</code> if it succeeds and <code>false</code> otherwise. (Currently, all saves should succeed; we’ll see cases in <a class="ref" href="modeling-users.html#sec-user_validations">Section 6.2</a> when some will fail.) As soon as you save, you should see a line in the development log with the SQL command to <code>INSERT INTO "users"</code>. Because of the many methods supplied by Active Record, we won’t ever need raw SQL in this book, and I’ll omit discussion of the SQL commands from now on. But you can learn a lot by watching the log.</p>
<p>You may have noticed that the new user object had <code>nil</code> values for the <code>id</code> and the magic columns <code>created_at</code> and <code>updated_at</code> attributes. Let’s see if our <code>save</code> changed anything:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">user</span>
<span class="go">=> #<User id: 1, name: "Michael Hartl", email: "[email protected]",</span>
<span class="go">created_at: "2011-12-05 00:57:46", updated_at: "2011-12-05 00:57:46"></span>
</pre></div>
</div>
<p>We see that the <code>id</code> has been assigned a value of <code>1</code>, while the magic columns have been assigned the current time and date.<sup class="footnote" id="fnref-6_6"><a href="#fn-6_6">6</a></sup> Currently, the created and updated timestamps are identical; we’ll see them differ in <a class="ref" href="modeling-users.html#sec-updating_user_objects">Section 6.1.5</a>.</p>
<p>As with the User class in <a class="ref" href="rails-flavored-ruby.html#sec-a_user_class">Section 4.4.5</a>, instances of the User model allow access to their attributes using a dot notation:<sup class="footnote" id="fnref-6_7"><a href="#fn-6_7">7</a></sup></p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">name</span>
<span class="go">=> "Michael Hartl"</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">email</span>
<span class="go">=> "[email protected]"</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">updated_at</span>
<span class="go">=> Tue, 05 Dec 2011 00:57:46 UTC +00:00</span>
</pre></div>
</div>
<p>As we’ll see in <a class="ref" href="sign-up.html#top">Chapter 7</a>, it’s often convenient to make and save a model in two steps as we have above, but Active Record also lets you combine them into one step with <code>User.create</code>:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="no">User</span><span class="o">.</span><span class="n">create</span><span class="p">(</span><span class="nb">name</span><span class="p">:</span> <span class="s2">"A Nother"</span><span class="p">,</span> <span class="ss">email:</span> <span class="s2">"[email protected]"</span><span class="p">)</span>
<span class="go">#<User id: 2, name: "A Nother", email: "[email protected]", created_at:</span>
<span class="go">"2011-12-05 01:05:24", updated_at: "2011-12-05 01:05:24"></span>
<span class="gp">>> </span><span class="n">foo</span> <span class="o">=</span> <span class="no">User</span><span class="o">.</span><span class="n">create</span><span class="p">(</span><span class="nb">name</span><span class="p">:</span> <span class="s2">"Foo"</span><span class="p">,</span> <span class="ss">email:</span> <span class="s2">"[email protected]"</span><span class="p">)</span>
<span class="go">#<User id: 3, name: "Foo", email: "[email protected]", created_at: "2011-12-05</span>
<span class="go">01:05:42", updated_at: "2011-12-05 01:05:42"></span>
</pre></div>
</div>
<p>Note that <code>User.create</code>, rather than returning <code>true</code> or <code>false</code>, returns the User object itself, which we can optionally assign to a variable (such as <code>foo</code> in the second command above).</p>
<p>The inverse of <code>create</code> is <code>destroy</code>:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">foo</span><span class="o">.</span><span class="n">destroy</span>
<span class="go">=> #<User id: 3, name: "Foo", email: "[email protected]", created_at: "2011-12-05</span>
<span class="go">01:05:42", updated_at: "2011-12-05 01:05:42"></span>
</pre></div>
</div>
<p>Oddly, <code>destroy</code>, like <code>create</code>, returns the object in question, though I can’t recall ever having used the return value of <code>destroy</code>. Even odder, perhaps, is that the <code>destroy</code>ed object still exists in memory:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">foo</span>
<span class="go">=> #<User id: 3, name: "Foo", email: "[email protected]", created_at: "2011-12-05</span>
<span class="go">01:05:42", updated_at: "2011-12-05 01:05:42"></span>
</pre></div>
</div>
<p>How do we know if we really destroyed an object? And for saved and non-destroyed objects, how can we retrieve users from the database? It’s time to learn how to use Active Record to find user objects.</p>
<div class="label" id="sec-finding_user_objects"></div>
<h3><a id="sec-6_1_4" href="modeling-users.html#sec-finding_user_objects" class="heading"><span class="number">6.1.4</span> Finding user objects</a></h3>
<p>Active Record provides several options for finding objects. Let’s use them to find the first user we created while verifying that the third user (<code>foo</code>) has been destroyed. We’ll start with the existing user:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="no">User</span><span class="o">.</span><span class="n">find</span><span class="p">(</span><span class="mi">1</span><span class="p">)</span>
<span class="go">=> #<User id: 1, name: "Michael Hartl", email: "[email protected]",</span>
<span class="go">created_at: "2011-12-05 00:57:46", updated_at: "2011-12-05 00:57:46"></span>
</pre></div>
</div>
<p>Here we’ve passed the id of the user to <code>User.find</code>; Active Record returns the user with that id.</p>
<p>Let’s see if the user with an <code>id</code> of <code>3</code> still exists in the database:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="no">User</span><span class="o">.</span><span class="n">find</span><span class="p">(</span><span class="mi">3</span><span class="p">)</span>
<span class="go">ActiveRecord::RecordNotFound: Couldn't find User with ID=3</span>
</pre></div>
</div>
<p>Since we destroyed our third user in <a class="ref" href="modeling-users.html#sec-creating_user_objects">Section 6.1.3</a>, Active Record can’t find it in the database. Instead, <code>find</code> raises an <em>exception</em>, which is a way of indicating an exceptional event in the execution of a program—in this case, a nonexistent Active Record id, which causes <code>find</code> to raise an <code>ActiveRecord::RecordNotFound</code> exception.<sup class="footnote" id="fnref-6_8"><a href="#fn-6_8">8</a></sup></p>
<p>In addition to the generic <code>find</code>, Active Record also allows us to find users by specific attributes:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="no">User</span><span class="o">.</span><span class="n">find_by_email</span><span class="p">(</span><span class="s2">"[email protected]"</span><span class="p">)</span>
<span class="go">=> #<User id: 1, name: "Michael Hartl", email: "[email protected]",</span>
<span class="go">created_at: "2011-12-05 00:57:46", updated_at: "2011-12-05 00:57:46"></span>
</pre></div>
</div>
<p>The <code>find_by_email</code> method is automatically created by Active Record based on the <code>email</code> attribute in the <code>users</code> table. (As you might guess, Active Record creates a <code>find_by_name</code> method as well.) Since we will be using email addresses as usernames, this sort of <code>find</code> will be useful when we learn how to let users sign in to our site (<a class="ref" href="sign-up.html#top">Chapter 7</a>). If you’re worried that <code>find_by_email</code> will be inefficient if there are a large number of users, you’re ahead of the game; we’ll cover this issue, and its solution via database indices, in <a class="ref" href="modeling-users.html#sec-uniqueness_validation">Section 6.2.5</a>.</p>
<p>We’ll end with a couple of more general ways of finding users. First, there’s <code>first</code>:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="no">User</span><span class="o">.</span><span class="n">first</span>
<span class="go">=> #<User id: 1, name: "Michael Hartl", email: "[email protected]",</span>
<span class="go">created_at: "2011-12-05 00:57:46", updated_at: "2011-12-05 00:57:46"></span>
</pre></div>
</div>
<p>Naturally, <code>first</code> just returns the first user in the database. There’s also <code>all</code>:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="no">User</span><span class="o">.</span><span class="n">all</span>
<span class="go">=> [#<User id: 1, name: "Michael Hartl", email: "[email protected]",</span>
<span class="go">created_at: "2011-12-05 00:57:46", updated_at: "2011-12-05 00:57:46">,</span>
<span class="go">#<User id: 2, name: "A Nother", email: "[email protected]", created_at:</span>
<span class="go">"2011-12-05 01:05:24", updated_at: "2011-12-05 01:05:24">]</span>
</pre></div>
</div>
<p>No prizes for inferring that <code>all</code> returns an array (<a class="ref" href="rails-flavored-ruby.html#sec-arrays_and_ranges">Section 4.3.1</a>) of all users in the database.</p>
<div class="label" id="sec-updating_user_objects"></div>
<h3><a id="sec-6_1_5" href="modeling-users.html#sec-updating_user_objects" class="heading"><span class="number">6.1.5</span> Updating user objects</a></h3>
<p>Once we’ve created objects, we often want to update them. There are two basic ways to do this. First, we can assign attributes individually, as we did in <a class="ref" href="rails-flavored-ruby.html#sec-a_user_class">Section 4.4.5</a>:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">user</span> <span class="c1"># Just a reminder about our user's attributes</span>
<span class="go">=> #<User id: 1, name: "Michael Hartl", email: "[email protected]",</span>
<span class="go">created_at: "2011-12-05 00:57:46", updated_at: "2011-12-05 00:57:46"></span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">email</span> <span class="o">=</span> <span class="s2">"[email protected]"</span>
<span class="go">=> "[email protected]"</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">save</span>
<span class="go">=> true</span>
</pre></div>
</div>
<p>Note that the final step is necessary to write the changes to the database. We can see what happens without a save by using <code>reload</code>, which reloads the object based on the database information:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">email</span>
<span class="go">=> "[email protected]"</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">email</span> <span class="o">=</span> <span class="s2">"[email protected]"</span>
<span class="go">=> "[email protected]"</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">reload</span><span class="o">.</span><span class="n">email</span>
<span class="go">=> "[email protected]"</span>
</pre></div>
</div>
<p>Now that we’ve updated the user by running <code>user.save</code>, the magic columns differ, as promised in <a class="ref" href="modeling-users.html#sec-creating_user_objects">Section 6.1.3</a>:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">created_at</span>
<span class="go">=> "2011-12-05 00:57:46"</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">updated_at</span>
<span class="go">=> "2011-12-05 01:37:32"</span>
</pre></div>
</div>
<p>The second way to update attributes is to use <code>update_attributes</code>:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">update_attributes</span><span class="p">(</span><span class="nb">name</span><span class="p">:</span> <span class="s2">"The Dude"</span><span class="p">,</span> <span class="ss">email:</span> <span class="s2">"[email protected]"</span><span class="p">)</span>
<span class="go">=> true</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">name</span>
<span class="go">=> "The Dude"</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">email</span>
<span class="go">=> "[email protected]"</span>
</pre></div>
</div>
<p>The <code>update_attributes</code> method accepts a hash of attributes, and on success performs both the update and the save in one step (returning <code>true</code> to indicate that the save went through). It’s worth noting that, once you have defined some attributes as accessible using <code>attr_accessible</code> (<a class="ref" href="modeling-users.html#sec-accessible_attributes">Section 6.1.2.2</a>), <em>only</em> those attributes can be modified using <code>update_attributes</code>. If you ever find that your models mysteriously start refusing to update certain columns, check to make sure that those columns are included in the call to <code>attr_accessible</code>.</p>
<div class="label" id="sec-user_validations"></div>
<h2><a id="sec-6_2" href="modeling-users.html#sec-user_validations" class="heading"><span class="number">6.2</span> User validations</a></h2>
<p>The User model we created in <a class="ref" href="modeling-users.html#sec-user_model">Section 6.1</a> now has working <code>name</code> and <code>email</code> attributes, but they are completely generic: any string (including an empty one) is currently valid in either case. And yet, names and email addresses are more specific than this. For example, <code>name</code> should be non-blank, and <code>email</code> should match the specific format characteristic of email addresses. Moreover, since we’ll be using email addresses as unique usernames when users sign in, we shouldn’t allow email duplicates in the database.</p>
<p>In short, we shouldn’t allow <code>name</code> and <code>email</code> to be just any strings; we should enforce certain constraints on their values. Active Record allows us to impose such constraints using <em>validations</em>. In this section, we’ll cover several of the most common cases, validating <em>presence</em>, <em>length</em>, <em>format</em> and <em>uniqueness</em>. In <a class="ref" href="modeling-users.html#sec-has_secure_password">Section 6.3.4</a> we’ll add a final common validation, <em>confirmation</em>. And we’ll see in <a class="ref" href="sign-up.html#sec-signup_failure">Section 7.3</a> how validations give us convenient error messages when users make submissions that violate them.</p>
<div class="label" id="sec-initial_user_tests"></div>
<h3><a id="sec-6_2_1" href="modeling-users.html#sec-initial_user_tests" class="heading"><span class="number">6.2.1</span> Initial user tests</a></h3>
<p>As with the other features of our sample app, we’ll add User model validations using test-driven development. Because we didn’t pass the</p>
<pre class="verbatim">--no-test-framework</pre>
<p>flag when we generated the User model (unlike, e.g., <a class="ref" href="filling-in-the-layout.html#code-generate_users_controller">Listing 5.28</a>), the command in <a class="ref" href="modeling-users.html#code-generate_user_model">Listing 6.1</a> produces an initial spec for testing users, but in this case it’s practically blank (<a class="ref" href="modeling-users.html#code-default_user_spec">Listing 6.7</a>).</p>
<div class="label" id="code-default_user_spec"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.7.</span> <span class="description">The practically blank default User spec. <br /> <code>spec/models/user_spec.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="nb">require</span> <span class="s1">'spec_helper'</span>
<span class="n">describe</span> <span class="no">User</span> <span class="k">do</span>
<span class="n">pending</span> <span class="s2">"add some examples to (or delete) </span><span class="si">#{</span><span class="bp">__FILE__</span><span class="si">}</span><span class="s2">"</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>This simply uses the <code>pending</code> method to indicate that we should fill the spec with something useful. We can see its effect by running the User model spec:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> bundle <span class="nb">exec </span>rspec spec/models/user_spec.rb
<span class="go">*</span>
<span class="go">Finished in 0.01999 seconds</span>
<span class="go">1 example, 0 failures, 1 pending</span>
<span class="go">Pending:</span>
<span class="go"> User add some examples to (or delete)</span>
<span class="go"> /Users/mhartl/rails_projects/sample_app/spec/models/user_spec.rb</span>
<span class="go"> (Not Yet Implemented)</span>
</pre></div>
</div>
<p>On many systems, pending specs will be displayed in yellow to indicate that they are in between passing (green) and failing (red).</p>
<p>We’ll follow the advice of the default spec by filling it in with some RSpec examples, shown in <a class="ref" href="modeling-users.html#code-user_spec">Listing 6.8</a>.</p>
<div class="label" id="code-user_spec"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.8.</span> <span class="description">Testing for the <code>:name</code> and <code>:email</code> attributes. <br /> <code>spec/models/user_spec.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="nb">require</span> <span class="s1">'spec_helper'</span>
<span class="n">describe</span> <span class="no">User</span> <span class="k">do</span>
<span class="n">before</span> <span class="p">{</span> <span class="vi">@user</span> <span class="o">=</span> <span class="no">User</span><span class="o">.</span><span class="n">new</span><span class="p">(</span><span class="nb">name</span><span class="p">:</span> <span class="s2">"Example User"</span><span class="p">,</span> <span class="ss">email:</span> <span class="s2">"[email protected]"</span><span class="p">)</span> <span class="p">}</span>
<span class="n">subject</span> <span class="p">{</span> <span class="vi">@user</span> <span class="p">}</span>
<span class="n">it</span> <span class="p">{</span> <span class="n">should</span> <span class="n">respond_to</span><span class="p">(</span><span class="ss">:name</span><span class="p">)</span> <span class="p">}</span>
<span class="n">it</span> <span class="p">{</span> <span class="n">should</span> <span class="n">respond_to</span><span class="p">(</span><span class="ss">:email</span><span class="p">)</span> <span class="p">}</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>The <code>before</code> block, which we saw in <a class="ref" href="filling-in-the-layout.html#code-pretty_page_tests">Listing 5.27</a>), runs the code inside the block before each example—in this case, creating a new <code>@user</code> instance variable using <code>User.new</code> and a valid initialization hash. Then</p>
<div class="code"><div class="highlight"><pre><span class="n">subject</span> <span class="p">{</span> <span class="vi">@user</span> <span class="p">}</span>
</pre></div>
</div>
<p>makes <code>@user</code> the default subject of the test example, as seen before in the context of the <code>page</code> variable in <a class="ref" href="filling-in-the-layout.html#sec-pretty_rspec">Section 5.3.4</a>.</p>
<p>The two examples in <a class="ref" href="modeling-users.html#code-user_spec">Listing 6.8</a> test for the existence of <code>name</code> and <code>email</code> attributes:</p>
<div class="code"><div class="highlight"><pre><span class="n">it</span> <span class="p">{</span> <span class="n">should</span> <span class="n">respond_to</span><span class="p">(</span><span class="ss">:name</span><span class="p">)</span> <span class="p">}</span>
<span class="n">it</span> <span class="p">{</span> <span class="n">should</span> <span class="n">respond_to</span><span class="p">(</span><span class="ss">:email</span><span class="p">)</span> <span class="p">}</span>
</pre></div>
</div>
<p>These examples implicitly use the Ruby method <code>respond_to?</code>, which accepts a symbol and returns <code>true</code> if the object responds to the given method or attribute and <code>false</code> otherwise:</p>
<div class="code"><div class="highlight"><pre><span class="go">$ rails console --sandbox</span>
<span class="gp">>> </span><span class="n">user</span> <span class="o">=</span> <span class="no">User</span><span class="o">.</span><span class="n">new</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">respond_to?</span><span class="p">(</span><span class="ss">:name</span><span class="p">)</span>
<span class="go">=> true</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">respond_to?</span><span class="p">(</span><span class="ss">:foobar</span><span class="p">)</span>
<span class="go">=> false</span>
</pre></div>
</div>
<p>(Recall from <a class="ref" href="rails-flavored-ruby.html#sec-objects_and_message_passing">Section 4.2.3</a> that Ruby uses a question mark to indicate such true/false boolean methods.) The tests themselves rely on the <em>boolean convention</em> used by RSpec: the code</p>
<div class="code"><div class="highlight"><pre><span class="vi">@user</span><span class="o">.</span><span class="n">respond_to?</span><span class="p">(</span><span class="ss">:name</span><span class="p">)</span>
</pre></div>
</div>
<p>can be tested using the RSpec code</p>
<div class="code"><div class="highlight"><pre><span class="vi">@user</span><span class="o">.</span><span class="n">should</span> <span class="n">respond_to</span><span class="p">(</span><span class="ss">:name</span><span class="p">)</span>
</pre></div>
</div>
<p>Because of <code>subject { @user }</code>, we can leave off <code>@user</code> in the test, yielding</p>
<div class="code"><div class="highlight"><pre><span class="n">it</span> <span class="p">{</span> <span class="n">should</span> <span class="n">respond_to</span><span class="p">(</span><span class="ss">:name</span><span class="p">)</span> <span class="p">}</span>
</pre></div>
</div>
<p>These kinds of tests allow us to use TDD to add new attributes and methods to our User model, and as a side-effect we get a nice specification for the methods that all <code>User</code> objects should respond to.</p>
<p>You should verify at this point that the tests fail:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> bundle <span class="nb">exec </span>rspec spec/
</pre></div>
</div>
<p>Even though we created a development database with <code>rake db:migrate</code> in <a class="ref" href="modeling-users.html#sec-database_migrations">Section 6.1.1</a>, the tests fail because the <em>test database</em> doesn’t yet know about the data model (indeed, it doesn’t yet exist at all). We can create a test database with the correct structure, and thereby get the tests to pass, using the <code>db:test:prepare</code> Rake task:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> bundle <span class="nb">exec </span>rake db:test:prepare
</pre></div>
</div>
<p>This just ensures that the data model from the development database, <code>db/development.sqlite3</code>, is reflected in the test database, <code>db/test.sqlite3</code>. Failure to run this Rake task after a migration is a common source of confusion. In addition, sometimes the test database gets corrupted and needs to be reset. If your test suite is mysteriously breaking, be sure to try running <code>rake db:test:prepare</code> to see if that fixes the problem.</p>
<div class="label" id="sec-presence_validation"></div>
<h3><a id="sec-6_2_2" href="modeling-users.html#sec-presence_validation" class="heading"><span class="number">6.2.2</span> Validating presence</a></h3>
<p>Perhaps the most elementary validation is <em>presence</em>, which simply verifies that a given attribute is present. For example, in this section we’ll ensure that both the name and email fields are present before a user gets saved to the database. In <a class="ref" href="sign-up.html#sec-signup_error_messages">Section 7.3.2</a>, we’ll see how to propagate this requirement up to the signup form for creating new users.</p>
<p>We’ll start with a test for the presence of a <code>name</code> attribute. Although the first step in TDD is to write a <em>failing</em> test (<a class="ref" href="static-pages.html#sec-TDD">Section 3.2.1</a>), in this case we don’t yet know enough about validations to write the proper test, so we’ll write the validation first, using the console to understand it. Then we’ll comment out the validation, write a failing test, and verify that uncommenting the validation gets the test to pass. This procedure may seem pedantic for such a simple test, but I have seen many “simple” tests that actually test the wrong thing; being meticulous about TDD is simply the <em>only</em> way to be confident that we’re testing the right thing. (This comment-out technique is also useful when rescuing an application whose application code is already written but—<a href="http://en.wiktionary.org/wiki/quelle_horreur"><em>quelle horreur!</em></a>—has no tests.)</p>
<p>The way to validate the presence of the name attribute is to use the <code>validates</code> method with argument <code>presence: true</code>, as shown in <a class="ref" href="modeling-users.html#code-validates_presence_of_name">Listing 6.9</a>. The <code>presence: true</code> argument is a one-element <em>options hash</em>; recall from <a class="ref" href="rails-flavored-ruby.html#sec-css_revisited">Section 4.3.4</a> that curly braces are optional when passing hashes as the final argument in a method. (As noted in <a class="ref" href="filling-in-the-layout.html#sec-adding_to_the_layout">Section 5.1.1</a>, the use of options hashes is a recurring theme in Rails.)</p>
<div class="label" id="code-validates_presence_of_name"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.9.</span> <span class="description">Validating the presence of a <code>name</code> attribute. <br /> <code>app/models/user.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="k">class</span> <span class="nc">User</span> <span class="o"><</span> <span class="ss">ActiveRecord::Base</span>
<span class="n">attr_accessible</span> <span class="ss">:name</span><span class="p">,</span> <span class="ss">:email</span>
<span class="n">validates</span> <span class="ss">:name</span><span class="p">,</span> <span class="ss">presence:</span> <span class="kp">true</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p><a class="ref" href="modeling-users.html#code-validates_presence_of_name">Listing 6.9</a> may look like magic, but <code>validates</code> is just a method, as indeed is <code>attr_accessible</code>. An equivalent formulation of <a class="ref" href="modeling-users.html#code-validates_presence_of_name">Listing 6.9</a> using parentheses is as follows:</p>
<div class="code"><div class="highlight"><pre><span class="k">class</span> <span class="nc">User</span> <span class="o"><</span> <span class="ss">ActiveRecord::Base</span>
<span class="n">attr_accessible</span><span class="p">(</span><span class="ss">:name</span><span class="p">,</span> <span class="ss">:email</span><span class="p">)</span>
<span class="n">validates</span><span class="p">(</span><span class="ss">:name</span><span class="p">,</span> <span class="ss">presence:</span> <span class="kp">true</span><span class="p">)</span>
<span class="k">end</span>
</pre></div>
</div>
<p>Let’s drop into the console to see the effects of adding a validation to our User model:<sup class="footnote" id="fnref-6_9"><a href="#fn-6_9">9</a></sup></p>
<div class="code"><div class="highlight"><pre><span class="go">$ rails console --sandbox</span>
<span class="gp">>> </span><span class="n">user</span> <span class="o">=</span> <span class="no">User</span><span class="o">.</span><span class="n">new</span><span class="p">(</span><span class="nb">name</span><span class="p">:</span> <span class="s2">""</span><span class="p">,</span> <span class="ss">email:</span> <span class="s2">"[email protected]"</span><span class="p">)</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">save</span>
<span class="go">=> false</span>
<span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">valid?</span>
<span class="go">=> false</span>
</pre></div>
</div>
<p>Here <code>user.save</code> returns <code>false</code>, indicating a failed save. In the final command, we use the <code>valid?</code> method, which returns <code>false</code> when the object fails one or more validations, and <code>true</code> when all validations pass. In this case, we only have one validation, so we know which one failed, but it can still be helpful to check using the <code>errors</code> object generated on failure:</p>
<div class="code"><div class="highlight"><pre><span class="gp">>> </span><span class="n">user</span><span class="o">.</span><span class="n">errors</span><span class="o">.</span><span class="n">full_messages</span>
<span class="go">=> ["Name can't be blank"]</span>
</pre></div>
</div>
<p>(The error message is a hint that Rails validates the presence of an attribute using the <code>blank?</code> method, which we saw at the end of <a class="ref" href="rails-flavored-ruby.html#sec-modifying_built_in_classes">Section 4.4.3</a>.)</p>
<p>Now for the failing test. To ensure that our incipient test will fail, let’s comment out the validation at this point (<a class="ref" href="modeling-users.html#code-commented_out_validation">Listing 6.10</a>).</p>
<div class="label" id="code-commented_out_validation"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.10.</span> <span class="description">Commenting out a validation to ensure a failing test. <br /> <code>app/models/user.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="k">class</span> <span class="nc">User</span> <span class="o"><</span> <span class="ss">ActiveRecord::Base</span>
<span class="n">attr_accessible</span> <span class="ss">:name</span><span class="p">,</span> <span class="ss">:email</span>
<span class="c1"># validates :name, presence: true</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>The initial validation tests then appear as in <a class="ref" href="modeling-users.html#code-failing_validates_name_spec">Listing 6.11</a>.</p>
<div class="label" id="code-failing_validates_name_spec"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.11.</span> <span class="description">A failing test for validation of the <code>name</code> attribute. <br /> <code>spec/models/user_spec.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="nb">require</span> <span class="s1">'spec_helper'</span>
<span class="n">describe</span> <span class="no">User</span> <span class="k">do</span>
<span class="n">before</span> <span class="k">do</span>
<span class="vi">@user</span> <span class="o">=</span> <span class="no">User</span><span class="o">.</span><span class="n">new</span><span class="p">(</span><span class="nb">name</span><span class="p">:</span> <span class="s2">"Example User"</span><span class="p">,</span> <span class="ss">email:</span> <span class="s2">"[email protected]"</span><span class="p">)</span>
<span class="k">end</span>
<span class="n">subject</span> <span class="p">{</span> <span class="vi">@user</span> <span class="p">}</span>
<span class="n">it</span> <span class="p">{</span> <span class="n">should</span> <span class="n">respond_to</span><span class="p">(</span><span class="ss">:name</span><span class="p">)</span> <span class="p">}</span>
<span class="n">it</span> <span class="p">{</span> <span class="n">should</span> <span class="n">respond_to</span><span class="p">(</span><span class="ss">:email</span><span class="p">)</span> <span class="p">}</span>
<span class="n">it</span> <span class="p">{</span> <span class="n">should</span> <span class="n">be_valid</span> <span class="p">}</span>
<span class="n">describe</span> <span class="s2">"when name is not present"</span> <span class="k">do</span>
<span class="n">before</span> <span class="p">{</span> <span class="vi">@user</span><span class="o">.</span><span class="n">name</span> <span class="o">=</span> <span class="s2">" "</span> <span class="p">}</span>
<span class="n">it</span> <span class="p">{</span> <span class="n">should_not</span> <span class="n">be_valid</span> <span class="p">}</span>
<span class="k">end</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>The first new example is just a sanity check, verifying that the <code>@user</code> object is initially valid:</p>
<div class="code"><div class="highlight"><pre><span class="n">it</span> <span class="p">{</span> <span class="n">should</span> <span class="n">be_valid</span> <span class="p">}</span>
</pre></div>
</div>
<p>This is another example of the RSpec boolean convention we saw in <a class="ref" href="modeling-users.html#sec-initial_user_tests">Section 6.2.1</a>: whenever an object responds to a boolean method <code>foo?</code>, there is a corresponding test method called <code>be_foo</code>. In this case, we can test the result of calling</p>
<div class="code"><div class="highlight"><pre><span class="vi">@user</span><span class="o">.</span><span class="n">valid?</span>
</pre></div>
</div>
<p>with</p>
<div class="code"><div class="highlight"><pre><span class="vi">@user</span><span class="o">.</span><span class="n">should</span> <span class="n">be_valid</span>
</pre></div>
</div>
<p>As before, <code>subject { @user }</code> lets us leave off <code>@user</code>, yielding</p>
<div class="code"><div class="highlight"><pre><span class="n">it</span> <span class="p">{</span> <span class="n">should</span> <span class="n">be_valid</span> <span class="p">}</span>
</pre></div>
</div>
<p>The second test first sets the user’s name to an invalid (blank) value, and then tests to see that the resulting <code>@user</code> object is invalid:</p>
<div class="code"><div class="highlight"><pre><span class="n">describe</span> <span class="s2">"when name is not present"</span> <span class="k">do</span>
<span class="n">before</span> <span class="p">{</span> <span class="vi">@user</span><span class="o">.</span><span class="n">name</span> <span class="o">=</span> <span class="s2">" "</span> <span class="p">}</span>
<span class="n">it</span> <span class="p">{</span> <span class="n">should_not</span> <span class="n">be_valid</span> <span class="p">}</span>
<span class="k">end</span>
</pre></div>
</div>
<p>This uses a <code>before</code> block to set the user’s name to an invalid (blank) value and then checks that the resulting user object is not valid.</p>
<p>You should verify that the tests fail at this point:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> bundle <span class="nb">exec </span>rspec spec/models/user_spec.rb
<span class="go">...F</span>
<span class="go">4 examples, 1 failure</span>
</pre></div>
</div>
<p>Now uncomment the validation (i.e., revert <a class="ref" href="modeling-users.html#code-commented_out_validation">Listing 6.10</a> back to <a class="ref" href="modeling-users.html#code-validates_presence_of_name">Listing 6.9</a>) to get the tests to pass:</p>
<div class="code"><div class="highlight"><pre><span class="gp">$</span> bundle <span class="nb">exec </span>rspec spec/models/user_spec.rb
<span class="go">....</span>
<span class="go">4 examples, 0 failures</span>
</pre></div>
</div>
<p>Of course, we also want to validate the presence of email addresses. The test (<a class="ref" href="modeling-users.html#code-validates_email_spec">Listing 6.12</a>) is analogous to the one for the <code>name</code> attribute.</p>
<div class="label" id="code-validates_email_spec"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.12.</span> <span class="description">A test for presence of the <code>email</code> attribute. <br /> <code>spec/models/user_spec.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="nb">require</span> <span class="s1">'spec_helper'</span>
<span class="n">describe</span> <span class="no">User</span> <span class="k">do</span>
<span class="n">before</span> <span class="k">do</span>
<span class="vi">@user</span> <span class="o">=</span> <span class="no">User</span><span class="o">.</span><span class="n">new</span><span class="p">(</span><span class="nb">name</span><span class="p">:</span> <span class="s2">"Example User"</span><span class="p">,</span> <span class="ss">email:</span> <span class="s2">"[email protected]"</span><span class="p">)</span>
<span class="k">end</span>
<span class="o">.</span>
<span class="o">.</span>
<span class="o">.</span>
<span class="n">describe</span> <span class="s2">"when email is not present"</span> <span class="k">do</span>
<span class="n">before</span> <span class="p">{</span> <span class="vi">@user</span><span class="o">.</span><span class="n">email</span> <span class="o">=</span> <span class="s2">" "</span> <span class="p">}</span>
<span class="n">it</span> <span class="p">{</span> <span class="n">should_not</span> <span class="n">be_valid</span> <span class="p">}</span>
<span class="k">end</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>The implementation is also virtually the same, as seen in <a class="ref" href="modeling-users.html#code-validates_presence_of_email">Listing 6.13</a>.</p>
<div class="label" id="code-validates_presence_of_email"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.13.</span> <span class="description">Validating the presence of the <code>name</code> and <code>email</code> attributes. <br /> <code>app/models/user.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="k">class</span> <span class="nc">User</span> <span class="o"><</span> <span class="ss">ActiveRecord::Base</span>
<span class="n">attr_accessible</span> <span class="ss">:name</span><span class="p">,</span> <span class="ss">:email</span>
<span class="n">validates</span> <span class="ss">:name</span><span class="p">,</span> <span class="ss">presence:</span> <span class="kp">true</span>
<span class="n">validates</span> <span class="ss">:email</span><span class="p">,</span> <span class="ss">presence:</span> <span class="kp">true</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>Now all the tests should pass, and the presence validations are complete.</p>
<div class="label" id="sec-length_validation"></div>
<h3><a id="sec-6_2_3" href="modeling-users.html#sec-length_validation" class="heading"><span class="number">6.2.3</span> Length validation</a></h3>
<p>We’ve constrained our User model to require a name for each user, but we should go further: the user’s names will be displayed on the sample site, so we should enforce some limit on their length. With all the work we did in <a class="ref" href="modeling-users.html#sec-presence_validation">Section 6.2.2</a>, this step is easy.</p>
<p>We start with a test. There’s no science to picking a maximum length; we’ll just pull <code>50</code> out of thin air as a reasonable upper bound, which means verifying that names of <code>51</code> characters are too long (<a class="ref" href="modeling-users.html#code-length_validation_test">Listing 6.14</a>).</p>
<div class="label" id="code-length_validation_test"></div>
<div class="codelisting">
<div class="listing"><span class="header">Listing 6.14.</span> <span class="description">A test for <code>name</code> length validation. <br /> <code>spec/models/user_spec.rb</code></span> </div>
<div class="code"><div class="highlight"><pre><span class="nb">require</span> <span class="s1">'spec_helper'</span>
<span class="n">describe</span> <span class="no">User</span> <span class="k">do</span>
<span class="n">before</span> <span class="k">do</span>
<span class="vi">@user</span> <span class="o">=</span> <span class="no">User</span><span class="o">.</span><span class="n">new</span><span class="p">(</span><span class="nb">name</span><span class="p">:</span> <span class="s2">"Example User"</span><span class="p">,</span> <span class="ss">email:</span> <span class="s2">"[email protected]"</span><span class="p">)</span>
<span class="k">end</span>
<span class="o">.</span>
<span class="o">.</span>
<span class="o">.</span>
<span class="n">describe</span> <span class="s2">"when name is too long"</span> <span class="k">do</span>
<span class="n">before</span> <span class="p">{</span> <span class="vi">@user</span><span class="o">.</span><span class="n">name</span> <span class="o">=</span> <span class="s2">"a"</span> <span class="o">*</span> <span class="mi">51</span> <span class="p">}</span>
<span class="n">it</span> <span class="p">{</span> <span class="n">should_not</span> <span class="n">be_valid</span> <span class="p">}</span>
<span class="k">end</span>
<span class="k">end</span>
</pre></div>
</div></div>
<p>For convenience, we’ve used “string multiplication” in <a class="ref" href="modeling-users.html#code-length_validation_test">Listing 6.14</a> to make a string 51 characters long. We can see how this works using the console:</p>