From a68bf3ad557762049f96958e2fbf9cc543e53a04 Mon Sep 17 00:00:00 2001 From: Adam Keys Date: Wed, 4 Jun 2008 08:55:34 -0500 Subject: [PATCH] Started AR::Base.configure (for use in environments) * Added configuration module for configuration proxies * DatabaseSpec for configuring a specific connection * DatabaseEnvironment for configuring multiple environments --- activerecord/lib/active_record.rb | 2 + .../configuration/database_environment.rb | 23 +++++ .../active_record/configuration/database_spec.rb | 21 ++++ .../abstract/connection_specification.rb | 9 ++- activerecord/test/cases/configuration_test.rb | 98 ++++++++++++++++++++ 5 files changed, 152 insertions(+), 1 deletions(-) create mode 100644 activerecord/lib/active_record/configuration/database_environment.rb create mode 100644 activerecord/lib/active_record/configuration/database_spec.rb create mode 100644 activerecord/test/cases/configuration_test.rb diff --git a/activerecord/lib/active_record.rb b/activerecord/lib/active_record.rb index d4f7170..5dd31f3 100755 --- a/activerecord/lib/active_record.rb +++ b/activerecord/lib/active_record.rb @@ -37,6 +37,8 @@ unless defined? ActiveSupport end require 'active_record/base' +require 'active_record/configuration/database_spec' +require 'active_record/configuration/database_environment' require 'active_record/named_scope' require 'active_record/observer' require 'active_record/query_cache' diff --git a/activerecord/lib/active_record/configuration/database_environment.rb b/activerecord/lib/active_record/configuration/database_environment.rb new file mode 100644 index 0000000..d723aad --- /dev/null +++ b/activerecord/lib/active_record/configuration/database_environment.rb @@ -0,0 +1,23 @@ +module ActiveRecord + module Configuration + class DatabaseEnvironment + + attr_reader :db_specs + + def initialize + @db_specs = Hash.new { |hash, key| hash[key] = DatabaseSpec.new } + end + + def method_missing(env, *args, &block) + yield db_specs[env] + end + + def specs + db_specs.inject({}) do |acc, env_spec| + acc.update(env_spec.first => env_spec.last.spec) + end + end + + end + end +end \ No newline at end of file diff --git a/activerecord/lib/active_record/configuration/database_spec.rb b/activerecord/lib/active_record/configuration/database_spec.rb new file mode 100644 index 0000000..aa978fd --- /dev/null +++ b/activerecord/lib/active_record/configuration/database_spec.rb @@ -0,0 +1,21 @@ +module ActiveRecord + module Configuration + class DatabaseSpec + attr_reader :spec + + def initialize + @spec = {} + end + + def method_missing(meth, *values, &block) + spec[name_for(meth)] = values.first + end + + protected + + def name_for(sym) + sym.to_s.gsub('=', '').to_sym + end + end + end +end \ No newline at end of file diff --git a/activerecord/lib/active_record/connection_adapters/abstract/connection_specification.rb b/activerecord/lib/active_record/connection_adapters/abstract/connection_specification.rb index 2a8807f..5487763 100644 --- a/activerecord/lib/active_record/connection_adapters/abstract/connection_specification.rb +++ b/activerecord/lib/active_record/connection_adapters/abstract/connection_specification.rb @@ -122,7 +122,14 @@ module ActiveRecord connection.verify!(@@verification_timeout) end end - + + # Set the database configuration + def configure(&block) + env = ActiveRecord::Configuration::DatabaseEnvironment.new + yield env + self.configurations = env.specs + end + private def clear_cache!(cache, thread_id = nil, &block) if cache diff --git a/activerecord/test/cases/configuration_test.rb b/activerecord/test/cases/configuration_test.rb new file mode 100644 index 0000000..cb96a27 --- /dev/null +++ b/activerecord/test/cases/configuration_test.rb @@ -0,0 +1,98 @@ +require 'cases/helper' + +class ConfigurationTest < Test::Unit::TestCase + def setup + @spec = {:development => {:adapter => 'sqlite3', + :database => 'db/foo_development.sqlite3', + :timeout => 5000}, + :test => {:adapter => 'sqlite3', + :database => 'db/foo_development.sqlite3', + :timeout => 5000}, + :production => {:adapter => 'sqlite3', + :database => 'db/foo_development.sqlite3', + :timeout => 5000} + } + end + + def test_generate_spec_for_one_environment + + db_spec = ActiveRecord::Configuration::DatabaseSpec.new + db_spec.adapter = @spec[:development][:adapter] + db_spec.database = @spec[:development][:database] + db_spec.timeout = @spec[:development][:timeout] + + assert_equal @spec[:development], db_spec.spec + end + + def test_spec_correctly_translates_keys + db_spec = ActiveRecord::Configuration::DatabaseSpec.new + assert_equal :foo, db_spec.send(:name_for, 'foo=') + end + + def test_generate_multiple_environments + + env = ActiveRecord::Configuration::DatabaseEnvironment.new + env.development do |setup| + setup.adapter = @spec[:development][:adapter] + setup.database = @spec[:development][:database] + setup.timeout = @spec[:development][:timeout] + end + env.test do |setup| + setup.adapter = @spec[:test][:adapter] + setup.database = @spec[:test][:database] + setup.timeout = @spec[:test][:timeout] + end + env.production do |setup| + setup.adapter = @spec[:production][:adapter] + setup.database = @spec[:production][:database] + setup.timeout = @spec[:production][:timeout] + end + + assert_equal @spec, env.specs + end + + def test_generate_from_partial_specifications + spec = {:development => @spec[:development], :test => @spec[:test]} + + env = ActiveRecord::Configuration::DatabaseEnvironment.new + env.development do |setup| + setup.adapter = spec[:development][:adapter] + end + env.development do |setup| + setup.database = spec[:development][:database] + setup.timeout = spec[:development][:timeout] + end + env.test do |setup| + setup.adapter = spec[:test][:adapter] + setup.database = spec[:test][:database] + end + env.test do |setup| + setup.timeout = spec[:test][:timeout] + end + + assert_equal spec, env.specs + end + + def test_configuration + ActiveRecord::Base.configure do |db| + db.development do |setup| + setup.adapter = @spec[:development][:adapter] + setup.database = @spec[:development][:database] + setup.timeout = @spec[:development][:timeout] + end + db.test do |setup| + setup.adapter = @spec[:test][:adapter] + setup.database = @spec[:test][:database] + setup.timeout = @spec[:test][:timeout] + end + db.production do |setup| + setup.adapter = @spec[:production][:adapter] + setup.database = @spec[:production][:database] + setup.timeout = @spec[:production][:timeout] + end + end + + assert_equal @spec, ActiveRecord::Base.configurations + end + +end \ No newline at end of file -- 1.5.4.4 From 89a5636d4c8d357177857f622891eef32a14592b Mon Sep 17 00:00:00 2001 From: Adam Keys Date: Thu, 5 Jun 2008 09:03:25 -0500 Subject: [PATCH] Hooked AR config into initializer * Changed environments from symbols to strings to appease AR::Base.establish_connection * Properly set AR::Base.configurations * Try to configure AR from Configuration before attempting to load database.yml * Subclassed OrderedOptions to ActiveRecordOptions for AR connection info --- .../configuration/database_environment.rb | 2 +- .../abstract/connection_specification.rb | 2 +- activerecord/test/cases/configuration_test.rb | 64 ++++++++++---------- railties/lib/initializer.rb | 25 +++++++- 4 files changed, 57 insertions(+), 36 deletions(-) diff --git a/activerecord/lib/active_record/configuration/database_environment.rb b/activerecord/lib/active_record/configuration/database_environment.rb index d723aad..a22d26d 100644 --- a/activerecord/lib/active_record/configuration/database_environment.rb +++ b/activerecord/lib/active_record/configuration/database_environment.rb @@ -9,7 +9,7 @@ module ActiveRecord end def method_missing(env, *args, &block) - yield db_specs[env] + yield db_specs[env.to_s] end def specs diff --git a/activerecord/lib/active_record/connection_adapters/abstract/connection_specification.rb b/activerecord/lib/active_record/connection_adapters/abstract/connection_specification.rb index 5487763..d8febe3 100644 --- a/activerecord/lib/active_record/connection_adapters/abstract/connection_specification.rb +++ b/activerecord/lib/active_record/connection_adapters/abstract/connection_specification.rb @@ -127,7 +127,7 @@ module ActiveRecord def configure(&block) env = ActiveRecord::Configuration::DatabaseEnvironment.new yield env - self.configurations = env.specs + @@configurations = env.specs end private diff --git a/activerecord/test/cases/configuration_test.rb b/activerecord/test/cases/configuration_test.rb index cb96a27..221bb0b 100644 --- a/activerecord/test/cases/configuration_test.rb +++ b/activerecord/test/cases/configuration_test.rb @@ -2,13 +2,13 @@ require 'cases/helper' class ConfigurationTest < Test::Unit::TestCase def setup - @spec = {:development => {:adapter => 'sqlite3', + @spec = {'development' => {:adapter => 'sqlite3', :database => 'db/foo_development.sqlite3', :timeout => 5000}, - :test => {:adapter => 'sqlite3', + 'test' => {:adapter => 'sqlite3', :database => 'db/foo_development.sqlite3', :timeout => 5000}, - :production => {:adapter => 'sqlite3', + 'production' => {:adapter => 'sqlite3', :database => 'db/foo_development.sqlite3', :timeout => 5000} } @@ -17,11 +17,11 @@ class ConfigurationTest < Test::Unit::TestCase def test_generate_spec_for_one_environment db_spec = ActiveRecord::Configuration::DatabaseSpec.new - db_spec.adapter = @spec[:development][:adapter] - db_spec.database = @spec[:development][:database] - db_spec.timeout = @spec[:development][:timeout] + db_spec.adapter = @spec['development'][:adapter] + db_spec.database = @spec['development'][:database] + db_spec.timeout = @spec['development'][:timeout] - assert_equal @spec[:development], db_spec.spec + assert_equal @spec['development'], db_spec.spec end def test_spec_correctly_translates_keys @@ -33,41 +33,41 @@ class ConfigurationTest < Test::Unit::TestCase env = ActiveRecord::Configuration::DatabaseEnvironment.new env.development do |setup| - setup.adapter = @spec[:development][:adapter] - setup.database = @spec[:development][:database] - setup.timeout = @spec[:development][:timeout] + setup.adapter = @spec['development'][:adapter] + setup.database = @spec['development'][:database] + setup.timeout = @spec['development'][:timeout] end env.test do |setup| - setup.adapter = @spec[:test][:adapter] - setup.database = @spec[:test][:database] - setup.timeout = @spec[:test][:timeout] + setup.adapter = @spec['test'][:adapter] + setup.database = @spec['test'][:database] + setup.timeout = @spec['test'][:timeout] end env.production do |setup| - setup.adapter = @spec[:production][:adapter] - setup.database = @spec[:production][:database] - setup.timeout = @spec[:production][:timeout] + setup.adapter = @spec['production'][:adapter] + setup.database = @spec['production'][:database] + setup.timeout = @spec['production'][:timeout] end assert_equal @spec, env.specs end def test_generate_from_partial_specifications - spec = {:development => @spec[:development], :test => @spec[:test]} + spec = {'development' => @spec['development'], 'test' => @spec['test']} env = ActiveRecord::Configuration::DatabaseEnvironment.new env.development do |setup| - setup.adapter = spec[:development][:adapter] + setup.adapter = spec['development'][:adapter] end env.development do |setup| - setup.database = spec[:development][:database] - setup.timeout = spec[:development][:timeout] + setup.database = spec['development'][:database] + setup.timeout = spec['development'][:timeout] end env.test do |setup| - setup.adapter = spec[:test][:adapter] - setup.database = spec[:test][:database] + setup.adapter = spec['test'][:adapter] + setup.database = spec['test'][:database] end env.test do |setup| - setup.timeout = spec[:test][:timeout] + setup.timeout = spec['test'][:timeout] end assert_equal spec, env.specs @@ -76,19 +76,19 @@ class ConfigurationTest < Test::Unit::TestCase def test_configuration ActiveRecord::Base.configure do |db| db.development do |setup| - setup.adapter = @spec[:development][:adapter] - setup.database = @spec[:development][:database] - setup.timeout = @spec[:development][:timeout] + setup.adapter = @spec['development'][:adapter] + setup.database = @spec['development'][:database] + setup.timeout = @spec['development'][:timeout] end db.test do |setup| - setup.adapter = @spec[:test][:adapter] - setup.database = @spec[:test][:database] - setup.timeout = @spec[:test][:timeout] + setup.adapter = @spec['test'][:adapter] + setup.database = @spec['test'][:database] + setup.timeout = @spec['test'][:timeout] end db.production do |setup| - setup.adapter = @spec[:production][:adapter] - setup.database = @spec[:production][:database] - setup.timeout = @spec[:production][:timeout] + setup.adapter = @spec['production'][:adapter] + setup.database = @spec['production'][:database] + setup.timeout = @spec['production'][:timeout] end end diff --git a/railties/lib/initializer.rb b/railties/lib/initializer.rb index f0b5e3f..694a344 100644 --- a/railties/lib/initializer.rb +++ b/railties/lib/initializer.rb @@ -332,7 +332,11 @@ module Rails # and then establishes the connection. def initialize_database if configuration.frameworks.include?(:active_record) - ActiveRecord::Base.configurations = configuration.database_configuration + ActiveRecord::Base.configure do |db| + configuration.active_record.connector.call(db) + end + ActiveRecord::Base.configurations ||= configuration.database_configuration + ActiveRecord::Base.establish_connection end end @@ -672,9 +676,10 @@ module Rails self.routes_configuration_file = default_routes_configuration_file self.gems = default_gems - for framework in default_frameworks + for framework in (default_frameworks - [:active_record]) self.send("#{framework}=", Rails::OrderedOptions.new) end + self.active_record = Rails::ActiveRecordOptions.new self.active_support = Rails::OrderedOptions.new end @@ -902,3 +907,19 @@ class Rails::OrderedOptions < Array #:nodoc: return false end end + +class Rails::ActiveRecordOptions < Rails::OrderedOptions + + def initialize + @connector = Proc.new {} + super + end + + def configure(&block) + @connector = block + end + + def connector + @connector + end +end -- 1.5.4.4 From 1c430e8d517ffcf3f29a19bcd4c244e0c0f321e8 Mon Sep 17 00:00:00 2001 From: Adam Keys Date: Thu, 5 Jun 2008 23:23:05 -0500 Subject: [PATCH] Properly handle multiple calls to ActiveRecordOptions#configure --- railties/lib/initializer.rb | 12 +++++++----- 1 files changed, 7 insertions(+), 5 deletions(-) diff --git a/railties/lib/initializer.rb b/railties/lib/initializer.rb index 694a344..2059072 100644 --- a/railties/lib/initializer.rb +++ b/railties/lib/initializer.rb @@ -333,7 +333,9 @@ module Rails def initialize_database if configuration.frameworks.include?(:active_record) ActiveRecord::Base.configure do |db| - configuration.active_record.connector.call(db) + configuration.active_record.connectors.each do |connector| + connector.call(db) + end end ActiveRecord::Base.configurations ||= configuration.database_configuration @@ -911,15 +913,15 @@ end class Rails::ActiveRecordOptions < Rails::OrderedOptions def initialize - @connector = Proc.new {} + @connectors = [] super end def configure(&block) - @connector = block + @connectors << block end - def connector - @connector + def connectors + @connectors end end -- 1.5.4.4 From 9a7979c95eab866022eed1f33ae526b6cddc52e8 Mon Sep 17 00:00:00 2001 From: Adam Keys Date: Thu, 5 Jun 2008 23:50:44 -0500 Subject: [PATCH] Read database credentials from a YAML file --- .../active_record/configuration/database_spec.rb | 23 ++++++++++++++++++++ 1 files changed, 23 insertions(+), 0 deletions(-) diff --git a/activerecord/lib/active_record/configuration/database_spec.rb b/activerecord/lib/active_record/configuration/database_spec.rb index aa978fd..ea1ba7f 100644 --- a/activerecord/lib/active_record/configuration/database_spec.rb +++ b/activerecord/lib/active_record/configuration/database_spec.rb @@ -1,5 +1,23 @@ module ActiveRecord module Configuration + class Credentials + attr_reader :filename + def initialize(filename) + @filename = filename + end + + def validate! + raise "Credentials file #{filename} not found" unless File.exists?(filename) + raise "Invalid credentials file #{filename} (must be .yml)" unless File.extname(filename) == '.yml' + end + + def extract + validate! + vars = YAML.load_file(filename) + [vars['username'], vars['password']] + end + end + class DatabaseSpec attr_reader :spec @@ -7,6 +25,10 @@ module ActiveRecord @spec = {} end + def credentials=(path) + self.username, self.password = Credentials.new(path).extract + end + def method_missing(meth, *values, &block) spec[name_for(meth)] = values.first end @@ -16,6 +38,7 @@ module ActiveRecord def name_for(sym) sym.to_s.gsub('=', '').to_sym end + end end end \ No newline at end of file -- 1.5.4.4 From 03cabc8448e097e70b3dcf464bf5346372aa16b3 Mon Sep 17 00:00:00 2001 From: Adam Keys Date: Fri, 6 Jun 2008 00:21:28 -0500 Subject: [PATCH] Read credentials from a Ruby file. * Moved AR::Configuration::Credentials to is own file * Refactored Credentials to support multiple file formats --- activerecord/lib/active_record.rb | 5 +- .../lib/active_record/configuration/credentials.rb | 45 ++++++++++++++++++++ .../active_record/configuration/database_spec.rb | 18 -------- activerecord/test/cases/configuration_test.rb | 33 ++++++++++++++ 4 files changed, 81 insertions(+), 20 deletions(-) create mode 100644 activerecord/lib/active_record/configuration/credentials.rb diff --git a/activerecord/lib/active_record.rb b/activerecord/lib/active_record.rb index 5dd31f3..be20daf 100755 --- a/activerecord/lib/active_record.rb +++ b/activerecord/lib/active_record.rb @@ -37,8 +37,6 @@ unless defined? ActiveSupport end require 'active_record/base' -require 'active_record/configuration/database_spec' -require 'active_record/configuration/database_environment' require 'active_record/named_scope' require 'active_record/observer' require 'active_record/query_cache' @@ -58,6 +56,9 @@ require 'active_record/calculations' require 'active_record/serialization' require 'active_record/attribute_methods' require 'active_record/dirty' +require 'active_record/configuration/database_spec' +require 'active_record/configuration/database_environment' +require 'active_record/configuration/credentials' ActiveRecord::Base.class_eval do extend ActiveRecord::QueryCache diff --git a/activerecord/lib/active_record/configuration/credentials.rb b/activerecord/lib/active_record/configuration/credentials.rb new file mode 100644 index 0000000..a5c29fb --- /dev/null +++ b/activerecord/lib/active_record/configuration/credentials.rb @@ -0,0 +1,45 @@ +module ActiveRecord + module Configuration + class Credentials + + attr_reader :filename + def initialize(filename) + @filename = filename + end + + def validate! + unless File.exists?(filename) + raise "Credentials file #{filename} not found" + end + + unless %w{.yml .rb}.include?(File.extname(filename)) + raise "Unknown credentials file #{filename}" + end + end + + def extract + validate! + case File.extname(filename) + when '.yml' + extract_yaml + when '.rb' + extract_rb + end + end + + protected + + def extract_yaml + vars = YAML.load_file(filename) + [vars['username'], vars['password']] + end + + def extract_rb + username = '' + password = '' + eval(File.read(filename), binding, filename) + [username, password] + end + end + end +end \ No newline at end of file diff --git a/activerecord/lib/active_record/configuration/database_spec.rb b/activerecord/lib/active_record/configuration/database_spec.rb index ea1ba7f..377ba85 100644 --- a/activerecord/lib/active_record/configuration/database_spec.rb +++ b/activerecord/lib/active_record/configuration/database_spec.rb @@ -1,23 +1,5 @@ module ActiveRecord module Configuration - class Credentials - attr_reader :filename - def initialize(filename) - @filename = filename - end - - def validate! - raise "Credentials file #{filename} not found" unless File.exists?(filename) - raise "Invalid credentials file #{filename} (must be .yml)" unless File.extname(filename) == '.yml' - end - - def extract - validate! - vars = YAML.load_file(filename) - [vars['username'], vars['password']] - end - end - class DatabaseSpec attr_reader :spec diff --git a/activerecord/test/cases/configuration_test.rb b/activerecord/test/cases/configuration_test.rb index 221bb0b..f7646b4 100644 --- a/activerecord/test/cases/configuration_test.rb +++ b/activerecord/test/cases/configuration_test.rb @@ -95,4 +95,37 @@ class ConfigurationTest < Test::Unit::TestCase assert_equal @spec, ActiveRecord::Base.configurations end + def test_read_yaml_creds + credentials = {'username' => 'foo', 'password' => 'bar'} + + with_temporary_credentials(:yml, credentials.to_yaml) do |filename| + creds = ActiveRecord::Configuration::Credentials.new(filename) + assert_equal ['foo', 'bar'], creds.extract + end + end + + def test_read_ruby_creds + credentials = <<-EOR + username = 'foo' + password = 'bar' + EOR + + with_temporary_credentials(:rb, credentials) do |filename| + creds = ActiveRecord::Configuration::Credentials.new(filename) + assert_equal ['foo', 'bar'], creds.extract + end + end + + private + + def with_temporary_credentials(kind, creds) + filename = File.join(Dir.tmpdir, "credentials.#{kind}") + File.open(filename, 'w') do |f| + f.write creds + end + + yield filename + + File.delete(filename) if File.exists?(filename) + end end \ No newline at end of file -- 1.5.4.4 From 99a1339aa9d5476350f13cc27b170cda81a9e990 Mon Sep 17 00:00:00 2001 From: Adam Keys Date: Fri, 6 Jun 2008 00:52:30 -0500 Subject: [PATCH] Throw a fit if the user tries to set username/password directly in production --- .../active_record/configuration/database_spec.rb | 18 +++++++++++++++++- activerecord/test/cases/configuration_test.rb | 16 ++++++++++++++++ 2 files changed, 33 insertions(+), 1 deletions(-) diff --git a/activerecord/lib/active_record/configuration/database_spec.rb b/activerecord/lib/active_record/configuration/database_spec.rb index 377ba85..80702ae 100644 --- a/activerecord/lib/active_record/configuration/database_spec.rb +++ b/activerecord/lib/active_record/configuration/database_spec.rb @@ -7,8 +7,24 @@ module ActiveRecord @spec = {} end + def username=(value) + if const_defined?(Rails) && Rails.env.production? + raise "You cannot set username directly in production. Use a credentials file instead." + else + spec['username'] = value + end + end + + def password=(value) + if const_defined?(Rails) && Rails.env.production? + raise "You cannot set password directly in production. Use a credentials file instead." + else + spec['password'] = value + end + end + def credentials=(path) - self.username, self.password = Credentials.new(path).extract + spec['username'], spec['password'] = Credentials.new(path).extract end def method_missing(meth, *values, &block) diff --git a/activerecord/test/cases/configuration_test.rb b/activerecord/test/cases/configuration_test.rb index f7646b4..28beeb3 100644 --- a/activerecord/test/cases/configuration_test.rb +++ b/activerecord/test/cases/configuration_test.rb @@ -1,5 +1,16 @@ require 'cases/helper' +module Rails + def self.env + o = Class.new do + def production? + true + end + end + o.new + end +end + class ConfigurationTest < Test::Unit::TestCase def setup @spec = {'development' => {:adapter => 'sqlite3', @@ -116,6 +127,11 @@ class ConfigurationTest < Test::Unit::TestCase end end + def test_cant_set_user_pass_in_production + spec = ActiveRecord::Configuration::DatabaseSpec.new + assert_raises(RuntimeError) { spec.username = 'foo' } + end + private def with_temporary_credentials(kind, creds) -- 1.5.4.4 From c55a3cb7bbf9285b3163f4b9f98563ff612b0f3d Mon Sep 17 00:00:00 2001 From: Adam Keys Date: Fri, 6 Jun 2008 08:17:56 -0500 Subject: [PATCH] First take on generating apps without database.yml. * Put database config in environments.rb * Add method in AppGenerator to figure out what database config to use --- railties/environments/environment.rb | 45 ++++++++++++++++++++ .../generators/applications/app/app_generator.rb | 32 ++++++++++++-- 2 files changed, 72 insertions(+), 5 deletions(-) diff --git a/railties/environments/environment.rb b/railties/environments/environment.rb index a85ade3..d2b7692 100644 --- a/railties/environments/environment.rb +++ b/railties/environments/environment.rb @@ -64,4 +64,49 @@ Rails::Initializer.run do |config| # Activate observers that should always be running # config.active_record.observers = :cacher, :garbage_collector + + # Specify your database connections. You can partially configure your + # your database here and then finish in an environment-specific file or + # an initializer. + config.active_record.configure do |db| + + <%= header %> + db.development do |setup| + <%- config.each do |key, value| -%> + setup.<%= key %> = <%= value %> + <%- end -%> + setup.database = "<%= app_name %>_development" + end + + # Warning: The database defined as "test" will be erased and + # re-generated from your development database when you run "rake". + # Do not set this db to the same as development or production. + db.test do |setup| + <%- config.each do |key, value| -%> + setup.<%= key %> = <%= value %> + <%- end -%> + setup.database = "<%= app_name %>_test" + end + + # You cannot specify the username and password for your database directly + # here. You need to add those details to a credentials file that looks + # like this: + # + # username = 'root' + # password = '' + # + # Specify the path to your credentials file below. For more info see + # http://rubyonrails.org/awesome_credentials_docs + db.production do |setup| + <%- + production_config = config.dup + [:username, :password].each { |key| production_config.delete(key) } + production_config[:credentials] = '"/path/to/your/credentials.rb"' + -%> + <%- production_config.each do |key, value| -%> + setup.<%= key %> = <%= value %> + <%- end -%> + setup.database = "<%= app_name %>_production" + end + end end diff --git a/railties/lib/rails_generator/generators/applications/app/app_generator.rb b/railties/lib/rails_generator/generators/applications/app/app_generator.rb index 2f2dd82..58683fa 100644 --- a/railties/lib/rails_generator/generators/applications/app/app_generator.rb +++ b/railties/lib/rails_generator/generators/applications/app/app_generator.rb @@ -53,10 +53,10 @@ class AppGenerator < Rails::Generator::Base m.template "helpers/test_helper.rb", "test/test_helper.rb" # database.yml and routes.rb - m.template "configs/databases/#{options[:db]}.yml", "config/database.yml", :assigns => { - :app_name => @app_name, - :socket => options[:db] == "mysql" ? mysql_socket_location : nil - } + # m.template "configs/databases/#{options[:db]}.yml", "config/database.yml", :assigns => { + # :app_name => @app_name, + # :socket => options[:db] == "mysql" ? mysql_socket_location : nil + # } m.template "configs/routes.rb", "config/routes.rb" # Initializers @@ -66,7 +66,7 @@ class AppGenerator < Rails::Generator::Base # Environments m.file "environments/boot.rb", "config/boot.rb" - m.template "environments/environment.rb", "config/environment.rb", :assigns => { :freeze => options[:freeze], :app_name => @app_name, :app_secret => secret } + m.template "environments/environment.rb", "config/environment.rb", :assigns => { :freeze => options[:freeze], :app_name => @app_name, :app_secret => secret }.merge(database_environment_for(options[:db])) m.file "environments/production.rb", "config/environments/production.rb" m.file "environments/development.rb", "config/environments/development.rb" m.file "environments/test.rb", "config/environments/test.rb" @@ -131,6 +131,28 @@ class AppGenerator < Rails::Generator::Base def mysql_socket_location MYSQL_SOCKET_LOCATIONS.find { |f| File.exist?(f) } unless RUBY_PLATFORM =~ /(:?mswin|mingw)/ end + + def database_environment_for(db) + # header = File.read("#{RAILS_ROOT}/configs/databases/#{db}.txt") + header = '# TODO: add the adapter-specific header' + config = {:username => 'root', :password => '', :adapter => db} + config = case db + when 'mysql' + {:encoding => 'utf8', + :socket => mysql_socket_location}.merge(config) + when 'postgresql' + {:encoding => 'unicode'}.merge(config) + when 'sqlite2' + config.delete(:username) + config.delete(:password) + config + when 'sqlite3' + config.delete(:username) + config.delete(:password) + config + end + {:header => header.lstrip, :config => config} + end # Installation skeleton. Intermediate directories are automatically -- 1.5.4.4 From beaf834845fc1b11d132433535a0c479f33d7c50 Mon Sep 17 00:00:00 2001 From: Adam Keys Date: Fri, 6 Jun 2008 08:30:22 -0500 Subject: [PATCH] Properly generate the database name --- railties/environments/environment.rb | 6 +++--- .../generators/applications/app/app_generator.rb | 15 ++++++++------- 2 files changed, 11 insertions(+), 10 deletions(-) diff --git a/railties/environments/environment.rb b/railties/environments/environment.rb index d2b7692..66aaa2e 100644 --- a/railties/environments/environment.rb +++ b/railties/environments/environment.rb @@ -75,7 +75,7 @@ Rails::Initializer.run do |config| <%- config.each do |key, value| -%> setup.<%= key %> = <%= value %> <%- end -%> - setup.database = "<%= app_name %>_development" + setup.database = <%= database[app_name, 'development'] %> end # Warning: The database defined as "test" will be erased and @@ -85,7 +85,7 @@ Rails::Initializer.run do |config| <%- config.each do |key, value| -%> setup.<%= key %> = <%= value %> <%- end -%> - setup.database = "<%= app_name %>_test" + setup.database = <%= database[app_name, 'test'] %> end # You cannot specify the username and password for your database directly @@ -106,7 +106,7 @@ Rails::Initializer.run do |config| <%- production_config.each do |key, value| -%> setup.<%= key %> = <%= value %> <%- end -%> - setup.database = "<%= app_name %>_production" + setup.database = <%= database[app_name, 'production'] %> end end end diff --git a/railties/lib/rails_generator/generators/applications/app/app_generator.rb b/railties/lib/rails_generator/generators/applications/app/app_generator.rb index 58683fa..34a7d95 100644 --- a/railties/lib/rails_generator/generators/applications/app/app_generator.rb +++ b/railties/lib/rails_generator/generators/applications/app/app_generator.rb @@ -52,11 +52,7 @@ class AppGenerator < Rails::Generator::Base m.template "helpers/application_helper.rb", "app/helpers/application_helper.rb" m.template "helpers/test_helper.rb", "test/test_helper.rb" - # database.yml and routes.rb - # m.template "configs/databases/#{options[:db]}.yml", "config/database.yml", :assigns => { - # :app_name => @app_name, - # :socket => options[:db] == "mysql" ? mysql_socket_location : nil - # } + # Routes m.template "configs/routes.rb", "config/routes.rb" # Initializers @@ -135,7 +131,10 @@ class AppGenerator < Rails::Generator::Base def database_environment_for(db) # header = File.read("#{RAILS_ROOT}/configs/databases/#{db}.txt") header = '# TODO: add the adapter-specific header' - config = {:username => 'root', :password => '', :adapter => db} + config = {:username => 'root', + :password => '', + :adapter => db} + database = lambda { |app, env| "#{app}_#{env}" } config = case db when 'mysql' {:encoding => 'utf8', @@ -143,15 +142,17 @@ class AppGenerator < Rails::Generator::Base when 'postgresql' {:encoding => 'unicode'}.merge(config) when 'sqlite2' + database = lambda { |app, env| "db/#{env}.sqlite2" } config.delete(:username) config.delete(:password) config when 'sqlite3' + database = lambda { |app, env| "db/#{env}.sqlite3" } config.delete(:username) config.delete(:password) config end - {:header => header.lstrip, :config => config} + {:header => header.lstrip, :config => config, :database => database} end -- 1.5.4.4 From 10be436ee14fb9fd4623f26ea4baf242fb4affe6 Mon Sep 17 00:00:00 2001 From: Adam Keys Date: Fri, 6 Jun 2008 08:44:29 -0500 Subject: [PATCH] Add adapter-specific comments before the database config. * Note, the formatting in the text files for each adapter is a little funky so that it lines up nicely in the generated environment. * Removed old database.yml templates --- railties/configs/databases/frontbase.txt | 4 ++ railties/configs/databases/frontbase.yml | 28 ---------- railties/configs/databases/mysql.txt | 16 ++++++ railties/configs/databases/mysql.yml | 54 -------------------- railties/configs/databases/oracle.txt | 18 +++++++ railties/configs/databases/oracle.yml | 39 -------------- railties/configs/databases/postgresql.txt | 25 +++++++++ railties/configs/databases/postgresql.yml | 48 ----------------- railties/configs/databases/sqlite2.txt | 2 + railties/configs/databases/sqlite2.yml | 16 ------ railties/configs/databases/sqlite3.txt | 2 + railties/configs/databases/sqlite3.yml | 19 ------- .../generators/applications/app/app_generator.rb | 9 ++- 13 files changed, 73 insertions(+), 207 deletions(-) create mode 100644 railties/configs/databases/frontbase.txt delete mode 100644 railties/configs/databases/frontbase.yml create mode 100644 railties/configs/databases/mysql.txt delete mode 100644 railties/configs/databases/mysql.yml create mode 100644 railties/configs/databases/oracle.txt delete mode 100644 railties/configs/databases/oracle.yml create mode 100644 railties/configs/databases/postgresql.txt delete mode 100644 railties/configs/databases/postgresql.yml create mode 100644 railties/configs/databases/sqlite2.txt delete mode 100644 railties/configs/databases/sqlite2.yml create mode 100644 railties/configs/databases/sqlite3.txt delete mode 100644 railties/configs/databases/sqlite3.yml diff --git a/railties/configs/databases/frontbase.txt b/railties/configs/databases/frontbase.txt new file mode 100644 index 0000000..8eeff14 --- /dev/null +++ b/railties/configs/databases/frontbase.txt @@ -0,0 +1,4 @@ + # FrontBase versions 4.x + # + # Get the bindings: + # gem install ruby-frontbase \ No newline at end of file diff --git a/railties/configs/databases/frontbase.yml b/railties/configs/databases/frontbase.yml deleted file mode 100644 index c0c3588..0000000 --- a/railties/configs/databases/frontbase.yml +++ /dev/null @@ -1,28 +0,0 @@ -# FrontBase versions 4.x -# -# Get the bindings: -# gem install ruby-frontbase - -development: - adapter: frontbase - host: localhost - database: <%= app_name %>_development - username: <%= app_name %> - password: '' - -# Warning: The database defined as "test" will be erased and -# re-generated from your development database when you run "rake". -# Do not set this db to the same as development or production. -test: - adapter: frontbase - host: localhost - database: <%= app_name %>_test - username: <%= app_name %> - password: '' - -production: - adapter: frontbase - host: localhost - database: <%= app_name %>_production - username: <%= app_name %> - password: '' diff --git a/railties/configs/databases/mysql.txt b/railties/configs/databases/mysql.txt new file mode 100644 index 0000000..0e2283d --- /dev/null +++ b/railties/configs/databases/mysql.txt @@ -0,0 +1,16 @@ + # MySQL. Versions 4.1 and 5.0 are recommended. + # + # Install the MySQL driver: + # gem install mysql + # On Mac OS X: + # sudo gem install mysql -- --with-mysql-dir=/usr/local/mysql + # On Mac OS X Leopard: + # sudo env ARCHFLAGS="-arch i386" gem install mysql -- --with-mysql-config=/usr/local/mysql/bin/mysql_config + # This sets the ARCHFLAGS environment variable to your native architecture + # On Windows: + # gem install mysql + # Choose the win32 build. + # Install MySQL and put its /bin directory on your path. + # + # And be sure to use new-style password hashing: + # http://dev.mysql.com/doc/refman/5.0/en/old-client.html \ No newline at end of file diff --git a/railties/configs/databases/mysql.yml b/railties/configs/databases/mysql.yml deleted file mode 100644 index 7fcadcd..0000000 --- a/railties/configs/databases/mysql.yml +++ /dev/null @@ -1,54 +0,0 @@ -# MySQL. Versions 4.1 and 5.0 are recommended. -# -# Install the MySQL driver: -# gem install mysql -# On Mac OS X: -# sudo gem install mysql -- --with-mysql-dir=/usr/local/mysql -# On Mac OS X Leopard: -# sudo env ARCHFLAGS="-arch i386" gem install mysql -- --with-mysql-config=/usr/local/mysql/bin/mysql_config -# This sets the ARCHFLAGS environment variable to your native architecture -# On Windows: -# gem install mysql -# Choose the win32 build. -# Install MySQL and put its /bin directory on your path. -# -# And be sure to use new-style password hashing: -# http://dev.mysql.com/doc/refman/5.0/en/old-client.html -development: - adapter: mysql - encoding: utf8 - database: <%= app_name %>_development - username: root - password: -<% if socket -%> - socket: <%= socket %> -<% else -%> - host: localhost -<% end -%> - -# Warning: The database defined as "test" will be erased and -# re-generated from your development database when you run "rake". -# Do not set this db to the same as development or production. -test: - adapter: mysql - encoding: utf8 - database: <%= app_name %>_test - username: root - password: -<% if socket -%> - socket: <%= socket %> -<% else -%> - host: localhost -<% end -%> - -production: - adapter: mysql - encoding: utf8 - database: <%= app_name %>_production - username: root - password: -<% if socket -%> - socket: <%= socket %> -<% else -%> - host: localhost -<% end -%> diff --git a/railties/configs/databases/oracle.txt b/railties/configs/databases/oracle.txt new file mode 100644 index 0000000..41dd152 --- /dev/null +++ b/railties/configs/databases/oracle.txt @@ -0,0 +1,18 @@ + # Oracle/OCI 8i, 9, 10g + # + # Requires Ruby/OCI8: + # http://rubyforge.org/projects/ruby-oci8/ + # + # Specify your database using any valid connection syntax, such as a + # tnsnames.ora service name, or a SQL connect url string of the form: + # + # //host:[port][/service name] + # + # By default prefetch_rows (OCI_ATTR_PREFETCH_ROWS) is set to 100. And + # until true bind variables are supported, cursor_sharing is set by default + # to 'similar'. Both can be changed in the configation below; the defaults + # are equivalent to specifying: + # + # prefetch_rows: 100 + # cursor_sharing: similar + # \ No newline at end of file diff --git a/railties/configs/databases/oracle.yml b/railties/configs/databases/oracle.yml deleted file mode 100644 index a1883f6..0000000 --- a/railties/configs/databases/oracle.yml +++ /dev/null @@ -1,39 +0,0 @@ -# Oracle/OCI 8i, 9, 10g -# -# Requires Ruby/OCI8: -# http://rubyforge.org/projects/ruby-oci8/ -# -# Specify your database using any valid connection syntax, such as a -# tnsnames.ora service name, or a SQL connect url string of the form: -# -# //host:[port][/service name] -# -# By default prefetch_rows (OCI_ATTR_PREFETCH_ROWS) is set to 100. And -# until true bind variables are supported, cursor_sharing is set by default -# to 'similar'. Both can be changed in the configation below; the defaults -# are equivalent to specifying: -# -# prefetch_rows: 100 -# cursor_sharing: similar -# - -development: - adapter: oracle - database: <%= app_name %>_development - username: <%= app_name %> - password: - -# Warning: The database defined as "test" will be erased and -# re-generated from your development database when you run "rake". -# Do not set this db to the same as development or production. -test: - adapter: oracle - database: <%= app_name %>_test - username: <%= app_name %> - password: - -production: - adapter: oracle - database: <%= app_name %>_production - username: <%= app_name %> - password: diff --git a/railties/configs/databases/postgresql.txt b/railties/configs/databases/postgresql.txt new file mode 100644 index 0000000..c0b45bd --- /dev/null +++ b/railties/configs/databases/postgresql.txt @@ -0,0 +1,25 @@ + # PostgreSQL. Versions 7.4 and 8.x are supported. + # + # Install the ruby-postgres driver: + # gem install ruby-postgres + # On Mac OS X: + # gem install ruby-postgres -- --include=/usr/local/pgsql + # On Windows: + # gem install ruby-postgres + # Choose the win32 build. + # Install PostgreSQL and put its /bin directory on your path. + # + # Connect on a TCP socket. Omitted by default since the client uses a + # domain socket that doesn't need configuration. Windows does not have + # domain sockets, so uncomment these lines. + #host: localhost + #port: 5432 + # + # Schema search path. The server defaults to $user,public + #schema_search_path: myapp,sharedapp,public + # + # Minimum log levels, in increasing order: + # debug5, debug4, debug3, debug2, debug1, + # log, notice, warning, error, fatal, and panic + # The server defaults to notice. + #min_messages: warning \ No newline at end of file diff --git a/railties/configs/databases/postgresql.yml b/railties/configs/databases/postgresql.yml deleted file mode 100644 index 36f6e5a..0000000 --- a/railties/configs/databases/postgresql.yml +++ /dev/null @@ -1,48 +0,0 @@ -# PostgreSQL. Versions 7.4 and 8.x are supported. -# -# Install the ruby-postgres driver: -# gem install ruby-postgres -# On Mac OS X: -# gem install ruby-postgres -- --include=/usr/local/pgsql -# On Windows: -# gem install ruby-postgres -# Choose the win32 build. -# Install PostgreSQL and put its /bin directory on your path. -development: - adapter: postgresql - encoding: unicode - database: <%= app_name %>_development - username: <%= app_name %> - password: - - # Connect on a TCP socket. Omitted by default since the client uses a - # domain socket that doesn't need configuration. Windows does not have - # domain sockets, so uncomment these lines. - #host: localhost - #port: 5432 - - # Schema search path. The server defaults to $user,public - #schema_search_path: myapp,sharedapp,public - - # Minimum log levels, in increasing order: - # debug5, debug4, debug3, debug2, debug1, - # log, notice, warning, error, fatal, and panic - # The server defaults to notice. - #min_messages: warning - -# Warning: The database defined as "test" will be erased and -# re-generated from your development database when you run "rake". -# Do not set this db to the same as development or production. -test: - adapter: postgresql - encoding: unicode - database: <%= app_name %>_test - username: <%= app_name %> - password: - -production: - adapter: postgresql - encoding: unicode - database: <%= app_name %>_production - username: <%= app_name %> - password: diff --git a/railties/configs/databases/sqlite2.txt b/railties/configs/databases/sqlite2.txt new file mode 100644 index 0000000..6631628 --- /dev/null +++ b/railties/configs/databases/sqlite2.txt @@ -0,0 +1,2 @@ + # SQLite version 2.x + # gem install sqlite-ruby diff --git a/railties/configs/databases/sqlite2.yml b/railties/configs/databases/sqlite2.yml deleted file mode 100644 index fc48bd6..0000000 --- a/railties/configs/databases/sqlite2.yml +++ /dev/null @@ -1,16 +0,0 @@ -# SQLite version 2.x -# gem install sqlite-ruby -development: - adapter: sqlite - database: db/development.sqlite2 - -# Warning: The database defined as "test" will be erased and -# re-generated from your development database when you run "rake". -# Do not set this db to the same as development or production. -test: - adapter: sqlite - database: db/test.sqlite2 - -production: - adapter: sqlite - database: db/production.sqlite2 diff --git a/railties/configs/databases/sqlite3.txt b/railties/configs/databases/sqlite3.txt new file mode 100644 index 0000000..2fdf770 --- /dev/null +++ b/railties/configs/databases/sqlite3.txt @@ -0,0 +1,2 @@ + # SQLite version 3.x + # gem install sqlite3-ruby (not necessary on OS X Leopard) \ No newline at end of file diff --git a/railties/configs/databases/sqlite3.yml b/railties/configs/databases/sqlite3.yml deleted file mode 100644 index fff44a4..0000000 --- a/railties/configs/databases/sqlite3.yml +++ /dev/null @@ -1,19 +0,0 @@ -# SQLite version 3.x -# gem install sqlite3-ruby (not necessary on OS X Leopard) -development: - adapter: sqlite3 - database: db/development.sqlite3 - timeout: 5000 - -# Warning: The database defined as "test" will be erased and -# re-generated from your development database when you run "rake". -# Do not set this db to the same as development or production. -test: - adapter: sqlite3 - database: db/test.sqlite3 - timeout: 5000 - -production: - adapter: sqlite3 - database: db/production.sqlite3 - timeout: 5000 diff --git a/railties/lib/rails_generator/generators/applications/app/app_generator.rb b/railties/lib/rails_generator/generators/applications/app/app_generator.rb index 34a7d95..d790434 100644 --- a/railties/lib/rails_generator/generators/applications/app/app_generator.rb +++ b/railties/lib/rails_generator/generators/applications/app/app_generator.rb @@ -129,8 +129,7 @@ class AppGenerator < Rails::Generator::Base end def database_environment_for(db) - # header = File.read("#{RAILS_ROOT}/configs/databases/#{db}.txt") - header = '# TODO: add the adapter-specific header' + header = header_for(db) config = {:username => 'root', :password => '', :adapter => db} @@ -150,10 +149,14 @@ class AppGenerator < Rails::Generator::Base database = lambda { |app, env| "db/#{env}.sqlite3" } config.delete(:username) config.delete(:password) - config + {:timeout => 5000}.merge(config) end {:header => header.lstrip, :config => config, :database => database} end + + def header_for(db) + File.read(source_path("configs/databases/#{db}.txt")) + end # Installation skeleton. Intermediate directories are automatically -- 1.5.4.4