confset 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (66) hide show
  1. checksums.yaml +7 -0
  2. data/Rakefile +44 -0
  3. data/docs/CHANGELOG.md +15 -0
  4. data/docs/LICENSE.md +29 -0
  5. data/lib/confset/configuration.rb +37 -0
  6. data/lib/confset/integrations/heroku.rb +61 -0
  7. data/lib/confset/integrations/rails/railtie.rb +40 -0
  8. data/lib/confset/integrations/sinatra.rb +27 -0
  9. data/lib/confset/options.rb +187 -0
  10. data/lib/confset/rack/reloader.rb +17 -0
  11. data/lib/confset/sources/env_source.rb +74 -0
  12. data/lib/confset/sources/hash_source.rb +18 -0
  13. data/lib/confset/sources/yaml_source.rb +34 -0
  14. data/lib/confset/tasks/heroku.rake +9 -0
  15. data/lib/confset/validation/error.rb +13 -0
  16. data/lib/confset/validation/schema.rb +22 -0
  17. data/lib/confset/validation/validate.rb +26 -0
  18. data/lib/confset/version.rb +5 -0
  19. data/lib/confset.rb +89 -0
  20. data/lib/generators/confset/install_generator.rb +34 -0
  21. data/lib/generators/confset/templates/confset.rb +58 -0
  22. data/lib/generators/confset/templates/settings/development.yml +0 -0
  23. data/lib/generators/confset/templates/settings/production.yml +0 -0
  24. data/lib/generators/confset/templates/settings/test.yml +0 -0
  25. data/lib/generators/confset/templates/settings.local.yml +0 -0
  26. data/lib/generators/confset/templates/settings.yml +0 -0
  27. data/spec/config_env_spec.rb +238 -0
  28. data/spec/config_spec.rb +468 -0
  29. data/spec/configuration_spec.rb +16 -0
  30. data/spec/fixtures/bool_override/config1.yml +2 -0
  31. data/spec/fixtures/bool_override/config2.yml +2 -0
  32. data/spec/fixtures/custom_types/hash.yml +7 -0
  33. data/spec/fixtures/deep_merge/config1.yml +31 -0
  34. data/spec/fixtures/deep_merge/config2.yml +28 -0
  35. data/spec/fixtures/deep_merge2/config1.yml +3 -0
  36. data/spec/fixtures/deep_merge2/config2.yml +2 -0
  37. data/spec/fixtures/deep_merge3/config1.yml +1 -0
  38. data/spec/fixtures/deep_merge3/config2.yml +1 -0
  39. data/spec/fixtures/development.yml +4 -0
  40. data/spec/fixtures/empty1.yml +0 -0
  41. data/spec/fixtures/empty2.yml +0 -0
  42. data/spec/fixtures/knockout_prefix/config1.yml +40 -0
  43. data/spec/fixtures/knockout_prefix/config2.yml +28 -0
  44. data/spec/fixtures/knockout_prefix/config3.yml +14 -0
  45. data/spec/fixtures/malformed.yml +6 -0
  46. data/spec/fixtures/multilevel.yml +10 -0
  47. data/spec/fixtures/overwrite_arrays/config1.yml +17 -0
  48. data/spec/fixtures/overwrite_arrays/config2.yml +12 -0
  49. data/spec/fixtures/overwrite_arrays/config3.yml +10 -0
  50. data/spec/fixtures/reserved_keywords.yml +7 -0
  51. data/spec/fixtures/settings.yml +22 -0
  52. data/spec/fixtures/settings2.yml +1 -0
  53. data/spec/fixtures/unsafe_load.yml +12 -0
  54. data/spec/fixtures/validation/confset.yml +3 -0
  55. data/spec/fixtures/with_erb.yml +4 -0
  56. data/spec/fixtures/with_malformed_erb.yml +1 -0
  57. data/spec/options_spec.rb +255 -0
  58. data/spec/sources/env_source_spec.rb +81 -0
  59. data/spec/sources/hash_source_spec.rb +49 -0
  60. data/spec/sources/yaml_source_spec.rb +145 -0
  61. data/spec/spec_helper.rb +28 -0
  62. data/spec/support/fixture_helper.rb +14 -0
  63. data/spec/support/rails_helper.rb +24 -0
  64. data/spec/support/shared_contexts/rake.rb +8 -0
  65. data/spec/validation_spec.rb +84 -0
  66. metadata +295 -0
