9

I have a simple question. I have a seriaizer that looks like this:

class GroupSerializer < ActiveModel::Serializer
  attributes :id, :name, :about, :city 
end

The problem is that, whenever I change my model, I have to add/remove attributes from this serializer. I just want to get the whole object by default as in the default rails json respond:

render json: @group

How can I do that?

Kevin Jalbert
  • 3,115
  • 3
  • 26
  • 39
Salah Saleh
  • 793
  • 9
  • 29
  • Can you tell about more.. what is the problem. Did you mean, you don't want to put attributes names _manually_ like this `attributes :id, :name, :about, :city ` ? – Arup Rakshit Mar 27 '15 at 11:27
  • yes, exactly. I just want the whole object to return by default. I want also to exclude things if required. – Salah Saleh Mar 27 '15 at 11:30

5 Answers5

18

At least on 0.8.2 of ActiveModelSerializers you can use the following:

class GroupSerializer < ActiveModel::Serializer
  def attributes
    object.attributes.symbolize_keys
  end
end

Be carful with this though as it will add every attribute that your object has attached to it. You probably will want to put in some filtering logic on your serializer to prevent sensitive information from being shown (i.e., encrypted passwords, etc...)

This does not address associations, although with a little digging around you could probably implement something similar.

============================================================

UPDATE: 01/12/2016

On 0.10.x version of ActiveModelSerializers, attributes receives two arguments by default. I added *args to avoid exception:

class GroupSerializer < ActiveModel::Serializer
  def attributes(*args)
    object.attributes.symbolize_keys
  end
end
adriancm
  • 5
  • 2
Kevin Jalbert
  • 3,115
  • 3
  • 26
  • 39
  • 1
    How do I get all attributes + few more? `key = object.attributes.symbolize_keys` `key[:one_more] = 'haha'` like this? – NamNamNam Sep 15 '18 at 05:20
  • 1
    @NamNamNam this worked for me: def attributes(*_args) object.attributes.symbolize_keys.merge(one_more: 'haha') end – dbeachy1 Aug 12 '19 at 22:15
1

Just to add to @kevin's answer. I was looking also to how to add filters on the returned attributes. I looked to the the documentation active_model_serializers 0.9 and it does support filters that looks like this:

  def attributes
    object.attributes.symbolize_keys
  end
  def filter(keys)
          keys - [:author, :id]
  end

I tried it, but it did not work. I assumed that's because the attributes are not specified explicitly. I had to do it the same way specified in the rails cast to work:

@@except=[:author, :id]
def attributes
    data = object.attributes.symbolize_keys
    @@except.each { |e| data.delete e  }
    data
end
Salah Saleh
  • 793
  • 9
  • 29
0

Try the following to get all the attribute keys for the Group class:

Group.new.attributes.keys

For example, I get the following for users on one app:

> User.new.attributes.keys
=> ["id", "password_digest", "auth_token", "password_reset_token", "password_reset_requested_at", "created_at", "updated_at"]
Prakash Murthy
  • 12,923
  • 3
  • 46
  • 74
0

On 0.10.x version of ActiveModelSerializers, attributes receives two arguments by default. I added *args to avoid exception:

class GroupSerializer < ActiveModel::Serializer
  def attributes(*args)
    object.attributes.symbolize_keys
  end
end
adriancm
  • 5
  • 2
0

I want get all attributes + few more.

base on answer above, this work:

class NotificationSerializer < ActiveModel::Serializer

def actor
  'asdasd'
end

def attributes(*args)
  keys = object.attributes
  keys[:actor] = actor()  # add attribute here
  keys.symbolize_keys
end

end

NamNamNam
  • 1,190
  • 3
  • 13
  • 22