Hacker News new | past | comments | ask | show | jobs | submit login
Ruby on Rails Tutorial Chapter 12 is out (railstutorial.org)
67 points by mhartl on May 26, 2010 | hide | past | favorite | 29 comments



This is an awesome tutorial not just for programmers new to Rails, but also people new to programming and web development. I'm glad you gave an overview of editors, IDEs, version control, and all the other tools associated with development that you usually don't see mentioned in programming books.


I couldn't agree more. This is _the_ place to go for learning Rails _and_ about other programming must-haves.


This tutorial is great.

One question for experienced Rails folks:

I noticed that a lot of the test code seems to be somewhat redundant and not actually testing many different paths of execution.

E.g. I saw a lot of test cases like this in his examples:

  it "should be successful" do
    get :new
    response.should be_success
  end

  it "should have a follower attribute" do
    @relationship.should respond_to(:follower)
  end

  it "should have a followers method" do
    @user.should respond_to(:followers)
  end

  it "should render the home page" do
    post :create, :micropost => @attr
    response.should render_template('pages/home')
  end
Writing a unit test that verifies that some object has a new method/attribute that you're about to add to it, or that some request returns a 200 OK, or that some request renders a specific template? It all seems very...boilerplate to me.

Is this a common practice?


This is a good question, and I actually just added a footnote yesterday to address it. The deal is that, when doing test-driven development, you often bounce back and forth between test and application code, like this:

  it "should be successful" do
    get :new
    response.should be_success
  end

Then

  def new
  
  end
Next you'd add a test for what the 'new' action actually does, and then get the 'new' action to do it.

