JSONBuilder is to JSON as Builder is to XML
Add the following line to your application's Gemfile:
gem 'json_builder'
And then run:
$ bundle install
Or install it yourself with:
$ gem install json_builder
require 'json_builder'
json = JSONBuilder::Compiler.generate do
name 'Garrett Bjerkhoel'
email 'spam@garrettbjerkhoel.com'
url root_path
address do
street '1234 1st Ave'
street2 'Apt 1'
city 'New York'
state 'NY'
zip 10065
end
key :nil, 'testing a custom key name'
skills do
ruby true
asp false
end
longstring do
# Could be a highly intensive process that only returns a string
'12345' * 25
end
end
Which will generate:
{
"name": "Garrett Bjerkhoel",
"email": "spam@garrettbjerkhoel.com",
"url": "/",
"address": {
"street": "1234 1st Ave",
"street2": "Apt 1",
"city": "New York",
"state": "NY",
"zip": 10065
},
"nil": "testing a custom key name",
"skills": {
"ruby": true,
"asp": false
},
"longstring": "1234512345123451234512345..."
}
If you'd like to just generate an array:
array ['Garrett Bjerkhoel', 'John Doe'] do |name|
first, last = name.split(' ')
first first
last last
end
Which will return:
[
{
"first": "Garrett",
"last": "Bjerkhoel"
},
{
"first": "John",
"last": "Doe"
}
]
Just a note, if you use an array block as above, all other sibling method calls will be ignored.
To use JSONBuilder with your Rails application, make sure your controller responds to json:
class UsersController < ApplicationController
respond_to :json
def index
@users = User.order('id DESC').page(params[:page]).per(2)
respond_with @users
end
end
Then create your view app/views/users/index.json.json_builder which could look something like:
count @users.count
page @users.current_page
per_page @users.per_page
pages_count @users.num_pages
results @users do |user|
id user.id
name user.name
body user.body
url user_url(user)
links user.links do |link|
url link.url
visits link.visits
last_visited link.last_visited
end
end
The response that is returned:
{
"count": 10,
"page": 1,
"per_page": 2,
"pages_count": 5,
"results": [
{
"id": 1,
"name": "Garrett Bjerkhoel",
"body": "Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod.",
"url": "http://example.com/users/garrett-bjerkhoel",
"links": [
{
"url": "http://github.com/",
"visits": 500,
"last_visited": "2011-11-271T00:00:01Z"
},
{
"url": "http://garrettbjerkhoel.com/",
"visits": 1500,
"last_visited": "2011-11-261T00:00:01Z"
}
]
}, {
"id": 2,
"name": "John Doe",
"body": "Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod.",
"url": "http://example.com/users/john-doe",
"links": [
{
"url": "http://google.com/",
"visits": 11000,
"last_visited": "2010-05-221T00:00:01Z"
},
{
"url": "http://twitter.com/",
"visits": 155012857,
"last_visited": "2011-11-261T00:00:01Z"
}
]
}
]
}
Out of the box JSONBuilder supports JSONP callbacks when used within a Rails project just by using the callback parameter. For instance, if you requested /users.json?callback=myjscallback, you'll get a callback wrapping the response:
myjscallback([
{
"name": "Garrett Bjerkhoel"
},
{
"name": "John Doe"
}
])
To turn off JSONP callbacks globally or just per-environment:
ActionView::Base.json_callback = false
Sample::Application.configure do
config.action_view.json_callback = false
end
Out of the box JSONBuilder supports pretty printing only during development, it's disabled by default in other environments for performance. If you'd like to enable or disable pretty printing you can do it within your environment file or you can do it globally.
With pretty print on:
{
"name": "Garrett Bjerkhoel",
"email": "spam@garrettbjerkhoel.com"
}
Without:
{"name": "Garrett Bjerkhoel", "email": "spam@garrettbjerkhoel.com"}
Sample::Application.configure do
config.action_view.pretty_print_json = false
end
ActionView::Base.pretty_print_json = false
JSONBuilder is very fast, it's roughly 3.6 times faster than Builder based on the speed benchmark.
user system total real
JSONBuilder 2.950000 0.010000 2.960000 (2.968790)
Builder 10.820000 0.040000 10.860000 (10.930497)
There are alternatives to JSONBuilder, each good in their own way with different API's and design approaches that are worth checking out. Although, I would love to hear why JSONBuilder didn't fit your needs, by message or issue.
Copyright © 2012 Garrett Bjerkhoel. See MIT-LICENSE for details.