From 489ebf21321a5a8043c1f4581454b0784180eaac Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Wojciech=20Wn=C4=99trzak?= Date: Sat, 20 Apr 2013 23:52:43 +0200 Subject: [PATCH] Added support for :only and :except methods. It is possible now to filter returned attributes and associations by: UserSerializer.new(user, only: [:first_name, :last_name]) UserSerializer.new(user, except: :first_name) --- lib/active_model/serializer.rb | 2 ++ test/serializer_test.rb | 59 +++++++++++++++++++++++++++++++--- 2 files changed, 56 insertions(+), 5 deletions(-) diff --git a/lib/active_model/serializer.rb b/lib/active_model/serializer.rb index 9fa00404..5e1c69ea 100644 --- a/lib/active_model/serializer.rb +++ b/lib/active_model/serializer.rb @@ -363,6 +363,8 @@ module ActiveModel end def include?(name) + return false if options.key?(:only) && !Array(options[:only]).include?(name) + return false if options.key?(:except) && Array(options[:except]).include?(name) send INCLUDE_METHODS[name] end diff --git a/test/serializer_test.rb b/test/serializer_test.rb index 3a47a395..a5d514e4 100644 --- a/test/serializer_test.rb +++ b/test/serializer_test.rb @@ -1349,7 +1349,7 @@ class SerializerTest < ActiveModel::TestCase ] }, actual) end - + def test_inheritance_does_not_used_cached_attributes parent = Class.new(ActiveModel::Serializer) do attributes :title @@ -1359,18 +1359,18 @@ class SerializerTest < ActiveModel::TestCase attributes :body end - data_class = Class.new do + data_class = Class.new do attr_accessor :title, :body end - item = data_class.new + item = data_class.new item.title = "title" item.body = "body" 2.times do - assert_equal({:title => "title"}, + assert_equal({:title => "title"}, parent.new(item).attributes) - assert_equal({:body => "body", :title => "title"}, + assert_equal({:body => "body", :title => "title"}, child.new(item).attributes) end @@ -1390,4 +1390,53 @@ class SerializerTest < ActiveModel::TestCase a_serializer = serializer.new(post, :scope => user, :scope_name => :current_user) assert a_serializer.has_permission? end + + def test_only_option_filters_attributes_and_associations + post = Post.new(:title => "New Post", :body => "Body of new post") + comments = [Comment.new(:title => "Comment1")] + post.comments = comments + + post_serializer = PostSerializer.new(post, :only => :title) + + assert_equal({ + :post => { + :title => "New Post" + } + }, post_serializer.as_json) + end + + def test_except_option_filters_attributes_and_associations + post = Post.new(:title => "New Post", :body => "Body of new post") + comments = [Comment.new(:title => "Comment1")] + post.comments = comments + + post_serializer = PostSerializer.new(post, :except => [:body, :comments]) + + assert_equal({ + :post => { + :title => "New Post" + } + }, post_serializer.as_json) + end + + def test_only_option_takes_precedence_over_custom_defined_include_methods + user = User.new + + post = Post.new(:title => "New Post", :body => "Body of new post", :author => "Sausage King") + comments = [Comment.new(:title => "Comment")] + post.comments = comments + + post_serializer = PostWithMultipleConditionalsSerializer.new(post, :scope => user, :only => :title) + + # comments enabled + post.comments_disabled = false + # superuser - should see author + user.superuser = true + + assert_equal({ + :post => { + :title => "New Post" + } + }, post_serializer.as_json) + end end