Based on yesterday’s demo, we will explore some further here: First, we will write two more test classes to complete some functions of dynamic data source extraction:

public void init() { try { DruidDataSource druidDataSource = DataSourceToolsUtils.getDataSource("dynamic", "com.mysql.jdbc.Driver", "jdbc:mysql://localhost:3306/test? useUnicode=true&characterEncoding=utf-8&serverTimezone=UTC", "root", "root"); } catch (SQLException e) { e.printStackTrace(); } } public Map<String,Object> getDataSourceStat(String name) { return DataSourceToolsUtils.getDataSourceStat(name); }Copy the code

The above method initializes the connection pool, and the following method is used to get the connection pool information based on the name of the newly initialized connection pool.

Then we can do business based on the pool of connections we get. As you can see from the code we just wrote; DruidDataSourceStatManager druid is used to manage is initialization method of connection pool.

public class DruidDataSourceStatManager implements DruidDataSourceStatManagerMBean {
    private static final Lock staticLock = new ReentrantLock();
    public static final String SYS_PROP_INSTANCES = "druid.dataSources";
    public static final String SYS_PROP_REGISTER_SYS_PROPERTY = "druid.registerToSysProperty";
    private static final Log LOG = LogFactory.getLog(DruidDataSourceStatManager.class);
    private static final DruidDataSourceStatManager instance = new DruidDataSourceStatManager();
    private final AtomicLong resetCount = new AtomicLong();
    private static volatile Map dataSources;
    private static final String MBEAN_NAME = "com.alibaba.druid:type=DruidDataSourceStat";
    private static CompositeType COMPOSITE_TYPE = null;
Copy the code

We can see in DruidDataSourceStatManager private static volatile Map dataSources. This map is used by statManager to store dataSources in the cache. Let’s break the getInstance method to see what happens: Mysql > initialize connection pool dyamic1 (TMP, TMP); mysql > initialize connection pool dyamic1 (TMP, TMP, datasources);

Then we will create a connection pool named dyamic3

Then we can see that the addDataSources method is called to add an instance.

These add instances, initializing the entire connection pool information map class, are thread-safe.

There’s a lot to learn from the code here.

public static synchronized ObjectName addDataSource(Object dataSource, String name) { Map<Object, ObjectName> instances = getInstances(); MBeanServer mbeanServer = ManagementFactory.getPlatformMBeanServer(); synchronized(instances) { if (instances.size() == 0) { try { ObjectName objectName = new ObjectName("com.alibaba.druid:type=DruidDataSourceStat"); if (! mbeanServer.isRegistered(objectName)) { mbeanServer.registerMBean(instance, objectName); } } catch (JMException var9) { LOG.error("register mbean error", var9); } DruidStatService.registerMBean(); } } ObjectName objectName = null; if (name ! = null) { try { objectName = new ObjectName("com.alibaba.druid:type=DruidDataSource,id=" + name); mbeanServer.registerMBean(dataSource, objectName); } catch (Throwable var8) { LOG.error("register mbean error", var8); objectName = null; } } if (objectName == null) { try { int id = System.identityHashCode(dataSource); objectName = new ObjectName("com.alibaba.druid:type=DruidDataSource,id=" + id); mbeanServer.registerMBean(dataSource, objectName); } catch (Throwable var7) { LOG.error("register mbean error", var7); objectName = null; } } instances.put(dataSource, objectName); return objectName; }Copy the code

Adding an instance to the STAT management map with the name passed in at initialization, generating an ID to identify the connection pool resource if no name is passed in, and druid can provide multiple connection pool resources that are isolated from each other, greatly enhancing Druid’s capabilities.