MIT License CircleCI

ObjectableJSON

ObjectableJSON is simple and clever JSON => Object Mapper. ObjectableJSON automatically analyze your JSON values and convert the values to Single Object. So, you can easily convert JSON to Single Object by only calling ObjectableJSON#parse method. Especially, this gem is powerful & useful when you treat some API JSON response. Also, this gem can work for Hash.

Installation

Add this line to your application's Gemfile:

gem 'objectable_json'

And then execute:

$ bundle

Or install it yourself as:

$ gem install objectable_json

Usage

For example, you get some API response JSON like this

{
  "user": {
    "first_name": "kazuya",
    "last_name": "matsumoto"
  }
}

If you need user first_name, maybe you will write code like this.

response = JSON.parse(json_response)
first_name = response["user"]["first_name"]

This code is little verbose because of two raw string hash key. If you have to access deeper nest, code will become more messy.

By using ObjectableJSON, you can write first_name access more simple.

response = ObjectableJSON.parse(json_response)
first_name = response.user.first_name

Cool! You can access response values with dot chain.

ObjectableJSON automatically analyze your JSON values and convert it to single object. In this case, ObjectedJSON & User Object is created and set instance variable like this.

# define class like this
# top level class. This class has User class object as attribute.
class ObjectedJSON
  attr_accessor: :user
  def initialize(args)
    @user = args[:user]
  end
end
# user object. first_name & last_name are defined as attributes.
class ObjectedJSON::User
  attr_accessor: :first_name, :last_name
  def initialize(args)
    @first_name = args[:first_name]
    @last_name  = args[:last_name]
  end
end
# created object with setting 
values
response = ObjectableJSON.parse(json_response)
=> #<ObjectedJSON:0x007f9718b60100 @user=#<ObjectedJSON::User:0x007f9718b607e0 @first_name="matsumoto", @last_name="kazuya">>

ObjectableJSON defines classes, So you can easily definine method to JSON attributes.

response.user.class_eval do
  def full_name
    first_name + last_name
  end
end
response.user.full_name
=> "matsumotokauzya"

Also, if you get hash array JSON like this

{
  "user": {
    "friends": [
      {
        "name": "yamada",
        "sex": "male"
      },
      {
        "name": "sato",
        "sex": "female"
      },
      {
        "name": "john",
        "sex": "male",
        "country": "us"
      }
    ]
  }
}

friends is recognized as Friend Object Array. (plural is renamed to singular only if it is available)

response = ObjectableJSON.parse(json_response, 'SimpleAPI') # you can optionally set top level name space

