How to pass variables to ActiveModel Serializers from the controller

Sometimes, when you’re building a Ruby on Rails API with Serializers, you want to pass a variable into the serializer from the controller - in this example, we want to pass in the search query.

If we have a serializer like this:

class ReviewSerializer < ActiveModel::Serializer
  attributes :overall_review, :author_name
end

and our controller like this:

def search
  @results = Reviews.where(author_name: params[:author_name])
  render json: @results, each_serializer: ReviewSerializer
end

This gets JSON responses like this:

[
  {
    "overall_review": "Terrible book. Don't read. Ever",
    "author_name": "George Brown"
  }
]

In order to get our search query to show up in the JSON response, we need to add it to the scope. To do that, lets modify our controller like this:

  render json: @results, each_serializer: ReviewSerializer, scope: {
    'search_query': params[:author_name]
  }

Then, modify the ReviewSerializer to look like this:

class ReviewSerializer < ActiveModel::Serializer
  attributes :overall_review, :author_name, :search_query

  def search_query
    return scope[:search_query]
  end
end

And then the JSON response will look like this:

[
  {
    "overall_review": "Terrible book. Don't read. Ever",
    "author_name": "George Brown",
    "search_query": "George Brown"
  }
]

I hope this is useful to pass parameters into your serializers from the controller (or really, wherever you are serializing data!)

The code for this is available on GitHub.

Want more like this? Join the email list and get it delivered right to your inbox!