Skip to content

Commit f37f8e5

Browse files
authored
Add tests for every database handler (#49)
* add tests for every database handler * add permissions to the phpunit workflow * update workflow * update tests and workflow * update tests for SQLSRV * update tests * fix sqlsrv tests * update workflow * update skipLocked() method for OCI8 * update skipLocked() method for OCI8 * update tests * simplify the code as text type is deprecated in SQLSRV * fix rector * update sqlsrv extension in the workflow * froze ubuntu version * cleanup
1 parent 0bc2957 commit f37f8e5

File tree

8 files changed

+321
-23
lines changed

8 files changed

+321
-23
lines changed

.github/workflows/phpunit.yml

+107-8
Original file line numberDiff line numberDiff line change
@@ -18,12 +18,95 @@ on:
1818
- 'phpunit*'
1919
- '.github/workflows/phpunit.yml'
2020

21+
concurrency:
22+
group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }}
23+
cancel-in-progress: true
24+
25+
permissions:
26+
contents: read
27+
28+
env:
29+
NLS_LANG: 'AMERICAN_AMERICA.UTF8'
30+
NLS_DATE_FORMAT: 'YYYY-MM-DD HH24:MI:SS'
31+
NLS_TIMESTAMP_FORMAT: 'YYYY-MM-DD HH24:MI:SS'
32+
NLS_TIMESTAMP_TZ_FORMAT: 'YYYY-MM-DD HH24:MI:SS'
33+
2134
jobs:
2235
main:
23-
name: PHP ${{ matrix.php-versions }} Unit Tests
36+
name: PHP ${{ matrix.php-versions }} - ${{ matrix.db-platforms }}
2437
runs-on: ubuntu-22.04
38+
if: "!contains(github.event.head_commit.message, '[ci skip]')"
39+
strategy:
40+
matrix:
41+
php-versions: ['8.1', '8.2', '8.3']
42+
db-platforms: ['MySQLi', 'SQLite3']
43+
include:
44+
# Postgre
45+
- php-versions: '8.1'
46+
db-platforms: Postgre
47+
# SQLSRV
48+
- php-versions: '8.1'
49+
db-platforms: SQLSRV
50+
# OCI8
51+
- php-versions: '8.1'
52+
db-platforms: OCI8
2553

2654
services:
55+
mysql:
56+
image: mysql:8.0
57+
env:
58+
MYSQL_ALLOW_EMPTY_PASSWORD: yes
59+
MYSQL_DATABASE: test
60+
ports:
61+
- 3306:3306
62+
options: >-
63+
--health-cmd="mysqladmin ping"
64+
--health-interval=10s
65+
--health-timeout=5s
66+
--health-retries=3
67+
68+
postgres:
69+
image: postgres
70+
env:
71+
POSTGRES_USER: postgres
72+
POSTGRES_PASSWORD: postgres
73+
POSTGRES_DB: test
74+
ports:
75+
- 5432:5432
76+
options: >-
77+
--health-cmd=pg_isready
78+
--health-interval=10s
79+
--health-timeout=5s
80+
--health-retries=3
81+
82+
mssql:
83+
image: mcr.microsoft.com/mssql/server:2022-latest
84+
env:
85+
MSSQL_SA_PASSWORD: 1Secure*Password1
86+
ACCEPT_EULA: Y
87+
MSSQL_PID: Developer
88+
ports:
89+
- 1433:1433
90+
options: >-
91+
--health-cmd="/opt/mssql-tools18/bin/sqlcmd -C -S 127.0.0.1 -U sa -P 1Secure*Password1 -Q 'SELECT @@VERSION'"
92+
--health-interval=10s
93+
--health-timeout=5s
94+
--health-retries=3
95+
96+
oracle:
97+
image: gvenzl/oracle-xe:21
98+
env:
99+
ORACLE_RANDOM_PASSWORD: true
100+
APP_USER: ORACLE
101+
APP_USER_PASSWORD: ORACLE
102+
ports:
103+
- 1521:1521
104+
options: >-
105+
--health-cmd healthcheck.sh
106+
--health-interval 20s
107+
--health-timeout 10s
108+
--health-retries 10
109+
27110
redis:
28111
image: redis
29112
ports:
@@ -34,12 +117,27 @@ jobs:
34117
--health-timeout=5s
35118
--health-retries=3
36119
37-
if: "!contains(github.event.head_commit.message, '[ci skip]')"
38-
strategy:
39-
matrix:
40-
php-versions: ['8.1', '8.2', '8.3']
41-
42120
steps:
121+
- name: Free Disk Space (Ubuntu)
122+
uses: jlumbroso/free-disk-space@main
123+
with:
124+
# this might remove tools that are actually needed,
125+
# if set to "true" but frees about 6 GB
126+
tool-cache: false
127+
128+
# all of these default to true, but feel free to set to
129+
# "false" if necessary for your workflow
130+
android: true
131+
dotnet: true
132+
haskell: true
133+
large-packages: false
134+
docker-images: true
135+
swap-storage: true
136+
137+
- name: Create database for MSSQL Server
138+
if: matrix.db-platforms == 'SQLSRV'
139+
run: sqlcmd -S 127.0.0.1 -U sa -P 1Secure*Password1 -Q "CREATE DATABASE test"
140+
43141
- name: Checkout
44142
uses: actions/checkout@v4
45143

