1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.apache.ibatis.datasource.pooled;
17
18 import static org.junit.jupiter.api.Assertions.assertEquals;
19 import static org.junit.jupiter.api.Assertions.assertFalse;
20 import static org.junit.jupiter.api.Assertions.assertNotEquals;
21 import static org.junit.jupiter.api.Assertions.assertTrue;
22
23 import java.sql.Connection;
24 import java.sql.SQLException;
25 import java.util.ArrayList;
26 import java.util.List;
27 import java.util.concurrent.CountDownLatch;
28 import java.util.concurrent.TimeUnit;
29
30 import org.junit.jupiter.api.BeforeEach;
31 import org.junit.jupiter.api.Test;
32
33 class PooledDataSourceTest {
34
35 PooledDataSource dataSource;
36
37 @BeforeEach
38 void beforeEach() {
39 dataSource = new PooledDataSource("org.hsqldb.jdbcDriver", "jdbc:hsqldb:mem:multipledrivers", "sa", "");
40 }
41
42 @Test
43 void shouldBlockUntilConnectionIsAvailableInPooledDataSource() throws Exception {
44 dataSource.setPoolMaximumCheckoutTime(20000);
45
46 List<Connection> connections = new ArrayList<>();
47 CountDownLatch latch = new CountDownLatch(1);
48
49 for (int i = 0; i < dataSource.getPoolMaximumActiveConnections(); i++) {
50 connections.add(dataSource.getConnection());
51 }
52
53 new Thread(() -> {
54 try {
55 dataSource.getConnection();
56 latch.countDown();
57 } catch (Exception e) {
58 throw new RuntimeException(e);
59 }
60 }).start();
61
62 assertFalse(latch.await(1000, TimeUnit.MILLISECONDS));
63 connections.get(0).close();
64 assertTrue(latch.await(1000, TimeUnit.MILLISECONDS));
65 }
66
67 @Test
68 void PoppedConnectionShouldBeNotEqualToClosedConnection() throws Exception {
69 Connection connectionToClose = dataSource.getConnection();
70 CountDownLatch latch = new CountDownLatch(1);
71
72 new Thread(() -> {
73 try {
74 latch.await();
75 assertNotEquals(connectionToClose, dataSource.getConnection());
76 } catch (Exception e) {
77 throw new RuntimeException(e);
78 }
79 }).start();
80
81 connectionToClose.close();
82 latch.countDown();
83 }
84
85 @Test
86 void shouldEnsureCorrectIdleConnectionCount() throws Exception {
87 dataSource.setPoolMaximumActiveConnections(10);
88 dataSource.setPoolMaximumIdleConnections(5);
89
90 PoolState poolState = dataSource.getPoolState();
91 List<Connection> connections = new ArrayList<>();
92
93 for (int i = 0; i < dataSource.getPoolMaximumActiveConnections(); i++) {
94 connections.add(dataSource.getConnection());
95 }
96
97 assertEquals(0, poolState.getIdleConnectionCount());
98
99 for (int i = 0; i < dataSource.getPoolMaximumActiveConnections(); i++) {
100 connections.get(i).close();
101 }
102
103 assertEquals(dataSource.getPoolMaximumIdleConnections(), poolState.getIdleConnectionCount());
104
105 for (int i = 0; i < dataSource.getPoolMaximumIdleConnections(); i++) {
106 dataSource.getConnection();
107 }
108
109 assertEquals(0, poolState.getIdleConnectionCount());
110 }
111
112 @Test
113 void connectionShouldBeAvailableAfterMaximumCheckoutTime() throws Exception {
114 dataSource.setPoolMaximumCheckoutTime(1000);
115 dataSource.setPoolTimeToWait(500);
116
117 int poolMaximumActiveConnections = dataSource.getPoolMaximumActiveConnections();
118 CountDownLatch latch = new CountDownLatch(1);
119
120 for (int i = 0; i < poolMaximumActiveConnections; i++) {
121 dataSource.getConnection();
122 }
123
124 new Thread(() -> {
125 try {
126 dataSource.getConnection();
127 latch.countDown();
128 } catch (Exception e) {
129 throw new RuntimeException(e);
130 }
131 }).start();
132
133 assertTrue(latch.await(5000, TimeUnit.MILLISECONDS));
134 }
135
136 @Test
137 void forceCloseAllShouldRemoveAllActiveAndIdleConnection() throws SQLException {
138 dataSource.setPoolMaximumActiveConnections(10);
139 dataSource.setPoolMaximumIdleConnections(5);
140
141 PoolState poolState = dataSource.getPoolState();
142 List<Connection> connections = new ArrayList<>();
143
144 for (int i = 0; i < dataSource.getPoolMaximumActiveConnections(); i++) {
145 connections.add(dataSource.getConnection());
146 }
147
148 for (int i = 0; i < dataSource.getPoolMaximumIdleConnections(); i++) {
149 connections.get(i).close();
150 }
151
152 assertEquals(dataSource.getPoolMaximumActiveConnections() - poolState.getIdleConnectionCount(),
153 poolState.getActiveConnectionCount());
154 assertEquals(dataSource.getPoolMaximumIdleConnections(), poolState.getIdleConnectionCount());
155
156 dataSource.forceCloseAll();
157
158 assertEquals(0, poolState.getActiveConnectionCount());
159 assertEquals(0, poolState.getIdleConnectionCount());
160 }
161 }