mirror of
https://github.com/rails/rails.git
synced 2022-11-09 12:12:34 -05:00
686f6a762f
Before this commit, the database connection used in Action Cable's PostgreSQL adapter was "owned" by `ActiveRecord::Base.connection_pool`. This meant that if, for example, `#clear_reloadable_connections!` was called on the pool, Active Record would "steal" the database connection from Action Cable, and would cause all sorts of issues. This became evident during file reloads; despite Action Cable trying its hardest to return its borrowed database connection to Active Record via `@pubsub.shutdown`, Active Record calls `#clear_reloadable_connections!` on the connection pool, and due to the order of callbacks, Active Record's callback was being executed first. This meant that if you tried to rerender a view after a file was reloaded, you would have to wait through Active Record's timeout and such. Now, Action Cable takes direct ownership of the database connection it uses. It removes the connection from the pool to avoid the situation described above. Action Cable also makes sure to call `#disconnect!` on the connection when appropriate, to match the previous behavior of Active Record. [ Jon Moss & Matthew Draper]
63 lines
1.6 KiB
Ruby
63 lines
1.6 KiB
Ruby
require "test_helper"
|
|
require_relative "./common"
|
|
|
|
require "active_record"
|
|
|
|
class PostgresqlAdapterTest < ActionCable::TestCase
|
|
include CommonSubscriptionAdapterTest
|
|
|
|
def setup
|
|
database_config = { "adapter" => "postgresql", "database" => "activerecord_unittest" }
|
|
ar_tests = File.expand_path("../../../activerecord/test", __dir__)
|
|
if Dir.exist?(ar_tests)
|
|
require File.join(ar_tests, "config")
|
|
require File.join(ar_tests, "support/config")
|
|
local_config = ARTest.config["arunit"]
|
|
database_config.update local_config if local_config
|
|
end
|
|
|
|
ActiveRecord::Base.establish_connection database_config
|
|
|
|
begin
|
|
ActiveRecord::Base.connection
|
|
rescue
|
|
@rx_adapter = @tx_adapter = nil
|
|
skip "Couldn't connect to PostgreSQL: #{database_config.inspect}"
|
|
end
|
|
|
|
super
|
|
end
|
|
|
|
def teardown
|
|
super
|
|
|
|
ActiveRecord::Base.clear_all_connections!
|
|
end
|
|
|
|
def cable_config
|
|
{ adapter: "postgresql" }
|
|
end
|
|
|
|
def test_clear_active_record_connections_adapter_still_works
|
|
server = ActionCable::Server::Base.new
|
|
server.config.cable = cable_config.with_indifferent_access
|
|
server.config.logger = Logger.new(StringIO.new).tap { |l| l.level = Logger::UNKNOWN }
|
|
|
|
adapter_klass = Class.new(server.config.pubsub_adapter) do
|
|
def active?
|
|
!@listener.nil?
|
|
end
|
|
end
|
|
|
|
adapter = adapter_klass.new(server)
|
|
|
|
subscribe_as_queue("channel", adapter) do |queue|
|
|
adapter.broadcast("channel", "hello world")
|
|
assert_equal "hello world", queue.pop
|
|
end
|
|
|
|
ActiveRecord::Base.clear_reloadable_connections!
|
|
|
|
assert adapter.active?
|
|
end
|
|
end
|