yacht 0.1.2 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +3 -0
- data/.yardopts +6 -0
- data/Gemfile +3 -1
- data/README.rdoc +12 -18
- data/Rakefile +1 -1
- data/features/load.feature +80 -0
- data/features/missing_yaml_files.feature +30 -0
- data/features/step_definitions/aruba_extension_steps.rb +5 -0
- data/features/step_definitions/error_handling_steps.rb +27 -0
- data/features/step_definitions/loader_steps.rb +28 -0
- data/features/support/cleanup.rb +9 -0
- data/features/support/env.rb +4 -0
- data/gem_tasks/cucumber.rake +5 -0
- data/lib/yacht/base.rb +14 -0
- data/lib/yacht/classy_struct.rb +32 -0
- data/lib/{yacht_loader/base.rb → yacht/loader.rb} +23 -35
- data/lib/{yacht_loader → yacht}/rails.rb +1 -1
- data/lib/yacht/version.rb +3 -0
- data/lib/yacht.rb +6 -11
- data/spec/spec_helper.rb +3 -96
- data/spec/yacht/base_spec.rb +16 -0
- data/spec/yacht/classy_struct_spec.rb +81 -0
- data/spec/yacht/loader_spec.rb +215 -0
- data/spec/{yacht_loader → yacht}/rails_spec.rb +7 -5
- data/yacht.gemspec +7 -3
- metadata +66 -19
- data/lib/yacht_loader/classy_struct.rb +0 -15
- data/lib/yacht_loader/version.rb +0 -3
- data/spec/yacht_loader/base_spec.rb +0 -179
- data/spec/yacht_loader/classy_struct_spec.rb +0 -39
data/.gitignore
CHANGED
data/.yardopts
ADDED
data/Gemfile
CHANGED
data/README.rdoc
CHANGED
@@ -4,6 +4,7 @@ Yacht is an application configuration gem that lets you define settings for mult
|
|
4
4
|
* use of ClassyStruct for improved performance over OpenStruct
|
5
5
|
* protection of sensitive settings by specifying a whitelist in a YAML file
|
6
6
|
* easy override of nested keys (not pretty with YAML references)
|
7
|
+
* no need for an initializer or constant to store loaded values (just use Yacht.my_key)
|
7
8
|
|
8
9
|
== Installation
|
9
10
|
|
@@ -39,8 +40,13 @@ First create two (or more) YAML files in the same directory to define your setti
|
|
39
40
|
|
40
41
|
# config/yacht/whitelist.yml (required)
|
41
42
|
# any keys specified here can be used as a whitelist filter:
|
42
|
-
#
|
43
|
+
# Yacht::Loader.to_hash(:apply_whitelist? => true)
|
44
|
+
# or
|
45
|
+
# Yacht::Loader.to_classy_struct(:apply_whitelist? => true)
|
43
46
|
# (by default the whitelist is ignored)
|
47
|
+
# NOTE: the whitelist is ignored when using Yacht.my_key or Yacht['my_key']
|
48
|
+
# you have to use Yacht::Loader#to_hash or
|
49
|
+
# Yacht::Loader#to_classy_struct to use the whitelist
|
44
50
|
- super_secret_info
|
45
51
|
|
46
52
|
# config/yacht/local.yml (optional)
|
@@ -49,28 +55,16 @@ First create two (or more) YAML files in the same directory to define your setti
|
|
49
55
|
production:
|
50
56
|
cdn_host: localhost
|
51
57
|
|
52
|
-
=== Step 2:
|
58
|
+
=== Step 2: Use Yacht.my_key or Yacht['my_key']
|
53
59
|
|
54
60
|
* <b>Rails</b>:
|
55
|
-
# config/initializers/01_yacht.rb
|
56
|
-
# Define a constant that will store all settings
|
57
|
-
# looks for the following YAML files:
|
58
|
-
# * config/yacht/base.yml
|
59
|
-
# * config/yacht/local.yml
|
60
|
-
# * config/yacht/whitelist.yml
|
61
|
-
Yacht = YachtLoader.to_classy_struct
|
62
61
|
# now you can access any key set in your YAML files with:
|
63
62
|
# Yacht.my_key
|
64
63
|
|
65
|
-
* Outside of rails, you need to tell +
|
66
|
-
|
67
|
-
|
68
|
-
Yacht
|
69
|
-
|
70
|
-
|
71
|
-
== How it works
|
72
|
-
|
73
|
-
Currently, the +Yacht+ gem defines a class called +YachtLoader+ that will read your YAML files and output them as a regular +Hash+ or a +ClassyStruct+ . Then you use <tt>YachtLoader#to_classy_struct</tt> (or <tt>YachtLoader#to_hash</tt>) to define a constant. You can name the constant whatever you like, but you should use +Yacht+. This is because a planned feature is to have +Yacht+ defined when the gem is required and have everything namespaced under a single +Yacht+ class.
|
64
|
+
* Outside of rails, you need to tell +Yacht+ where your YAML files are stored, and what environment you want to use.
|
65
|
+
Yacht::Loader.dir = '/path/to/YAML/dir'
|
66
|
+
Yacht::Loader.environment = 'my_environment'
|
67
|
+
Yacht.my_key
|
74
68
|
|
75
69
|
== License
|
76
70
|
|
data/Rakefile
CHANGED
@@ -0,0 +1,80 @@
|
|
1
|
+
Feature: Load configuration settings
|
2
|
+
In order to organize my configuration settings
|
3
|
+
As a developer using Yacht
|
4
|
+
I want to load configuration settings from an external source like a YAML file
|
5
|
+
|
6
|
+
Background:
|
7
|
+
Given a file named "base.yml" with:
|
8
|
+
"""
|
9
|
+
default:
|
10
|
+
:api_key: some_fake_key
|
11
|
+
:partner_sites:
|
12
|
+
- twitter
|
13
|
+
- github
|
14
|
+
:mail:
|
15
|
+
:host: localhost
|
16
|
+
:from: Our great company
|
17
|
+
development:
|
18
|
+
:api_key: some_development_key
|
19
|
+
production:
|
20
|
+
:api_key: the_real_mccoy
|
21
|
+
:partner_sites:
|
22
|
+
- facebook
|
23
|
+
:mail:
|
24
|
+
host: example.com
|
25
|
+
reply-to: info@example.com
|
26
|
+
"""
|
27
|
+
|
28
|
+
Scenario: Load from YAML
|
29
|
+
When I load Yacht with environment: "development"
|
30
|
+
Then Yacht should contain the following hash:
|
31
|
+
"""
|
32
|
+
{
|
33
|
+
:api_key => 'some_development_key',
|
34
|
+
:partner_sites => [
|
35
|
+
'twitter',
|
36
|
+
'github'
|
37
|
+
],
|
38
|
+
:mail => {
|
39
|
+
:host => 'localhost',
|
40
|
+
:from => 'Our great company'
|
41
|
+
}
|
42
|
+
}
|
43
|
+
"""
|
44
|
+
|
45
|
+
Scenario: Local overrides with local.yml
|
46
|
+
Given a file named "local.yml" with:
|
47
|
+
"""
|
48
|
+
:api_key: some_crazy_local_key
|
49
|
+
"""
|
50
|
+
When I load Yacht with environment: "development"
|
51
|
+
Then Yacht should contain the following hash:
|
52
|
+
"""
|
53
|
+
{
|
54
|
+
:api_key => 'some_crazy_local_key',
|
55
|
+
:partner_sites => [
|
56
|
+
'twitter',
|
57
|
+
'github'
|
58
|
+
],
|
59
|
+
:mail => {
|
60
|
+
:host => 'localhost',
|
61
|
+
:from => 'Our great company'
|
62
|
+
}
|
63
|
+
}
|
64
|
+
"""
|
65
|
+
|
66
|
+
Scenario: Whitelisting with whitelist.yml
|
67
|
+
Given a file named "whitelist.yml" with:
|
68
|
+
"""
|
69
|
+
- :partner_sites
|
70
|
+
"""
|
71
|
+
When I define the constant "MyYacht" with environment: "development" using a whitelist
|
72
|
+
Then the constant "MyYacht" should contain the following hash:
|
73
|
+
"""
|
74
|
+
{
|
75
|
+
:partner_sites => [
|
76
|
+
'twitter',
|
77
|
+
'github'
|
78
|
+
]
|
79
|
+
}
|
80
|
+
"""
|
@@ -0,0 +1,30 @@
|
|
1
|
+
Feature: Handle missing YAML files reasonably
|
2
|
+
In order to ensure robustness and correctness of data
|
3
|
+
Missing YAML files should cause an error to be raised when reasonable
|
4
|
+
|
5
|
+
Background:
|
6
|
+
Given a file named "base.yml" with:
|
7
|
+
"""
|
8
|
+
development:
|
9
|
+
api_key: some_fake_key
|
10
|
+
"""
|
11
|
+
|
12
|
+
Scenario: No base.yml
|
13
|
+
Given a file named "base.yml" does not exist
|
14
|
+
When I try to use Yacht
|
15
|
+
Then Yacht should raise an error with message: "Couldn't load base config"
|
16
|
+
|
17
|
+
Scenario: No local.yml
|
18
|
+
Given a file named "local.yml" does not exist
|
19
|
+
When I try to use Yacht
|
20
|
+
Then Yacht should not raise an error
|
21
|
+
|
22
|
+
Scenario: No whitelist.yml but whitelist not used
|
23
|
+
Given a file named "whitelist.yml" does not exist
|
24
|
+
When I try to use Yacht
|
25
|
+
Then Yacht should not raise an error
|
26
|
+
|
27
|
+
Scenario: No whitelist.yml and whitelist used
|
28
|
+
Given a file named "whitelist.yml" does not exist
|
29
|
+
When I try to use Yacht with a whitelist
|
30
|
+
Then Yacht should raise an error with message: "Couldn't load whitelist"
|
@@ -0,0 +1,27 @@
|
|
1
|
+
Then /^Yacht should raise an error with message: "([^"]*)"$/ do |message|
|
2
|
+
@last_yacht.class.should be(Yacht::LoadError)
|
3
|
+
@last_yacht.message.should == message
|
4
|
+
end
|
5
|
+
|
6
|
+
When /^I try to use Yacht( with a whitelist)?$/ do |whitelist|
|
7
|
+
@last_yacht = use_yacht(!!whitelist)
|
8
|
+
end
|
9
|
+
|
10
|
+
Then /^Yacht should not raise an error$/ do
|
11
|
+
@last_yacht.class.should_not <= Exception
|
12
|
+
end
|
13
|
+
|
14
|
+
module ErrorHandlingHelpers
|
15
|
+
# Try to use Yacht and return output of Yacht#to_classy_struct if no error raised
|
16
|
+
# If an error is raised, return it instead
|
17
|
+
def use_yacht(whitelist=false)
|
18
|
+
in_current_dir do
|
19
|
+
Yacht::Loader.dir = '.'
|
20
|
+
Yacht::Loader.environment = 'development'
|
21
|
+
Yacht::Loader.to_classy_struct(:apply_whitelist? => whitelist)
|
22
|
+
end
|
23
|
+
rescue Exception => e
|
24
|
+
e
|
25
|
+
end
|
26
|
+
end
|
27
|
+
World(ErrorHandlingHelpers)
|
@@ -0,0 +1,28 @@
|
|
1
|
+
When /^I define the constant "([^"]*)" with environment: "([^"]*)"( using a whitelist)?$/ do |constant_name, env, whitelist|
|
2
|
+
in_current_dir do
|
3
|
+
Yacht::Loader.dir = '.'
|
4
|
+
Yacht::Loader.environment = env
|
5
|
+
Object.const_set( constant_name, Yacht::Loader.to_classy_struct(:apply_whitelist? => whitelist ) )
|
6
|
+
end
|
7
|
+
end
|
8
|
+
|
9
|
+
|
10
|
+
Then /^the constant "([^"]*)" should contain the following hash:$/ do |constant_name, stringified|
|
11
|
+
hash = eval(stringified)
|
12
|
+
Object.const_get(constant_name).to_hash.should == hash # don't forget to tack on to_hash to avoid weird errors
|
13
|
+
# TODO: make ClassyStruct more Hash-like so
|
14
|
+
# i t can be compared against hashes using `==`
|
15
|
+
end
|
16
|
+
|
17
|
+
When /^I load Yacht with environment: "([^"]*)"$/ do |env|
|
18
|
+
Yacht::Loader.dir = '.'
|
19
|
+
Yacht::Loader.environment = env
|
20
|
+
end
|
21
|
+
|
22
|
+
Then /^Yacht should contain the following hash:$/ do |stringified|
|
23
|
+
hash = eval(stringified)
|
24
|
+
|
25
|
+
in_current_dir do
|
26
|
+
Yacht::Loader.to_hash.should == hash
|
27
|
+
end
|
28
|
+
end
|
data/lib/yacht/base.rb
ADDED
@@ -0,0 +1,32 @@
|
|
1
|
+
require 'classy_struct'
|
2
|
+
|
3
|
+
class Yacht < BasicObject
|
4
|
+
class Loader
|
5
|
+
class << self
|
6
|
+
def classy_struct_instance
|
7
|
+
@classy_struct_instance ||= ClassyStruct.new
|
8
|
+
end
|
9
|
+
|
10
|
+
def to_classy_struct(opts={})
|
11
|
+
classy_struct_instance.new( self.to_hash(opts) )
|
12
|
+
rescue StandardError => e
|
13
|
+
# don't do anything to our own custom errors
|
14
|
+
if e.is_a? Yacht::LoadError
|
15
|
+
raise e
|
16
|
+
else
|
17
|
+
raise Yacht::LoadError.new("Error creating ClassyStruct: #{e.message}")
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
class << self
|
24
|
+
def method_missing(method, *args, &block)
|
25
|
+
_classy_struct.send(method)
|
26
|
+
end
|
27
|
+
|
28
|
+
def _classy_struct
|
29
|
+
@_classy_struct ||= Loader.to_classy_struct
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
@@ -1,9 +1,6 @@
|
|
1
1
|
# TODO: Rename YachtLoader to Yacht and somehow incorporate ClassyStruct
|
2
2
|
|
3
|
-
class
|
4
|
-
class LoadError < StandardError
|
5
|
-
end
|
6
|
-
|
3
|
+
class Yacht::Loader
|
7
4
|
class << self
|
8
5
|
def environment
|
9
6
|
@environment ||= 'default'
|
@@ -20,7 +17,7 @@ class YachtLoader
|
|
20
17
|
end
|
21
18
|
|
22
19
|
def config_file_for(config_type)
|
23
|
-
raise LoadError.new "#{config_type} is not a valid config type" unless valid_config_types.include?(config_type.to_s)
|
20
|
+
raise Yacht::LoadError.new "#{config_type} is not a valid config type" unless valid_config_types.include?(config_type.to_s)
|
24
21
|
|
25
22
|
full_file_path_for_config(config_type)
|
26
23
|
end
|
@@ -34,7 +31,7 @@ class YachtLoader
|
|
34
31
|
end
|
35
32
|
|
36
33
|
def to_hash(opts={})
|
37
|
-
opts[:apply_whitelist?]
|
34
|
+
opts[:apply_whitelist?] ||= false unless opts.has_key?(:apply_whitelist?)
|
38
35
|
self.environment = opts[:env] if opts.has_key?(:env)
|
39
36
|
|
40
37
|
if opts[:apply_whitelist?]
|
@@ -45,60 +42,47 @@ class YachtLoader
|
|
45
42
|
end
|
46
43
|
|
47
44
|
def whitelist
|
48
|
-
load_config_file(:whitelist, :expect_to_load => Array) ||
|
49
|
-
raise LoadError.new("Couldn't load whitelist")
|
50
|
-
end
|
45
|
+
load_config_file(:whitelist, :expect_to_load => Array) || raise( Yacht::LoadError.new("Couldn't load whitelist") )
|
51
46
|
end
|
52
47
|
|
53
48
|
def base_config
|
54
|
-
load_config_file(:base) ||
|
55
|
-
raise LoadError.new("Couldn't load base config")
|
56
|
-
end
|
49
|
+
load_config_file(:base) || raise( Yacht::LoadError.new("Couldn't load base config") )
|
57
50
|
end
|
58
51
|
|
59
52
|
def local_config
|
60
|
-
load_config_file(:local
|
53
|
+
load_config_file(:local) || {}
|
61
54
|
end
|
62
55
|
|
63
56
|
protected
|
57
|
+
# Wrap the YAML.load for easier mocking
|
58
|
+
def _load_config_file(file_name)
|
59
|
+
YAML.load( File.read(file_name) ) if File.exists?(file_name)
|
60
|
+
end
|
61
|
+
|
62
|
+
# Load a config file with plenty of error-checking
|
64
63
|
def load_config_file(file_type, opts={})
|
65
64
|
# by default, expect a Hash to be loaded
|
66
65
|
expected_class = opts[:expect_to_load] || Hash
|
67
66
|
|
68
|
-
# by default, raise error if file missing or empty
|
69
|
-
presence_required = if opts.has_key?(:require_presence?)
|
70
|
-
opts[:require_presence?]
|
71
|
-
else
|
72
|
-
true
|
73
|
-
end
|
74
|
-
|
75
67
|
file_name = self.config_file_for(file_type)
|
76
|
-
|
77
|
-
loaded = if File.exists?(file_name)
|
78
|
-
YAML.load( File.read(file_name) )
|
79
|
-
else
|
80
|
-
nil
|
81
|
-
end
|
82
|
-
|
83
|
-
# an empty YAML file will be converted to boolean false
|
84
|
-
raise LoadError.new "#{file_name} cannot be empty" if presence_required && loaded === false
|
68
|
+
loaded = self._load_config_file(file_name)
|
85
69
|
|
86
70
|
# YAML contained the wrong type
|
87
|
-
raise LoadError.new "#{file_name} must contain #{expected_class} (got #{loaded.class})" if loaded && !loaded.is_a?(expected_class)
|
71
|
+
raise Yacht::LoadError.new "#{file_name} must contain #{expected_class} (got #{loaded.class})" if loaded && !loaded.is_a?(expected_class)
|
88
72
|
|
89
73
|
loaded
|
90
74
|
rescue => e
|
91
75
|
# don't do anything to our own custom errors
|
92
|
-
if e.is_a?
|
76
|
+
if e.is_a? Yacht::LoadError
|
93
77
|
raise e
|
94
78
|
else
|
95
|
-
# convert other errors to YachtLoader::LoadError
|
96
|
-
raise LoadError.new "ERROR: loading config file: '#{file_type}': #{e}"
|
79
|
+
# convert other errors to YachtLoader::Yacht::LoadError
|
80
|
+
raise Yacht::LoadError.new "ERROR: loading config file: '#{file_type}': #{e}"
|
97
81
|
end
|
98
82
|
end
|
99
83
|
|
100
84
|
def chain_configs(config, env)
|
101
|
-
raise LoadError.new "environment '#{env}' does not exist" unless config.has_key?(env)
|
85
|
+
raise Yacht::LoadError.new "environment '#{env}' does not exist" unless config.has_key?(env)
|
102
86
|
|
103
87
|
parent = if config[env]['_parent']
|
104
88
|
chain_configs(config, config[env]['_parent'])
|
@@ -109,4 +93,8 @@ class YachtLoader
|
|
109
93
|
parent.deep_merge(config[env])
|
110
94
|
end
|
111
95
|
end
|
112
|
-
|
96
|
+
|
97
|
+
end
|
98
|
+
|
99
|
+
# Alias for Yacht::Loader for backwards compatibility
|
100
|
+
Object.const_set(:YachtLoader, Yacht::Loader)
|
data/lib/yacht.rb
CHANGED
@@ -1,12 +1,7 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
# YachtLoader will be renamed to Yacht
|
1
|
+
require "yacht/base"
|
2
|
+
require "yacht/loader"
|
3
|
+
require "yacht/classy_struct"
|
4
|
+
require "yacht/version"
|
6
5
|
|
7
|
-
require "
|
8
|
-
require
|
9
|
-
require "yacht_loader/version"
|
10
|
-
|
11
|
-
require "yacht_loader/rails" if Object.const_defined?(:Rails)
|
12
|
-
require 'monkeypatches/hash'
|
6
|
+
require "yacht/rails" if Object.const_defined?(:Rails)
|
7
|
+
require 'monkeypatches/hash'
|
data/spec/spec_helper.rb
CHANGED
@@ -15,101 +15,8 @@ require 'yacht'
|
|
15
15
|
|
16
16
|
RSpec.configure do |config|
|
17
17
|
config.after :each do
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
end
|
22
|
-
end
|
23
|
-
|
24
|
-
BASE_CONFIG_FILE = <<EOF
|
25
|
-
default:
|
26
|
-
name: default
|
27
|
-
defaultkey: defaultvalue
|
28
|
-
dog: schnauzer
|
29
|
-
hashkey:
|
30
|
-
foo: bar
|
31
|
-
baz: wurble
|
32
|
-
xyzzy: thud
|
33
|
-
an_environment:
|
34
|
-
name: an_environment
|
35
|
-
hashkey:
|
36
|
-
baz: yay
|
37
|
-
dog: terrier
|
38
|
-
a_child_environment:
|
39
|
-
_parent: an_environment
|
40
|
-
name: a_child_environment
|
41
|
-
hashkey:
|
42
|
-
foo: kung
|
43
|
-
test:
|
44
|
-
baloney: delicious
|
45
|
-
EOF
|
46
|
-
|
47
|
-
WHITELIST_CONFIG_FILE = <<EOF
|
48
|
-
- defaultkey
|
49
|
-
- hashkey
|
50
|
-
EOF
|
51
|
-
|
52
|
-
EMPTY_WHITELIST_CONFIG_FILE = <<EOF
|
53
|
-
EOF
|
54
|
-
|
55
|
-
INVALID_WHITELIST_CONFIG_FILE = <<EOF
|
56
|
-
somenonsenseorother
|
57
|
-
EOF
|
58
|
-
|
59
|
-
LOCAL_CONFIG_FILE = <<EOF
|
60
|
-
localkey: localvalue
|
61
|
-
EOF
|
62
|
-
|
63
|
-
EMPTY_LOCAL_CONFIG_FILE = <<EOF
|
64
|
-
EOF
|
65
|
-
|
66
|
-
INVALID_LOCAL_CONFIG_FILE = <<EOF
|
67
|
-
someinvalidstufforother
|
68
|
-
EOF
|
69
|
-
|
70
|
-
|
71
|
-
# ===================================
|
72
|
-
# = Helpers to mock file operations =
|
73
|
-
# ===================================
|
74
|
-
def banish_config_file_from_prefix(prefix)
|
75
|
-
file_name = YachtLoader.config_file_for(prefix)
|
76
|
-
banish_file(file_name)
|
77
|
-
end
|
78
|
-
|
79
|
-
# shortcut to mock config file
|
80
|
-
def conjure_config_file_from_prefix(prefix, file_contents=nil)
|
81
|
-
file_name = YachtLoader.config_file_for(prefix)
|
82
|
-
file_contents ||= "#{prefix.upcase}_CONFIG_FILE".constantize
|
83
|
-
|
84
|
-
conjure_file(file_name, file_contents)
|
85
|
-
end
|
86
|
-
|
87
|
-
def conjure_bad_config_file_from_prefix(prefix)
|
88
|
-
file_name = "#{prefix}_config_file"
|
89
|
-
file_contents = file_name.upcase.constantize
|
90
|
-
|
91
|
-
conjure_file(file_name, file_contents)
|
92
|
-
end
|
93
|
-
|
94
|
-
# mock file existence & contents
|
95
|
-
def conjure_file(file_name, file_contents)
|
96
|
-
File.stub!(:exists?).with(file_name).and_return true
|
97
|
-
File.stub!(:read).with(file_name).and_return file_contents
|
98
|
-
end
|
99
|
-
|
100
|
-
# mock file non-existence
|
101
|
-
def banish_file(file_name)
|
102
|
-
File.stub!(:exists?).with(file_name).and_return(false)
|
103
|
-
File.stub!(:read).with(file_name).and_raise Errno::ENOENT.new("No such file or directory - #{file_name}")
|
104
|
-
end
|
105
|
-
|
106
|
-
# ================================================
|
107
|
-
# = Railsy helper to turn strings into constants =
|
108
|
-
# ================================================
|
109
|
-
if !String.instance_methods.include?(:constantize)
|
110
|
-
class String
|
111
|
-
def constantize # NOT as awesome as ActiveSupport::Inflector#constantize
|
112
|
-
Object.const_get(self)
|
113
|
-
end
|
18
|
+
Yacht::Loader.environment = nil
|
19
|
+
Yacht::Loader.dir = nil
|
20
|
+
Yacht::Loader.instance_variable_set(:@config_file_names, nil)
|
114
21
|
end
|
115
22
|
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Yacht do
|
4
|
+
subject { Yacht }
|
5
|
+
|
6
|
+
describe :[] do
|
7
|
+
it "should retrieve value of key from Yacht::Loader.to_hash" do
|
8
|
+
mock_hash = {}
|
9
|
+
|
10
|
+
Yacht::Loader.should_receive(:to_hash).and_return(mock_hash)
|
11
|
+
mock_hash.should_receive(:[]).with(:foo)
|
12
|
+
|
13
|
+
subject[:foo]
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|