@@ -48,7 +146,7 @@ jobs:
48146
with:
49147
php-version: ${{ matrix.php-versions }}
50148
tools: composer, phive, phpunit
51-
extensions: intl, json, mbstring, gd, xdebug, xml, sqlite3, redis
149+
extensions: intl, json, mbstring, gd, xdebug, xml, sqlite3, sqlsrv, oci8, pgsql
52150
coverage: xdebug
53151
env:
54152
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
@@ -74,6 +172,7 @@ jobs:
74172
- name: Test with PHPUnit
75173
run: vendor/bin/phpunit --coverage-text
76174
env:
175+
DB: ${{ matrix.db-platforms }}
77176
TERM: xterm-256color
78177
TACHYCARDIA_MONITOR_GA: enabled
79178

@@ -86,7 +185,7 @@ jobs:
86185
env:
87186
COVERALLS_REPO_TOKEN: ${{ secrets.GITHUB_TOKEN }}
88187
COVERALLS_PARALLEL: true
89-
COVERALLS_FLAG_NAME: PHP ${{ matrix.php-versions }}
188+
COVERALLS_FLAG_NAME: PHP ${{ matrix.php-versions }} - ${{ matrix.db-platforms }}
90189

91190
coveralls:
92191
needs: [main]
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
/**
6+
* This file is part of CodeIgniter Queue.
7+
*
8+
* (c) CodeIgniter Foundation <admin@codeigniter.com>
9+
*
10+
* For the full copyright and license information, please view
11+
* the LICENSE file that was distributed with this source code.
12+
*/
13+
14+
namespace CodeIgniter\Queue\Database\Migrations;
15+
16+
use CodeIgniter\Database\BaseConnection;
17+
use CodeIgniter\Database\Migration;
18+
19+
/**
20+
* @property BaseConnection $db
21+
*/
22+
class ChangePayloadFieldTypeInSqlsrv extends Migration
23+
{
24+
public function up(): void
25+
{
26+
if ($this->db->DBDriver === 'SQLSRV') {
27+
$fields = [
28+
'payload' => [
29+
'name' => 'payload',
30+
'type' => 'NVARCHAR',
31+
'constraint' => 'MAX',
32+
'null' => false,
33+
],
34+
];
35+
$this->forge->modifyColumn('queue_jobs', $fields);
36+
}
37+
}
38+
39+
public function down(): void
40+
{
41+
if ($this->db->DBDriver === 'SQLSRV') {
42+
$fields = [
43+
'payload' => [
44+
'name' => 'payload',
45+
'type' => 'TEXT', // already deprecated
46+
'null' => false,
47+
],
48+
];
49+
$this->forge->modifyColumn('queue_jobs', $fields);
50+
}
51+
}
52+
}

src/Models/QueueJobModel.php

+9-3
Original file line numberDiff line numberDiff line change
@@ -100,7 +100,13 @@ private function skipLocked(string $sql): string
100100
return str_replace('WHERE', $replace, $sql);
101101
}
102102

103-
return $sql .= ' FOR UPDATE SKIP LOCKED';
103+
if ($this->db->DBDriver === 'OCI8') {
104+
$sql = str_replace('SELECT *', 'SELECT "id"', $sql);
105+
// prepare final query
106+
$sql = sprintf('SELECT * FROM "%s" WHERE "id" = (%s)', $this->db->prefixTable($this->table), $sql);
107+
}
108+
109+
return $sql . ' FOR UPDATE SKIP LOCKED';
104110
}
105111

