How does `only:` at `before_action` work in Rails?

Option :only runs a method, ':set_newsletter_email' in this example, when any of the action defined in the list in square brackets [:show, :edit, :update, :destroy] is called in the current controller and runs before the actions is run. Any other action defined in the controller will not execute :set_newsletter_email method.

You can also do the opposite with :except option to define method that will run on every actions defined in the controller except the one's that are listed.

You can also do after_action that will run after the action in the controller

You can read about the filters and all the options here: http://guides.rubyonrails.org/action_controller_overview.html#filters


The only option of before_action defines one action OR a list of actions when the method/block will be executed first.

Ex:

# defined actions: [:show, :edit, :update, :destroy]
before_action :set_newsletter_email, only: [:show, :edit]

The set_newsletter_email method will be called just before the show and edit actions.


The opposite option except define when NOT to execute the method/block.

# defined actions: [:show, :edit, :update, :destroy]
before_action :set_newsletter_email, except: [:show, :edit]

The set_newsletter_email method will be called for all existing actions EXCEPT show and edit.


only / except is just a kind of whitelist/blacklist.


When a user navigates only to those routes, it will trigger the :set_newsletter_email function, usually at the end of that controller file.

So when the user navigates to the index method, it will not trigger it because :set_newsletter_email is only called for the methods on brackets.

In this case that callback is needed because it sets the resource in the single resource views before it is rendered.

For example:

/newsletter/2 route will trigger the :set_newsletter_email that will first get the id from the link params and then it will look for the resource and set an instance variable with it.

I don't know what is your concern about security in this case, but this callback only gets the id param to set the resource and because you're using scaffolds it also generates a params function (also at the end of the file) that whitelists the parameters you defined earlier while generating the scaffold.

You can find more info here: http://api.rubyonrails.org/classes/AbstractController/Callbacks/ClassMethods.html

If you want me to explain more or clarify something just ask 👍🏼