psych 1.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (89) hide show
  1. data/.autotest +18 -0
  2. data/.gemtest +0 -0
  3. data/CHANGELOG.rdoc +3 -0
  4. data/Manifest.txt +87 -0
  5. data/README.rdoc +50 -0
  6. data/Rakefile +66 -0
  7. data/ext/psych/emitter.c +517 -0
  8. data/ext/psych/emitter.h +8 -0
  9. data/ext/psych/extconf.rb +22 -0
  10. data/ext/psych/parser.c +384 -0
  11. data/ext/psych/parser.h +6 -0
  12. data/ext/psych/psych.c +34 -0
  13. data/ext/psych/psych.h +20 -0
  14. data/ext/psych/to_ruby.c +41 -0
  15. data/ext/psych/to_ruby.h +8 -0
  16. data/ext/psych/yaml_tree.c +24 -0
  17. data/ext/psych/yaml_tree.h +8 -0
  18. data/lib/psych.rb +263 -0
  19. data/lib/psych/coder.rb +94 -0
  20. data/lib/psych/core_ext.rb +39 -0
  21. data/lib/psych/deprecated.rb +82 -0
  22. data/lib/psych/handler.rb +221 -0
  23. data/lib/psych/json.rb +6 -0
  24. data/lib/psych/json/ruby_events.rb +19 -0
  25. data/lib/psych/json/stream.rb +15 -0
  26. data/lib/psych/json/tree_builder.rb +12 -0
  27. data/lib/psych/json/yaml_events.rb +29 -0
  28. data/lib/psych/nodes.rb +77 -0
  29. data/lib/psych/nodes/alias.rb +18 -0
  30. data/lib/psych/nodes/document.rb +60 -0
  31. data/lib/psych/nodes/mapping.rb +56 -0
  32. data/lib/psych/nodes/node.rb +52 -0
  33. data/lib/psych/nodes/scalar.rb +67 -0
  34. data/lib/psych/nodes/sequence.rb +81 -0
  35. data/lib/psych/nodes/stream.rb +37 -0
  36. data/lib/psych/omap.rb +4 -0
  37. data/lib/psych/parser.rb +47 -0
  38. data/lib/psych/scalar_scanner.rb +105 -0
  39. data/lib/psych/set.rb +4 -0
  40. data/lib/psych/stream.rb +36 -0
  41. data/lib/psych/streaming.rb +22 -0
  42. data/lib/psych/tree_builder.rb +94 -0
  43. data/lib/psych/visitors.rb +6 -0
  44. data/lib/psych/visitors/depth_first.rb +26 -0
  45. data/lib/psych/visitors/emitter.rb +44 -0
  46. data/lib/psych/visitors/json_tree.rb +21 -0
  47. data/lib/psych/visitors/to_ruby.rb +267 -0
  48. data/lib/psych/visitors/visitor.rb +19 -0
  49. data/lib/psych/visitors/yaml_tree.rb +373 -0
  50. data/test/psych/helper.rb +63 -0
  51. data/test/psych/json/test_stream.rb +109 -0
  52. data/test/psych/nodes/test_enumerable.rb +43 -0
  53. data/test/psych/test_alias_and_anchor.rb +26 -0
  54. data/test/psych/test_array.rb +19 -0
  55. data/test/psych/test_boolean.rb +36 -0
  56. data/test/psych/test_class.rb +17 -0
  57. data/test/psych/test_coder.rb +184 -0
  58. data/test/psych/test_date_time.rb +17 -0
  59. data/test/psych/test_deprecated.rb +210 -0
  60. data/test/psych/test_document.rb +46 -0
  61. data/test/psych/test_emitter.rb +94 -0
  62. data/test/psych/test_encoding.rb +179 -0
  63. data/test/psych/test_engine_manager.rb +57 -0
  64. data/test/psych/test_exception.rb +39 -0
  65. data/test/psych/test_hash.rb +30 -0
  66. data/test/psych/test_json_tree.rb +65 -0
  67. data/test/psych/test_merge_keys.rb +72 -0
  68. data/test/psych/test_nil.rb +18 -0
  69. data/test/psych/test_null.rb +19 -0
  70. data/test/psych/test_object.rb +27 -0
  71. data/test/psych/test_omap.rb +68 -0
  72. data/test/psych/test_parser.rb +297 -0
  73. data/test/psych/test_psych.rb +168 -0
  74. data/test/psych/test_scalar.rb +11 -0
  75. data/test/psych/test_scalar_scanner.rb +69 -0
  76. data/test/psych/test_serialize_subclasses.rb +38 -0
  77. data/test/psych/test_set.rb +49 -0
  78. data/test/psych/test_stream.rb +49 -0
  79. data/test/psych/test_string.rb +49 -0
  80. data/test/psych/test_struct.rb +51 -0
  81. data/test/psych/test_symbol.rb +17 -0
  82. data/test/psych/test_to_yaml_properties.rb +63 -0
  83. data/test/psych/test_tree_builder.rb +79 -0
  84. data/test/psych/test_yaml.rb +1256 -0
  85. data/test/psych/visitors/test_depth_first.rb +49 -0
  86. data/test/psych/visitors/test_emitter.rb +144 -0
  87. data/test/psych/visitors/test_to_ruby.rb +325 -0
  88. data/test/psych/visitors/test_yaml_tree.rb +155 -0
  89. metadata +232 -0
