所以......首先,我应该明确我的目标。我的目标是让一个环境定义常量填充我的应用程序可以引用的yaml文件中的属性。
我能给出的最简单的例子是这样的:
# initalizers / config.rb
CONFIG = YAML.load_file("#{Rails.root}/config/config.yml")[RAILS_ENV]
# config.yml:
production:
host:
foo.com
development:
host:
localhost
port:
3000
# 配置/环境/ development.rb
Foo::Application.configure do
#...
config.action_mailer.default_url_options = { :host => CONFIG[:host], :port => CONFIG[:port] }
config.after_initialize do
Rails.application.routes.default_url_options = { :host => CONFIG[:host], :port => CONFIG[:port] }
end
end
我的问题是:
在after_initialize块之前不存在常量“CONFIG”(显然因为CONFIG被设置为初始化过程的一部分),所以我需要将它移动到after_initialize块中,但我不能引用“config.action_mailer”在after_initialize块中,因为在该范围内不存在“config”...这对我来说真的很困惑。不应该在块内部访问“config”,因为它存在于它之外?
作为一个附带问题,我真的很困惑这个config.x业务如何工作。该块没有产生任何变量,那么“配置”在Foo :: Application.configure的上下文中是如何有效的呢?
我认为它应该完全适用于它:
Foo::Application.configure do |config|
但事实并非如此,所以我很好奇这是如何运作的。
答案 0 :(得分:0)
如果您在config/application.rb
内部而不是初始化程序中定义配置加载程序,则应该能够抢先调用configure
,并及时设置所有内容。
有时最好创建一个处理配置文件的子类。一个非常基本的例子就是:
class Foo::Configuration
def initialize
# Read in contents of config file
end
def method_missing(name)
@config[name.to_s]
end
end
然后在您的应用程序中定义一个这样的方法:
class Foo::Application
def self.config
@config ||= Foo::Configuration.new
end
end
这将根据需要自动加载。它还避免了在每个单个对象的上下文中出现的混乱常量。