hocon 1.2.5 → 1.2.6

Sign up to get free protection for your applications and to get access to all the features.
Files changed (50) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +6 -1
  3. data/lib/hocon/version.rb +1 -1
  4. metadata +1 -47
  5. data/spec/fixtures/hocon/by_extension/cat.conf +0 -4
  6. data/spec/fixtures/hocon/by_extension/cat.test +0 -4
  7. data/spec/fixtures/hocon/by_extension/cat.test-json +0 -3
  8. data/spec/fixtures/hocon/with_substitution/subst.conf +0 -2
  9. data/spec/fixtures/parse_render/example1/input.conf +0 -21
  10. data/spec/fixtures/parse_render/example1/output.conf +0 -26
  11. data/spec/fixtures/parse_render/example1/output_nocomments.conf +0 -17
  12. data/spec/fixtures/parse_render/example2/input.conf +0 -10
  13. data/spec/fixtures/parse_render/example2/output.conf +0 -17
  14. data/spec/fixtures/parse_render/example2/output_nocomments.conf +0 -17
  15. data/spec/fixtures/parse_render/example3/input.conf +0 -2
  16. data/spec/fixtures/parse_render/example3/output.conf +0 -2
  17. data/spec/fixtures/parse_render/example4/input.json +0 -6
  18. data/spec/fixtures/parse_render/example4/output.conf +0 -6
  19. data/spec/fixtures/test_utils/resources/bom.conf +0 -2
  20. data/spec/fixtures/test_utils/resources/cycle.conf +0 -1
  21. data/spec/fixtures/test_utils/resources/file-include.conf +0 -5
  22. data/spec/fixtures/test_utils/resources/include-from-list.conf +0 -4
  23. data/spec/fixtures/test_utils/resources/subdir/bar.conf +0 -1
  24. data/spec/fixtures/test_utils/resources/subdir/baz.conf +0 -1
  25. data/spec/fixtures/test_utils/resources/subdir/foo.conf +0 -5
  26. data/spec/fixtures/test_utils/resources/test01.conf +0 -80
  27. data/spec/fixtures/test_utils/resources/test01.json +0 -4
  28. data/spec/fixtures/test_utils/resources/test03.conf +0 -36
  29. data/spec/fixtures/test_utils/resources/utf16.conf +0 -0
  30. data/spec/fixtures/test_utils/resources/utf8.conf +0 -2
  31. data/spec/fixtures/test_utils/resources//341/232/240/341/233/207/341/232/273.conf +0 -2
  32. data/spec/spec_helper.rb +0 -43
  33. data/spec/test_utils.rb +0 -758
  34. data/spec/unit/cli/cli_spec.rb +0 -157
  35. data/spec/unit/hocon/README.md +0 -7
  36. data/spec/unit/hocon/hocon_spec.rb +0 -114
  37. data/spec/unit/typesafe/config/README.md +0 -4
  38. data/spec/unit/typesafe/config/concatenation_spec.rb +0 -417
  39. data/spec/unit/typesafe/config/conf_parser_spec.rb +0 -831
  40. data/spec/unit/typesafe/config/config_document_parser_spec.rb +0 -494
  41. data/spec/unit/typesafe/config/config_document_spec.rb +0 -576
  42. data/spec/unit/typesafe/config/config_factory_spec.rb +0 -120
  43. data/spec/unit/typesafe/config/config_node_spec.rb +0 -552
  44. data/spec/unit/typesafe/config/config_value_factory_spec.rb +0 -85
  45. data/spec/unit/typesafe/config/config_value_spec.rb +0 -959
  46. data/spec/unit/typesafe/config/path_spec.rb +0 -261
  47. data/spec/unit/typesafe/config/public_api_spec.rb +0 -520
  48. data/spec/unit/typesafe/config/simple_config_spec.rb +0 -112
  49. data/spec/unit/typesafe/config/token_spec.rb +0 -188
  50. data/spec/unit/typesafe/config/tokenizer_spec.rb +0 -801