106112
/**
@@ -111,9 +117,9 @@ private function setPriority(BaseBuilder $builder, array $priority): BaseBuilder
111117
$builder->whereIn('priority', $priority);
112118

113119
if ($priority !== ['default']) {
114-
if ($this->db->DBDriver === 'SQLite3') {
120+
if ($this->db->DBDriver !== 'MySQLi') {
115121
$builder->orderBy(
116-
'CASE priority '
122+
sprintf('CASE %s ', $this->db->protectIdentifiers('priority'))
117123
. implode(
118124
' ',
119125
array_map(static fn ($value, $key) => "WHEN '{$value}' THEN {$key}", $priority, array_keys($priority))

tests/DatabaseHandlerTest.php

+6-6
Original file line numberDiff line numberDiff line change
@@ -89,7 +89,7 @@ public function testPush(): void
8989
$this->seeInDatabase('queue_jobs', [
9090
'queue' => 'queue',
9191
'payload' => json_encode(['job' => 'success', 'data' => ['key' => 'value']]),
92-
'available_at' => '1703859316',
92+
'available_at' => 1703859316,
9393
]);
9494
}
9595

@@ -108,7 +108,7 @@ public function testPushWithPriority(): void
108108
'queue' => 'queue',
109109
'payload' => json_encode(['job' => 'success', 'data' => ['key' => 'value']]),
110110
'priority' => 'high',
111-
'available_at' => '1703859316',
111+
'available_at' => 1703859316,
112112
]);
113113
}
114114

@@ -124,7 +124,7 @@ public function testPushAndPopWithPriority(): void
124124
'queue' => 'queue',
125125
'payload' => json_encode(['job' => 'success', 'data' => ['key1' => 'value1']]),
126126
'priority' => 'low',
127-
'available_at' => '1703859316',
127+
'available_at' => 1703859316,
128128
]);
129129

130130
$result = $handler->setPriority('high')->push('queue', 'success', ['key2' => 'value2']);
@@ -134,7 +134,7 @@ public function testPushAndPopWithPriority(): void
134134
'queue' => 'queue',
135135
'payload' => json_encode(['job' => 'success', 'data' => ['key2' => 'value2']]),
136136
'priority' => 'high',
137-
'available_at' => '1703859316',
137+
'available_at' => 1703859316,
138138
]);
139139

140140
$result = $handler->pop('queue', ['high', 'low']);
@@ -268,7 +268,7 @@ public function testFailedAndKeepJob(): void
268268
'id' => 2,
269269
'connection' => 'database',
270270
'queue' => 'queue1',
271-
'failed_at' => '1703859316',
271+
'failed_at' => 1703859316,
272272
]);
273273
}
274274

@@ -344,7 +344,7 @@ public function testRetry(): void
344344
$handler = new DatabaseHandler($this->config);
345345
$count = $handler->retry(1, 'queue1');
346346

347-
$this->assertSame($count, 1);
347+
$this->assertSame(1, $count);
348348

349349
$this->seeInDatabase('queue_jobs', [
350350
'id' => 3,

tests/Models/QueueJobModelTest.php

+2-4
Original file line numberDiff line numberDiff line change
@@ -41,11 +41,9 @@ public function testSkipLocked(): void
4141
if ($model->db->DBDriver === 'SQLite3') {
4242
$this->assertSame($sql, $result);
4343
} elseif ($model->db->DBDriver === 'SQLSRV') {
44-
$expected = 'SELECT * FROM queue_jobs WITH (ROWLOCK,UPDLOCK,READPAST) WHERE queue = "test" AND status = 0 AND available_at < 123456 LIMIT 1';
45-
$this->assertSame($expected, $result);
44+
$this->assertStringContainsString('WITH (ROWLOCK,UPDLOCK,READPAST) WHERE', $result);
4645
} else {
47-
$expected = 'SELECT * FROM queue_jobs WHERE queue = "test" AND status = 0 AND available_at < 123456 LIMIT 1 FOR UPDATE SKIP LOCKED';
48-
$this->assertSame($expected, $result);
46+
$this->assertStringContainsString('FOR UPDATE SKIP LOCKED', $result);
4947
}
5048
}
5149

tests/PredisHandlerTest.php

+1-1
Original file line numberDiff line numberDiff line change
@@ -288,7 +288,7 @@ public function testRetry(): void
288288
$handler = new PredisHandler($this->config);
289289
$count = $handler->retry(1, 'queue1');
290290

291-
$this->assertSame($count, 1);
291+
$this->assertSame(1, $count);
292292

293293
$predis = self::getPrivateProperty($handler, 'predis');
294294
$this->assertSame(2, $predis->zcard('queues:queue1:default'));

tests/RedisHandlerTest.php

+1-1
Original file line numberDiff line numberDiff line change
@@ -254,7 +254,7 @@ public function testRetry(): void
254254
$handler = new RedisHandler($this->config);
255255
$count = $handler->retry(1, 'queue1');
256256

257-
$this->assertSame($count, 1);
257+
$this->assertSame(1, $count);
258258

259259
$redis = self::getPrivateProperty($handler, 'redis');
260260
$this->assertSame(2, $redis->zCard('queues:queue1:default'));

0 commit comments

Comments
 (0)