In a book, interleaving the test and application code like this is rather cumbersome. The real payoff to this approach will be in the upcoming screencast series (http://www.railstutorial.org/screencasts), which will allow me to interleave the tests and application code much more finely. Together with Autotest continuous testing and Growl notifications, the screencasts will show just how addictive TDD can be.

I should probably motivate this practice better in the book, because it is counter-intuitive. In fact, I thought this technique was crazy when I first saw it. (The same goes for TDD in general.) But it's amazing how much easier it is to get started on a method when the first step is "make sure the method is there". Indeed, such tests aren't really designed to make the application better-tested; they're designed to help the programmer stay in the zone.

That being said, there probably are some places where such fine-grained tests aren't worth the trouble, or might even be confusing. I'm about to embark on a Rails 3 update of the book, so I'll keep my eye out for tests that should be removed. If you have any suggestions for tests that should be on the chopping block, please let me know (http://www.railstutorial.org/feedback).


I guess my question is whether that type of testing is worthwhile. It seems to create a lot of brittle test cases where renaming or moving something can cause a bunch of tests to break, creating extra maintenance overhead, while not actually telling you all that much.


I've taken a run at this, and I can't find any tests that obviously need to go. In many cases, some tests aren't strictly necessary, but they do make clearer what the code is supposed to do. Indeed, they often bring to mind the maxim from Structure and Interpretation of Computer Programs:

  Programs should be written for people to read,
  and only incidentally for machines to execute.
(That's a bit of an over-statement, of course, but its spirit is true.)

I also reevaluated the code for possible implementation lock-down. It looks like most such cases involve standard REST action names, such as new and show, or other aspects of the application that are unlikely to change.

In the end, you'll have to develop a style that works for you. The code presented in the book is based on the style I've developed in my own work and from reading the code of others, but there are as many styles as there are Rails developers. My job is to help get you on the road to finding a style of your own.


I think people are still figuring this out. You're right that tests sometimes lock down the implementation a bit much. I'll be on the lookout for changing practices and update the tutorial accordingly.


I've gone through 9 chapters of this tutorial, but I don't know if I want to finish it. The first few chapters were great and a lot of fun. Michael removed a lot of magic that I never understood. But I suppose my worries are irreconcilable: Michael attempts to please both programmers and non-programmers at the same time.

For example, I enjoyed things such as Figure 2.11 (a detailed explanation of MVC in Rails), but then Michael flashes through Ruby in Chapter 4. I understood it because I'm a programmer, but I don't know if any of the other target audiences would.

And as the tutorial progressed, I felt that Michael explained concepts and topics less and less.

For example, for user sign-in/out, another Rails book simply insert a session[:user_id] = @user.id, but Michael goes through the trouble of creating a new User.remeber_token field (Chapter 9). Why?

Security? Surely not, since he previously explained that cookies are checksumed to make sure that it was not tampered with on the client side. Efficiency? Nope. The session[:user_id] = @user.id is more efficient.

Then there are also other quirks such as modifying the Users table everytime the user logs in (it calls User.remember_me!). (I might be wrong about this, please check me).

I started this tutorial to remove some magic fairy dust from my eyes, but I'm afraid it has blinded me even more.

Michael, I'd really appreciate it if you could answer some of my questions.

NOTE: I've played around w/ RoR before, but not much.


I think that as the tutorial progresses, the number of potential confusions increases combinatorially. I've done my best to answer them in the text, but given the broad audience for the book it's hard to anticipate all possible questions.

I'll do my best to answer your questions. The session[:user_id] solution you mention only persists over one session, i.e., if a user closes his browser, his session is lost. The tutorial's remember token, on the other hand, persists even after the browser is closed. Once you have a persistent cookie, though, you have a potential security breach. The reason a persistent cookie can't just be the user id is because it can be trivially spoofed: if you can simulate a cookie with id 17 (not hard with, e.g., Perl, Python, or Ruby), you can log in as user 17. That would be a Bad Thing™. By hashing the user id with a salt, we avoid this problem. I've made a note to motivate the remember token better in the tutorial.

Saving the user on each login is correct; it's needed to change the remember token for security purposes. That the remember token doesn't currently change on each login is a bug in the tutorial, and I'll fix it ASAP (probably tomorrow). (The id-salt hash should also include a timestamp.)

Finally, Rails does have a lot of magic, which is a source of its power but is also a potential stumbling block. The Rails Tutorial book is designed not to remove fairy dust but rather to teach you how to use it—mainly because most Rails application developers never need to know what's behind the curtain. (Indeed, in many cases I don't know, nor do I particularly care. After all, Ruby is mostly written in C, but you don't have to dig into the C source to use Ruby.) If you're a pull-back-the-curtain kind of guy, I recommend The Rails Way as a companion volume to Rails Tutorial.

You've raised some good issues here. Let me know if you have any other suggestions: http://www.railstutorial.org/feedback


You can configure cookie-based sessions to be persistent.

http://api.rubyonrails.org/classes/ActionController/Session/...

For rails 3 in config/initializers/session_store.rb

    Rails.application.config.session_store :cookie_store, :key => '_session', :expire_after => 2.weeks


I'll take a look at this. I know that Rails 3 has a new way of doing things, but every Rails 2.3.x authentication system I've seen uses some kind of remember token. Maybe we're all just doing it wrong. :-)

Update: I don't see any way to persist the session variable (where do the options go in session[:user_id] = user.id?), and I'm a little nervous about doing so, since the whole point of a session is that it doesn't persist. I'll stick with cookies for now. The Rails 3 version of the tutorial will probably use "permanent" cookies as per this blog post: http://m.onkey.org/2010/2/5/signed-and-permanent-cookies-in-...


Well I did roll my own signed cookies using http://gist.github.com/416030

Just a note, that cookie is used by created by rails and used dokuwiki using a custom authenication class I made. (dokuwiki verifies the signing)


Thanks for the reply. I am now at peace and can continue the tutorial.

But a question. I guess I don't fully comprehend Rails sessions, but if you try to spoof user 17, wouldn't Rails notice this due to the cookie checksum?


If you have 17 in the session, you're protected, but I think once it's in a persistent cookie you're in trouble.


I've fixed the cookie/remember token issues in Chapter 9. See especially

http://www.railstutorial.org/chapters/sign-in-sign-out#sideb...

and the material surrounding

http://www.railstutorial.org/chapters/sign-in-sign-out#code:...


I've added a box in Chapter 9 addressing some of your concerns:

http://www.railstutorial.org/chapters/sign-in-sign-out#sideb...

Thanks again for bringing this to my attention! :-)


Here's a direct link to the new chapter:

http://www.railstutorial.org/chapters/following-users#top


Great work! This tutorial is a huge asset to the Rails community.


Thanks! Glad you like it. :-)


I've been through the tutorial using Rails 2.x and also 3beta. The tests don't all work in 3beta but in case you're wondering, yes, you can almost the entire app in 3.0. It is indeed a wonderful thing and Michael has, I think, become one of the largest gems in the Rails community with this contribution.

-- Fred


I think this tutorial is THE place to start to learn rails.


This is an awesome tutorial one of the best I have seen in quite a while. This book is highly addictive.


What's the best way to send you feedback from a non hardcore programmer perspective on a chapter by chapter basis? I am very much enjoying your book and wanted to contribute back.


There's a feedback link in the top menu of the website and also on the right sidebar. In the PDF, each page has a feedback link in the footer. Or just click here: http://www.railstutorial.org/feedback


I'm working through this now. As an experienced ASP.Net developer it's a great intro to how things are done in the Rails world.


Any plans on releasing PolyTeXnic soon(ish)?


(N.B. For those who don't know, PolyTeXnic is the markup system (built on top of LaTeX) used to produce the Ruby on Rails Tutorial book.)

There's a lot of prepwork to be done before PolyTeXnic is ready for release—among other things, I want to write some good documentation first, which IMHO is important for an open-source project but takes a lot of time—so it won't be available soon(ish). More like eventually(ish). :-)


Are you still planning to release screencasts as part of railstutorial?


Indeed I am! Sign up for an email notification at http://www.railstutorial.org/screencasts :-)




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: