configuration_loader 1.0.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.
data/README ADDED
@@ -0,0 +1,47 @@
1
+ = Configuration Files Loader
2
+
3
+ Configuration Files Loader can be used as a gem or a Rails plugin to load various config files.
4
+
5
+ It finds config file fragments in a Rails config directory and in config directories of plugins and dependent gems. It then tries to merge them in the following order: gem<-plugin<-application. This allows overrides of global (gem/plugin) configs by individual applications. The supported types for merging are String, Hash, and Array. It caches the content of files by default. ConfigurationLoader is RoR environment aware and provides a shortcut ('load_section') to load a section of a config file corresponding to RAILS_ENV. It is being used in another method provided by ConfigurationLoader - 'load_db_config'. It loads a section from 'config/database.yml' providing a convenient method for placing secondary DB entries in a code as seen here:
6
+
7
+ establish_connection ConfigurationLoader.load_db_config['secondary_db']
8
+
9
+ See the 'DRYing Up Configuration Files' post in our team blog http://revolutiononrails.blogspot.com/2007/03/drying-up-configuration-files.html for additional details.
10
+
11
+
12
+ == Setup
13
+
14
+ === Installation
15
+
16
+ To install Configuration Files Loader as a gem:
17
+
18
+ Get the gem file from the project page (http://rubyforge.org/projects/config-loader) and install it
19
+
20
+ To install as a Rails plugin:
21
+
22
+ ruby script/plugin install svn://rubyforge.org/var/svn/config-loader/trunk/vendor/plugins/configuration_loader
23
+
24
+
25
+ === Usage
26
+
27
+ require 'configuration_loader'
28
+
29
+ ConfigurationLoader.load_db_config # gets the RAILS_ENV section from database.yml
30
+
31
+ ConfigurationLoader.load('cfg.yml') # loads a YAML-processed config file
32
+
33
+ ConfigurationLoader.load('cfg.yml', :erb => true) # loads a ERB+YAML-processed config file
34
+
35
+ ConfigurationLoader.load('cfg.yml', :section => RAILS_ENV) # loads a current RAILS_ENV section from a YAML-processed config file
36
+
37
+ ConfigLoader.load('cfg.yml', :cache => false) # loads an uncached copy YAML-processed config file
38
+
39
+
40
+ == License
41
+
42
+ Configuration Files Loader is released under the MIT license.
43
+
44
+
45
+ == Support
46
+
47
+ The RubyForge home page is http://rubyforge.org/projects/config-loader
@@ -0,0 +1,183 @@
1
+ # Configuration Files Loader can be used as a gem or a Rails plugin to load config files.
2
+ #
3
+ # It finds config file fragments in a rails config directory and in config directories of plugins and dependent gems.
4
+ # It then tries to merge them in order gem<-plugin<-application thus allowing overrides of global (gem/plugin) configs by individual applications.
5
+ # The supported types for merging are String, Hash, and Array.
6
+ #
7
+ # It caches the content of files by default.
8
+ #
9
+ # ConfigurationLoader is RoR environment aware and provides a short-cut 'load_section' to load a section of a config file corresponding to RAILS_ENV.
10
+ # It is being used in another method provided by ConfigurationLoader - load_db_config.
11
+ # It loads a section from 'config/database.yml' providing a convenience method for getting secondary DB entries in a code like this:
12
+ #
13
+ # establish_connection ConfigurationLoader.load_db_config['secondary_db']
14
+ #
15
+ # See the 'DRYing Up Configuration Files' post in our team blog http://revolutiononrails.blogspot.com/2007/03/drying-up-configuration-files.html
16
+ # for additional details.
17
+ #
18
+ #
19
+ # == Usage
20
+ #
21
+ # require 'configuration_loader'
22
+ #
23
+ # ConfigurationLoader.load_db_config # gets the RAILS_ENV section from database.yml
24
+ #
25
+ # ConfigurationLoader.load('cfg.yml') # loads a YAML-processed config file
26
+ #
27
+ # ConfigurationLoader.load('cfg.yml', :erb => true) # loads a ERB+YAML-processed config file
28
+ #
29
+ # ConfigurationLoader.load('cfg.yml', :section => RAILS_ENV) # loads a current RAILS_ENV section from a YAML-processed config file
30
+ #
31
+ # ConfigLoader.load('cfg.yml', :cache => false) # loads an uncached copy YAML-processed config file
32
+ #
33
+ class ConfigurationLoader
34
+
35
+ require 'yaml'
36
+ require 'erb'
37
+ require 'pp'
38
+
39
+ class << self
40
+
41
+ @@cached = {}
42
+
43
+ # Finds files with a provided file name, loads and processes them. The +options+ control the processing:
44
+ # :erb => true -- runs the file through ERB before YAML-processing (DEFAULT: false)
45
+ # :section => 'section_name' -- loads a specific section of the file (like 'development' for 'database.yml') (DEFAULT: nil)
46
+ # :merge => false -- returns an arrary of processed resulted without trying to merge them into a single entry (DEFAULT: true)
47
+ # :cache => false -- returns a non-cached copy (DEFAULT: true)
48
+ def load(file, supplied_options = {})
49
+ options = default_options.merge(supplied_options)
50
+ res = load_file(file, options)
51
+ res = sections(res, options[:section]) if options[:section]
52
+ res = merge(res) if options[:merge]
53
+ res
54
+ end
55
+
56
+ # A convenience method for loading the current RAILS_ENV section of the Rails DB config file
57
+ def load_db_config(section = default_section)
58
+ load('database.yml', :section => section)
59
+ end
60
+
61
+ # Empties the cached entry[es] thus forcing to reload from a file system next time
62
+ def refresh!(key = :everything)
63
+ case key
64
+ when :everything then
65
+ @@cached = {}
66
+ else
67
+ @@cached.delete(:__configs__)
68
+ @@cached.delete(key)
69
+ end
70
+ end
71
+
72
+ private
73
+
74
+ def default_options
75
+ {
76
+ :erb => false,
77
+ :section => nil,
78
+ :merge => true,
79
+ :cache => true
80
+ }
81
+ end
82
+
83
+ def load_file(file, options)
84
+ cache(options[:cache])[file] ||= load_yaml_file(file, options)
85
+ end
86
+
87
+ def sections(configs, section)
88
+ configs.empty? ? nil : collect_sections(configs, section)
89
+ end
90
+
91
+ def collect_sections(configs, section)
92
+ configs.inject([]) do |config_sections, config|
93
+ config_sections << config[section] if (config.respond_to?('[]') && config[section])
94
+ config_sections
95
+ end
96
+ end
97
+
98
+ def default_section
99
+ (defined?(RAILS_ENV) && RAILS_ENV) || 'development'
100
+ end
101
+
102
+ def file_path(path, file)
103
+ File.join(path, file)
104
+ end
105
+
106
+ def cache(use_cache)
107
+ use_cache ? @@cached : {}
108
+ end
109
+
110
+ def config_files(use_cache)
111
+ cache(use_cache)[:__configs__] ||= begin
112
+ (load_pathes("/gems/") + load_pathes("vendor/plugins/") + app_root).uniq.inject([]) do |configs, path|
113
+ debug("Component: #{ path }")
114
+ config = File.join(path, 'config')
115
+ if File.exist?(config)
116
+ configs << config
117
+ debug('Has config')
118
+ else
119
+ debug('No config')
120
+ end
121
+ configs
122
+ end
123
+ end
124
+ end
125
+
126
+ def app_root
127
+ path = defined?(CONFIG_LOADER_ROOT) ? CONFIG_LOADER_ROOT : RAILS_ROOT
128
+ [ File.expand_path(path) ]
129
+ end
130
+
131
+ def load_pathes(pattern)
132
+ $:.grep(%r{#{ pattern }}).collect { |path| File.expand_path(path[%r{.*#{ pattern }[^/]+}]) }
133
+ end
134
+
135
+ def load_yaml_file(file_name, options)
136
+ config_files(options[:cache]).inject([]) do |loaded, config_path|
137
+ file = file_path(config_path, file_name)
138
+ debug("Probing #{ file }")
139
+ if File.exist?(file)
140
+ loaded << YAML.load(file_loader(file, options))
141
+ debug('Found')
142
+ else
143
+ debug('Not found')
144
+ end
145
+ loaded
146
+ end
147
+
148
+ end
149
+
150
+ def file_loader(file, options)
151
+ res = IO.read(file)
152
+ res = ERB.new(res).result if options[:erb]
153
+ res
154
+ end
155
+
156
+ def merge(values)
157
+
158
+ debug('Merging configs:') { pp values }
159
+
160
+ case
161
+ when all_are?(values, Hash) then
162
+ values.inject({}) { |c, v| c.merge(v) }
163
+ when all_are?(values, Array) then
164
+ values.inject([]) { |c, v| c + v }
165
+ else
166
+ values.last
167
+ end
168
+
169
+ end
170
+
171
+ def all_are?(values, type)
172
+ values.all? { |v| v.is_a?(type) }
173
+ end
174
+
175
+ def debug(msg)
176
+ if ENV['CONFIG_LOADER_DEBUG']
177
+ puts "CONFIG_LOADER: #{ msg }"
178
+ yield if block_given?
179
+ end
180
+ end
181
+
182
+ end
183
+ end
@@ -0,0 +1,110 @@
1
+ require File.dirname(__FILE__) + '/../lib/configuration_loader'
2
+ require 'test/unit'
3
+
4
+ class ConfigurationLoaderTest < Test::Unit::TestCase
5
+
6
+ ::CONFIG_LOADER_ROOT = File.join(File.dirname(__FILE__), 'configs')
7
+
8
+ ['vendor/plugins', 'gems'].each do |dir|
9
+ Dir["#{ CONFIG_LOADER_ROOT }/#{ dir }/*"].each { |path| $: << path }
10
+ end
11
+
12
+ def test_default_db_config
13
+ cfg = ConfigurationLoader.load_db_config
14
+ assert_not_equal Hash.new, cfg
15
+ assert cfg['loaded']
16
+ end
17
+
18
+ def test_db_config_section
19
+ cfg = ConfigurationLoader.load_db_config('test')
20
+ assert_not_equal Hash.new, cfg
21
+ assert_equal 'app_db', cfg['db']
22
+ assert cfg['app_db']
23
+ assert cfg['plugin_db']
24
+ assert cfg['gem_db']
25
+ end
26
+
27
+ def test_db_config_unknown_section
28
+ cfg = ConfigurationLoader.load_db_config('unknown')
29
+ assert_equal Hash.new, cfg
30
+ end
31
+
32
+ def test_merging_config
33
+ cfg = ConfigurationLoader.load('cfg.yml')
34
+ assert cfg['hash']['app']
35
+ assert_nil cfg['hash']['plugin']
36
+ assert_nil cfg['hash']['gem']
37
+ assert_equal [ "app_one", "app_two" ], cfg['array']
38
+ end
39
+
40
+ def test_merging_hash
41
+ cfg = ConfigurationLoader.load('cfg.yml', :section => 'hash')
42
+ assert_equal 'app', cfg['global'], 'App takes the precedence among app, plugin, and gem'
43
+ assert_equal 'plugin', cfg['component'], 'Plugin takes the precedence between plugin and gem'
44
+ assert cfg['app']
45
+ assert cfg['plugin']
46
+ assert cfg['gem']
47
+ end
48
+
49
+ def test_merging_array
50
+ cfg = ConfigurationLoader.load('cfg.yml', :section => 'array')
51
+ ["app_one", "app_two", "plugin_one", "plugin_two", "gem_one", "gem_two"].each { |e| assert cfg.include?(e) }
52
+ end
53
+
54
+ def test_merging_string
55
+ cfg = ConfigurationLoader.load('cfg.yml', :section => 'string')
56
+ assert_equal 'app', cfg
57
+ end
58
+
59
+ def test_no_merging
60
+ cfg = ConfigurationLoader.load('cfg.yml', :section => 'string', :merge => false)
61
+ ["app", "plugin", "gem"].each { |e| assert cfg.include?(e) }
62
+ end
63
+
64
+ def test_erb_processing
65
+ cfg = ConfigurationLoader.load('cfg.yml')
66
+ assert_equal '<%= 1 %>', cfg['erb']
67
+ erb = ConfigurationLoader.load('cfg.yml', :erb => true, :cache => false)
68
+ assert_equal 1, erb['erb']
69
+ end
70
+
71
+ def test_no_caching
72
+
73
+ cfg = ConfigurationLoader.load('cfg.yml')
74
+ assert_nil cfg['optional']
75
+
76
+ add_optional_gem
77
+
78
+ cached = ConfigurationLoader.load('cfg.yml')
79
+ assert_nil cached['optional'], "Still nil since cached"
80
+
81
+ fresh = ConfigurationLoader.load('cfg.yml', :cache => false)
82
+ assert fresh['optional']
83
+
84
+ end
85
+
86
+ def test_refresh
87
+
88
+ assert_equal Hash.new, ConfigurationLoader.load('optional.yml')
89
+ cfg = ConfigurationLoader.load('cfg.yml')
90
+ assert_nil cfg['optional']
91
+
92
+ add_optional_gem
93
+ ConfigurationLoader.refresh!('cfg.yml')
94
+
95
+ fresh = ConfigurationLoader.load('cfg.yml', :cache => false)
96
+ assert fresh['optional']
97
+ assert_equal Hash.new, ConfigurationLoader.load('optional.yml'), 'Was not refreshed'
98
+
99
+ ConfigurationLoader.refresh!
100
+ assert ConfigurationLoader.load('optional.yml')['loaded']
101
+
102
+ end
103
+
104
+ private
105
+
106
+ def add_optional_gem
107
+ $: << "#{ CONFIG_LOADER_ROOT }/optional_config/gems/optional_gem"
108
+ end
109
+
110
+ end
metadata ADDED
@@ -0,0 +1,47 @@
1
+ --- !ruby/object:Gem::Specification
2
+ rubygems_version: 0.9.2
3
+ specification_version: 1
4
+ name: configuration_loader
5
+ version: !ruby/object:Gem::Version
6
+ version: 1.0.0
7
+ date: 2007-03-16 00:00:00 -04:00
8
+ summary: Configuration files loader
9
+ require_paths:
10
+ - lib
11
+ email: rails-trunk@revolution.com
12
+ homepage:
13
+ rubyforge_project:
14
+ description:
15
+ autorequire:
16
+ default_executable:
17
+ bindir: bin
18
+ has_rdoc: false
19
+ required_ruby_version: !ruby/object:Gem::Version::Requirement
20
+ requirements:
21
+ - - ">"
22
+ - !ruby/object:Gem::Version
23
+ version: 0.0.0
24
+ version:
25
+ platform: ruby
26
+ signing_key:
27
+ cert_chain:
28
+ post_install_message:
29
+ authors:
30
+ - RHG Team
31
+ files:
32
+ - lib/configuration_loader.rb
33
+ - README
34
+ test_files:
35
+ - test/configuration_loader_test.rb
36
+ rdoc_options: []
37
+
38
+ extra_rdoc_files:
39
+ - README
40
+ executables: []
41
+
42
+ extensions: []
43
+
44
+ requirements: []
45
+
46
+ dependencies: []
47
+