mirror of
https://github.com/rails/rails.git
synced 2022-11-09 12:12:34 -05:00
9617db2078
The current code base is not uniform. After some discussion, we have chosen to go with double quotes by default.
300 lines
9.1 KiB
Ruby
300 lines
9.1 KiB
Ruby
require "cases/helper"
|
|
require "models/contact"
|
|
require "models/post"
|
|
require "models/author"
|
|
require "models/tagging"
|
|
require "models/tag"
|
|
require "models/comment"
|
|
|
|
module JsonSerializationHelpers
|
|
private
|
|
|
|
def set_include_root_in_json(value)
|
|
original_root_in_json = ActiveRecord::Base.include_root_in_json
|
|
ActiveRecord::Base.include_root_in_json = value
|
|
yield
|
|
ensure
|
|
ActiveRecord::Base.include_root_in_json = original_root_in_json
|
|
end
|
|
end
|
|
|
|
class JsonSerializationTest < ActiveRecord::TestCase
|
|
include JsonSerializationHelpers
|
|
|
|
class NamespacedContact < Contact
|
|
column :name, :string
|
|
end
|
|
|
|
def setup
|
|
@contact = Contact.new(
|
|
:name => "Konata Izumi",
|
|
:age => 16,
|
|
:avatar => "binarydata",
|
|
:created_at => Time.utc(2006, 8, 1),
|
|
:awesome => true,
|
|
:preferences => { :shows => "anime" }
|
|
)
|
|
end
|
|
|
|
def test_should_demodulize_root_in_json
|
|
set_include_root_in_json(true) do
|
|
@contact = NamespacedContact.new name: "whatever"
|
|
json = @contact.to_json
|
|
assert_match %r{^\{"namespaced_contact":\{}, json
|
|
end
|
|
end
|
|
|
|
def test_should_include_root_in_json
|
|
set_include_root_in_json(true) do
|
|
json = @contact.to_json
|
|
|
|
assert_match %r{^\{"contact":\{}, json
|
|
assert_match %r{"name":"Konata Izumi"}, json
|
|
assert_match %r{"age":16}, json
|
|
assert json.include?(%("created_at":#{ActiveSupport::JSON.encode(Time.utc(2006, 8, 1))}))
|
|
assert_match %r{"awesome":true}, json
|
|
assert_match %r{"preferences":\{"shows":"anime"\}}, json
|
|
end
|
|
end
|
|
|
|
def test_should_encode_all_encodable_attributes
|
|
json = @contact.to_json
|
|
|
|
assert_match %r{"name":"Konata Izumi"}, json
|
|
assert_match %r{"age":16}, json
|
|
assert json.include?(%("created_at":#{ActiveSupport::JSON.encode(Time.utc(2006, 8, 1))}))
|
|
assert_match %r{"awesome":true}, json
|
|
assert_match %r{"preferences":\{"shows":"anime"\}}, json
|
|
end
|
|
|
|
def test_should_allow_attribute_filtering_with_only
|
|
json = @contact.to_json(:only => [:name, :age])
|
|
|
|
assert_match %r{"name":"Konata Izumi"}, json
|
|
assert_match %r{"age":16}, json
|
|
assert_no_match %r{"awesome":true}, json
|
|
assert !json.include?(%("created_at":#{ActiveSupport::JSON.encode(Time.utc(2006, 8, 1))}))
|
|
assert_no_match %r{"preferences":\{"shows":"anime"\}}, json
|
|
end
|
|
|
|
def test_should_allow_attribute_filtering_with_except
|
|
json = @contact.to_json(:except => [:name, :age])
|
|
|
|
assert_no_match %r{"name":"Konata Izumi"}, json
|
|
assert_no_match %r{"age":16}, json
|
|
assert_match %r{"awesome":true}, json
|
|
assert json.include?(%("created_at":#{ActiveSupport::JSON.encode(Time.utc(2006, 8, 1))}))
|
|
assert_match %r{"preferences":\{"shows":"anime"\}}, json
|
|
end
|
|
|
|
def test_methods_are_called_on_object
|
|
# Define methods on fixture.
|
|
def @contact.label; "Has cheezburger"; end
|
|
def @contact.favorite_quote; "Constraints are liberating"; end
|
|
|
|
# Single method.
|
|
assert_match %r{"label":"Has cheezburger"}, @contact.to_json(:only => :name, :methods => :label)
|
|
|
|
# Both methods.
|
|
methods_json = @contact.to_json(:only => :name, :methods => [:label, :favorite_quote])
|
|
assert_match %r{"label":"Has cheezburger"}, methods_json
|
|
assert_match %r{"favorite_quote":"Constraints are liberating"}, methods_json
|
|
end
|
|
|
|
def test_uses_serializable_hash_with_only_option
|
|
def @contact.serializable_hash(options=nil)
|
|
super(only: %w(name))
|
|
end
|
|
|
|
json = @contact.to_json
|
|
assert_match %r{"name":"Konata Izumi"}, json
|
|
assert_no_match %r{awesome}, json
|
|
assert_no_match %r{age}, json
|
|
end
|
|
|
|
def test_uses_serializable_hash_with_except_option
|
|
def @contact.serializable_hash(options=nil)
|
|
super(except: %w(age))
|
|
end
|
|
|
|
json = @contact.to_json
|
|
assert_match %r{"name":"Konata Izumi"}, json
|
|
assert_match %r{"awesome":true}, json
|
|
assert_no_match %r{age}, json
|
|
end
|
|
|
|
def test_does_not_include_inheritance_column_from_sti
|
|
@contact = ContactSti.new(@contact.attributes)
|
|
assert_equal "ContactSti", @contact.type
|
|
|
|
json = @contact.to_json
|
|
assert_match %r{"name":"Konata Izumi"}, json
|
|
assert_no_match %r{type}, json
|
|
assert_no_match %r{ContactSti}, json
|
|
end
|
|
|
|
def test_serializable_hash_with_default_except_option_and_excluding_inheritance_column_from_sti
|
|
@contact = ContactSti.new(@contact.attributes)
|
|
assert_equal "ContactSti", @contact.type
|
|
|
|
def @contact.serializable_hash(options={})
|
|
super({ except: %w(age) }.merge!(options))
|
|
end
|
|
|
|
json = @contact.to_json
|
|
assert_match %r{"name":"Konata Izumi"}, json
|
|
assert_no_match %r{age}, json
|
|
assert_no_match %r{type}, json
|
|
assert_no_match %r{ContactSti}, json
|
|
end
|
|
|
|
def test_serializable_hash_should_not_modify_options_in_argument
|
|
options = { :only => :name }
|
|
@contact.serializable_hash(options)
|
|
|
|
assert_nil options[:except]
|
|
end
|
|
end
|
|
|
|
class DatabaseConnectedJsonEncodingTest < ActiveRecord::TestCase
|
|
fixtures :authors, :posts, :comments, :tags, :taggings
|
|
|
|
include JsonSerializationHelpers
|
|
|
|
def setup
|
|
@david = authors(:david)
|
|
@mary = authors(:mary)
|
|
end
|
|
|
|
def test_includes_uses_association_name
|
|
json = @david.to_json(:include => :posts)
|
|
|
|
assert_match %r{"posts":\[}, json
|
|
|
|
assert_match %r{"id":1}, json
|
|
assert_match %r{"name":"David"}, json
|
|
|
|
assert_match %r{"author_id":1}, json
|
|
assert_match %r{"title":"Welcome to the weblog"}, json
|
|
assert_match %r{"body":"Such a lovely day"}, json
|
|
|
|
assert_match %r{"title":"So I was thinking"}, json
|
|
assert_match %r{"body":"Like I hopefully always am"}, json
|
|
end
|
|
|
|
def test_includes_uses_association_name_and_applies_attribute_filters
|
|
json = @david.to_json(:include => { :posts => { :only => :title } })
|
|
|
|
assert_match %r{"name":"David"}, json
|
|
assert_match %r{"posts":\[}, json
|
|
|
|
assert_match %r{"title":"Welcome to the weblog"}, json
|
|
assert_no_match %r{"body":"Such a lovely day"}, json
|
|
|
|
assert_match %r{"title":"So I was thinking"}, json
|
|
assert_no_match %r{"body":"Like I hopefully always am"}, json
|
|
end
|
|
|
|
def test_includes_fetches_second_level_associations
|
|
json = @david.to_json(:include => { :posts => { :include => { :comments => { :only => :body } } } })
|
|
|
|
assert_match %r{"name":"David"}, json
|
|
assert_match %r{"posts":\[}, json
|
|
|
|
assert_match %r{"comments":\[}, json
|
|
assert_match %r{\{"body":"Thank you again for the welcome"\}}, json
|
|
assert_match %r{\{"body":"Don't think too hard"\}}, json
|
|
assert_no_match %r{"post_id":}, json
|
|
end
|
|
|
|
def test_includes_fetches_nth_level_associations
|
|
json = @david.to_json(
|
|
:include => {
|
|
:posts => {
|
|
:include => {
|
|
:taggings => {
|
|
:include => {
|
|
:tag => { :only => :name }
|
|
}
|
|
}
|
|
}
|
|
}
|
|
})
|
|
|
|
assert_match %r{"name":"David"}, json
|
|
assert_match %r{"posts":\[}, json
|
|
|
|
assert_match %r{"taggings":\[}, json
|
|
assert_match %r{"tag":\{"name":"General"\}}, json
|
|
end
|
|
|
|
def test_includes_doesnt_merge_opts_from_base
|
|
json = @david.to_json(
|
|
:only => :id,
|
|
:include => :posts
|
|
)
|
|
|
|
assert_match %{"title":"Welcome to the weblog"}, json
|
|
end
|
|
|
|
def test_should_not_call_methods_on_associations_that_dont_respond
|
|
def @david.favorite_quote; "Constraints are liberating"; end
|
|
json = @david.to_json(:include => :posts, :methods => :favorite_quote)
|
|
|
|
assert !@david.posts.first.respond_to?(:favorite_quote)
|
|
assert_match %r{"favorite_quote":"Constraints are liberating"}, json
|
|
assert_equal %r{"favorite_quote":}.match(json).size, 1
|
|
end
|
|
|
|
def test_should_allow_only_option_for_list_of_authors
|
|
set_include_root_in_json(false) do
|
|
authors = [@david, @mary]
|
|
assert_equal %([{"name":"David"},{"name":"Mary"}]), ActiveSupport::JSON.encode(authors, only: :name)
|
|
end
|
|
end
|
|
|
|
def test_should_allow_except_option_for_list_of_authors
|
|
set_include_root_in_json(false) do
|
|
authors = [@david, @mary]
|
|
encoded = ActiveSupport::JSON.encode(authors, except: [
|
|
:name, :author_address_id, :author_address_extra_id,
|
|
:organization_id, :owned_essay_id
|
|
])
|
|
assert_equal %([{"id":1},{"id":2}]), encoded
|
|
end
|
|
end
|
|
|
|
def test_should_allow_includes_for_list_of_authors
|
|
authors = [@david, @mary]
|
|
json = ActiveSupport::JSON.encode(authors,
|
|
:only => :name,
|
|
:include => {
|
|
:posts => { :only => :id }
|
|
}
|
|
)
|
|
|
|
['"name":"David"', '"posts":[', '{"id":1}', '{"id":2}', '{"id":4}',
|
|
'{"id":5}', '{"id":6}', '"name":"Mary"', '"posts":[', '{"id":7}', '{"id":9}'].each do |fragment|
|
|
assert json.include?(fragment), json
|
|
end
|
|
end
|
|
|
|
def test_should_allow_options_for_hash_of_authors
|
|
set_include_root_in_json(true) do
|
|
authors_hash = {
|
|
1 => @david,
|
|
2 => @mary
|
|
}
|
|
assert_equal %({"1":{"author":{"name":"David"}}}), ActiveSupport::JSON.encode(authors_hash, only: [1, :name])
|
|
end
|
|
end
|
|
|
|
def test_should_be_able_to_encode_relation
|
|
set_include_root_in_json(true) do
|
|
authors_relation = Author.where(id: [@david.id, @mary.id])
|
|
|
|
json = ActiveSupport::JSON.encode authors_relation, only: :name
|
|
assert_equal '[{"author":{"name":"David"}},{"author":{"name":"Mary"}}]', json
|
|
end
|
|
end
|
|
end
|