使用 Active Record 的时候,把连接放回连接池的时机,是在请求结束的时候。也就是说, 执行 Active Record 语句,从连接池中取得了连接,但不会立刻把连接放回连接池。
如果使用了常驻线程,线程在从连接池取得了连接之后,会占据这个连接不放回。
假如连接池设置为 5:
6.times do
Thread.new do
ActiveRecord::Base.connection.execute('SELECT 1')
sleep
end
end
sleep
将会报 ActiveRecord::ConnectionTimeoutError
此时需要使用 with_connection
。
6.times do
Thread.new do
ActiveRecord::Base.connection_pool.with_connection do
ActiveRecord::Base.connection.execute('SELECT 1')
end
sleep
end
end
sleep
假如有如下任务,池接池至少要设多大,Active Record 才不会报错?
ActiveRecord::Base.connection.execute('SELECT 1')
4.times do
Thread.new do
ActiveRecord::Base.connection.execute('SELECT 1')
sleep
end
end
sleep
答案是 5,因为主线程也占据了一个连接。