Skip to content

Commit af6cb97

Browse files
committed
Support boolean type
1 parent 6357713 commit af6cb97

11 files changed

+119
-12
lines changed

src/Column/BooleanColumn.php

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace Yiisoft\Db\Oracle\Column;
6+
7+
use Yiisoft\Db\Constant\ColumnType;
8+
use Yiisoft\Db\Constant\PhpType;
9+
use Yiisoft\Db\Expression\ExpressionInterface;
10+
use Yiisoft\Db\Schema\Column\AbstractColumn;
11+
12+
final class BooleanColumn extends AbstractColumn
13+
{
14+
protected const DEFAULT_TYPE = ColumnType::BOOLEAN;
15+
16+
public function dbTypecast(mixed $value): string|ExpressionInterface|null
17+
{
18+
return match ($value) {
19+
true => '1',
20+
false => '0',
21+
null, '' => null,
22+
default => $value instanceof ExpressionInterface ? $value : ($value ? '1' : '0'),
23+
};
24+
}
25+
26+
public function getPhpType(): string
27+
{
28+
return PhpType::BOOL;
29+
}
30+
31+
public function phpTypecast(mixed $value): bool|null
32+
{
33+
if ($value === null) {
34+
return null;
35+
}
36+
37+
return (bool) $value;
38+
}
39+
}

src/Column/ColumnBuilder.php

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,11 @@ public static function binary(int|null $size = null): BinaryColumn
1313
return new BinaryColumn(ColumnType::BINARY, size: $size);
1414
}
1515

