从require获取数据库配置

时间:2014-10-20 18:26:25

标签: ruby sinatra

现在我有一个连接数据库的简单Sinatra应用程序。

现在我在repo本身内部有硬编码的连接字符串。我的目标是从不同的文件(最终将在repo之外)返回连接信息。

这是我迄今为止所尝试过的:

app.rb

class MySinatraApp < Sinatra::Application

  configure do

    conf = require_relative 'configuration'

    # set public dirs, sessions, etc.

    set :mongourl, conf[:mongourl]
    set :mongodb,  conf[:mongodb]
  end
end

...最后在configuration.rb

env = ENV['RACK_ENV'].to_sym

case env
when :production
  return {
    "mongourl" => 'mongodb://localhost/prod',
    "mongodb" => 'prod'
  }

when :development
  return {
    "mongourl" => 'mongodb://localhost/dev',
    "mongodb" => 'prod'
  }

else
  return {
    "mongourl" => 'mongodb://localhost/test',
    "mongodb" => 'test'
  }
end

我的想法是返回我需要使用的任何哈希值,但是当我尝试上述操作时,它会出错并出现这些错误:

<my_project_dir>/configuration.rb: <my_project_dir>/configuration.rb:9: Invalid return (SyntaxError)
<my_project_dir>/configuration.rb:16: Invalid return
<my_project_dir>/configuration.rb:21: Invalid return

从错误中,您无法按照我现在的方式返回。我假设这是因为它不是某种函数调用?人们通常如何在Ruby / Sinatra中包含配置文件?

3 个答案:

答案 0 :(得分:2)

你是不对的,因为你不能以这种方式从return d文件中require at least not at the moment)。您的解决方案是使用顶级常量而不是全局变量(全局变量看起来像$foo,常量看起来像FooFOO)但它几乎相同。

在Sinatra中进行此类配置的常见解决方案是使用ConfigFile from Sinatra-contrib

创建配置Yaml文件:

production:
  mongourl: mongodb://localhost/prod
  mongodb: prod
develepment:
  mongourl: mongodb://localhost/dev
  mongodb: prod
test:
  mongourl: mongodb://localhost/test
  mongodb: test

然后在你的Sinatra文件中(首先安装sinatra-contrib gem):

require 'sinatra'
require 'sinatra/config_file'

config_file 'path/to/config.yml'

现在,配置文件中的设置将根据正在运行的环境提供。

执行此类操作的另一种方法是将所有配置数据放入环境变量中,然后使用ENV访问它们。这样做可以防止您意外地将生产凭据签入到版本控制中,但这意味着您必须以某种方式管理所有配置变量。如果您想这样做,请查看dotenvForeman以获取可以提供帮助的工具。

答案 1 :(得分:1)

  

如果有人有更好的方法来包含数据库连接字符串,请分享!

我不会说这是一种更好的方式,但我这样做是因为它很简单。 或多或少与sinatra / config_file相同。

因此,您的配置文件包含每个环境的不同值

$cat config.yaml
development:
  mongourl: mongodb://localhost/test
  mongodb: dev
production:
  mongourl: mongodb://localhost/test
  mongodb: prod

现在只需使用它:

configure do
    env = ENV['RACK_ENV']
    AppConfig = YAML.load_file(File.expand_path("../config.yaml", File.dirname(__FILE__)))[env]
    set :mongourl, AppConfig['mongourl']
    set :mongodb,  AppConfig['mongodb']
end 

答案 2 :(得分:0)

看起来我只能在require'ed文件的根目录中声明一个变量,它自动是全局的(我认为)。在任何一种情况下,这都是我改变文件的方式:

app.rb

class MySinatraApp < Sinatra::Application

  configure do

    require_relative 'configuration'

    # set public dirs, sessions, etc.

    set :mongourl, CONFIG["mongourl"]
    set :mongodb,  CONFIG["mongodb"]
  end
end

configuration.rb

env = ENV['RACK_ENV'].to_sym

case env
when :production
  CONFIG = {
    "mongourl" => 'mongodb://localhost/prod',
    "mongodb" => 'prod'
  }

when :development
  CONFIG = {
    "mongourl" => 'mongodb://localhost/dev',
    "mongodb" => 'prod'
  }

else
  CONFIG = {
    "mongourl" => 'mongodb://localhost/test',
    "mongodb" => 'test'
  }
end

不是将连接字符串放在全局变量中的超级粉丝,但我认为它现在可以正常工作。如果有人有更好的方法来包含数据库连接字符串,请分享!