oj 3.8.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/LICENSE +21 -0
- data/README.md +104 -0
- data/ext/oj/buf.h +103 -0
- data/ext/oj/cache8.c +107 -0
- data/ext/oj/cache8.h +48 -0
- data/ext/oj/circarray.c +68 -0
- data/ext/oj/circarray.h +23 -0
- data/ext/oj/code.c +235 -0
- data/ext/oj/code.h +42 -0
- data/ext/oj/compat.c +299 -0
- data/ext/oj/custom.c +1191 -0
- data/ext/oj/dump.c +1252 -0
- data/ext/oj/dump.h +96 -0
- data/ext/oj/dump_compat.c +977 -0
- data/ext/oj/dump_leaf.c +252 -0
- data/ext/oj/dump_object.c +837 -0
- data/ext/oj/dump_strict.c +433 -0
- data/ext/oj/encode.h +45 -0
- data/ext/oj/err.c +57 -0
- data/ext/oj/err.h +70 -0
- data/ext/oj/extconf.rb +47 -0
- data/ext/oj/fast.c +1771 -0
- data/ext/oj/hash.c +163 -0
- data/ext/oj/hash.h +46 -0
- data/ext/oj/hash_test.c +512 -0
- data/ext/oj/mimic_json.c +878 -0
- data/ext/oj/object.c +771 -0
- data/ext/oj/odd.c +231 -0
- data/ext/oj/odd.h +44 -0
- data/ext/oj/oj.c +1704 -0
- data/ext/oj/oj.h +385 -0
- data/ext/oj/parse.c +1086 -0
- data/ext/oj/parse.h +111 -0
- data/ext/oj/rails.c +1493 -0
- data/ext/oj/rails.h +21 -0
- data/ext/oj/reader.c +231 -0
- data/ext/oj/reader.h +151 -0
- data/ext/oj/resolve.c +102 -0
- data/ext/oj/resolve.h +14 -0
- data/ext/oj/rxclass.c +147 -0
- data/ext/oj/rxclass.h +27 -0
- data/ext/oj/saj.c +714 -0
- data/ext/oj/scp.c +224 -0
- data/ext/oj/sparse.c +910 -0
- data/ext/oj/stream_writer.c +363 -0
- data/ext/oj/strict.c +212 -0
- data/ext/oj/string_writer.c +534 -0
- data/ext/oj/trace.c +79 -0
- data/ext/oj/trace.h +28 -0
- data/ext/oj/util.c +136 -0
- data/ext/oj/util.h +19 -0
- data/ext/oj/val_stack.c +118 -0
- data/ext/oj/val_stack.h +185 -0
- data/ext/oj/wab.c +631 -0
- data/lib/oj.rb +21 -0
- data/lib/oj/active_support_helper.rb +41 -0
- data/lib/oj/bag.rb +88 -0
- data/lib/oj/easy_hash.rb +52 -0
- data/lib/oj/error.rb +22 -0
- data/lib/oj/json.rb +176 -0
- data/lib/oj/mimic.rb +267 -0
- data/lib/oj/saj.rb +66 -0
- data/lib/oj/schandler.rb +142 -0
- data/lib/oj/state.rb +131 -0
- data/lib/oj/version.rb +5 -0
- data/pages/Advanced.md +22 -0
- data/pages/Compatibility.md +25 -0
- data/pages/Custom.md +23 -0
- data/pages/Encoding.md +65 -0
- data/pages/JsonGem.md +79 -0
- data/pages/Modes.md +155 -0
- data/pages/Options.md +283 -0
- data/pages/Rails.md +116 -0
- data/pages/Security.md +20 -0
- data/pages/WAB.md +13 -0
- data/test/_test_active.rb +76 -0
- data/test/_test_active_mimic.rb +96 -0
- data/test/_test_mimic_rails.rb +126 -0
- data/test/activerecord/result_test.rb +27 -0
- data/test/activesupport4/decoding_test.rb +108 -0
- data/test/activesupport4/encoding_test.rb +531 -0
- data/test/activesupport4/test_helper.rb +41 -0
- data/test/activesupport5/decoding_test.rb +125 -0
- data/test/activesupport5/encoding_test.rb +485 -0
- data/test/activesupport5/encoding_test_cases.rb +90 -0
- data/test/activesupport5/test_helper.rb +50 -0
- data/test/activesupport5/time_zone_test_helpers.rb +24 -0
- data/test/bar.rb +25 -0
- data/test/files.rb +29 -0
- data/test/foo.rb +167 -0
- data/test/helper.rb +26 -0
- data/test/isolated/shared.rb +308 -0
- data/test/isolated/test_mimic_after.rb +13 -0
- data/test/isolated/test_mimic_alone.rb +12 -0
- data/test/isolated/test_mimic_as_json.rb +45 -0
- data/test/isolated/test_mimic_before.rb +13 -0
- data/test/isolated/test_mimic_define.rb +28 -0
- data/test/isolated/test_mimic_rails_after.rb +22 -0
- data/test/isolated/test_mimic_rails_before.rb +21 -0
- data/test/isolated/test_mimic_redefine.rb +15 -0
- data/test/json_gem/json_addition_test.rb +216 -0
- data/test/json_gem/json_common_interface_test.rb +148 -0
- data/test/json_gem/json_encoding_test.rb +107 -0
- data/test/json_gem/json_ext_parser_test.rb +20 -0
- data/test/json_gem/json_fixtures_test.rb +35 -0
- data/test/json_gem/json_generator_test.rb +383 -0
- data/test/json_gem/json_generic_object_test.rb +90 -0
- data/test/json_gem/json_parser_test.rb +470 -0
- data/test/json_gem/json_string_matching_test.rb +42 -0
- data/test/json_gem/test_helper.rb +18 -0
- data/test/perf.rb +107 -0
- data/test/perf_compat.rb +130 -0
- data/test/perf_fast.rb +164 -0
- data/test/perf_file.rb +64 -0
- data/test/perf_object.rb +138 -0
- data/test/perf_saj.rb +109 -0
- data/test/perf_scp.rb +151 -0
- data/test/perf_simple.rb +287 -0
- data/test/perf_strict.rb +145 -0
- data/test/perf_wab.rb +131 -0
- data/test/sample.rb +54 -0
- data/test/sample/change.rb +14 -0
- data/test/sample/dir.rb +19 -0
- data/test/sample/doc.rb +36 -0
- data/test/sample/file.rb +48 -0
- data/test/sample/group.rb +16 -0
- data/test/sample/hasprops.rb +16 -0
- data/test/sample/layer.rb +12 -0
- data/test/sample/line.rb +20 -0
- data/test/sample/oval.rb +10 -0
- data/test/sample/rect.rb +10 -0
- data/test/sample/shape.rb +35 -0
- data/test/sample/text.rb +20 -0
- data/test/sample_json.rb +37 -0
- data/test/test_compat.rb +509 -0
- data/test/test_custom.rb +503 -0
- data/test/test_debian.rb +53 -0
- data/test/test_fast.rb +470 -0
- data/test/test_file.rb +239 -0
- data/test/test_gc.rb +49 -0
- data/test/test_hash.rb +29 -0
- data/test/test_integer_range.rb +73 -0
- data/test/test_null.rb +376 -0
- data/test/test_object.rb +1018 -0
- data/test/test_saj.rb +186 -0
- data/test/test_scp.rb +433 -0
- data/test/test_strict.rb +410 -0
- data/test/test_various.rb +741 -0
- data/test/test_wab.rb +307 -0
- data/test/test_writer.rb +380 -0
- data/test/tests.rb +24 -0
- data/test/tests_mimic.rb +14 -0
- data/test/tests_mimic_addition.rb +7 -0
- data/test/zoo.rb +13 -0
- metadata +359 -0
data/lib/oj/saj.rb
ADDED
@@ -0,0 +1,66 @@
|
|
1
|
+
module Oj
|
2
|
+
# A SAX style parse handler for JSON hence the acronym SAJ for Simple API for
|
3
|
+
# JSON. The Oj::Saj handler class should be subclassed and then used with the
|
4
|
+
# Oj::Saj key_parse() method. The Saj methods will then be called as the file
|
5
|
+
# is parsed.
|
6
|
+
#
|
7
|
+
# @example
|
8
|
+
#
|
9
|
+
# require 'oj'
|
10
|
+
#
|
11
|
+
# class MySaj < ::Oj::Saj
|
12
|
+
# def initialize()
|
13
|
+
# @hash_cnt = 0
|
14
|
+
# end
|
15
|
+
#
|
16
|
+
# def hash_start(key)
|
17
|
+
# @hash_cnt += 1
|
18
|
+
# end
|
19
|
+
# end
|
20
|
+
#
|
21
|
+
# cnt = MySaj.new()
|
22
|
+
# File.open('any.json', 'r') do |f|
|
23
|
+
# Oj.saj_parse(cnt, f)
|
24
|
+
# end
|
25
|
+
#
|
26
|
+
# To make the desired methods active while parsing the desired method should
|
27
|
+
# be made public in the subclasses. If the methods remain private they will
|
28
|
+
# not be called during parsing.
|
29
|
+
#
|
30
|
+
# def hash_start(key); end
|
31
|
+
# def hash_end(key); end
|
32
|
+
# def array_start(key); end
|
33
|
+
# def array_end(key); end
|
34
|
+
# def add_value(value, key); end
|
35
|
+
# def error(message, line, column); end
|
36
|
+
#
|
37
|
+
class Saj
|
38
|
+
# Create a new instance of the Saj handler class.
|
39
|
+
def initialize()
|
40
|
+
end
|
41
|
+
|
42
|
+
# To make the desired methods active while parsing the desired method should
|
43
|
+
# be made public in the subclasses. If the methods remain private they will
|
44
|
+
# not be called during parsing.
|
45
|
+
private
|
46
|
+
|
47
|
+
def hash_start(key)
|
48
|
+
end
|
49
|
+
|
50
|
+
def hash_end(key)
|
51
|
+
end
|
52
|
+
|
53
|
+
def array_start(key)
|
54
|
+
end
|
55
|
+
|
56
|
+
def array_end(key)
|
57
|
+
end
|
58
|
+
|
59
|
+
def add_value(value, key)
|
60
|
+
end
|
61
|
+
|
62
|
+
def error(message, line, column)
|
63
|
+
end
|
64
|
+
|
65
|
+
end # Saj
|
66
|
+
end # Oj
|
data/lib/oj/schandler.rb
ADDED
@@ -0,0 +1,142 @@
|
|
1
|
+
module Oj
|
2
|
+
# A Simple Callback Parser (SCP) for JSON. The Oj::ScHandler class should be
|
3
|
+
# subclassed and then used with the Oj.sc_parse() method. The Scp methods will
|
4
|
+
# then be called as the file is parsed. The handler does not have to be a
|
5
|
+
# subclass of the ScHandler class as long as it responds to the desired
|
6
|
+
# methods.
|
7
|
+
#
|
8
|
+
# @example
|
9
|
+
#
|
10
|
+
# require 'oj'
|
11
|
+
#
|
12
|
+
# class MyHandler < ::Oj::ScHandler
|
13
|
+
# def hash_start
|
14
|
+
# {}
|
15
|
+
# end
|
16
|
+
#
|
17
|
+
# def hash_set(h,k,v)
|
18
|
+
# h[k] = v
|
19
|
+
# end
|
20
|
+
#
|
21
|
+
# def array_start
|
22
|
+
# []
|
23
|
+
# end
|
24
|
+
#
|
25
|
+
# def array_append(a,v)
|
26
|
+
# a << v
|
27
|
+
# end
|
28
|
+
#
|
29
|
+
# def add_value(v)
|
30
|
+
# p v
|
31
|
+
# end
|
32
|
+
#
|
33
|
+
# def error(message, line, column)
|
34
|
+
# p "ERROR: #{message}"
|
35
|
+
# end
|
36
|
+
# end
|
37
|
+
#
|
38
|
+
# File.open('any.json', 'r') do |f|
|
39
|
+
# Oj.sc_parse(MyHandler.new, f)
|
40
|
+
# end
|
41
|
+
#
|
42
|
+
# To make the desired methods active while parsing the desired method should
|
43
|
+
# be made public in the subclasses. If the methods remain private they will
|
44
|
+
# not be called during parsing.
|
45
|
+
#
|
46
|
+
# def hash_start(); end
|
47
|
+
# def hash_end(); end
|
48
|
+
# def hash_key(key); end
|
49
|
+
# def hash_set(h, key, value); end
|
50
|
+
# def array_start(); end
|
51
|
+
# def array_end(); end
|
52
|
+
# def array_append(a, value); end
|
53
|
+
# def add_value(value); end
|
54
|
+
#
|
55
|
+
# As certain elements of a JSON document are reached during parsing the
|
56
|
+
# callbacks are called. The parser helps by keeping track of objects created
|
57
|
+
# by the callbacks but does not create those objects itself.
|
58
|
+
#
|
59
|
+
# hash_start
|
60
|
+
#
|
61
|
+
# When a JSON object element starts the hash_start() callback is called if
|
62
|
+
# public. It should return what ever Ruby Object is to be used as the element
|
63
|
+
# that will later be included in the hash_set() callback.
|
64
|
+
#
|
65
|
+
# hash_end
|
66
|
+
#
|
67
|
+
# When a hash key is encountered the hash_key method is called with the parsed
|
68
|
+
# hash value key. The return value from the call is then used as the key in
|
69
|
+
# the key-value pair that follows.
|
70
|
+
#
|
71
|
+
# hash_key
|
72
|
+
#
|
73
|
+
# At the end of a JSON object element the hash_end() callback is called if public.
|
74
|
+
#
|
75
|
+
# hash_set
|
76
|
+
#
|
77
|
+
# When a key value pair is encountered during parsing the hash_set() callback
|
78
|
+
# is called if public. The first element will be the object returned from the
|
79
|
+
# enclosing hash_start() callback. The second argument is the key and the last
|
80
|
+
# is the value.
|
81
|
+
#
|
82
|
+
# array_start
|
83
|
+
#
|
84
|
+
# When a JSON array element is started the array_start() callback is called if
|
85
|
+
# public. It should return what ever Ruby Object is to be used as the element
|
86
|
+
# that will later be included in the array_append() callback.
|
87
|
+
#
|
88
|
+
# array_end
|
89
|
+
#
|
90
|
+
# At the end of a JSON array element the array_end() callback is called if public.
|
91
|
+
#
|
92
|
+
# array_append
|
93
|
+
#
|
94
|
+
# When a element is encountered that is an element of an array the
|
95
|
+
# array_append() callback is called if public. The first argument to the
|
96
|
+
# callback is the Ruby object returned from the enclosing array_start()
|
97
|
+
# callback.
|
98
|
+
#
|
99
|
+
# add_value
|
100
|
+
#
|
101
|
+
# The handler is expected to handle multiple JSON elements in one stream,
|
102
|
+
# file, or string. When a top level JSON has been read completely the
|
103
|
+
# add_value() callback is called. Even if only one element was ready this
|
104
|
+
# callback returns the Ruby object that was constructed during the parsing.
|
105
|
+
#
|
106
|
+
class ScHandler
|
107
|
+
# Create a new instance of the ScHandler class.
|
108
|
+
def initialize()
|
109
|
+
end
|
110
|
+
|
111
|
+
# To make the desired methods active while parsing the desired method should
|
112
|
+
# be made public in the subclasses. If the methods remain private they will
|
113
|
+
# not be called during parsing.
|
114
|
+
private
|
115
|
+
|
116
|
+
def hash_start()
|
117
|
+
end
|
118
|
+
|
119
|
+
def hash_end()
|
120
|
+
end
|
121
|
+
|
122
|
+
def hash_key(key)
|
123
|
+
key
|
124
|
+
end
|
125
|
+
|
126
|
+
def hash_set(h, key, value)
|
127
|
+
end
|
128
|
+
|
129
|
+
def array_start()
|
130
|
+
end
|
131
|
+
|
132
|
+
def array_end()
|
133
|
+
end
|
134
|
+
|
135
|
+
def add_value(value)
|
136
|
+
end
|
137
|
+
|
138
|
+
def array_append(a, value)
|
139
|
+
end
|
140
|
+
|
141
|
+
end # ScHandler
|
142
|
+
end # Oj
|
data/lib/oj/state.rb
ADDED
@@ -0,0 +1,131 @@
|
|
1
|
+
|
2
|
+
module JSON
|
3
|
+
module Ext
|
4
|
+
module Generator
|
5
|
+
unless defined?(::JSON::Ext::Generator::State)
|
6
|
+
# This class exists for json gem compatibility only. While it can be
|
7
|
+
# used as the options for other than compatibility a simple Hash is
|
8
|
+
# recommended as it is simpler and performs better. The only bit
|
9
|
+
# missing by not using a state object is the depth availability which
|
10
|
+
# may be the depth during dumping or maybe not since it can be set and
|
11
|
+
# the docs for depth= is the same as max_nesting. Note: Had to make
|
12
|
+
# this a subclass of Object instead of Hash like EashyHash due to
|
13
|
+
# conflicts with the json gem.
|
14
|
+
class State
|
15
|
+
|
16
|
+
def self.from_state(opts)
|
17
|
+
s = self.new()
|
18
|
+
s.clear()
|
19
|
+
s.merge(opts)
|
20
|
+
s
|
21
|
+
end
|
22
|
+
|
23
|
+
def initialize(opts = {})
|
24
|
+
@attrs = {}
|
25
|
+
|
26
|
+
# Populate with all vars then merge in opts. This class deviates from
|
27
|
+
# the json gem in that any of the options can be set with the opts
|
28
|
+
# argument. The json gem limits the opts use to 7 of the options.
|
29
|
+
@attrs[:indent] = ''
|
30
|
+
@attrs[:space] = ''
|
31
|
+
@attrs[:space_before] = ''
|
32
|
+
@attrs[:array_nl] = ''
|
33
|
+
@attrs[:object_nl] = ''
|
34
|
+
@attrs[:allow_nan] = false
|
35
|
+
@attrs[:buffer_initial_length] = 1024 # completely ignored by Oj
|
36
|
+
@attrs[:depth] = 0
|
37
|
+
@attrs[:max_nesting] = 100
|
38
|
+
@attrs[:check_circular?] = true
|
39
|
+
@attrs[:ascii_only] = false
|
40
|
+
|
41
|
+
@attrs.merge!(opts)
|
42
|
+
end
|
43
|
+
|
44
|
+
def to_h()
|
45
|
+
return @attrs.dup
|
46
|
+
end
|
47
|
+
|
48
|
+
def to_hash()
|
49
|
+
return @attrs.dup
|
50
|
+
end
|
51
|
+
|
52
|
+
def allow_nan?()
|
53
|
+
@attrs[:allow_nan]
|
54
|
+
end
|
55
|
+
|
56
|
+
def ascii_only?()
|
57
|
+
@attrs[:ascii_only]
|
58
|
+
end
|
59
|
+
|
60
|
+
def configure(opts)
|
61
|
+
raise TypeError.new('expected a Hash') unless opts.respond_to?(:to_h)
|
62
|
+
@attrs.merge!(opts.to_h)
|
63
|
+
end
|
64
|
+
|
65
|
+
def generate(obj)
|
66
|
+
JSON.generate(obj)
|
67
|
+
end
|
68
|
+
|
69
|
+
def merge(opts)
|
70
|
+
@attrs.merge!(opts)
|
71
|
+
end
|
72
|
+
|
73
|
+
# special rule for this.
|
74
|
+
def buffer_initial_length=(len)
|
75
|
+
len = 1024 if 0 >= len
|
76
|
+
@attrs[:buffer_initial_length] = len
|
77
|
+
end
|
78
|
+
|
79
|
+
# Replaces the Object.respond_to?() method.
|
80
|
+
# @param [Symbol] m method symbol
|
81
|
+
# @return [Boolean] true for any method that matches an instance
|
82
|
+
# variable reader, otherwise false.
|
83
|
+
def respond_to?(m)
|
84
|
+
return true if super
|
85
|
+
return true if has_key?(key)
|
86
|
+
return true if has_key?(key.to_s)
|
87
|
+
has_key?(key.to_sym)
|
88
|
+
end
|
89
|
+
|
90
|
+
def [](key)
|
91
|
+
key = key.to_sym
|
92
|
+
@attrs.fetch(key, nil)
|
93
|
+
end
|
94
|
+
|
95
|
+
def []=(key, value)
|
96
|
+
key = key.to_sym
|
97
|
+
@attrs[key] = value
|
98
|
+
end
|
99
|
+
|
100
|
+
def clear()
|
101
|
+
@attrs.clear()
|
102
|
+
end
|
103
|
+
|
104
|
+
def has_key?(k)
|
105
|
+
@attrs.has_key?(key.to_sym)
|
106
|
+
end
|
107
|
+
|
108
|
+
# Handles requests for Hash values. Others cause an Exception to be raised.
|
109
|
+
# @param [Symbol|String] m method symbol
|
110
|
+
# @return [Boolean] the value of the specified instance variable.
|
111
|
+
# @raise [ArgumentError] if an argument is given. Zero arguments expected.
|
112
|
+
# @raise [NoMethodError] if the instance variable is not defined.
|
113
|
+
def method_missing(m, *args, &block)
|
114
|
+
if m.to_s.end_with?('=')
|
115
|
+
raise ArgumentError.new("wrong number of arguments (#{args.size} for 1 with #{m}) to method #{m}") if args.nil? or 1 != args.length
|
116
|
+
m = m.to_s[0..-2]
|
117
|
+
m = m.to_sym
|
118
|
+
return @attrs.store(m, args[0])
|
119
|
+
else
|
120
|
+
raise ArgumentError.new("wrong number of arguments (#{args.size} for 0 with #{m}) to method #{m}") unless args.nil? or args.empty?
|
121
|
+
return @attrs[m.to_sym]
|
122
|
+
end
|
123
|
+
raise NoMethodError.new("undefined method #{m}", m)
|
124
|
+
end
|
125
|
+
|
126
|
+
end # State
|
127
|
+
end # defined check
|
128
|
+
end # Generator
|
129
|
+
end # Ext
|
130
|
+
|
131
|
+
end # JSON
|
data/lib/oj/version.rb
ADDED
data/pages/Advanced.md
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
# Advanced Features
|
2
|
+
|
3
|
+
Optimized JSON (Oj), as the name implies, was written to provide speed optimized
|
4
|
+
JSON handling. It was designed as a faster alternative to Yajl and other
|
5
|
+
common Ruby JSON parsers. So far it has achieved that, and is about 2 times faster
|
6
|
+
than any other Ruby JSON parser, and 3 or more times faster at serializing JSON.
|
7
|
+
|
8
|
+
Oj has several `dump` or serialization modes which control how Ruby `Object`s are
|
9
|
+
converted to JSON. These modes are set with the `:mode` option in either the
|
10
|
+
default options or as one of the options to the `dump` method. In addition to
|
11
|
+
the various options there are also alternative APIs for parsing JSON.
|
12
|
+
|
13
|
+
The fastest alternative parser API is the `Oj::Doc` API. The `Oj::Doc` API takes
|
14
|
+
a completely different approach by opening a JSON document and providing calls
|
15
|
+
to navigate around the JSON while it is open. With this approach, JSON access
|
16
|
+
can be well over 20 times faster than conventional JSON parsing.
|
17
|
+
|
18
|
+
The `Oj::Saj` and `Oj::ScHandler` APIs are callback parsers that
|
19
|
+
walk the JSON document depth first and makes callbacks for each element.
|
20
|
+
Both callback parser are useful when only portions of the JSON are of
|
21
|
+
interest. Performance up to 20 times faster than conventional JSON is
|
22
|
+
possible if only a few elements of the JSON are of interest.
|
@@ -0,0 +1,25 @@
|
|
1
|
+
# Compatibility
|
2
|
+
|
3
|
+
**Ruby**
|
4
|
+
|
5
|
+
Oj is compatible with Ruby 2.0.0, 2.1, 2.2, 2.3, 2.4 and RBX.
|
6
|
+
Support for JRuby has been removed as JRuby no longer supports C extensions and
|
7
|
+
there are bugs in the older versions that are not being fixed.
|
8
|
+
|
9
|
+
**Rails**
|
10
|
+
|
11
|
+
Although up until 4.1 Rails uses [multi_json](https://github.com/intridea/multi_json), an [issue in Rails](https://github.com/rails/rails/issues/9212) causes ActiveSupport to fail to make use Oj for JSON handling.
|
12
|
+
There is a
|
13
|
+
[gem to patch this](https://github.com/GoodLife/rails-patch-json-encode) for
|
14
|
+
Rails 3.2 and 4.0. As of the Oj 2.6.0 release the default behavior is to not use
|
15
|
+
the `to_json()` method unless the `:use_to_json` option is set. This provides
|
16
|
+
another work around to the rails older and newer behavior.
|
17
|
+
|
18
|
+
The latest ActiveRecord is able to work with Oj by simply using the line:
|
19
|
+
|
20
|
+
```
|
21
|
+
serialize :metadata, Oj
|
22
|
+
```
|
23
|
+
|
24
|
+
In version Rails 4.1, multi_json has been removed, and this patch is unnecessary and will no longer work.
|
25
|
+
See {file:Rails.md}.
|
data/pages/Custom.md
ADDED
@@ -0,0 +1,23 @@
|
|
1
|
+
# Custom mode
|
2
|
+
|
3
|
+
The `:custom` mode is the most configurable mode and honors almost all
|
4
|
+
options. It provides the most flexibility although it can not be configured to
|
5
|
+
be exactly like any of the other modes. Each mode has some special aspect that
|
6
|
+
makes it unique. For example, the `:object` mode has it's own unique format
|
7
|
+
for object dumping and loading. The `:compat` mode mimic the json gem
|
8
|
+
including methods called for encoding and inconsistencies between
|
9
|
+
`JSON.dump()`, `JSON.generate()`, and `JSON()`.
|
10
|
+
|
11
|
+
The `:custom` mode is the default mode. It can be configured either by passing
|
12
|
+
options to the `Oj.dump()` and `Oj.load()` methods or by modifying the default
|
13
|
+
options.
|
14
|
+
|
15
|
+
The ability to create objects from JSON object elements is supported and
|
16
|
+
considers the `:create_additions` option. Special treatment is given to the
|
17
|
+
`:create_id` though. If the `:create_id` is set to `"^o"` then the Oj internal
|
18
|
+
encoding and decoding is used. These are more efficient than calling out to a
|
19
|
+
`to_json` method or `create_json` method on the classes. Those method do not
|
20
|
+
have to exist for the `"^o"` behavior to be utilized. Any other `:create_id`
|
21
|
+
value behaves similar to the json gem by calling `to_json` and `create_json`
|
22
|
+
as appropriate.
|
23
|
+
|
data/pages/Encoding.md
ADDED
@@ -0,0 +1,65 @@
|
|
1
|
+
# Oj `:object` Mode Encoding
|
2
|
+
|
3
|
+
Object mode is for fast Ruby object serialization and deserialization. That
|
4
|
+
was the primary purpose of Oj when it was first developed. As such it is the
|
5
|
+
default mode unless changed in the Oj default options. In :object mode Oj
|
6
|
+
generates JSON that follows conventions which allow Class and other
|
7
|
+
information such as Object IDs for circular reference detection to be encoded
|
8
|
+
in a JSON document. The formatting follows these rules.
|
9
|
+
|
10
|
+
* JSON native types, true, false, nil, String, Hash, Array, and Number are
|
11
|
+
encoded normally.
|
12
|
+
|
13
|
+
* A Symbol is encoded as a JSON string with a preceding `':'` character.
|
14
|
+
|
15
|
+
* The `'^'` character denotes a special key value when in a JSON Object sequence.
|
16
|
+
|
17
|
+
* A Ruby String that starts with `':'`or the sequence `'^i'` or `'^r'` are
|
18
|
+
encoded by excaping the first character so that it appears as `'\u005e'` or
|
19
|
+
`'\u003a'` instead of `':'` or `'^'`.
|
20
|
+
|
21
|
+
* A `"^c"` JSON Object key indicates the value should be converted to a Ruby
|
22
|
+
class. The sequence `{"^c":"Oj::Bag"}` is read as the Oj::Bag class.
|
23
|
+
|
24
|
+
* A `"^t"` JSON Object key indicates the value should be converted to a Ruby
|
25
|
+
Time. The sequence `{"^t":1325775487.000000}` is read as Jan 5, 2012 at
|
26
|
+
23:58:07.
|
27
|
+
|
28
|
+
* A `"^o"` JSON Object key indicates the value should be converted to a Ruby
|
29
|
+
Object. The first entry in the JSON Object must be a class with the `"^o"`
|
30
|
+
key. After that each entry is treated as a variable of the Object where the
|
31
|
+
key is the variable name without the preceding `'@'`. An example is
|
32
|
+
`{"^o":"Oj::Bag","x":58,"y":"marbles"}`. `"^O"`is the same except that it
|
33
|
+
is for built in or odd classes that don't obey the normal Ruby
|
34
|
+
rules. Examples are Rational, Date, and DateTime.
|
35
|
+
|
36
|
+
* A `"^u"` JSON Object key indicates the value should be converted to a Ruby
|
37
|
+
Struct. The first entry in the JSON Object must be a class with the
|
38
|
+
`"^u"` key. After that each entry is is given a numeric position in the
|
39
|
+
struct and that is used as the key in the JSON Object. An example is
|
40
|
+
`{"^u":["Range",1,7,false]}`.
|
41
|
+
|
42
|
+
* When encoding an Object, if the variable name does not begin with an
|
43
|
+
`'@'`character then the name preceded by a `'~'` character. This occurs in
|
44
|
+
the Exception class. An example is `{"^o":"StandardError","~mesg":"A
|
45
|
+
Message","~bt":[".\/tests.rb:345:in 'test_exception'"]}`.
|
46
|
+
|
47
|
+
* If a Hash entry has a key that is not a String or Symbol then the entry is
|
48
|
+
encoded with a key of the form `"^#n"` where n is a hex number. The value
|
49
|
+
is an Array where the first element is the key in the Hash and the second
|
50
|
+
is the value. An example is `{"^#3":[2,5]}`.
|
51
|
+
|
52
|
+
* A `"^i"` JSON entry in either an Object or Array is the ID of the Ruby
|
53
|
+
Object being encoded. It is used when the :circular flag is set. It can
|
54
|
+
appear in either a JSON Object or in a JSON Array. In an Object the
|
55
|
+
`"^i"` key has a corresponding reference Fixnum. In an array the sequence
|
56
|
+
will include an embedded reference number. An example is
|
57
|
+
`{"^o":"Oj::Bag","^i":1,"x":["^i2",true],"me":"^r1"}`.
|
58
|
+
|
59
|
+
* A `"^r"`JSON entry in an Object is a references to a Object or Array that
|
60
|
+
already appears in the JSON String. It must match up with a previous
|
61
|
+
`"^i"` ID. An example is `{"^o":"Oj::Bag","^i":1,"x":3,"me":"^r1"}`.
|
62
|
+
|
63
|
+
* If an Array element is a String and starts with `"^i"` then the first
|
64
|
+
character, the `'^'` is encoded as a hex character sequence. An example is
|
65
|
+
`["\u005ei37",3]`.
|