Skip to content

Commit

Permalink
Merge pull request #217 from rails/stop-auto-configuring-database-yml
Browse files Browse the repository at this point in the history
Too error-prone to munge config/database.yml automatically
  • Loading branch information
dhh committed Sep 9, 2024
2 parents 94ea379 + 133a850 commit 1a7bc82
Show file tree
Hide file tree
Showing 5 changed files with 9 additions and 266 deletions.
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,9 @@ Solid Cache is configured by default in new Rails 8 applications. But if you're
1. `bundle add solid_cache`
2. `bin/rails solid_cache:install`

This will configure Solid Cache as the production cache store, create `config/solid_cache.yml`, create `db/cache_schema.rb`, and attempt to alter `config/database.yml` to include the new cache database.
This will configure Solid Cache as the production cache store, create `config/solid_cache.yml`, and create `db/cache_schema.rb`.

If you've already made material changes to your `config/database.yml` file, the installer may not be able to add the cache db configuration directly. If you need to do it yourself, this is what it should look like:
You will then have to add the configuration for the queue database in `config/database.yml`. If you're using sqlite, it'll look like this:

```yaml
production:
Expand Down
67 changes: 5 additions & 62 deletions lib/generators/solid_cache/install/install_generator.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,70 +3,13 @@
class SolidCache::InstallGenerator < Rails::Generators::Base
source_root File.expand_path("templates", __dir__)

def add_rails_cache
gsub_file app_root.join("config/environments/production.rb"),
/(# )?config\.cache_store = (:.*)/, "config.cache_store = :solid_cache_store"
end

def create_config_solid_cache_yml
def copy_files
template "config/solid_cache.yml"
end

def add_cache_db_to_database_yml
if app_is_using_sqlite?
gsub_file database_yml, /production:\s*<<: \*default.*/m, sqlite_database_config_with_cache
else
gsub_file database_yml, /production:\s*<<: \*default.*/m, generic_database_config_with_cache
end
end

def add_solid_cache_db_schema
template "db/cache_schema.rb"
end

private
def app_root
Pathname.new(destination_root)
end

def database_yml
app_root.join("config/database.yml")
end

def app_is_using_sqlite?
database_yml.read.match?(/production:.*sqlite3/m)
end

def sqlite_database_config_with_cache
<<~YAML
production:
primary:
<<: *default
database: storage/production.sqlite3
cache:
<<: *default
database: storage/production_cache.sqlite3
migrations_paths: db/cache_migrate
YAML
end

def app_name_from_production_database_name
database_yml.read.scan(/database: (\w+)_production/).flatten.first
end

def generic_database_config_with_cache
app_name = app_name_from_production_database_name

<<~YAML
production:
primary: &production_primary
<<: *default
database: #{app_name}_production
username: #{app_name}
password: <%= ENV["#{app_name.upcase}_DATABASE_PASSWORD"] %>
cache:
<<: *production_primary
database: #{app_name}_production_cache
YAML
end
def configure_cache_store_adapter
gsub_file Pathname.new(destination_root).join("config/environments/production.rb"),
/(# )?config\.cache_store = (:.*)/, "config.cache_store = :solid_cache_store"
end
end
59 changes: 0 additions & 59 deletions test/configs/mysql-database.yml

This file was deleted.

28 changes: 0 additions & 28 deletions test/configs/sqlite-database.yml

This file was deleted.

117 changes: 2 additions & 115 deletions test/lib/generators/solid_cache/solid_cache/install_generator_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -17,121 +17,15 @@ class SolidCache::InstallGeneratorTest < Rails::Generators::TestCase
end

test "generator updates environment config" do
copy_database_config_fixture_to_destination_root "sqlite"
run_generator [ "--skip-migrations" ]
run_generator
assert_file "#{destination_root}/config/solid_cache.yml", expected_solid_cache_config
assert_file "#{destination_root}/db/cache_schema.rb"
assert_file "#{destination_root}/config/environments/development.rb", /config.cache_store = :memory_store\n/
assert_file "#{destination_root}/config/environments/development.rb", /config.cache_store = :null_store\n/
assert_file "#{destination_root}/config/environments/test.rb", /config.cache_store = :null_store\n/
assert_file "#{destination_root}/config/environments/production.rb", /config.cache_store = :solid_cache_store\n/
end

test "generator updates sqlite database config" do
copy_database_config_fixture_to_destination_root "sqlite"
run_generator [ "--skip-migrations" ]
assert_file "#{destination_root}/config/database.yml", <<~YAML
# SQLite. Versions 3.8.0 and up are supported.
# gem install sqlite3
#
# Ensure the SQLite 3 gem is defined in your Gemfile
# gem "sqlite3"
#
default: &default
adapter: sqlite3
pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
timeout: 5000
development:
<<: *default
database: storage/development.sqlite3
# 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:
<<: *default
database: storage/test.sqlite3
# Store production database in the storage/ directory, which by default
# is mounted as a persistent Docker volume in config/deploy.yml.
production:
primary:
<<: *default
database: storage/production.sqlite3
cache:
<<: *default
database: storage/production_cache.sqlite3
migrations_paths: db/cache_migrate
YAML
end

test "generator updates mysql database config" do
copy_database_config_fixture_to_destination_root "mysql"
run_generator [ "--skip-migrations" ]
assert_file "#{destination_root}/config/database.yml", <<~YAML
# MySQL. Versions 5.5.8 and up are supported.
#
# Install the MySQL driver
# gem install mysql2
#
# Ensure the MySQL gem is defined in your Gemfile
# gem "mysql2"
#
# And be sure to use new-style password hashing:
# https://dev.mysql.com/doc/refman/5.7/en/password-hashing.html
#
default: &default
adapter: mysql2
encoding: utf8mb4
pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
username: root
password:
host: <%= ENV.fetch("DB_HOST") { "127.0.0.1" } %>
development:
<<: *default
database: bongo_development
# 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:
<<: *default
database: bongo_test
# As with config/credentials.yml, you never want to store sensitive information,
# like your database password, in your source code. If your source code is
# ever seen by anyone, they now have access to your database.
#
# Instead, provide the password or a full connection URL as an environment
# variable when you boot the app. For example:
#
# DATABASE_URL="mysql2://myuser:mypass@localhost/somedatabase"
#
# If the connection URL is provided in the special DATABASE_URL environment
# variable, Rails will automatically merge its configuration values on top of
# the values provided in this file. Alternatively, you can specify a connection
# URL environment variable explicitly:
#
# production:
# url: <%= ENV["MY_APP_DATABASE_URL"] %>
#
# Read https://guides.rubyonrails.org/configuring.html#configuring-a-database
# for a full overview on how database connection configuration can be specified.
#
production:
primary: &production_primary
<<: *default
database: bongo_production
username: bongo
password: <%= ENV["BONGO_DATABASE_PASSWORD"] %>
cache:
<<: *production_primary
database: bongo_production_cache
YAML
end

private
def expected_solid_cache_config
<<~YAML
Expand All @@ -153,12 +47,5 @@ def expected_solid_cache_config
<<: *default
YAML
end

def copy_database_config_fixture_to_destination_root(database)
FileUtils.cp(File.expand_path("../../../../configs/#{database}-database.yml", __dir__), Pathname.new(destination_root).join("config/database.yml"))
end

def expected_mysql_database_config
end
end
end

0 comments on commit 1a7bc82

Please sign in to comment.