0

Can I use active_model_serializers with Sinatra? If not, is there any better way for json output in Sinatra for building a web service?

Bhushan Lodha
  • 6,824
  • 7
  • 62
  • 100

3 Answers3

1

Yes, you can. However, the design and architecture of AMS is strongly focuses on ActiveModel instances, therefore if you don't use an ActiveModel-based library (such as Mongoid, ActiveRecord, etc) the choice may be overkill.

Still, the approach reflects the common Presenter pattern applied to JSON serialization. You can easily create your own simple library to extract the attributes you define from an object you pass.

Sinatra also provides some JSON serialization extensions. What they do by default, is to call as_json. That's not the best approach, it is not extremely flexible, but you can combine those two elements to create your own solution, or start from scratch.

Simone Carletti
  • 173,507
  • 49
  • 363
  • 364
1

You can, includes a json.rb inside the lib folder with the following piece of code and do require this file on your application.rb .

# lib/json.rb

module Sinatra
  module JSON
    def json(object, options={})
      serializer = ActiveModel::Serializer.serializer_for(object, options)
      if serializer
        serializer.new(object, options).to_json
      else
        object.to_json(options)
      end
    end
  end
end

To use just do

get '/foo' do
  json Foo.find(params[:id])
end

get '/bar' do
  json Bar.find(params[:id]), { scope: self }
end
Saulo Santiago
  • 524
  • 5
  • 6
0

I used to_json to return JSON output from Sinatra API's. It turns out that there are dozens of JSON gems for Ruby, of varying efficiency.

One approach is to create list of attributes for each object that you want to render to JSON. For example, if your User has an image that you don't want to render, you could create a blacklist for the User class:

JSON_BLACKLIST = [ 'image' ]

Then, when you render the JSON, you can call:

user.attributes.reject{|a| JSON_BLACKLIST.include?( a )}.to_json
B Seven
  • 44,484
  • 66
  • 240
  • 385