@@ -0,0 +1,109 @@
1
+ require 'psych/helper'
2
+
3
+ module Psych
4
+ module JSON
5
+ class TestStream < TestCase
6
+ def setup
7
+ @io = StringIO.new
8
+ @stream = Psych::JSON::Stream.new(@io)
9
+ @stream.start
10
+ end
11
+
12
+ def test_explicit_documents
13
+ @io = StringIO.new
14
+ @stream = Psych::JSON::Stream.new(@io)
15
+ @stream.start
16
+
17
+ @stream.push({ 'foo' => 'bar' })
18
+
19
+ assert !@stream.finished?, 'stream not finished'
20
+ @stream.finish
21
+ assert @stream.finished?, 'stream finished'
22
+
23
+ assert_match(/^---/, @io.string)
24
+ assert_match(/\.\.\.$/, @io.string)
25
+ end
26
+
27
+ def test_null
28
+ @stream.push(nil)
29
+ assert_match(/^--- null/, @io.string)
30
+ end
31
+
32
+ def test_string
33
+ @stream.push "foo"
34
+ assert_match(/(["])foo\1/, @io.string)
35
+ end
36
+
37
+ def test_symbol
38
+ @stream.push :foo
39
+ assert_match(/(["])foo\1/, @io.string)
40
+ end
41
+
42
+ def test_int
43
+ @stream.push 10
44
+ assert_match(/^--- 10/, @io.string)
45
+ end
46
+
47
+ def test_float
48
+ @stream.push 1.2
49
+ assert_match(/^--- 1.2/, @io.string)
50
+ end
51
+
52
+ def test_hash
53
+ hash = { 'one' => 'two' }
54
+ @stream.push hash
55
+
56
+ json = @io.string
57
+ assert_match(/}$/, json)
58
+ assert_match(/^--- \{/, json)
59
+ assert_match(/["]one['"]/, json)
60
+ assert_match(/["]two['"]/, json)
61
+ end
62
+
63
+ def test_list_to_json
64
+ list = %w{ one two }
65
+ @stream.push list
66
+
67
+ json = @io.string
68
+ assert_match(/]$/, json)
69
+ assert_match(/^--- \[/, json)
70
+ assert_match(/["]one["]/, json)
71
+ assert_match(/["]two["]/, json)
72
+ end
73
+
74
+ class Foo; end
75
+
76
+ def test_json_dump_exclude_tag
77
+ @stream << Foo.new
78
+ json = @io.string
79
+ refute_match('Foo', json)
80
+ end
81
+
82
+ class Bar
83
+ def encode_with coder
84
+ coder.represent_seq 'omg', %w{ a b c }
85
+ end
86
+ end
87
+
88
+ def test_json_list_dump_exclude_tag
89
+ @stream << Bar.new
90
+ json = @io.string
91
+ refute_match('omg', json)
92
+ end
93
+
94
+ def test_time
95
+ time = Time.utc(2010, 10, 10)
96
+ @stream.push({'a' => time })
97
+ json = @io.string
98
+ assert_match "{\"a\": \"2010-10-10 00:00:00.000000000Z\"}\n", json
99
+ end
100
+
101
+ def test_datetime
102
+ time = Time.new(2010, 10, 10).to_datetime
103
+ @stream.push({'a' => time })
104
+ json = @io.string
105
+ assert_match "{\"a\": \"#{time.strftime("%Y-%m-%d %H:%M:%S.%9N %:z")}\"}\n", json
106
+ end
107
+ end
108
+ end
109
+ end
@@ -0,0 +1,43 @@
1
+ require 'psych/helper'
2
+
3
+ module Psych
4
+ module Nodes
5
+ class TestEnumerable < TestCase
6
+ def test_includes_enumerable
7
+ yaml = '--- hello'
8
+ assert_equal 3, Psych.parse_stream(yaml).to_a.length
9
+ end
10
+
11
+ def test_returns_enumerator
12
+ yaml = '--- hello'
13
+ assert_equal 3, Psych.parse_stream(yaml).each.map { |x| x }.length
14
+ end
15
+
16
+ def test_scalar
17
+ assert_equal 3, calls('--- hello').length
18
+ end
19
+
20
+ def test_sequence
21
+ assert_equal 4, calls("---\n- hello").length
22
+ end
23
+
24
+ def test_mapping
25
+ assert_equal 5, calls("---\nhello: world").length
26
+ end
27
+
28
+ def test_alias
29
+ assert_equal 5, calls("--- &yay\n- foo\n- *yay\n").length
30
+ end
31
+
32
+ private
33
+
34
+ def calls yaml
35
+ calls = []
36
+ Psych.parse_stream(yaml).each do |node|
37
+ calls << node
38
+ end
39
+ calls
40
+ end
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,26 @@
1
+ require 'psych/helper'
2
+
3
+ module Psych
4
+ class TestAliasAndAnchor < TestCase
5
+ def test_mri_compatibility
6
+ yaml = <<EOYAML
7
+ ---
8
+ - &id001 !ruby/object {}
9
+
10
+ - *id001
11
+ - *id001
12
+ EOYAML
13
+ result = Psych.load yaml
14
+ result.each {|el| assert_same(result[0], el) }
15
+ end
16
+
17
+ def test_anchor_alias_round_trip
18
+ o = Object.new
19
+ original = [o,o,o]
20
+
21
+ yaml = Psych.dump original
22
+ result = Psych.load yaml
23
+ result.each {|el| assert_same(result[0], el) }
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,19 @@
1
+ require 'psych/helper'
2
+
3
+ module Psych
4
+ class TestArray < TestCase
5
+ def setup
6
+ super
7
+ @list = [{ :a => 'b' }, 'foo']
8
+ end
9
+
10
+ def test_self_referential
11
+ @list << @list
12
+ assert_cycle(@list)
13
+ end
14
+
15
+ def test_cycle
16
+ assert_cycle(@list)
17
+ end
18
+ end
19
+ end
@@ -0,0 +1,36 @@
1
+ require 'psych/helper'
2
+
3
+ module Psych
4
+ ###
5
+ # Test booleans from YAML spec:
6
+ # http://yaml.org/type/bool.html
7
+ class TestBoolean < TestCase
8
+ %w{ yes Yes YES true True TRUE on On ON }.each do |truth|
9
+ define_method(:"test_#{truth}") do
10
+ assert_equal true, Psych.load("--- #{truth}")
11
+ end
12
+ end
13
+
14
+ %w{ no No NO false False FALSE off Off OFF }.each do |truth|
15
+ define_method(:"test_#{truth}") do
16
+ assert_equal false, Psych.load("--- #{truth}")
17
+ end
18
+ end
19
+
20
+ ###
21
+ # YAML spec says "y" and "Y" may be used as true, but Syck treats them
22
+ # as literal strings
23
+ def test_y
24
+ assert_equal "y", Psych.load("--- y")
25
+ assert_equal "Y", Psych.load("--- Y")
26
+ end
27
+
28
+ ###
29
+ # YAML spec says "n" and "N" may be used as false, but Syck treats them
30
+ # as literal strings
31
+ def test_n
32
+ assert_equal "n", Psych.load("--- n")
33
+ assert_equal "N", Psych.load("--- N")
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,17 @@
1
+ require 'psych/helper'
2
+
3
+ module Psych
4
+ class TestClass < TestCase
5
+ def test_cycle
6
+ assert_raises(::TypeError) do
7
+ assert_cycle(TestClass)
8
+ end
9
+ end
10
+
11
+ def test_dump
12
+ assert_raises(::TypeError) do
13
+ Psych.dump TestClass
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,184 @@
1
+ require 'psych/helper'
2
+
3
+ module Psych
4
+ class TestCoder < TestCase
5
+ class InitApi
6
+ attr_accessor :implicit
7
+ attr_accessor :style
8
+ attr_accessor :tag
9
+ attr_accessor :a, :b, :c
10
+
11
+ def initialize
12
+ @a = 1
13
+ @b = 2
14
+ @c = 3
15
+ end
16
+
17
+ def init_with coder
18
+ @a = coder['aa']
19
+ @b = coder['bb']
20
+ @implicit = coder.implicit
21
+ @tag = coder.tag
22
+ @style = coder.style
23
+ end
24
+
25
+ def encode_with coder
26
+ coder['aa'] = @a
27
+ coder['bb'] = @b
28
+ end
29
+ end
30
+
31
+ class TaggingCoder < InitApi
32
+ def encode_with coder
33
+ super
34
+ coder.tag = coder.tag.sub(/!/, '!hello')
35
+ coder.implicit = false
36
+ coder.style = Psych::Nodes::Mapping::FLOW
37
+ end
38
+ end
39
+
40
+ class ScalarCoder
41
+ def encode_with coder
42
+ coder.scalar = "foo"
43
+ end
44
+ end
45
+
46
+ class Represent
47
+ yaml_tag 'foo'
48
+ def encode_with coder
49
+ coder.represent_scalar 'foo', 'bar'
50
+ end
51
+ end
52
+
53
+ class RepresentWithInit
54
+ yaml_tag name
55
+ attr_accessor :str
56
+
57
+ def init_with coder
58
+ @str = coder.scalar
59
+ end
60
+
61
+ def encode_with coder
62
+ coder.represent_scalar self.class.name, 'bar'
63
+ end
64
+ end
65
+
66
+ class RepresentWithSeq
67
+ yaml_tag name
68
+ attr_accessor :seq
69
+
70
+ def init_with coder
71
+ @seq = coder.seq
72
+ end
73
+
74
+ def encode_with coder
75
+ coder.represent_seq self.class.name, %w{ foo bar }
76
+ end
77
+ end
78
+
79
+ class RepresentWithMap
80
+ yaml_tag name
81
+ attr_accessor :map
82
+
83
+ def init_with coder
84
+ @map = coder.map
85
+ end
86
+
87
+ def encode_with coder
88
+ coder.represent_map self.class.name, { 'a' => 'b' }
89
+ end
90
+ end
91
+
92
+ class RepresentWithObject
93
+ def encode_with coder
94
+ coder.represent_object self.class.name, 20
95
+ end
96
+ end
97
+
98
+ def test_represent_with_object
99
+ thing = Psych.load(Psych.dump(RepresentWithObject.new))
100
+ assert_equal 20, thing
101
+ end
102
+
103
+ def test_json_dump_exclude_tag
104
+ refute_match('TestCoder::InitApi', Psych.to_json(InitApi.new))
105
+ end
106
+
107
+ def test_map_takes_block
108
+ coder = Psych::Coder.new 'foo'
109
+ tag = coder.tag
110
+ style = coder.style
111
+ coder.map { |map| map.add 'foo', 'bar' }
112
+ assert_equal 'bar', coder['foo']
113
+ assert_equal tag, coder.tag
114
+ assert_equal style, coder.style
115
+ end
116
+
117
+ def test_map_with_tag
118
+ coder = Psych::Coder.new 'foo'
119
+ coder.map('hello') { |map| map.add 'foo', 'bar' }
120
+ assert_equal 'bar', coder['foo']
121
+ assert_equal 'hello', coder.tag
122
+ end
123
+
124
+ def test_map_with_tag_and_style
125
+ coder = Psych::Coder.new 'foo'
126
+ coder.map('hello', 'world') { |map| map.add 'foo', 'bar' }
127
+ assert_equal 'bar', coder['foo']
128
+ assert_equal 'hello', coder.tag
129
+ assert_equal 'world', coder.style
130
+ end
131
+
132
+ def test_represent_map
133
+ thing = Psych.load(Psych.dump(RepresentWithMap.new))
134
+ assert_equal({ 'a' => 'b' }, thing.map)
135
+ end
136
+
137
+ def test_represent_sequence
138
+ thing = Psych.load(Psych.dump(RepresentWithSeq.new))
139
+ assert_equal %w{ foo bar }, thing.seq
140
+ end
141
+
142
+ def test_represent_with_init
143
+ thing = Psych.load(Psych.dump(RepresentWithInit.new))
144
+ assert_equal 'bar', thing.str
145
+ end
146
+
147
+ def test_represent!
148
+ assert_match(/foo/, Psych.dump(Represent.new))
149
+ assert_instance_of(Represent, Psych.load(Psych.dump(Represent.new)))
150
+ end
151
+
152
+ def test_scalar_coder
153
+ foo = Psych.load(Psych.dump(ScalarCoder.new))
154
+ assert_equal 'foo', foo
155
+ end
156
+
157
+ def test_load_dumped_tagging
158
+ foo = InitApi.new
159
+ bar = Psych.load(Psych.dump(foo))
160
+ assert_equal false, bar.implicit
161
+ assert_equal "!ruby/object:Psych::TestCoder::InitApi", bar.tag
162
+ assert_equal Psych::Nodes::Mapping::BLOCK, bar.style
163
+ end
164
+
165
+ def test_dump_with_tag
166
+ foo = TaggingCoder.new
167
+ assert_match(/hello/, Psych.dump(foo))
168
+ assert_match(/\{aa/, Psych.dump(foo))
169
+ end
170
+
171
+ def test_dump_encode_with
172
+ foo = InitApi.new
173
+ assert_match(/aa/, Psych.dump(foo))
174
+ end
175
+
176
+ def test_dump_init_with
177
+ foo = InitApi.new
178
+ bar = Psych.load(Psych.dump(foo))
179
+ assert_equal foo.a, bar.a
180
+ assert_equal foo.b, bar.b
181
+ assert_nil bar.c
182
+ end
183
+ end
184
+ end
@@ -0,0 +1,17 @@
1
+ require 'psych/helper'
2
+ require 'date'
3
+
4
+ module Psych
5
+ class TestDateTime < TestCase
6
+ def test_string_tag
7
+ dt = DateTime.now
8
+ yaml = Psych.dump dt
9
+ assert_match(/DateTime/, yaml)
10
+ end
11
+
12
+ def test_round_trip
13
+ dt = DateTime.now
14
+ assert_cycle dt
15
+ end
16
+ end
17
+ end