diff --git a/.gitignore b/.gitignore
index 763cc5a2..385f5fef 100644
--- a/.gitignore
+++ b/.gitignore
@@ -10,6 +10,9 @@ tmtags
## VIM
*.swp
+## IDEA
+.idea
+
## PROJECT::GENERAL
.yardoc
coverage
diff --git a/Rakefile b/Rakefile
index 9af21d7a..004a85ed 100644
--- a/Rakefile
+++ b/Rakefile
@@ -18,6 +18,7 @@ end
task :spec => %w[
base_spec
+ adapters:fast_jsonparser
adapters:oj
adapters:yajl
adapters:json_gem
diff --git a/benchmark.rb b/benchmark.rb
index 1dd89cd1..670652ce 100644
--- a/benchmark.rb
+++ b/benchmark.rb
@@ -1,4 +1,8 @@
+libx = File.expand_path("../lib", __FILE__)
+$LOAD_PATH.unshift(libx) unless $LOAD_PATH.include?(libx)
+
require 'oj'
+require 'fast_jsonparser'
require 'multi_json'
require 'benchmark/ips'
@@ -7,5 +11,13 @@
Benchmark.ips do |x|
x.time = 10
x.warmup = 1
- x.report { MultiJson.load(MultiJson.dump(a: 1, b: 2, c: 3)) }
+ x.report("oj") { MultiJson.load(MultiJson.dump(a: 1, b: 2, c: 3)) }
+end
+
+MultiJson.use :fast_jsonparser
+
+Benchmark.ips do |x|
+ x.time = 10
+ x.warmup = 1
+ x.report("fast_jsonparser") { MultiJson.load(MultiJson.dump(a: 1, b: 2, c: 3)) }
end
diff --git a/lib/multi_json.rb b/lib/multi_json.rb
index 5909370d..a83b35f7 100644
--- a/lib/multi_json.rb
+++ b/lib/multi_json.rb
@@ -31,6 +31,7 @@ def default_options
ALIASES = {'jrjackson' => 'jr_jackson'}
REQUIREMENT_MAP = [
+ [:fast_jsonparser, 'fast_jsonparser'],
[:oj, 'oj'],
[:yajl, 'yajl'],
[:jr_jackson, 'jrjackson'],
@@ -44,6 +45,7 @@ def default_options
# if any adapters are already loaded, then checks
# to see which are installed if none are loaded.
def default_adapter
+ return :fast_jsonparser if defined?(::FastJsonparser)
return :oj if defined?(::Oj)
return :yajl if defined?(::Yajl)
return :jr_jackson if defined?(::JrJackson)
@@ -79,6 +81,7 @@ def adapter
# Set the JSON parser utilizing a symbol, string, or class.
# Supported by default are:
#
+ # * :fast_jsonparser
# * :oj
# * :json_gem
# * :json_pure
diff --git a/lib/multi_json/adapters/fast_jsonparser.rb b/lib/multi_json/adapters/fast_jsonparser.rb
new file mode 100644
index 00000000..42e70dd5
--- /dev/null
+++ b/lib/multi_json/adapters/fast_jsonparser.rb
@@ -0,0 +1,44 @@
+require 'fast_jsonparser'
+require 'oj'
+require 'multi_json/adapter'
+
+module MultiJson
+ module Adapters
+ # Use the Oj library to dump/load.
+ class FastJsonparser < Adapter
+ defaults :load, :symbolize_keys => false
+ defaults :dump, :mode => :compat, :time_format => :ruby, :use_to_json => true
+
+ ParseError = ::FastJsonparser::Error
+
+ def load(string, options = {})
+ ::FastJsonparser.parse(string, options)
+ end
+
+ case ::Oj::VERSION
+ when /\A2\./
+ def dump(object, options = {})
+ options.merge!(:indent => 2) if options[:pretty]
+ options[:indent] = options[:indent].to_i if options[:indent]
+ ::Oj.dump(object, options)
+ end
+ when /\A3\./
+ PRETTY_STATE_PROTOTYPE = {
+ :indent => " ",
+ :space => " ",
+ :space_before => "",
+ :object_nl => "\n",
+ :array_nl => "\n",
+ :ascii_only => false,
+ }
+
+ def dump(object, options = {})
+ options.merge!(PRETTY_STATE_PROTOTYPE.dup) if options.delete(:pretty)
+ ::Oj.dump(object, options)
+ end
+ else
+ fail "Unsupported Oj version: #{::Oj::VERSION}"
+ end
+ end
+ end
+end
diff --git a/spec/fast_jsonparser_adapter_spec.rb b/spec/fast_jsonparser_adapter_spec.rb
new file mode 100644
index 00000000..d349fb22
--- /dev/null
+++ b/spec/fast_jsonparser_adapter_spec.rb
@@ -0,0 +1,10 @@
+require 'spec_helper'
+
+exit 0 if skip_adapter?('fast_jsonparser')
+
+require 'shared/adapter'
+require 'multi_json/adapters/fast_jsonparser'
+
+describe MultiJson::Adapters::FastJsonparser do
+ it_behaves_like 'an adapter', described_class
+end