[英]testing and establish_connection
如何为模型中使用establish_connection
连接到另一个数据库的项目编写测试?
When you do establish_connection for certain models to connect to a different database, one of the problem you would face while testing those tables is that the test data you created wont be rolled back automatically. 当您为某些模型建立connect_connection以连接到不同的数据库时,在测试这些表时您将面临的一个问题是您创建的测试数据不会自动回滚。
The actual code to create a transaction save point and to rollback the data for test lives in rails/activerecord/lib/active_record/fixtures.rb
. 用于创建事务保存点并在rails/activerecord/lib/active_record/fixtures.rb
回滚测试生命数据的实际代码。 And especially there are two methods setup_fixtures
and teardown_fixtures
. 特别是有两种方法setup_fixtures
和teardown_fixtures
。 The code in those methods are straight forward. 这些方法中的代码很简单。 They just create a savepoint and does rollback for each test. 它们只是创建一个保存点,并为每个测试进行回滚。 But it does only for the ActiveRecord::Base
connection. 但它仅适用于ActiveRecord::Base
连接。
So what you have to do is "monkey patch" these methods so that, in addition to the ActiveRecord::Base
connection, the same set of operations are done for your additional database connection. 所以你要做的就是“猴子补丁”这些方法,这样除了ActiveRecord::Base
连接之外,还为你的附加数据库连接完成了同样的操作。
Here is a sample code for the same: 以下是相同的示例代码:
## database.yml
development:
database: dev
test:
database: test
#...
my_connection_development:
database: my_connection_dev
my_connection_test:
database: my_connection_test
#...
## my_connection_base.rb
class MyConnectionBase < ActiveRecord::Base
establish_connection(ActiveRecord::Base.configurations["my_connection_#{RAILS_ENV}"])
self.abstract_class = true
end
## my_model.rb
class MyModel < MyConnectionBase
end
## my_another_model.rb
class MyAnotherModel < MyConnectionBase
end
## test_case_patch.rb
module ActiveSupport
class TestCase
def setup_fixtures
return unless defined?(ActiveRecord) && !ActiveRecord::Base.configurations.blank?
if pre_loaded_fixtures && !use_transactional_fixtures
raise RuntimeError, 'pre_loaded_fixtures requires use_transactional_fixtures'
end
@fixture_cache = {}
@@already_loaded_fixtures ||= {}
# Load fixtures once and begin transaction.
if run_in_transaction?
if @@already_loaded_fixtures[self.class]
@loaded_fixtures = @@already_loaded_fixtures[self.class]
else
load_fixtures
@@already_loaded_fixtures[self.class] = @loaded_fixtures
end
ActiveRecord::Base.connection.increment_open_transactions
ActiveRecord::Base.connection.transaction_joinable = false
ActiveRecord::Base.connection.begin_db_transaction
MyConnectionBase.connection.increment_open_transactions
MyConnectionBase.connection.transaction_joinable = false
MyConnectionBase.connection.begin_db_transaction
# Load fixtures for every test.
else
Fixtures.reset_cache
@@already_loaded_fixtures[self.class] = nil
load_fixtures
end
# Instantiate fixtures for every test if requested.
instantiate_fixtures if use_instantiated_fixtures
end
def teardown_fixtures
return unless defined?(ActiveRecord) && !ActiveRecord::Base.configurations.blank?
unless run_in_transaction?
Fixtures.reset_cache
end
# Rollback changes if a transaction is active.
if run_in_transaction? && MyConnectionBase.connection.open_transactions != 0
MyConnectionBase.connection.rollback_db_transaction
MyConnectionBase.connection.decrement_open_transactions
end
# Rollback changes if a transaction is active.
if run_in_transaction? && ActiveRecord::Base.connection.open_transactions != 0
ActiveRecord::Base.connection.rollback_db_transaction
ActiveRecord::Base.connection.decrement_open_transactions
end
MyConnectionBase.clear_active_connections!
ActiveRecord::Base.clear_active_connections!
end
end
end
因为您仍然在测试相同的模型功能,所以我认为在您的模型中放置establish_connection后不需要更改测试代码。
You will not need to Test the establish_connection method, as its a activrecord method and is well tested, before release. 在发布之前,您不需要测试establish_connection方法,因为它是一个activrecord方法并且经过了充分测试。
although if you still want to do so, call the method within a different method, and see if you can connect to appropriate tables in that DB. 虽然如果您仍想这样做,请在不同的方法中调用该方法,并查看是否可以连接到该DB中的相应表。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.