@@ -1,157 +0,0 @@
1
- # encoding: utf-8
2
-
3
- require 'spec_helper'
4
- require 'test_utils'
5
-
6
-
7
- describe Hocon::CLI do
8
- ####################
9
- # Argument Parsing
10
- ####################
11
- context 'argument parsing' do
12
- it 'should find all the flags and arguments' do
13
- args = %w(-i foo -o bar set some.path some_value --json)
14
- expected_options = {
15
- in_file: 'foo',
16
- out_file: 'bar',
17
- subcommand: 'set',
18
- path: 'some.path',
19
- new_value: 'some_value',
20
- json: true
21
- }
22
- expect(Hocon::CLI.parse_args(args)).to eq(expected_options)
23
- end
24
-
25
- it 'should set -i and -o to -f if given' do
26
- args = %w(-f foo set some.path some_value)
27
- expected_options = {
28
- file: 'foo',
29
- in_file: 'foo',
30
- out_file: 'foo',
31
- subcommand: 'set',
32
- path: 'some.path',
33
- new_value: 'some_value'
34
- }
35
- expect(Hocon::CLI.parse_args(args)).to eq(expected_options)
36
- end
37
- end
38
-
39
- context 'subcommands' do
40
- hocon_text =
41
- 'foo.bar {
42
- baz = 42
43
- array = [1, 2, 3]
44
- hash: {key: value}
45
- }'
46
-
47
- context 'do_get()' do
48
- it 'should get simple values' do
49
- options = {path: 'foo.bar.baz'}
50
- expect(Hocon::CLI.do_get(options, hocon_text)).to eq('42')
51
- end
52
-
53
- it 'should work with arrays' do
54
- options = {path: 'foo.bar.array'}
55
- expected = "[\n 1,\n 2,\n 3\n]"
56
- expect(Hocon::CLI.do_get(options, hocon_text)).to eq(expected)
57
- end
58
-
59
- it 'should work with hashes' do
60
- options = {path: 'foo.bar.hash'}
61
- expected = "key: value\n"
62
- expect(Hocon::CLI.do_get(options, hocon_text)).to eq(expected)
63
- end
64
-
65
- it 'should output json if specified' do
66
- options = {path: 'foo.bar.hash', json: true}
67
-
68
- # Note that this is valid json, while the test above is not
69
- expected = "{\n \"key\": \"value\"\n}\n"
70
- expect(Hocon::CLI.do_get(options, hocon_text)).to eq(expected)
71
- end
72
-
73
- it 'should throw a MissingPathError if the path does not exist' do
74
- options = {path: 'not.a.path'}
75
- expect {Hocon::CLI.do_get(options, hocon_text)}
76
- .to raise_error(Hocon::CLI::MissingPathError)
77
- end
78
-
79
- it 'should throw a MissingPathError if the path leads into an array' do
80
- options = {path: 'foo.array.1'}
81
- expect {Hocon::CLI.do_get(options, hocon_text)}
82
- .to raise_error(Hocon::CLI::MissingPathError)
83
- end
84
-
85
- it 'should throw a MissingPathError if the path leads into a string' do
86
- options = {path: 'foo.hash.key.value'}
87
- expect {Hocon::CLI.do_get(options, hocon_text)}
88
- .to raise_error(Hocon::CLI::MissingPathError)
89
- end
90
- end
91
-
92
- context 'do_set()' do
93
- it 'should overwrite values' do
94
- options = {path: 'foo.bar.baz', new_value: 'pi'}
95
- expected = hocon_text.sub(/42/, 'pi')
96
- expect(Hocon::CLI.do_set(options, hocon_text)).to eq(expected)
97
- end
98
-
99
- it 'should create new nested values' do
100
- options = {path: 'new.nested.path', new_value: 'hello'}
101
- expected = "new: {\n nested: {\n path: hello\n }\n}"
102
- # No config is supplied, so it will need to add new nested hashes
103
- expect(Hocon::CLI.do_set(options, '')).to eq(expected)
104
- end
105
-
106
- it 'should allow arrays to be set' do
107
- options = {path: 'my_array', new_value: '[1, 2, 3]'}
108
- expected = 'my_array: [1, 2, 3]'
109
- expect(Hocon::CLI.do_set(options, '')).to eq(expected)
110
- end
111
-
112
- it 'should allow arrays in strings to be set as strings' do
113
- options = {path: 'my_array', new_value: '"[1, 2, 3]"'}
114
- expected = 'my_array: "[1, 2, 3]"'
115
- expect(Hocon::CLI.do_set(options, '')).to eq(expected)
116
- end
117
-
118
- it 'should allow hashes to be set' do
119
- do_set_options = {path: 'my_hash', new_value: '{key: value}'}
120
- do_set_expected = 'my_hash: {key: value}'
121
- do_set_result = Hocon::CLI.do_set(do_set_options, '')
122
- expect(do_set_result).to eq(do_set_expected)
123
-
124
- # Make sure it can be parsed again and be seen as a real hash
125
- do_get_options = {path: 'my_hash.key'}
126
- do_get_expected = 'value'
127
- expect(Hocon::CLI.do_get(do_get_options, do_set_result)).to eq(do_get_expected)
128
- end
129
-
130
- it 'should allow hashes to be set as strings' do
131
- do_set_options = {path: 'my_hash', new_value: '"{key: value}"'}
132
- do_set_expected = 'my_hash: "{key: value}"'
133
- do_set_result = Hocon::CLI.do_set(do_set_options, '')
134
- expect(do_set_result).to eq(do_set_expected)
135
-
136
- # Make sure it can't be parsed again and be seen as a real hash
137
- do_get_options = {path: 'my_hash.key'}
138
- expect{Hocon::CLI.do_get(do_get_options, do_set_result)}
139
- .to raise_error(Hocon::CLI::MissingPathError)
140
- end
141
- end
142
-
143
- context 'do_unset()' do
144
- it 'should remove values' do
145
- options = {path: 'foo.bar.baz'}
146
- expected = hocon_text.sub(/baz = 42/, '')
147
- expect(Hocon::CLI.do_unset(options, hocon_text)).to eq(expected)
148
- end
149
-
150
- it 'should throw a MissingPathError if the path does not exist' do
151
- options = {path: 'fake.path'}
152
- expect{Hocon::CLI.do_unset(options, hocon_text)}
153
- .to raise_error(Hocon::CLI::MissingPathError)
154
- end
155
- end
156
- end
157
- end
@@ -1,7 +0,0 @@
1
- ## RUBY-SPECIFIC TESTS
2
-
3
- This directory should only contain tests that are specific to the Ruby library/API.
4
- Tests ported from the upstream Java library should live in spec/typesafe/config.
5
-
6
- Where possible it would be good to avoid sharing fixtures between the two types
7
- of tests as well.
@@ -1,114 +0,0 @@
1
- # encoding: utf-8
2
-
3
- require 'spec_helper'
4
- require 'hocon'
5
- require 'hocon/config_render_options'
6
- require 'hocon/config_error'
7
- require 'hocon/config_syntax'
8
-
9
- ConfigParseError = Hocon::ConfigError::ConfigParseError
10
- ConfigWrongTypeError = Hocon::ConfigError::ConfigWrongTypeError
11
-
12
- describe Hocon do
13
- let(:render_options) { Hocon::ConfigRenderOptions.defaults }
14
-
15
- before do
16
- render_options.origin_comments = false
17
- render_options.json = false
18
- end
19
-
20
- RSpec.shared_examples "hocon_parsing" do
21
-
22
- it "should make the config data available as a map" do
23
- expect(conf).to eq(expected)
24
- end
25
-
26
- end
27
-
28
- [EXAMPLE1, EXAMPLE2].each do |example|
29
- let(:input_file) { "#{FIXTURE_DIR}/parse_render/#{example[:name]}/input.conf" }
30
- let(:output_file) { "#{FIXTURE_DIR}/parse_render/#{example[:name]}/output.conf" }
31
- let(:output) { File.read("#{output_file}") }
32
- let(:output_nocomments_file) { "#{FIXTURE_DIR}/parse_render/#{example[:name]}/output_nocomments.conf" }
33
- let(:output_nocomments) { File.read("#{output_nocomments_file}") }
34
- let(:expected) { example[:hash] }
35
- # TODO 'reparsed' appears to be unused
36
- let(:reparsed) { Hocon::ConfigFactory.parse_file("#{FIXTURE_DIR}/parse_render/#{example[:name]}/output.conf") }
37
-
38
- context "loading a HOCON file" do
39
- let(:conf) { Hocon.load(input_file) }
40
- include_examples "hocon_parsing"
41
- end
42
-
43
- context "parsing a HOCON string" do
44
- let(:string) { File.open(input_file).read }
45
- let(:conf) { Hocon.parse(string) }
46
- include_examples "hocon_parsing"
47
- end
48
- end
49
-
50
- it "should fail to parse an array" do
51
- puts
52
- expect{(Hocon.parse('[1,2,3]'))}.
53
- to raise_error(ConfigWrongTypeError)
54
- end
55
-
56
- it "should fail to parse an array" do
57
- expect{(Hocon.parse('["one", "two" "three"]'))}.
58
- to raise_error(ConfigWrongTypeError)
59
- end
60
-
61
- context "loading a HOCON file with a substitution" do
62
- conf = Hocon.load("#{FIXTURE_DIR}/parse_render/#{EXAMPLE3[:name]}/input.conf")
63
- expected = EXAMPLE3[:hash]
64
- it "should successfully resolve the substitution" do
65
- expect(conf).to eq(expected)
66
- end
67
- end
68
-
69
- context "loading a file with an unknown extension" do
70
- context "without specifying the config format" do
71
- it "should raise an error" do
72
- expect {
73
- Hocon.load("#{FIXTURE_DIR}/hocon/by_extension/cat.test")
74
- }.to raise_error(ConfigParseError, /Unrecognized file extension '.test'/)
75
- end
76
- end
77
-
78
- context "while specifying the config format" do
79
- it "should parse properly if the config format is correct" do
80
- expect(Hocon.load("#{FIXTURE_DIR}/hocon/by_extension/cat.test",
81
- {:syntax => Hocon::ConfigSyntax::HOCON})).
82
- to eq({"meow" => "cats"})
83
- expect(Hocon.load("#{FIXTURE_DIR}/hocon/by_extension/cat.test-json",
84
- {:syntax => Hocon::ConfigSyntax::HOCON})).
85
- to eq({"meow" => "cats"})
86
- end
87
- it "should parse properly if the config format is compatible" do
88
- expect(Hocon.load("#{FIXTURE_DIR}/hocon/by_extension/cat.test-json",
89
- {:syntax => Hocon::ConfigSyntax::JSON})).
90
- to eq({"meow" => "cats"})
91
- end
92
- it "should raise an error if the config format is incompatible" do
93
- expect {
94
- Hocon.load("#{FIXTURE_DIR}/hocon/by_extension/cat.test",
95
- {:syntax => Hocon::ConfigSyntax::JSON})
96
- }.to raise_error(ConfigParseError, /Document must have an object or array at root/)
97
- end
98
- end
99
- end
100
-
101
- context "loading config that includes substitutions" do
102
- it "should be able to `load` from a file" do
103
- expect(Hocon.load("#{FIXTURE_DIR}/hocon/with_substitution/subst.conf")).
104
- to eq({"a" => true, "b" => true})
105
- end
106
- it "should be able to `parse` from a string" do
107
- expect(Hocon.parse(File.read("#{FIXTURE_DIR}/hocon/with_substitution/subst.conf"))).
108
- to eq({"a" => true, "b" => true})
109
- end
110
- end
111
-
112
-
113
- end
114
-
@@ -1,4 +0,0 @@
1
- ## TESTS PORTED FROM UPSTREAM
2
-
3
- This directory should only contain tests that are ported from the upstream
4
- Java library.
@@ -1,417 +0,0 @@
1
- # encoding: utf-8
2
-
3
- require 'test_utils'
4
-
5
- describe "concatenation" do
6
-
7
- it "string concat, no substitutions" do
8
- conf = TestUtils.parse_config(' a : true "xyz" 123 foo ').resolve
9
- expect(conf.get_string("a")).to eq("true xyz 123 foo")
10
- end
11
-
12
- it "trivial string concat" do
13
- conf = TestUtils.parse_config(" a : ${x}foo, x = 1 ").resolve
14
- expect(conf.get_string("a")).to eq("1foo")
15
- end
16
-
17
- it "two substitutions and string concat" do
18
- conf = TestUtils.parse_config(" a : ${x}foo${x}, x = 1 ").resolve
19
- expect(conf.get_string("a")).to eq("1foo1")
20
- end
21
-
22
- it "string concat cannot span lines" do
23
- e = TestUtils.intercept(Hocon::ConfigError::ConfigParseError) {
24
- TestUtils.parse_config(" a : ${x}
25
- foo, x = 1 ")
26
- }
27
- expect(e.message).to include("not be followed")
28
- expect(e.message).to include("','")
29
- end
30
-
31
- it "no objects in string concat" do
32
- e = TestUtils.intercept(Hocon::ConfigError::ConfigWrongTypeError) {
33
- TestUtils.parse_config(" a : abc { x : y } ")
34
- }
35
- expect(e.message).to include("Cannot concatenate")
36
- expect(e.message).to include("abc")
37
- expect(e.message).to include('{"x":"y"}')
38
- end
39
-
40
- it "no object concat with nil" do
41
- e = TestUtils.intercept(Hocon::ConfigError::ConfigWrongTypeError) {
42
- TestUtils.parse_config(" a : null { x : y } ")
43
- }
44
- expect(e.message).to include("Cannot concatenate")
45
- expect(e.message).to include("null")
46
- expect(e.message).to include('{"x":"y"}')
47
- end
48
-
49
- it "no arrays in string concat" do
50
- e = TestUtils.intercept(Hocon::ConfigError::ConfigWrongTypeError) {
51
- TestUtils.parse_config(" a : abc [1, 2] ")
52
- }
53
- expect(e.message).to include("Cannot concatenate")
54
- expect(e.message).to include("abc")
55
- expect(e.message).to include("[1,2]")
56
- end
57
-
58
- it "no objects substituted in string concat" do
59
- e = TestUtils.intercept(Hocon::ConfigError::ConfigWrongTypeError) {
60
- TestUtils.parse_config(" a : abc ${x}, x : { y : z } ").resolve
61
- }
62
- expect(e.message).to include("Cannot concatenate")
63
- expect(e.message).to include("abc")
64
- end
65
-
66
- it "no arrays substituted in string concat" do
67
- e = TestUtils.intercept(Hocon::ConfigError::ConfigWrongTypeError) {
68
- TestUtils.parse_config(" a : abc ${x}, x : [1,2] ").resolve
69
- }
70
- expect(e.message).to include("Cannot concatenate")
71
- expect(e.message).to include("abc")
72
- end
73
-
74
- it "no substitutions in list concat" do
75
- conf = TestUtils.parse_config(" a : [1,2] [3,4] ")
76
- expect([1, 2, 3, 4]).to eq(conf.get_list("a").unwrapped)
77
- end
78
-
79
- it "list concat with substitutions" do
80
- conf = TestUtils.parse_config(" a : ${x} [3,4] ${y}, x : [1,2], y : [5,6] ").resolve
81
- expect([1, 2, 3, 4, 5, 6]).to eq(conf.get_list("a").unwrapped)
82
- end
83
-
84
- it "list concat self referential" do
85
- conf = TestUtils.parse_config(" a : [1, 2], a : ${a} [3,4], a : ${a} [5,6] ").resolve
86
- expect([1, 2, 3, 4, 5, 6]).to eq(conf.get_list("a").unwrapped)
87
- end
88
-
89
- it "no substitutions in list concat cannot span lines" do
90
- e = TestUtils.intercept(Hocon::ConfigError::ConfigParseError) {
91
- TestUtils.parse_config(" a : [1,2]
92
- [3,4] ")
93
- }
94
- expect(e.message).to include("expecting")
95
- expect(e.message).to include("'['")
96
- end
97
-
98
- it "list concat can span lines inside brackest" do
99
- conf = TestUtils.parse_config(" a : [1,2
100
- ] [3,4] ")
101
- expect([1, 2, 3, 4]).to eq(conf.get_list("a").unwrapped)
102
- end
103
-
104
- it "no substitutions object concat" do
105
- conf = TestUtils.parse_config(" a : { b : c } { x : y } ")
106
- expect({"b" => "c", "x" => "y"}).to eq(conf.get_object("a").unwrapped)
107
- end
108
-
109
- it "object concat merge order" do
110
- conf = TestUtils.parse_config(" a : { b : 1 } { b : 2 } { b : 3 } { b : 4 } ")
111
- expect(4).to eq(conf.get_int("a.b"))
112
- end
113
-
114
- it "object concat with substitutions" do
115
- conf = TestUtils.parse_config(" a : ${x} { b : 1 } ${y}, x : { a : 0 }, y : { c : 2 } ").resolve
116
- expect({"a" => 0, "b" => 1, "c" => 2}).to eq(conf.get_object("a").unwrapped)
117
- end
118
-
119
- it "object concat self referential" do
120
- conf = TestUtils.parse_config(" a : { a : 0 }, a : ${a} { b : 1 }, a : ${a} { c : 2 } ").resolve
121
- expect({"a" => 0, "b" => 1, "c" => 2}).to eq(conf.get_object("a").unwrapped)
122
- end
123
-
124
- it "object concat self referential override" do
125
- conf = TestUtils.parse_config(" a : { b : 3 }, a : { b : 2 } ${a} ").resolve
126
- expect({"b" => 3}).to eq(conf.get_object("a").unwrapped)
127
- end
128
-
129
- it "no substitutions object concat cannot span lines" do
130
- e = TestUtils.intercept(Hocon::ConfigError::ConfigParseError) {
131
- TestUtils.parse_config(" a : { b : c }
132
- { x : y }")
133
- }
134
- expect(e.message).to include("expecting")
135
- expect(e.message).to include("'{'")
136
- end
137
-
138
- it "object concat can span lines inside braces" do
139
- conf = TestUtils.parse_config(" a : { b : c
140
- } { x : y } ")
141
- expect({"b" => "c", "x" => "y"}).to eq(conf.get_object("a").unwrapped)
142
- end
143
-
144
- it "string concat inside array value" do
145
- conf = TestUtils.parse_config(" a : [ foo bar 10 ] ")
146
- expect(["foo bar 10"]).to eq(conf.get_string_list("a"))
147
- end
148
-
149
- it "string non concat inside array value" do
150
- conf = TestUtils.parse_config(" a : [ foo
151
- bar
152
- 10 ] ")
153
- expect(["foo", "bar", "10"]).to eq(conf.get_string_list("a"))
154
- end
155
-
156
- it "object concat inside array value" do
157
- conf = TestUtils.parse_config(" a : [ { b : c } { x : y } ] ")
158
- expect([{"b" => "c", "x" => "y"}]).to eq(conf.get_object_list("a").map { |x| x.unwrapped })
159
- end
160
-
161
- it "object non concat inside array value" do
162
- conf = TestUtils.parse_config(" a : [ { b : c }
163
- { x : y } ] ")
164
- expect([{"b" => "c"}, {"x" => "y"}]).to eq(conf.get_object_list("a").map { |x| x.unwrapped })
165
- end
166
-
167
- it "list concat inside array value" do
168
- conf = TestUtils.parse_config(" a : [ [1, 2] [3, 4] ] ")
169
- expect([[1,2,3,4]]).to eq(conf.get_list("a").unwrapped)
170
- end
171
-
172
- it "list non concat inside array value" do
173
- conf = TestUtils.parse_config(" a : [ [1, 2]
174
- [3, 4] ] ")
175
- expect([[1, 2], [3, 4]]).to eq(conf.get_list("a").unwrapped)
176
- end
177
-
178
- it "string concats are keys" do
179
- conf = TestUtils.parse_config(' 123 foo : "value" ')
180
- expect("value").to eq(conf.get_string("123 foo"))
181
- end
182
-
183
- it "objects are not keys" do
184
- e = TestUtils.intercept(Hocon::ConfigError::ConfigParseError) {
185
- TestUtils.parse_config('{ { a : 1 } : "value" }')
186
- }
187
- expect(e.message).to include("expecting a close")
188
- expect(e.message).to include("'{'")
189
- end
190
-
191
- it "arrays are not keys" do
192
- e = TestUtils.intercept(Hocon::ConfigError::ConfigParseError) {
193
- TestUtils.parse_config('{ [ "a" ] : "value" }')
194
- }
195
- expect(e.message).to include("expecting a close")
196
- expect(e.message).to include("'['")
197
- end
198
-
199
- it "empty array plus equals" do
200
- conf = TestUtils.parse_config(' a = [], a += 2 ').resolve
201
- expect([2]).to eq(conf.get_int_list("a"))
202
- end
203
-
204
- it "missing array plus equals" do
205
- conf = TestUtils.parse_config(' a += 2 ').resolve
206
- expect([2]).to eq(conf.get_int_list("a"))
207
- end
208
-
209
- it "short array plus equals" do
210
- conf = TestUtils.parse_config(' a = [1], a += 2 ').resolve
211
- expect([1, 2]).to eq(conf.get_int_list("a"))
212
- end
213
-
214
- it "number plus equals" do
215
- e = TestUtils.intercept(Hocon::ConfigError::ConfigWrongTypeError) {
216
- TestUtils.parse_config(' a = 10, a += 2 ').resolve
217
- }
218
- expect(e.message).to include("Cannot concatenate")
219
- expect(e.message).to include("10")
220
- expect(e.message).to include("[2]")
221
- end
222
-
223
- it "string plus equals" do
224
- e = TestUtils.intercept(Hocon::ConfigError::ConfigWrongTypeError) {
225
- TestUtils.parse_config(' a = abc, a += 2 ').resolve
226
- }
227
- expect(e.message).to include("Cannot concatenate")
228
- expect(e.message).to include("abc")
229
- expect(e.message).to include("[2]")
230
- end
231
-
232
- it "objects plus equals" do
233
- e = TestUtils.intercept(Hocon::ConfigError::ConfigWrongTypeError) {
234
- TestUtils.parse_config(' a = { x : y }, a += 2 ').resolve
235
- }
236
- expect(e.message).to include("Cannot concatenate")
237
- expect(e.message).to include("\"x\":\"y\"")
238
- expect(e.message).to include("[2]")
239
- end
240
-
241
- it "plus equals nested path" do
242
- conf = TestUtils.parse_config(' a.b.c = [1], a.b.c += 2 ').resolve
243
- expect([1, 2]).to eq(conf.get_int_list("a.b.c"))
244
- end
245
-
246
- it "plus equals nested objects" do
247
- conf = TestUtils.parse_config(' a : { b : { c : [1] } }, a : { b : { c += 2 } }').resolve
248
- expect([1, 2]).to eq(conf.get_int_list("a.b.c"))
249
- end
250
-
251
- it "plus equals single nested object" do
252
- conf = TestUtils.parse_config(' a : { b : { c : [1], c += 2 } }').resolve
253
- expect([1, 2]).to eq(conf.get_int_list("a.b.c"))
254
- end
255
-
256
- it "substitution plus equals substitution" do
257
- conf = TestUtils.parse_config(' a = ${x}, a += ${y}, x = [1], y = 2 ').resolve
258
- expect([1, 2]).to eq(conf.get_int_list("a"))
259
- end
260
-
261
- it "plus equals multiple times" do
262
- conf = TestUtils.parse_config(' a += 1, a += 2, a += 3 ').resolve
263
- expect([1, 2, 3]).to eq(conf.get_int_list("a"))
264
- end
265
-
266
- it "plus equals multiple times nested" do
267
- conf = TestUtils.parse_config(' x { a += 1, a += 2, a += 3 } ').resolve
268
- expect([1, 2, 3]).to eq(conf.get_int_list("x.a"))
269
- end
270
-
271
- it "plus equals an object multiple times" do
272
- conf = TestUtils.parse_config(' a += { b: 1 }, a += { b: 2 }, a += { b: 3 } ').resolve
273
- expect([1, 2, 3]).to eq(conf.get_object_list("a").map { |x| x.to_config.get_int("b")})
274
- end
275
-
276
- it "plus equals an object multiple times nested" do
277
- conf = TestUtils.parse_config(' x { a += { b: 1 }, a += { b: 2 }, a += { b: 3 } } ').resolve
278
- expect([1, 2, 3]).to eq(conf.get_object_list("x.a").map { |x| x.to_config.get_int("b") })
279
- end
280
-
281
- # We would ideally make this case NOT throw an exception but we need to do some work
282
- # to get there, see https: // github.com/typesafehub/config/issues/160
283
- it "plus equals multiple times nested in array" do
284
- e = TestUtils.intercept(Hocon::ConfigError::ConfigParseError) {
285
- conf = TestUtils.parse_config('x = [ { a += 1, a += 2, a += 3 } ] ').resolve
286
- expect([1, 2, 3]).to eq(conf.get_object_list("x").to_config.get_int_list("a"))
287
- }
288
- expect(e.message).to include("limitation")
289
- end
290
-
291
- # We would ideally make this case NOT throw an exception but we need to do some work
292
- # to get there, see https: // github.com/typesafehub/config/issues/160
293
- it "plus equals multiple times nested in plus equals" do
294
- e = TestUtils.intercept(Hocon::ConfigError::ConfigParseError) {
295
- conf = TestUtils.parse_config('x += { a += 1, a += 2, a += 3 } ').resolve
296
- expect([1, 2, 3]).to eq(conf.get_object_list("x").to_config.get_int_list("a"))
297
- }
298
- expect(e.message).to include("limitation")
299
- end
300
-
301
- # from https://github.com/typesafehub/config/issues/177
302
- it "array concatenation in double nested delayed merge" do
303
- unresolved = TestUtils.parse_config("d { x = [] }, c : ${d}, c { x += 1, x += 2 }")
304
- conf = unresolved.resolve
305
- expect([1,2]).to eq(conf.get_int_list("c.x"))
306
- end
307
-
308
- # from https://github.com/typesafehub/config/issues/177
309
- it "array concatenation as part of delayed merge" do
310
- unresolved = TestUtils.parse_config(" c { x: [], x : ${c.x}[1], x : ${c.x}[2] }")
311
- conf = unresolved.resolve
312
- expect([1,2]).to eq(conf.get_int_list("c.x"))
313
- end
314
-
315
- # from https://github.com/typesafehub/config/issues/177
316
- it "array concatenation in double nested delayed merge 2" do
317
- unresolved = TestUtils.parse_config("d { x = [] }, c : ${d}, c { x : ${c.x}[1], x : ${c.x}[2] }")
318
- conf = unresolved.resolve
319
- expect([1,2]).to eq(conf.get_int_list("c.x"))
320
- end
321
-
322
- # from https://github.com/typesafehub/config/issues/177
323
- it "array concatenation in triple nested delayed merge" do
324
- unresolved = TestUtils.parse_config("{ r: { d.x=[] }, q: ${r}, q : { d { x = [] }, c : ${q.d}, c { x : ${q.c.x}[1], x : ${q.c.x}[2] } } }")
325
- conf = unresolved.resolve
326
- expect([1,2]).to eq(conf.get_int_list("q.c.x"))
327
- end
328
-
329
- it "concat undefined substitution with string" do
330
- conf = TestUtils.parse_config("a = foo${?bar}").resolve
331
- expect("foo").to eq(conf.get_string("a"))
332
- end
333
-
334
- it "concat defined optional substitution with string" do
335
- conf = TestUtils.parse_config("bar=bar, a = foo${?bar}").resolve
336
- expect("foobar").to eq(conf.get_string("a"))
337
- end
338
-
339
- it "concat defined substitution with array" do
340
- conf = TestUtils.parse_config("a = [1] ${?bar}").resolve
341
- expect([1]).to eq(conf.get_int_list("a"))
342
- end
343
-
344
- it "concat defined optional substitution with array" do
345
- conf = TestUtils.parse_config("bar=[2], a = [1] ${?bar}").resolve
346
- expect([1, 2]).to eq(conf.get_int_list("a"))
347
- end
348
-
349
- it "concat undefined substitution with object" do
350
- conf = TestUtils.parse_config('a = { x : "foo" } ${?bar}').resolve
351
- expect('foo').to eq(conf.get_string("a.x"))
352
- end
353
-
354
- it "concat defined optional substitution with object" do
355
- conf = TestUtils.parse_config('bar={ y : 42 }, a = { x : "foo" } ${?bar}').resolve
356
- expect('foo').to eq(conf.get_string("a.x"))
357
- expect(42).to eq(conf.get_int("a.y"))
358
- end
359
-
360
- it "concat two undefined substitutions" do
361
- conf = TestUtils.parse_config("a = ${?foo}${?bar}").resolve
362
- expect(conf.has_path?("a")).to be_falsey
363
- end
364
-
365
- it "concat several undefined substitutions" do
366
- conf = TestUtils.parse_config("a = ${?foo}${?bar}${?baz}${?woooo}").resolve
367
- expect(conf.has_path?("a")).to be_falsey
368
- end
369
-
370
- it "concat two undefined substitutions with a space" do
371
- conf = TestUtils.parse_config("a = ${?foo} ${?bar}").resolve
372
- expect(conf.get_string("a")).to eq(" ")
373
- end
374
-
375
- it "concat two defined substitutions with a space" do
376
- conf = TestUtils.parse_config("foo=abc, bar=def, a = ${foo} ${bar}").resolve
377
- expect(conf.get_string("a")).to eq("abc def")
378
- end
379
-
380
- it "concat two undefined substitutions with empty string" do
381
- conf = TestUtils.parse_config('a = ""${?foo}${?bar}').resolve
382
- expect(conf.get_string("a")).to eq("")
383
- end
384
-
385
- it "concat substitutions that are objects with no space" do
386
- conf = TestUtils.parse_config('foo = { a : 1}, bar = { b : 2 }, x = ${foo}${bar}').resolve
387
- expect(1).to eq(conf.get_int("x.a"))
388
- expect(2).to eq(conf.get_int("x.b"))
389
- end
390
-
391
- # whitespace is insignificant if substitutions don't turn out to be a string
392
- it "concat substitutions that are objects with space" do
393
- conf = TestUtils.parse_config('foo = { a : 1}, bar = { b : 2 }, x = ${foo} ${bar}').resolve
394
- expect(1).to eq(conf.get_int("x.a"))
395
- expect(2).to eq(conf.get_int("x.b"))
396
- end
397
-
398
- # whitespace is insignificant if substitutions don't turn out to be a string
399
- it "concat substitutions that are lists with space" do
400
- conf = TestUtils.parse_config('foo = [1], bar = [2], x = ${foo} ${bar}').resolve
401
- expect([1,2]).to eq(conf.get_int_list("x"))
402
- end
403
-
404
- # but quoted whitespace should be an error
405
- it "concat substitutions that are objects with quoted space" do
406
- e = TestUtils.intercept(Hocon::ConfigError::ConfigWrongTypeError) {
407
- conf = TestUtils.parse_config('foo = { a : 1}, bar = { b : 2 }, x = ${foo}" "${bar}').resolve
408
- }
409
- end
410
-
411
- # but quoted whitespace should be an error
412
- it "concat substitutions that are lists with quoted space" do
413
- e = TestUtils.intercept(Hocon::ConfigError::ConfigWrongTypeError) {
414
- conf = TestUtils.parse_config('foo = [1], bar = [2], x = ${foo}" "${bar}').resolve
415
- }
416
- end
417
- end