@@ -0,0 +1,17 @@
1
+ array1:
2
+ - item1
3
+ - item2
4
+ - item3
5
+ - item4
6
+
7
+ array2:
8
+ inner:
9
+ - item1
10
+ - item2
11
+ - item3
12
+ - item4
13
+
14
+ array3:
15
+ - item1
16
+ - item2
17
+ - item3
@@ -0,0 +1,12 @@
1
+ array1:
2
+ - item2
3
+ - item4
4
+ - item5
5
+
6
+ array2:
7
+ inner:
8
+ - item2
9
+ - item4
10
+ - item5
11
+
12
+ array3: []
@@ -0,0 +1,10 @@
1
+ array1:
2
+ - item4
3
+ - item5
4
+ - item6
5
+
6
+ array2:
7
+ inner:
8
+ - item4
9
+ - item5
10
+ - item6
@@ -0,0 +1,7 @@
1
+ select: apple
2
+ collect: banana
3
+ count: lemon
4
+ zip: cherry
5
+ max: kumquat
6
+ min: fig
7
+ exit!: taro
@@ -0,0 +1,22 @@
1
+ ##
2
+ # Settings for Rails database.yml
3
+ #
4
+ databases:
5
+ development:
6
+ database: db/development.sqlite3
7
+ test:
8
+ database: db/test.sqlite3
9
+ production:
10
+ database: db/production.sqlite3
11
+ ##
12
+ # ...
13
+ #
14
+ size: 1
15
+ number_in_quotes: "2.56"
16
+ server: google.com
17
+ 1: "one"
18
+ photo_sizes:
19
+ avatar: [60, 60]
20
+ root:
21
+ yahoo.com: 2
22
+ 'google.com': 3
@@ -0,0 +1 @@
1
+ another: "something"
@@ -0,0 +1,12 @@
1
+ development: &defaults
2
+ adapter: postgresql
3
+ encoding: unicode
4
+ pool: &pool 5
5
+ test:
6
+ <<: *defaults # Psych::BadAlias: Unknown alias
7
+ database: myapp_test
8
+ pool: *pool # Psych::BadAlias: Unknown alias
9
+ others:
10
+ regex: !ruby/regexp '/https?:\/\/.*exmaple\.com/' # Tried to load unspecified class: Regexp (Psych::DisallowedClass)
11
+ date: 2021-08-03 # Tried to load unspecified class: Date (Psych::DisallowedClass)
12
+ time: 2001-12-14T21:59:43.10-05:00 # Tried to load unspecified class: Time (Psych::DisallowedClass)
@@ -0,0 +1,3 @@
1
+ youtube:
2
+ api_key: ADSEF453
3
+ multiple_requirements: A
@@ -0,0 +1,4 @@
1
+ computed: <%= 1 + 2 + 3 %>
2
+ section:
3
+ computed1: <%= "1" %>
4
+ computed2: <%= "2" %>
@@ -0,0 +1 @@
1
+ malformed_erb: <%= = %>
@@ -0,0 +1,255 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "spec_helper"
4
+
5
+ describe Confset::Options do
6
+ before :each do
7
+ Confset.reset
8
+ end
9
+
10
+ context "when Settings file is using keywords reserved for OpenStruct" do
11
+ let(:config) do
12
+ Confset.load_files("spec/fixtures/reserved_keywords.yml")
13
+ end
14
+
15
+ it "should allow to access them via object member notation" do
16
+ expect(config.select).to eq("apple")
17
+ expect(config.collect).to eq("banana")
18
+ expect(config.count).to eq("lemon")
19
+ expect(config.zip).to eq("cherry")
20
+ expect(config.max).to eq("kumquat")
21
+ expect(config.min).to eq("fig")
22
+ expect(config.exit!).to eq("taro")
23
+ end
24
+
25
+ it "should allow to access them using [] operator" do
26
+ expect(config["select"]).to eq("apple")
27
+ expect(config["collect"]).to eq("banana")
28
+ expect(config["count"]).to eq("lemon")
29
+ expect(config["zip"]).to eq("cherry")
30
+ expect(config["max"]).to eq("kumquat")
31
+ expect(config["min"]).to eq("fig")
32
+ expect(config["exit!"]).to eq("taro")
33
+
34
+ expect(config[:select]).to eq("apple")
35
+ expect(config[:collect]).to eq("banana")
36
+ expect(config[:count]).to eq("lemon")
37
+ expect(config[:zip]).to eq("cherry")
38
+ expect(config[:max]).to eq("kumquat")
39
+ expect(config[:min]).to eq("fig")
40
+ expect(config[:exit!]).to eq("taro")
41
+ end
42
+ end
43
+
44
+ context "adding sources" do
45
+ let(:config) do
46
+ Confset.load_files("spec/fixtures/settings.yml")
47
+ end
48
+
49
+ before do
50
+ config.add_source!("spec/fixtures/deep_merge2/config1.yml")
51
+ config.reload!
52
+ end
53
+
54
+ it "should still have the initial config" do
55
+ expect(config["size"]).to eq(1)
56
+ end
57
+
58
+ it "should add keys from the added file" do
59
+ expect(config["tvrage"]["service_url"]).to eq("http://services.tvrage.com")
60
+ end
61
+
62
+ context "overwrite with YAML file" do
63
+ before do
64
+ config.add_source!("spec/fixtures/deep_merge2/config2.yml")
65
+ config.reload!
66
+ end
67
+
68
+ it "should overwrite the previous values" do
69
+ expect(config["tvrage"]["service_url"]).to eq("http://url2")
70
+ end
71
+ end
72
+
73
+ context "overwrite with Hash" do
74
+ before do
75
+ config.add_source!({ tvrage: { service_url: "http://url3" } })
76
+ config.reload!
77
+ end
78
+
79
+ it "should overwrite the previous values" do
80
+ expect(config["tvrage"]["service_url"]).to eq("http://url3")
81
+ end
82
+ end
83
+ end
84
+
85
+ context "prepending sources" do
86
+ let(:config) do
87
+ Confset.load_files("spec/fixtures/settings.yml")
88
+ end
89
+
90
+ before do
91
+ config.prepend_source!("spec/fixtures/deep_merge2/config1.yml")
92
+ config.reload!
93
+ end
94
+
95
+ it "should still have the initial config" do
96
+ expect(config["size"]).to eq(1)
97
+ end
98
+
99
+ it "should add keys from the added file" do
100
+ expect(config["tvrage"]["service_url"]).to eq("http://services.tvrage.com")
101
+ end
102
+
103
+ context "be overwritten" do
104
+ before do
105
+ config.prepend_source!("spec/fixtures/deep_merge2/config2.yml")
106
+ config.reload!
107
+ end
108
+
109
+ it "should overwrite the previous values" do
110
+ expect(config["tvrage"]["service_url"]).to eq("http://services.tvrage.com")
111
+ end
112
+ end
113
+
114
+ context "source is a hash" do
115
+ let(:hash_source) {
116
+ { tvrage: { service_url: "http://url3" }, meaning_of_life: 42 }
117
+ }
118
+ before do
119
+ config.prepend_source!(hash_source)
120
+ config.reload!
121
+ end
122
+
123
+ it "should be overwriten by the following values" do
124
+ expect(config["tvrage"]["service_url"]).to eq("http://services.tvrage.com")
125
+ end
126
+
127
+ it "should set meaning of life" do
128
+ expect(config["meaning_of_life"]).to eq(42)
129
+ end
130
+ end
131
+ end
132
+
133
+ context "when fail_on_missing option" do
134
+ context "is set to true" do
135
+ before { Confset.setup { |cfg| cfg.fail_on_missing = true } }
136
+
137
+ it "should raise an error when accessing a missing key" do
138
+ config = Confset.load_files("spec/fixtures/empty1.yml")
139
+
140
+ expect { config.not_existing_method }.to raise_error(KeyError)
141
+ expect { config[:not_existing_method] }.to raise_error(KeyError)
142
+ end
143
+
144
+ it "should raise an error when accessing a removed key" do
145
+ config = Confset.load_files("spec/fixtures/empty1.yml")
146
+
147
+ config.tmp_existing = 1337
148
+ expect(config.tmp_existing).to eq(1337)
149
+
150
+ config.delete_field(:tmp_existing)
151
+ expect { config.tmp_existing }.to raise_error(KeyError)
152
+ expect { config[:tmp_existing] }.to raise_error(KeyError)
153
+ end
154
+ end
155
+
156
+ context "is set to false" do
157
+ before { Confset.setup { |cfg| cfg.fail_on_missing = false } }
158
+
159
+ it "should return nil when accessing a missing key" do
160
+ config = Confset.load_files("spec/fixtures/empty1.yml")
161
+
162
+ expect(config.not_existing_method).to eq(nil)
163
+ expect(config[:not_existing_method]).to eq(nil)
164
+ end
165
+ end
166
+ end
167
+
168
+ context "#key? and #has_key? methods" do
169
+ let(:config) {
170
+ config = Confset.load_files("spec/fixtures/empty1.yml")
171
+ config.existing = nil
172
+ config.send("complex_value=", nil)
173
+ config.send("even_more_complex_value==", nil)
174
+ config.nested = Confset.load_files("spec/fixtures/empty2.yml")
175
+ config.nested.existing = nil
176
+ config
177
+ }
178
+
179
+ it "should test if a value exists for a given key" do
180
+ expect(config.key?(:not_existing)).to eq(false)
181
+ expect(config.key?(:complex_value)).to eq(true)
182
+ expect(config.key?("even_more_complex_value=".to_sym)).to eq(true)
183
+ expect(config.key?(:nested)).to eq(true)
184
+ expect(config.nested.key?(:not_existing)).to eq(false)
185
+ expect(config.nested.key?(:existing)).to eq(true)
186
+ end
187
+
188
+ it "should be sensible to key's class" do
189
+ expect(config.key?(:existing)).to eq(true)
190
+ expect(config.key?("existing")).to eq(false)
191
+ end
192
+ end
193
+
194
+ context "when merge_hash_arrays options" do
195
+ context "is set to true" do
196
+ before { Confset.setup { |cfg|
197
+ cfg.overwrite_arrays = false
198
+ cfg.merge_hash_arrays = true
199
+ } }
200
+
201
+ it "should merge the arrays" do
202
+ config = Confset.load_files("spec/fixtures/deep_merge3/config1.yml", "spec/fixtures/deep_merge3/config2.yml")
203
+
204
+ expect(config.array.length).to eq(1)
205
+ expect(config.array[0].a).to eq("one")
206
+ expect(config.array[0].b).to eq("two")
207
+ end
208
+ end
209
+
210
+ context "is set to false" do
211
+ before { Confset.setup { |cfg|
212
+ cfg.overwrite_arrays = false
213
+ cfg.merge_hash_arrays = false
214
+ } }
215
+
216
+ it "should merge the arrays" do
217
+ config = Confset.load_files("spec/fixtures/deep_merge3/config1.yml", "spec/fixtures/deep_merge3/config2.yml")
218
+
219
+ expect(config.array.length).to eq(2)
220
+ expect(config.array[0].b).to eq(nil)
221
+ expect(config.array[1].b).to eq("two")
222
+ end
223
+ end
224
+ end
225
+
226
+ context "when calling #as_json" do
227
+ it "should return a Hash of the keys and values" do
228
+ unless defined?(::Rails)
229
+ skip <<~REASON
230
+ Confset::Options#as_json raises a runtime error unless Active Support
231
+ Core Extensions are loaded. We don't expect users to call this method
232
+ at all if they're not using AS, so we disable this test except when
233
+ running the suite against Rails.
234
+ REASON
235
+ end
236
+
237
+ options = Confset::Options.new(foo: :bar)
238
+ expect(options.as_json).to eq({ "foo" => "bar" })
239
+ end
240
+ end
241
+
242
+ context "parsing values" do
243
+ let(:config) do
244
+ Confset.load_files("spec/fixtures/settings.yml")
245
+ end
246
+
247
+ it "should return number when its specified without quotes" do
248
+ expect(config["size"]).to eq(1)
249
+ end
250
+
251
+ it "should return string when number specified with quotes" do
252
+ expect(config["number_in_quotes"]).to eq("2.56")
253
+ end
254
+ end
255
+ end
@@ -0,0 +1,81 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "spec_helper"
4
+
5
+ module Confset::Sources
6
+ describe EnvSource do
7
+ context "configuration options" do
8
+ before :each do
9
+ Confset.reset
10
+ Confset.env_prefix = nil
11
+ Confset.env_separator = "."
12
+ Confset.env_converter = :downcase
13
+ Confset.env_parse_values = true
14
+ end
15
+
16
+ context "default configuration" do
17
+ it "should use global prefix configuration by default" do
18
+ Confset.env_prefix = "MY_CONFIG"
19
+
20
+ source = EnvSource.new({ "MY_CONFIG.ACTION_MAILER" => "enabled" })
21
+ results = source.load
22
+ expect(results["action_mailer"]).to eq("enabled")
23
+ end
24
+
25
+ it "should use global separator configuration by default" do
26
+ Confset.env_separator = "__"
27
+
28
+ source = EnvSource.new({ "Settings__ACTION_MAILER__ENABLED" => "yes" })
29
+ results = source.load
30
+ expect(results["action_mailer"]["enabled"]).to eq("yes")
31
+ end
32
+
33
+ it "should use global converter configuration by default" do
34
+ Confset.env_converter = nil
35
+
36
+ source = EnvSource.new({ "Settings.ActionMailer.Enabled" => "yes" })
37
+ results = source.load
38
+ expect(results["ActionMailer"]["Enabled"]).to eq("yes")
39
+ end
40
+
41
+ it "should use global parse_values configuration by default" do
42
+ Confset.env_parse_values = false
43
+
44
+ source = EnvSource.new({ "Settings.ACTION_MAILER.ENABLED" => "true" })
45
+ results = source.load
46
+ expect(results["action_mailer"]["enabled"]).to eq("true")
47
+ end
48
+ end
49
+
50
+ context "configuration overrides" do
51
+ it "should allow overriding prefix configuration" do
52
+ source = EnvSource.new({ "MY_CONFIG.ACTION_MAILER" => "enabled" },
53
+ prefix: "MY_CONFIG")
54
+ results = source.load
55
+ expect(results["action_mailer"]).to eq("enabled")
56
+ end
57
+
58
+ it "should allow overriding separator configuration" do
59
+ source = EnvSource.new({ "Settings__ACTION_MAILER__ENABLED" => "yes" },
60
+ separator: "__")
61
+ results = source.load
62
+ expect(results["action_mailer"]["enabled"]).to eq("yes")
63
+ end
64
+
65
+ it "should allow overriding converter configuration" do
66
+ source = EnvSource.new({ "Settings.ActionMailer.Enabled" => "yes" },
67
+ converter: nil)
68
+ results = source.load
69
+ expect(results["ActionMailer"]["Enabled"]).to eq("yes")
70
+ end
71
+
72
+ it "should allow overriding parse_values configuration" do
73
+ source = EnvSource.new({ "Settings.ACTION_MAILER.ENABLED" => "true" },
74
+ parse_values: false)
75
+ results = source.load
76
+ expect(results["action_mailer"]["enabled"]).to eq("true")
77
+ end
78
+ end
79
+ end
80
+ end
81
+ end
@@ -0,0 +1,49 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "spec_helper"
4
+
5
+ module Confset::Sources
6
+ describe HashSource do
7
+ it "should take a hash as initializer" do
8
+ source = HashSource.new(foo: 5)
9
+ expect(source.hash).to eq(foo: 5)
10
+ end
11
+
12
+ context "basic hash" do
13
+ let(:source) do
14
+ HashSource.new(
15
+ {
16
+ "size" => 2,
17
+ "section" => {
18
+ "size" => 3,
19
+ "servers" => [ { "name" => "yahoo.com" }, { "name" => "amazon.com" } ]
20
+ }
21
+ }
22
+ )
23
+ end
24
+
25
+ it "should properly read the settings" do
26
+ results = source.load
27
+ expect(results["size"]).to eq(2)
28
+ end
29
+
30
+ it "should properly read nested settings" do
31
+ results = source.load
32
+ expect(results["section"]["size"]).to eq(3)
33
+ expect(results["section"]["servers"]).to be_instance_of(Array)
34
+ expect(results["section"]["servers"].size).to eq(2)
35
+ end
36
+ end
37
+
38
+ context "parameter is not a hash" do
39
+ let(:source) do
40
+ HashSource.new "hello world"
41
+ end
42
+
43
+ it "should return an empty hash" do
44
+ results = source.load
45
+ expect(results).to eq({})
46
+ end
47
+ end
48
+ end
49
+ end
@@ -0,0 +1,145 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "spec_helper"
4
+
5
+ module Confset::Sources
6
+ describe YAMLSource do
7
+ it "should take a path as initializer" do
8
+ source = YAMLSource.new "somepath"
9
+ expect(source.path).to eq("somepath")
10
+ end
11
+
12
+ context "basic yml file" do
13
+ let(:source) do
14
+ YAMLSource.new "spec/fixtures/development.yml"
15
+ end
16
+
17
+ it "should properly read the settings" do
18
+ results = source.load
19
+ expect(results["size"]).to eq(2)
20
+ end
21
+
22
+ it "should properly read nested settings" do
23
+ results = source.load
24
+ expect(results["section"]["size"]).to eq(3)
25
+ expect(results["section"]["servers"]).to be_instance_of(Array)
26
+ expect(results["section"]["servers"].size).to eq(2)
27
+ end
28
+ end
29
+
30
+ context "yml file with erb tags" do
31
+ let(:source) do
32
+ YAMLSource.new("spec/fixtures/with_erb.yml")
33
+ end
34
+
35
+ it "should properly evaluate the erb" do
36
+ results = source.load
37
+ expect(results["computed"]).to eq(6)
38
+ end
39
+
40
+ it "should properly evaluate the nested erb settings" do
41
+ results = source.load
42
+ expect(results["section"]["computed1"]).to eq(1)
43
+ expect(results["section"]["computed2"]).to eq(2)
44
+ end
45
+
46
+ context "with malformed erb tags" do
47
+ let(:source) do
48
+ YAMLSource.new("spec/fixtures/with_malformed_erb.yml")
49
+ end
50
+
51
+ it "should properly evaluate the erb" do
52
+ expect {
53
+ source.load
54
+ }.to raise_error(SyntaxError)
55
+ end
56
+ end
57
+ end
58
+
59
+ context "yaml file with erb tags but erb disabled" do
60
+ let(:source) do
61
+ YAMLSource.new("spec/fixtures/with_erb.yml", evaluate_erb: false)
62
+ end
63
+
64
+ it "should load the file and leave the erb without being evaluated" do
65
+ results = source.load
66
+ expect(results["computed"]).to eq("<%= 1 + 2 + 3 %>")
67
+ expect(results["section"]["computed1"]).to eq("<%= \"1\" %>")
68
+ end
69
+
70
+ context "with global config" do
71
+ let(:source) do
72
+ YAMLSource.new("spec/fixtures/with_erb.yml")
73
+ end
74
+
75
+ around do |example|
76
+ original_evaluate_erb_in_yaml = Confset.evaluate_erb_in_yaml
77
+ Confset.evaluate_erb_in_yaml = false
78
+ example.run
79
+ Confset.evaluate_erb_in_yaml = original_evaluate_erb_in_yaml
80
+ end
81
+
82
+ it "should load the file and leave the erb without being evaluated" do
83
+ results = source.load
84
+ expect(results["computed"]).to eq("<%= 1 + 2 + 3 %>")
85
+ expect(results["section"]["computed1"]).to eq("<%= \"1\" %>")
86
+ end
87
+ end
88
+
89
+ context "with malformed erb tags" do
90
+ let(:source) do
91
+ YAMLSource.new("spec/fixtures/with_malformed_erb.yml", evaluate_erb: false)
92
+ end
93
+
94
+ it "should properly evaluate the erb" do
95
+ expect {
96
+ results = source.load
97
+ expect(results["malformed_erb"]).to eq("<%= = %>")
98
+ }.to_not raise_error
99
+ end
100
+ end
101
+ end
102
+
103
+ context "missing yml file" do
104
+ let(:source) do
105
+ YAMLSource.new "somewhere_that_doesnt_exist.yml"
106
+ end
107
+
108
+ it "should return an empty hash" do
109
+ results = source.load
110
+ expect(results).to eq({})
111
+ end
112
+ end
113
+
114
+ context "blank yml file" do
115
+ let(:source) do
116
+ YAMLSource.new "spec/fixtures/empty1.yml"
117
+ end
118
+
119
+ it "should return an empty hash" do
120
+ results = source.load
121
+ expect(results).to eq({})
122
+ end
123
+ end
124
+
125
+ context "malformed yml file" do
126
+ let(:source) do
127
+ YAMLSource.new "spec/fixtures/malformed.yml"
128
+ end
129
+
130
+ it "should raise an useful exception" do
131
+ expect { source.load }.to raise_error(/malformed\.yml/)
132
+ end
133
+ end
134
+
135
+ context "unsafe yml file" do
136
+ let(:source) do
137
+ YAMLSource.new "spec/fixtures/unsafe_load.yml"
138
+ end
139
+
140
+ it "should load without any exception" do
141
+ expect { source.load }.not_to raise_error
142
+ end
143
+ end
144
+ end
145
+ end
@@ -0,0 +1,28 @@
1
+ # frozen_string_literal: true
2
+
3
+ ENV["RAILS_ENV"] ||= "test"
4
+
5
+ require "confset"
6
+
7
+ Dir["./spec/support/**/*.rb"].each { |f| require f }
8
+
9
+ RSpec.configure do |config|
10
+ # Turn the deprecation warnings into errors, giving you the full backtrace
11
+ config.raise_errors_for_deprecations!
12
+
13
+ config.before(:suite) do
14
+ Confset.module_eval do
15
+ # Extend Confset module with ability to reset configuration to the default values
16
+ def self.reset
17
+ self.const_name = "Settings"
18
+ self.use_env = false
19
+ self.knockout_prefix = nil
20
+ self.overwrite_arrays = true
21
+ self.schema = nil
22
+ self.validation_contract = nil
23
+ self.fail_on_missing = false
24
+ instance_variable_set(:@_ran_once, false)
25
+ end
26
+ end
27
+ end
28
+ end
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ ##
4
+ # Confset Fixture Helpers
5
+ #
6
+
7
+ module FixtureHelper
8
+ FIXTURE_PATH = File.expand_path("../../fixtures", __FILE__)
9
+
10
+ # Provide fixture path as same way as rspec-rails
11
+ def fixture_path
12
+ FIXTURE_PATH
13
+ end
14
+ end