Best practice for setting not accesible attributes in model

RicardoGV Posted by RicardoGV on July 10, 2012

Hi all! I'm a newbie to Rails, and I was thinking in a good solution to set protected attributes in my models before saving them, but I can't find out a proper way of doing it. Lets say I have Users, who belong to Companies, and these companies can have many Clients. Before saving a new Client, I want to set its company_id, getting it from the current_user's company_id that is stored in the session (I'm using Devise). I was thinking about using a model callback, as before_create or whatever, but I then I realized that my Rspec model tests may fail, because there will be no current_user while running them... Is there a best practice of setting this parameters that have to be set automatically? Thanks in advance!


zamith Answered by zamith on September 29, 2012

You could use a before_save callback and mock the current_user in the RSpec tests, but I don't think it's a really good practice to access the session from you model.

In this case I would do this in the controller before calling the save method.

In a more general case, it would depend on the amount of code you need to run and if it is duplicated a lot. I believe there are three options here:

  1. You extract the code into a private method in the controller and use it wherever it is necessary
  2. If the operations do not concern the actual saving of the object (as sending an email) but have to be done across controllers, then you should create a method in the model that does this and call where needed
  3. Lastly, you can use a callback in the model.

Notice that callbacks should be use carefully since they can disrupt the logic of your application, because when you call save on object you expect it to be saved, not to be saved and deliver an email, for example. This can lead to hard to maintain code.