In this conclusion to a four-part series covering security for a Ruby on Rails ecommerce application, you'll learn how to protect the application against SQL injection, cross-site request forgery, and more. This article is excerpted from chapter eight of the book Practical Rails Projects, written by Eldon Alameda (Apress; ISBN: 1590597818).
Now suppose the malicious user submits this form to your standard registration action, which has something like this in it:
@user = User.create(params[:user])
This way, he might end up being an admin user.
It is fairly easy to protect against this type of manipulation in Rails. Just define sensitive attributes as protected:
class User < Activerecord::Base attr_protected :accepted, :admin end
Now these variables cannot be mass-assigned with a parameters hash like the one in the preceding example. However, you can still set them individually when needed:
@user.accepted = true
Another vulnerability raises its ugly head when you let users edit their information; for example, with URLs likehttp://www.domain.com/posts/edit/28. It wonít take long before someone notices that by changing the last part of the URL, she can get access to posts created by other people. You can protect your application from this by always getting to the objects through the logged-in user:
# BAD @post = Post.find(params[:id]) # GOOD @post = current_user.posts.find(params[:id])
If someone now tries to access a post that doesnít belong to her, anActiveRecord::RecordNotFoundexception is raised, which you can then rescue and show a Not Found page to the user:
rescue ActiveRecord::RecordNotFound return render(:template => "/shared/404", :status => 404) end