Skip to content

Instantly share code, notes, and snippets.

@matthewrobertson
Last active June 14, 2016 07:16
Show Gist options
  • Star 11 You must be signed in to star a gist
  • Fork 5 You must be signed in to fork a gist
  • Save matthewrobertson/6129035 to your computer and use it in GitHub Desktop.
Save matthewrobertson/6129035 to your computer and use it in GitHub Desktop.
A simple pattern for creating classes that encapsulate JSON serialization logic. Simply inherit from the `BaseSerializer` and override the hook methods as necessary.
# An abstract base class used to create simple serializers
# for ActiveRecord objects
class BaseSerializer
include Rails.application.routes.url_helpers
attr_reader :serialized_object
def initialize(serialized_object)
@serialized_object = serialized_object
end
def as_json(options={})
if serialized_object.respond_to?(:to_ary)
serialized_object.map { |object| serialize(object, options) }
else
serialize(serialized_object, options)
end
end
private
# serialize a single instance
def serialize(object, options={})
object.as_json(as_json_options.merge(options))
end
# the default options passed to as_json
def as_json_options
{ :only => attributes,
:methods => methods,
:include => includes }
end
# hook methods
def attributes ; end
def includes ; end
def methods ; end
end
# serialize a comment to json:
#
# CommentSerializer.new(c).as_json
# => {
# "id"=>1,
# "html_body"=>"lorem ipsum dolor...",
# "created_at"=>"2013-07-26T10:38:47-07:00",
# "user"=>{
# "id"=>1,
# "name"=>"Matthew"
# }
# }
class CommentSerializer < BaseSerializer
private
def serialize(object, options={})
super(object, options).tap do |json|
json['link'] = user_path(serialized_object)
end
end
def attributes
%w(id created_at)
end
def includes
{ 'user' => { 'only' => %w(id name) } }
end
def methods
%w(html_body)
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment