Skip to content

Commit 0a80976

Browse files
committed
hyperf/test MysqlClientConnectionTest
1 parent 78d9457 commit 0a80976

1 file changed

Lines changed: 338 additions & 0 deletions

File tree

Lines changed: 338 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,338 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace HyperfTest\Cases;
6+
7+
use Hyperf\Context\ApplicationContext;
8+
use Hyperf\DbConnection\Db;
9+
use PHPUnit\Framework\Assert;
10+
use Swoole\Coroutine;
11+
use Swoole\Process;
12+
13+
/**
14+
* MySQL代理连接测试
15+
* 验证通过代理服务连接到MySQL容器并执行查询
16+
*/
17+
class MysqlClientConnectionTest extends \PHPUnit\Framework\TestCase
18+
{
19+
20+
/**
21+
* This method is called before each test.
22+
*
23+
* @codeCoverageIgnore
24+
*/
25+
protected function setUp(): void
26+
{
27+
parent::setUp();
28+
29+
30+
}
31+
32+
33+
/**
34+
* 测试数据库连接
35+
*/
36+
public function testDatabaseConnection(): void
37+
{
38+
echo "\n========== 开始测试数据库连接 ==========\n";
39+
40+
try {
41+
// 执行简单的查询
42+
$result = Db::connection()->select('SELECT 1 as test');
43+
// $result = Db::select('SELECT 1 as test');
44+
45+
echo "查询结果: " . json_encode($result) . "\n";
46+
47+
// 验证结果
48+
Assert::assertNotEmpty($result, '查询结果不应为空');
49+
Assert::assertEquals(1, $result[0]->test, '查询结果应为1');
50+
51+
echo "✅ 数据库连接测试成功\n";
52+
} catch (\Throwable $e) {
53+
var_dump(get_exception_hyperf_array($e));
54+
echo "❌ 数据库连接测试失败: " . $e->getMessage() . "\n";
55+
throw $e;
56+
}
57+
}
58+
59+
/**
60+
* 测试MySQL版本查询
61+
*/
62+
public function testMysqlVersion(): void
63+
{
64+
echo "\n========== 开始测试MySQL版本查询 ==========\n";
65+
66+
try {
67+
$result = Db::select('SELECT VERSION() as version');
68+
69+
echo "MySQL版本: " . $result[0]->version . "\n";
70+
71+
Assert::assertNotEmpty($result, '查询结果不应为空');
72+
Assert::assertArrayHasKey(0, $result);
73+
Assert::assertObjectHasAttribute('version', $result[0]);
74+
75+
echo "✅ MySQL版本查询测试成功\n";
76+
} catch (\Throwable $e) {
77+
echo "❌ MySQL版本查询测试失败: " . $e->getMessage() . "\n";
78+
throw $e;
79+
}
80+
}
81+
82+
/**
83+
* 测试数据库列表查询
84+
*/
85+
public function testDatabaseList(): void
86+
{
87+
echo "\n========== 开始测试数据库列表查询 ==========\n";
88+
89+
try {
90+
$databases = Db::select('SHOW DATABASES');
91+
92+
echo "数据库列表:\n";
93+
foreach ($databases as $db) {
94+
echo " - " . $db->Database . "\n";
95+
}
96+
97+
Assert::assertNotEmpty($databases, '应该至少有一个数据库');
98+
99+
echo "✅ 数据库列表查询测试成功\n";
100+
} catch (\Throwable $e) {
101+
echo "❌ 数据库列表查询测试失败: " . $e->getMessage() . "\n";
102+
throw $e;
103+
}
104+
}
105+
106+
/**
107+
* 测试创建表并插入数据
108+
*/
109+
public function testCreateTableAndInsertData(): void
110+
{
111+
echo "\n========== 开始测试创建表并插入数据 ==========\n";
112+
113+
try {
114+
// 创建测试表
115+
Db::statement('DROP TABLE IF EXISTS test_proxy');
116+
Db::statement('
117+
CREATE TABLE test_proxy (
118+
id INT AUTO_INCREMENT PRIMARY KEY,
119+
name VARCHAR(100) NOT NULL,
120+
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
121+
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4
122+
');
123+
124+
echo "✅ 创建表成功\n";
125+
126+
// 插入测试数据
127+
$id1 = Db::table('test_proxy')->insertGetId(['name' => '测试数据1']);
128+
$id2 = Db::table('test_proxy')->insertGetId(['name' => '测试数据2']);
129+
130+
echo "✅ 插入数据成功,ID: {$id1}, {$id2}\n";
131+
132+
// 查询数据
133+
$rows = Db::table('test_proxy')->get();
134+
135+
echo "查询到 " . $rows->count() . " 条记录\n";
136+
137+
Assert::assertEquals(2, $rows->count(), '应该有2条记录');
138+
Assert::assertEquals('测试数据1', $rows[0]->name, '第一条数据的name应该正确');
139+
Assert::assertEquals('测试数据2', $rows[1]->name, '第二条数据的name应该正确');
140+
141+
// 清理测试表
142+
Db::statement('DROP TABLE IF EXISTS test_proxy');
143+
144+
echo "✅ 清理测试表成功\n";
145+
echo "✅ 创建表并插入数据测试成功\n";
146+
} catch (\Throwable $e) {
147+
echo "❌ 创建表并插入数据测试失败: " . $e->getMessage() . "\n";
148+
throw $e;
149+
}
150+
}
151+
152+
/**
153+
* 测试事务操作
154+
*/
155+
public function testTransaction(): void
156+
{
157+
echo "\n========== 开始测试事务操作 ==========\n";
158+
159+
try {
160+
// 创建测试表
161+
Db::statement('DROP TABLE IF EXISTS test_transaction');
162+
Db::statement('
163+
CREATE TABLE test_transaction (
164+
id INT AUTO_INCREMENT PRIMARY KEY,
165+
value INT NOT NULL
166+
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4
167+
');
168+
169+
// 测试提交事务
170+
Db::transaction(function () {
171+
Db::table('test_transaction')->insert(['value' => 100]);
172+
Db::table('test_transaction')->insert(['value' => 200]);
173+
});
174+
175+
$count = Db::table('test_transaction')->count();
176+
echo "提交后记录数: {$count}\n";
177+
Assert::assertEquals(2, $count, '提交事务后应该有2条记录');
178+
179+
// 测试回滚事务
180+
try {
181+
Db::transaction(function () {
182+
Db::table('test_transaction')->insert(['value' => 300]);
183+
throw new \Exception('手动回滚');
184+
});
185+
} catch (\Exception $e) {
186+
// 忽略异常
187+
}
188+
189+
$count = Db::table('test_transaction')->count();
190+
echo "回滚后记录数: {$count}\n";
191+
Assert::assertEquals(2, $count, '回滚事务后应该仍有2条记录');
192+
193+
// 清理测试表
194+
Db::statement('DROP TABLE IF EXISTS test_transaction');
195+
196+
echo "✅ 事务操作测试成功\n";
197+
} catch (\Throwable $e) {
198+
echo "❌ 事务操作测试失败: " . $e->getMessage() . "\n";
199+
throw $e;
200+
}
201+
}
202+
203+
/**
204+
* 测试复杂查询
205+
*/
206+
public function testComplexQuery(): void
207+
{
208+
echo "\n========== 开始测试复杂查询 ==========\n";
209+
210+
try {
211+
// 创建测试表
212+
Db::statement('DROP TABLE IF EXISTS test_complex');
213+
Db::statement('
214+
CREATE TABLE test_complex (
215+
id INT AUTO_INCREMENT PRIMARY KEY,
216+
category VARCHAR(50) NOT NULL,
217+
amount DECIMAL(10,2) NOT NULL,
218+
status VARCHAR(20) DEFAULT \'pending\'
219+
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4
220+
');
221+
222+
// 插入测试数据
223+
Db::table('test_complex')->insert([
224+
['category' => 'A', 'amount' => 100.50, 'status' => 'completed'],
225+
['category' => 'A', 'amount' => 200.75, 'status' => 'completed'],
226+
['category' => 'B', 'amount' => 50.25, 'status' => 'pending'],
227+
['category' => 'B', 'amount' => 150.00, 'status' => 'completed'],
228+
['category' => 'A', 'amount' => 75.00, 'status' => 'pending'],
229+
]);
230+
231+
echo "✅ 插入测试数据成功\n";
232+
233+
// 测试分组和聚合
234+
$result = Db::table('test_complex')
235+
->select('category', Db::raw('SUM(amount) as total'), Db::raw('COUNT(*) as count'))
236+
->groupBy('category')
237+
->get();
238+
239+
echo "分组查询结果:\n";
240+
foreach ($result as $row) {
241+
echo " {$row->category}: 总计={$row->total}, 数量={$row->count}\n";
242+
}
243+
244+
Assert::assertEquals(2, $result->count(), '应该有2个分组');
245+
246+
// 测试条件查询
247+
$completed = Db::table('test_complex')
248+
->where('status', 'completed')
249+
->orderBy('amount', 'desc')
250+
->get();
251+
252+
echo "状态为completed的记录数: " . $completed->count() . "\n";
253+
Assert::assertEquals(3, $completed->count(), '应该有3条completed状态的记录');
254+
255+
// 测试更新操作
256+
Db::table('test_complex')
257+
->where('status', 'pending')
258+
->update(['status' => 'processed']);
259+
260+
$processed = Db::table('test_complex')
261+
->where('status', 'processed')
262+
->count();
263+
264+
echo "更新为processed的记录数: {$processed}\n";
265+
Assert::assertEquals(2, $processed, '应该有2条processed状态的记录');
266+
267+
// 清理测试表
268+
Db::statement('DROP TABLE IF EXISTS test_complex');
269+
270+
echo "✅ 复杂查询测试成功\n";
271+
} catch (\Throwable $e) {
272+
echo "❌ 复杂查询测试失败: " . $e->getMessage() . "\n";
273+
throw $e;
274+
}
275+
}
276+
277+
/**
278+
* 测试连接超时和重试
279+
*/
280+
public function testConnectionRetry(): void
281+
{
282+
echo "\n========== 开始测试连接重试 ==========\n";
283+
284+
try {
285+
$attempts = 3;
286+
$success = false;
287+
288+
for ($i = 1; $i <= $attempts; $i++) {
289+
try {
290+
echo "尝试连接 {$i}/{$attempts}...\n";
291+
$result = Db::select('SELECT CONNECTION_ID() as id');
292+
echo "✅ 连接成功,连接ID: {$result[0]->id}\n";
293+
$success = true;
294+
break;
295+
} catch (\Throwable $e) {
296+
echo "连接失败: " . $e->getMessage() . "\n";
297+
if ($i < $attempts) {
298+
Coroutine::sleep(1);
299+
}
300+
}
301+
}
302+
303+
Assert::assertTrue($success, '应该在3次尝试内连接成功');
304+
305+
echo "✅ 连接重试测试成功\n";
306+
} catch (\Throwable $e) {
307+
echo "❌ 连接重试测试失败: " . $e->getMessage() . "\n";
308+
throw $e;
309+
}
310+
}
311+
312+
/**
313+
* 测试长时间连接保持
314+
*/
315+
public function testLongConnection(): void
316+
{
317+
echo "\n========== 开始测试长时间连接保持 ==========\n";
318+
319+
try {
320+
$iterations = 5;
321+
$delay = 2; // 秒
322+
323+
for ($i = 1; $i <= $iterations; $i++) {
324+
$result = Db::select('SELECT NOW() as time, CONNECTION_ID() as id');
325+
echo "查询 {$i}/{$iterations}: 时间={$result[0]->time}, 连接ID={$result[0]->id}\n";
326+
327+
if ($i < $iterations) {
328+
Coroutine::sleep($delay);
329+
}
330+
}
331+
332+
echo "✅ 长时间连接保持测试成功\n";
333+
} catch (\Throwable $e) {
334+
echo "❌ 长时间连接保持测试失败: " . $e->getMessage() . "\n";
335+
throw $e;
336+
}
337+
}
338+
}

0 commit comments

Comments
 (0)