Druid connection pool to obtain a connection Source Analysis

JDBC API design in a DriverManager class, which provides a static method getConnection () This method is used to establish a connection to the database, to return a Connection instance.

Providing a new interface API version JDBC2.0: javax.sql.DataSource, this interface also provides abstract methods getConnection (), Druid made based on the interface to achieve a connection pool, i.e.: DruidDataSource implementation class.

The following will focus DruidDataSource the getConnection () interface, we can first find javax.sql.DataSource Interface:

Process briefly

Find down DruidDataSource implementation class

And getConnection () implementation

We see getConnection () calls an internal method, passing maxWait to the Senate (the maximum waiting time), into the internal method

getConnection () method is mainly done in two steps, 1) connection pool initialization operation; 2) obtaining a connection;

We look into the init method initializing, initialization method is very long, here following two content

1, connected to the synchronization initialization

Here we see the first maxActive based array configuration creates a Connection, and then configure the Connection instance initialized and stored in the corresponding array according to initialSize. (This is not the same and ThreadPoolExecutor thread pool, thread pool is to create a connection pool is the first direct all creation, follow-up is no longer calling the init method);

2, the thread producers, in the case of synchronous connection initialization will start to create a thread Connection as a producer.

We opened the producer thread run method implemented, mainly the following two codes

A first portion, waits for signal connection created

The second part, non-null signal the completion of creation (created thread waiting for notification to the consumer Connection)

We can see, creating a corresponding number of connection Connection in the initialization process, and then started a thread waits Connection producers inform consumers to create connections Connection.

init方法结束以后,我们再进入getConnectionDirect方法看看怎么获取连接

该方法又调用了一个内部方法,如果失败有重试机制,再进入内部方法

getConnectionInternal方法很长,我们忽略次要部分,关注以下内容

如果设置了等待时间则调用pollLast阻塞等待,如果没有则调用takeLast无限阻塞。这里我们点开pollLast()方法看看

首先,如果没有Connection就会发送空的信号给我们上面的生产者线程

然后就阻塞等待生产者的通知

等待结束以后再次判断是否为空(这里是典型的条件谓词的二次校验做法),还为空则再循环一遍。

如果有可用连接将获取并返回

原理实现

 DruidDataSource的原理看起来比较简单,就是基于ReentrantLock和Condition的条件队列实现了生产者和消费者模式。生产者由一个线程处理(同步模式),消费者多线程。

下面我们看一个伪代码:

首先定义一把锁和两个信号,一个是空信号,一个是非空信号

生产者,先进行条件判断,如果非空则进入等待,如果空,则创建

消费者

伪代码中注意一点,wait方法在之前要做条件谓词判断,之后也要做条件谓词判断这样才不会导致信号丢失。

 

Guess you like

Origin www.cnblogs.com/lay2017/p/10977300.html