16+
public static function boolean(): BooleanColumn
17+
{
18+
return new BooleanColumn(ColumnType::BOOLEAN);
19+
}
20+
1621
public static function json(): JsonColumn
1722
{
1823
return new JsonColumn(ColumnType::JSON);

src/Column/ColumnDefinitionBuilder.php

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -56,13 +56,17 @@ protected function buildCheck(ColumnInterface $column): string
5656
if (empty($check)) {
5757
$name = $column->getName();
5858

59-
if (empty($name) || version_compare($this->queryBuilder->getServerInfo()->getVersion(), '21', '>=')) {
59+
if (empty($name)) {
6060
return '';
6161
}
6262

6363
return match ($column->getType()) {
6464
ColumnType::ARRAY, ColumnType::STRUCTURED, ColumnType::JSON =>
65-
' CHECK (' . $this->queryBuilder->getQuoter()->quoteSimpleColumnName($name) . ' IS JSON)',
65+
version_compare($this->queryBuilder->getServerInfo()->getVersion(), '21', '<')
66+
? ' CHECK (' . $this->queryBuilder->getQuoter()->quoteSimpleColumnName($name) . ' IS JSON)'
67+
: '',
68+
ColumnType::BOOLEAN =>
69+
' CHECK (' . $this->queryBuilder->getQuoter()->quoteSimpleColumnName($name) . ' IN (0,1))',
6670
default => '',
6771
};
6872
}
@@ -94,7 +98,7 @@ protected function getDbType(ColumnInterface $column): string
9498
return match ($dbType) {
9599
default => $dbType,
96100
null => match ($column->getType()) {
97-
ColumnType::BOOLEAN => 'number(1)',
101+
ColumnType::BOOLEAN => 'char(1)',
98102
ColumnType::BIT => match (true) {
99103
$size === null => 'number(38)',
100104
$size <= 126 => 'number(' . ceil(log10(2 ** $size)) . ')',

src/Column/ColumnFactory.php

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -65,8 +65,18 @@ protected function getType(string $dbType, array $info = []): string
6565
};
6666
}
6767

68-
if (isset($info['check'], $info['name']) && strcasecmp($info['check'], '"' . $info['name'] . '" is json') === 0) {
69-
return ColumnType::JSON;
68+
if (isset($info['check'], $info['name'])) {
69+
if (strcasecmp($info['check'], '"' . $info['name'] . '" is json') === 0) {
70+
return ColumnType::JSON;
71+
}
72+
73+
if (isset($info['size'])
74+
&& $dbType === 'char'
75+
&& $info['size'] === 1
76+
&& strcasecmp($info['check'], '"' . $info['name'] . '" in (0,1)') === 0
77+
) {
78+
return ColumnType::BOOLEAN;
79+
}
7080
}
7181

7282
if ($dbType === 'interval day to second' && isset($info['scale']) && $info['scale'] === 0) {
@@ -80,6 +90,7 @@ protected function getColumnClass(string $type, array $info = []): string
8090
{
8191
return match ($type) {
8292
ColumnType::BINARY => BinaryColumn::class,
93+
ColumnType::BOOLEAN => BooleanColumn::class,
8394
ColumnType::JSON => JsonColumn::class,
8495
default => parent::getColumnClass($type, $info),
8596
};

src/QueryBuilder.php

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,10 @@
1515
*/
1616
final class QueryBuilder extends AbstractQueryBuilder
1717
{
18+
protected const FALSE_VALUE = "'0'";
19+
20+
protected const TRUE_VALUE = "'1'";
21+
1822
public function __construct(ConnectionInterface $db)
1923
{
2024
$quoter = $db->getQuoter();

tests/Provider/ColumnBuilderProvider.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
namespace Yiisoft\Db\Oracle\Tests\Provider;
66

77
use Yiisoft\Db\Oracle\Column\BinaryColumn;
8+
use Yiisoft\Db\Oracle\Column\BooleanColumn;
89
use Yiisoft\Db\Oracle\Column\JsonColumn;
910

1011
class ColumnBuilderProvider extends \Yiisoft\Db\Tests\Provider\ColumnBuilderProvider
@@ -15,6 +16,7 @@ public static function buildingMethods(): array
1516

1617
$values['binary()'][2] = BinaryColumn::class;
1718
$values['binary(8)'][2] = BinaryColumn::class;
19+
$values['boolean()'][2] = BooleanColumn::class;
1820
$values['json()'][2] = JsonColumn::class;
1921

2022
return $values;

tests/Provider/ColumnFactoryProvider.php

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
use Yiisoft\Db\Constant\ColumnType;
88
use Yiisoft\Db\Expression\Expression;
99
use Yiisoft\Db\Oracle\Column\BinaryColumn;
10+
use Yiisoft\Db\Oracle\Column\BooleanColumn;
1011
use Yiisoft\Db\Oracle\Column\JsonColumn;
1112
use Yiisoft\Db\Schema\Column\ArrayColumn;
1213
use Yiisoft\Db\Schema\Column\BigIntColumn;
@@ -85,6 +86,8 @@ public static function types(): array
8586
{
8687
$types = parent::types();
8788

89+
$types['binary'][2] = BinaryColumn::class;
90+
$types['boolean'][2] = BooleanColumn::class;
8891
$types['json'][2] = JsonColumn::class;
8992

9093
return $types;

tests/Provider/ColumnProvider.php

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,14 +4,19 @@
44

55
namespace Yiisoft\Db\Oracle\Tests\Provider;
66

7+
use Yiisoft\Db\Expression\Expression;
78
use Yiisoft\Db\Oracle\Column\BinaryColumn;
9+
use Yiisoft\Db\Oracle\Column\BooleanColumn;
10+
use Yiisoft\Db\Oracle\Column\JsonColumn;
811

912
class ColumnProvider extends \Yiisoft\Db\Tests\Provider\ColumnProvider
1013
{
1114
public static function predefinedTypes(): array
1215
{
1316
$values = parent::predefinedTypes();
1417
$values['binary'][0] = BinaryColumn::class;
18+
$values['boolean'][0] = BooleanColumn::class;
19+
$values['json'][0] = JsonColumn::class;
1520

1621
return $values;
1722
}
@@ -20,6 +25,23 @@ public static function dbTypecastColumns(): array
2025
{
2126
$values = parent::dbTypecastColumns();
2227
$values['binary'][0] = new BinaryColumn();
28+
$values['boolean'] = [
29+
new BooleanColumn(),
30+
[
31+
[null, null],
32+
[null, ''],
33+
['1', true],
34+
['1', 1],
35+
['1', 1.0],
36+
['1', '1'],
37+
['0', false],
38+
['0', 0],
39+
['0', 0.0],
40+
['0', '0'],
41+
[$expression = new Expression('expression'), $expression],
42+
],
43+
];
44+
$values['json'][0] = new JsonColumn();
2345

2446
return $values;
2547
}

tests/Provider/CommandProvider.php

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -99,6 +99,20 @@ public static function insertVarbinary(): array
9999
];
100100
}
101101

102+
public static function rawSql(): array
103+
{
104+
$rawSql = parent::rawSql();
105+
106+
foreach ($rawSql as &$values) {
107+
$values[2] = strtr($values[2], [
108+
'FALSE' => "'0'",
109+
'TRUE' => "'1'",
110+
]);
111+
}
112+
113+
return $rawSql;
114+
}
115+
102116
public static function createIndex(): array
103117
{
104118
return [

tests/Provider/QueryBuilderProvider.php

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -271,8 +271,8 @@ public static function buildColumnDefinition(): array
271271
$values['bigPrimaryKey(false)'][0] = 'number(20) PRIMARY KEY';
272272
$values['uuidPrimaryKey()'][0] = 'raw(16) DEFAULT sys_guid() PRIMARY KEY';
273273
$values['uuidPrimaryKey(false)'][0] = 'raw(16) PRIMARY KEY';
274-
$values['boolean()'][0] = 'number(1)';
275-
$values['boolean(100)'][0] = 'number(1)';
274+
$values['boolean()'] = ['char(1) CHECK ("boolean_col" IN (0,1))', $values['boolean()'][1]->withName('boolean_col')];
275+
$values['boolean(100)'] = ['char(1) CHECK ("boolean_100" IN (0,1))', $values['boolean(100)'][1]->withName('boolean_100')];
276276
$values['bit()'][0] = 'number(38)';
277277
$values['bit(1)'][0] = 'number(1)';
278278
$values['bit(8)'][0] = 'number(3)';
@@ -384,6 +384,8 @@ public static function prepareParam(): array
384384
{
385385
$values = parent::prepareParam();
386386

387+
$values['true'][0] = "'1'";
388+
$values['false'][0] = "'0'";
387389
$values['binary'][0] = "HEXTORAW('737472696e67')";
388390

389391
return $values;
@@ -393,6 +395,8 @@ public static function prepareValue(): array
393395
{
394396
$values = parent::prepareValue();
395397

398+
$values['true'][0] = "'1'";
399+
$values['false'][0] = "'0'";
396400
$values['binary'][0] = "HEXTORAW('737472696e67')";
397401
$values['paramBinary'][0] = "HEXTORAW('737472696e67')";
398402

0 commit comments

Comments
 (0)