friends = response.user.friends
=> [#<SimpleAPI::Friend:0x007fcfec305728 @name="yamada", @sex="male">,
 #<SimpleAPI::Friend:0x007fcfec3048a0 @name="sato", @sex="female">,
 #<SimpleAPI::Friend:0x007fcfec2feba8 @country="us", @name="john", @sex="male">]

friends.map(&:name)
=> ["yamada", "sato", "john"]

At last, let me introduce real GoogleMapAPI example. This is JSON response

{
  "results" : [
    {
      "address_components" : [
        {
          "long_name" : "1600",
          "short_name" : "1600",
          "types" : [ "street_number" ]
        },
        {
          "long_name" : "Amphitheatre Pkwy",
          "short_name" : "Amphitheatre Pkwy",
          "types" : [ "route" ]
        },
        {
          "long_name" : "Mountain View",
          "short_name" : "Mountain View",
          "types" : [ "locality", "political" ]
        },
        {
          "long_name" : "Santa Clara County",
          "short_name" : "Santa Clara County",
          "types" : [ "administrative_area_level_2", "political" ]
        },
        {
          "long_name" : "California",
          "short_name" : "CA",
          "types" : [ "administrative_area_level_1", "political" ]
        },
        {
          "long_name" : "United States",
          "short_name" : "US",
          "types" : [ "country", "political" ]
        },
        {
          "long_name" : "94043",
          "short_name" : "94043",
          "types" : [ "postal_code" ]
        }
      ],
      "formatted_address" : "1600 Amphitheatre Parkway, Mountain View, CA 94043, USA",
      "geometry" : {
        "location" : {
          "lat" : 37.4224764,
          "lng" : -122.0842499
        },
        "location_type" : "ROOFTOP",
        "viewport" : {
          "northeast" : {
            "lat" : 37.4238253802915,
            "lng" : -122.0829009197085
          },
          "southwest" : {
            "lat" : 37.4211274197085,
            "lng" : -122.0855988802915
          }
        }
      },
      "place_id" : "ChIJ2eUgeAK6j4ARbn5u_wAGqWA",
      "types" : [ "street_address" ]
    }
  ],
  "status" : "OK"
}

This is converted result

ObjectableJSON.parse(google_map_api_response, 'GoogleMapAPIWrapper')
=> [#<GoogleMapAPIWrapper::Result:0x007fb3cb1ddba8
  @address_components=
   [#<GoogleMapAPIWrapper::AddressComponent:0x007fb3cb216d40
     @long_name="1600",
     @short_name="1600",
     @types=["street_number"]>,
    #<GoogleMapAPIWrapper::AddressComponent:0x007fb3cb20dd80
     @long_name="Amphitheatre Pkwy",
     @short_name="Amphitheatre Pkwy",
     @types=["route"]>,
    #<GoogleMapAPIWrapper::AddressComponent:0x007fb3cb20c250
     @long_name="Mountain View",
     @short_name="Mountain View",
     @types=["locality", "political"]>,
    #<GoogleMapAPIWrapper::AddressComponent:0x007fb3ca988778
     @long_name="Santa Clara County",
     @short_name="Santa Clara County",
     @types=["administrative_area_level_2", "political"]>,
    #<GoogleMapAPIWrapper::AddressComponent:0x007fb3cb2054c8
     @long_name="California",
     @short_name="CA",
     @types=["administrative_area_level_1", "political"]>,
    #<GoogleMapAPIWrapper::AddressComponent:0x007fb3ca9816d0
     @long_name="United States",
     @short_name="US",
     @types=["country", "political"]>,
    #<GoogleMapAPIWrapper::AddressComponent:0x007fb3ca97a240
     @long_name="94043",
     @short_name="94043",
     @types=["postal_code"]>],
  @formatted_address="1600 Amphitheatre Parkway, Mountain View, CA 94043, USA",
  @geometry=
   #<GoogleMapAPIWrapper::Geometry:0x007fb3cb1f6a18
    @location=
     #<GoogleMapAPIWrapper::Location:0x007fb3ca973cb0
      @lat=37.4224764,
      @lng=-122.0842499>,
    @location_type="ROOFTOP",
    @viewport=
     #<GoogleMapAPIWrapper::Viewport:0x007fb3cb1f6270
      @northeast=
       #<GoogleMapAPIWrapper::Northeast:0x007fb3ca971bb8
        @lat=37.4238253802915,
        @lng=-122.0829009197085>,
      @southwest=
       #<GoogleMapAPIWrapper::Southwest:0x007fb3ca9703f8
        @lat=37.4211274197085,
        @lng=-122.0855988802915>>>,
  @place_id="ChIJ2eUgeAK6j4ARbn5u_wAGqWA",
  @types=["street_address"]>]

You can treat complex API with more simple and clean code.

Development

After checking out the repo, run bin/setup to install dependencies. Then, run rake spec to run the tests. You can also run bin/console for an interactive prompt that will allow you to experiment.

To install this gem onto your local machine, run bundle exec rake install. To release a new version, update the version number in version.rb, and then run bundle exec rake release, which will create a git tag for the version, push git commits and tags, and push the .gem file to rubygems.org.

Contributing

Bug reports and pull requests are welcome on GitHub at https://github.com/[USERNAME]/objectable_json. (very very welcome :) )

License

The gem is available as open source under the terms of the MIT License.