I have so. many. regrets. about using `spec_name` for database
configurations and now I'm finally putting this mistake to an end.
Back when I started multi-db work I assumed that eventually
`connection_specification_name` (sometimes called `spec_name`) and
`spec_name` for configurations would one day be the same thing. After
2 years I no longer believe they will ever be the same thing.
This PR deprecates `spec_name` on database configurations in favor of
`name`. It's the same behavior, just a better name, or at least a
less confusing name.
`connection_specification_name` refers to the parent class name (ie
ActiveRecord::Base, AnimalsBase, etc) that holds the connection for it's
models. In some places like ConnectionHandler it shortens this to
`spec_name`, hence the major confusion.
Recently I've been working with some new folks on database stuff and
connection management and realize how confusing it was to explain that
`db_config.spec_name` was not `spec_name` and
`connection_specification_name`. Worse than that one is a symbole while
the other is a class name. This was made even more complicated by the
fact that `ActiveRecord::Base` used `primary` as the
`connection_specification_name` until #38190.
After spending 2 years with connection management I don't believe that
we can ever use the symbols from the database configs as a way to
connect the database without the class name being _somewhere_ because
a db_config does not know who it's owner class is until it's been
connected and a model has no idea what db_config belongs to it until
it's connected. The model is the only way to tie a primary/writer config
to a replica/reader config. This could change in the future but I don't
see value in adding a class name to the db_configs before connection or
telling a model what config belongs to it before connection. That would
probably break a lot of application assumptions. If we do ever end up in
that world, we can use name, because tbh `spec_name` and
`connection_specification_name` were always confusing to me.
A .ruby-version file is not useful in a plugin dummy app because the
plugin itself dictates the required Ruby version. Indeed, the dummy app
.ruby-version file might fall out of sync with whatever the plugin
dictates, and thus result in unexpected "Could not find gem" errors when
running commands from within the dummy app directory.
Follow-up to #38429.
`Rails::Command.invoke` passes arguments through to the appropriate
command class. However, some command classes were ignoring those
arguments, and instead relying on the contents of ARGV. In particular,
RakeCommand expected ARGV to contain the arguments necessary to the Rake
task, and no other arguments. This caused the `webpacker:install` task
to fail when the `--dev` option from `rails new --dev` remained in ARGV.
This commit changes the relevant command classes to not rely on the
previous contents of ARGV. This commit also adds a missing `require`
for use of `Kernel#silence_warnings`.
Fixes#38459.
When is use a scaffold_controller add the routes as resources to the
config/route.rb
Also enable to use --skip-routes if doesn't want include the resources
into the config/routes.rb file.
The schema cache tests test the following scenarios:
1) The default case works (single db, primary spec name (dev is default
to primary in 2-tier config), standard default schema cache filename)
2) Primary always wins over other entries
3) A custom schema cache filename works when set in the configuration
4) A custom schema cache filename works when set in the ENV
Cases that don't work:
1) A non-primary database entry picks up a namespaced schema cache file
This can't work currently because there's no way of knowing which cache
we actually want. In this railtie we can only load ActiveRecord::Base's
schema cache. If we grab the first config we risk loading a cache for
another connection because order is not guaranteed.
2) Multi-db schema caches
The reasons are similar to above. In addition we can't loop through the
configs, establish a connection, and load the cache because we don't
know what parent class to establish a connection to. In that case AR
Base will always get the cache and it would cause the last one to win
and therefore be loaded on the wrong connection.
The real fix for these issues is to get rid of the railtie entirely, but
for now we needed to set this back to what the behavior was before
recent changes but with the ability to pass a custom key.
Co-authored-by: Katrina Owen <kytrinyx@github.com>
The documentation for Rails::Generators::TestCase suggests using tmp/ as
the destination directory when testing generators. Many plugins test
generators, so it makes sense to include tmp/ in the default .gitignore.
Rails has a number of places where a YAML configuration file is read,
then ERB is evaluated and finally the YAML is parsed.
This consolidates that into one common class.
Co-authored-by: Kasper Timm Hansen <kaspth@gmail.com>
If the plugin or one of its dependencies requires a version of Rake
that is different than the version executing the Rakefile,
`require 'bundler/setup'` will raise a LoadError with a helpful error
message like: "You have already activated rake 13.0.1, but your Gemfile
requires rake 12.3.3. Prepending `bundle exec` to your command may solve
this."
If that LoadError is swallowed, another LoadError will eventually be
raised with a less helpful / more confusing error message like: "cannot
load such file -- rake".
When generating applications, it initializes Git repository since
8989a5057b
However, it doesn't initialize Git when creating plugins.
Plugins are mostly libraries and are likely hosted on GitHub,
so initializing Git for plugins makes sense.
The initializer that loads the default schema cache on the default
connection doesn't account for the case where an app overrides the
default filename either via ENV["SCHEMA_PATH"], or via the
:schema_cache_path defined in the db config.
Note that as discussed in #34449 this initializer doesn't work for
applications using multiple databases, and this change doesn't fix that.
Introduce benchmark generator to add benchmarks to Rails applications.
The generator makes use of `benchmark-ips`, and will automatically add
the gem to the Gemfile as needed.
Co-authored-by: Gannon McGibbon <gannon.mcgibbon@gmail.com>
When generating a new app without `--skip-spring`, caching classes was
disabled in `environments/test.rb`. This was implicitly disabling caching
view templates too. This change will enable view template caching by adding
this to the generated `environments/test.rb`:
config.action_view.cache_template_loading = true
See 65344f254cde87950c7f176cb7aa09c002a6f882
Database configurations are now objects almost everywhere, so we don't
need to fake access to a hash with `#default_hash` or it's alias `#[]`.
Applications should `configs_for` and pass `env_name` and `spec_name` to
get the database config object. If you're looking for the default for
the test environment you can pass `configs_for(env_name: "test", spec_name:
"primary")`. Change test to developement to get the dev config, etc.
`#default_hash` and `#[]` will be removed in 6.2.
Co-authored-by: John Crepezzi <john.crepezzi@gmail.com>
This allows deprecation messages to be matched by substring, symbol (treated as
substring), or regular expression. If a warning is matched, the behaviors
configured for disallowed deprecations will be used. The default behavior for
disallowed deprecation warnings is `:raise`.
Also adds `ActiveSupport::Deprecation.allow` for thread-local, block level ignoring of deprecation warnings which would otherwise be disallowed by ActiveSupport::Deprecation.disallowed_warnings.
This change addresses a few issues:
First, shelling out to the `rails` command requires the destination
directory to contain certain files that the command uses to initialize
itself. While this is not an issue when running generators normally, it
is troublesome when testing generator-invoking generators which output
to ephemeral destination directories.
Second, shelling out to the `rails` command is very slow. This also is
not a particular concern when running generators normally, but it makes
test suites for generator-invoking generators painfully slow.
Third, shelling out to the `rails` command fails silently by default.
Such silent failures can be surprising, and can lead to confusing
downstream failures.
The Gemfile offers more flexibility than the gemspec in terms of gem
groups and platforms. Putting the default development dependencies in
the Gemfile encourages users to add their own development dependencies
to the Gemfile. This is similar to the current behavior of the
`bundle gem` command (see bundler/bundler#7222).
This change also fixes a corner case where using the "--skip-gemspec"
and "--skip-active-record" options together would incorrectly generate a
"sqlite3" dependency in the Gemfile.
While trying to fix#16433, we made the middleware deletions always
happen at the end. While this works for the case of deleting the
Rack::Runtime middleware, it makes operations like the following
misbehave.
```ruby
gem "bundler", "< 1.16"
begin
require "bundler/inline"
rescue LoadError => e
$stderr.puts "Bundler version 1.10 or later is required. Please update your Bundler"
raise e
end
gemfile(true) do
source "https://rubygems.org"
git_source(:github) { |repo| "https://github.com/#{repo}.git" }
gem "rails", github: "rails/rails"
end
require "action_controller/railtie"
class TestApp < Rails::Application
config.root = __dir__
secrets.secret_key_base = "secret_key_base"
config.logger = Logger.new($stdout)
Rails.logger = config.logger
middleware.insert_after ActionDispatch::Session::CookieStore, ::Rails::Rack::Logger, config.log_tags
middleware.delete ::Rails::Rack::Logger
end
require "minitest/autorun"
require "rack/test"
class BugTest < Minitest::Test
include Rack::Test::Methods
def test_returns_success
get "/"
assert last_response.ok?
end
private
def app
Rails.application
end
end
```
In the case ☝️ the ::Rails::Rack::Logger would be deleted instead of
moved, because the order of middleware stack building execution will be:
```ruby
[:insert, ActionDispatch::Session::CookieStore, [::Rails::Rack::Logger]]
[:delete, ::Rails::Rack::Logger, [config.log_tags]]
```
This is pretty surprising and hard to reason about behaviour, unless you
go spelunking into the Rails configuration code.
I have a few solutions in mind and all of them have their drawbacks.
1. Introduce a `Rails::Configuration::MiddlewareStackProxy#delete!` that
delays the deleted operations. This will make `#delete` to be executed
in order. The drawback here is backwards incompatible behavior and a new
public method.
2. Just revert to the old operations. This won't allow people to delete
the `Rack::Runtime` middleware.
3. Legitimize the middleware moving with the new `#move_after` and
`#move_before` methods. This does not breaks any backwards
compatibility, but includes 2 new methods to the middleware stack.
I have implemented `3.` in this pull request.
Happy holidays! 🎄