0

我正在研究一系列用于处理 Sphinx 2 和实时索引、独立、Datamapper 和 ActiveRecord 的 gem。为了做到这一点,它(显然)打开了与 Sphinx 的连接。

https://github.com/d11wtq/oedipus

Oedipus.connection("sphinxql.host.tld:9306")

现在我并没有对管理连接做任何花哨的事情……如果 gem 的用户建立了连接,就会打开一个新的连接,就是这样。管理该连接是用户的责任。但是,其他 gem 似乎带来了池的概念,而我在单线程环境中从未真正理解这一点。

有人可以告诉我为什么需要池化,我的 KISS 方法的后果是什么,以及如何添加池化?池化是否仅在多线程应用程序中才真正有意义,其中每个线程有效地存在一个连接,还是有其他有效的用例?如果它只是用于多线程应用程序,那么这不是用户可能比 gem 做出假设更好地管理的东西吗?

我猜对于线程实现,一个简单的“无限连接”方法是:

def connection
  Thread.current[:oedipus_connection] ||= connect(args)
end

因此,当线程消失时,连接也会消失(释放资源时会发生清理)。

它一直在我脑海中浮现,我想知道如果没有内置的连接池/管理会回来困扰我。

4

1 回答 1

1

Generally only multithreaded apps need multiple connections. It's theoretically possible for a single-threaded app to make use of multiple connections but there probably isn't a good reason for that.

The main benefit of a connection pool is to keep database connections for re-use, to minimise the overhead of setting up new database connections. This can matter in a typical request-per-connection scenario like rails where each request may result in just one or a few database queries. Then the connection setup becomes a significant portion of the request time.

But it's a bit of a PITA to set up a proper connection pooling system. You have connection timeouts and cleanups to worry about. Check the ActiveRecord connection pooling code for an example.

You can defer having to worry about connection pooling by creating an using the right interface. It would go something like

class MyConnection
    def self.get1(args)
        # establish a connection and return it
    end

    def close
        # close the connection
    end
end

Or maybe

def use_connection
  connection = nil
  begin
    connection = open_a_connection
    yield connection
  ensure
    connection and connection.close
  end
end

And then you can make the interface more sophisticated later on, without having to touch the rest of the app.

于 2012-04-29T06:15:20.247 回答