diff --git a/CHANGELOG.md b/CHANGELOG.md index 29aed4083..1c5c88e71 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -131,6 +131,7 @@ - New #1024: Add `ColumnName` and `Value` expressions (@vjik) - Chg #1025: Move expression builders to `Yiisoft\Db\Expression\Builder` namespace (@vjik) - Chg #1026: Remove `precision()`, `getPrecision()` and `getPhpType()` methods from `ColumnInterface` (@vjik) +- New #1034: Add `ConnectionInterface::getColumnBuilderClass()` method (@Tigrov) - Enh #1031: Optimize SQL generation for `Not` condition (@vjik) ## 1.3.0 March 21, 2024 diff --git a/UPGRADE.md b/UPGRADE.md index 53b77309c..ae4c5393b 100644 --- a/UPGRADE.md +++ b/UPGRADE.md @@ -136,6 +136,7 @@ Each table column has its own class in the `Yiisoft\Db\Schema\Column` namespace - `QueryPartsInterface::setFor()` - overwrites the `FOR` part of the query; - `QueryPartsInterface::setWhere()` - overwrites the `WHERE` part of the query; - `QueryPartsInterface::setHaving()` - overwrites the `HAVING` part of the query; +- `ConnectionInterface::getColumnBuilderClass()` - returns the column builder class name for concrete DBMS; - `ConnectionInterface::getColumnFactory()` - returns the column factory object for concrete DBMS; - `ConnectionInterface::getServerInfo()` - returns `ServerInfoInterface` instance which provides server information; - `ConnectionInterface::createQuery()` - creates a `Query` object; diff --git a/src/Connection/AbstractConnection.php b/src/Connection/AbstractConnection.php index ea7e51f7c..7d53201ea 100644 --- a/src/Connection/AbstractConnection.php +++ b/src/Connection/AbstractConnection.php @@ -11,6 +11,7 @@ use Yiisoft\Db\Query\BatchQueryResultInterface; use Yiisoft\Db\Query\Query; use Yiisoft\Db\Query\QueryInterface; +use Yiisoft\Db\Schema\Column\ColumnBuilder; use Yiisoft\Db\Schema\TableSchemaInterface; use Yiisoft\Db\Transaction\TransactionInterface; @@ -50,6 +51,11 @@ public function createQuery(): QueryInterface return new Query($this); } + public function getColumnBuilderClass(): string + { + return ColumnBuilder::class; + } + public function getTablePrefix(): string { return $this->tablePrefix; diff --git a/src/Connection/ConnectionInterface.php b/src/Connection/ConnectionInterface.php index a4acc5d78..5b277fa5a 100644 --- a/src/Connection/ConnectionInterface.php +++ b/src/Connection/ConnectionInterface.php @@ -16,6 +16,7 @@ use Yiisoft\Db\Query\QueryInterface; use Yiisoft\Db\Query\QueryPartsInterface; use Yiisoft\Db\QueryBuilder\QueryBuilderInterface; +use Yiisoft\Db\Schema\Column\ColumnBuilder; use Yiisoft\Db\Schema\Column\ColumnFactoryInterface; use Yiisoft\Db\Schema\QuoterInterface; use Yiisoft\Db\Schema\SchemaInterface; @@ -95,6 +96,13 @@ public function createTransaction(): TransactionInterface; */ public function close(): void; + /** + * Returns the column builder class name for the current DB connection. + * + * @psalm-return class-string + */ + public function getColumnBuilderClass(): string; + /** * Returns the column factory for creating column instances. */ diff --git a/src/Debug/ConnectionInterfaceProxy.php b/src/Debug/ConnectionInterfaceProxy.php index 60e92a598..75be41481 100644 --- a/src/Debug/ConnectionInterfaceProxy.php +++ b/src/Debug/ConnectionInterfaceProxy.php @@ -70,6 +70,11 @@ public function close(): void $this->connection->close(); } + public function getColumnBuilderClass(): string + { + return $this->connection->getColumnBuilderClass(); + } + public function getColumnFactory(): ColumnFactoryInterface { return $this->connection->getColumnFactory(); diff --git a/tests/AbstractColumnBuilderTest.php b/tests/AbstractColumnBuilderTest.php index 9707be712..98ef6288e 100644 --- a/tests/AbstractColumnBuilderTest.php +++ b/tests/AbstractColumnBuilderTest.php @@ -4,8 +4,8 @@ namespace Yiisoft\Db\Tests; +use PHPUnit\Framework\Attributes\DataProviderExternal; use PHPUnit\Framework\TestCase; -use Yiisoft\Db\Schema\Column\ColumnBuilder; use Yiisoft\Db\Tests\Provider\ColumnBuilderProvider; use Yiisoft\Db\Tests\Support\TestTrait; @@ -15,14 +15,7 @@ abstract class AbstractColumnBuilderTest extends TestCase { use TestTrait; - public function getColumnBuilderClass(): string - { - return ColumnBuilder::class; - } - - /** - * @dataProvider \Yiisoft\Db\Tests\Provider\ColumnBuilderProvider::buildingMethods - */ + #[DataProviderExternal(ColumnBuilderProvider::class, 'buildingMethods')] public function testBuildingMethods( string $buildingMethod, array $args, @@ -30,7 +23,7 @@ public function testBuildingMethods( string $expectedType, array $expectedMethodResults = [], ): void { - $columnBuilderClass = $this->getColumnBuilderClass(); + $columnBuilderClass = $this->getConnection()->getColumnBuilderClass(); $column = $columnBuilderClass::$buildingMethod(...$args); diff --git a/tests/AbstractConnectionTest.php b/tests/AbstractConnectionTest.php index 5c45001f8..ca8d45594 100644 --- a/tests/AbstractConnectionTest.php +++ b/tests/AbstractConnectionTest.php @@ -4,17 +4,15 @@ namespace Yiisoft\Db\Tests; -use Exception; use PHPUnit\Framework\TestCase; -use Throwable; use Yiisoft\Db\Driver\Pdo\PdoConnectionInterface; -use Yiisoft\Db\Exception\InvalidConfigException; use Yiisoft\Db\Exception\NotSupportedException; use Yiisoft\Db\Profiler\Context\ConnectionContext; use Yiisoft\Db\Profiler\ContextInterface; use Yiisoft\Db\Profiler\ProfilerInterface; use Yiisoft\Db\Query\BatchQueryResult; use Yiisoft\Db\Query\Query; +use Yiisoft\Db\Schema\Column\ColumnBuilder; use Yiisoft\Db\Tests\Support\Assert; use Yiisoft\Db\Tests\Support\DbHelper; use Yiisoft\Db\Tests\Support\Stub\ColumnFactory; @@ -25,9 +23,6 @@ abstract class AbstractConnectionTest extends TestCase { use TestTrait; - /** - * @throws Exception - */ public function testConnection(): void { $this->assertInstanceOf(PdoConnectionInterface::class, $this->getConnection()); @@ -42,10 +37,6 @@ public function testCreateBatchQueryResult(): void $this->assertInstanceOf(BatchQueryResult::class, $db->createBatchQueryResult($query)); } - /** - * @throws InvalidConfigException - * @throws \Yiisoft\Db\Exception\Exception - */ public function testCreateCommand(): void { $db = $this->getConnection(); @@ -68,9 +59,6 @@ public function testGetDriverName(): void $this->assertSame($this->getDriverName(), $db->getDriverName()); } - /** - * @throws Throwable - */ public function testNestedTransactionNotSupported(): void { $db = $this->getConnection(); @@ -161,6 +149,15 @@ private function getProfiler(): ProfilerInterface return $this->createMock(ProfilerInterface::class); } + public function getColumnBuilderClass(): void + { + $db = $this->getConnection(); + + $this->assertSame(ColumnBuilder::class, $db->getColumnBuilderClass()); + + $db->close(); + } + public function testGetColumnFactory(): void { $db = $this->getConnection(); diff --git a/tests/Common/CommonColumnTest.php b/tests/Common/CommonColumnTest.php index 05a74cb4e..9188f3291 100644 --- a/tests/Common/CommonColumnTest.php +++ b/tests/Common/CommonColumnTest.php @@ -10,7 +10,6 @@ use PHPUnit\Framework\Attributes\DataProviderExternal; use Yiisoft\Db\Connection\ConnectionInterface; use Yiisoft\Db\Expression\Expression; -use Yiisoft\Db\Schema\Column\ColumnBuilder; use Yiisoft\Db\Tests\AbstractColumnTest; use Yiisoft\Db\Tests\Provider\ColumnProvider; use Yiisoft\Db\Tests\Support\Stringable; @@ -27,8 +26,6 @@ abstract class CommonColumnTest extends AbstractColumnTest protected const DATETIME_COLUMN_TABLE = 'datetime_column_test'; - protected const COLUMN_BUILDER = ColumnBuilder::class; - abstract protected function insertTypeValues(ConnectionInterface $db): void; abstract protected function assertTypecastedValues(array $result, bool $allTypecasted = false): void; @@ -119,22 +116,23 @@ public function createDateTimeColumnTable(ConnectionInterface $db): void { $schema = $db->getSchema(); $command = $db->createCommand(); + $columnBuilder = $db->getColumnBuilderClass(); if ($schema->hasTable(static::DATETIME_COLUMN_TABLE)) { $command->dropTable(static::DATETIME_COLUMN_TABLE)->execute(); } $command->createTable(static::DATETIME_COLUMN_TABLE, [ - 'timestamp' => static::COLUMN_BUILDER::timestamp()->defaultValue(new Expression('CURRENT_TIMESTAMP')), - 'datetime' => static::COLUMN_BUILDER::datetime()->defaultValue('2025-04-19 14:11:35'), - 'datetime3' => static::COLUMN_BUILDER::datetime(3)->defaultValue(new Stringable('2025-04-19 14:11:35.123')), - 'datetimetz' => static::COLUMN_BUILDER::datetimeWithTimezone()->defaultValue(new DateTime('2025-04-19 14:11:35 +02:00')), - 'datetimetz6' => static::COLUMN_BUILDER::datetimeWithTimezone(6)->defaultValue(new DateTimeImmutable('2025-04-19 14:11:35.123456 +02:00')), - 'time' => static::COLUMN_BUILDER::time()->defaultValue('14:11:35'), - 'time3' => static::COLUMN_BUILDER::time(3)->defaultValue(new Stringable('14:11:35.123')), - 'timetz' => static::COLUMN_BUILDER::timeWithTimezone()->defaultValue(new DateTime('14:11:35 +02:00')), - 'timetz6' => static::COLUMN_BUILDER::timeWithTimezone(6)->defaultValue(new DateTimeImmutable('14:11:35.123456 +02:00')), - 'date' => static::COLUMN_BUILDER::date()->defaultValue('2025-04-19'), + 'timestamp' => $columnBuilder::timestamp()->defaultValue(new Expression('CURRENT_TIMESTAMP')), + 'datetime' => $columnBuilder::datetime()->defaultValue('2025-04-19 14:11:35'), + 'datetime3' => $columnBuilder::datetime(3)->defaultValue(new Stringable('2025-04-19 14:11:35.123')), + 'datetimetz' => $columnBuilder::datetimeWithTimezone()->defaultValue(new DateTime('2025-04-19 14:11:35 +02:00')), + 'datetimetz6' => $columnBuilder::datetimeWithTimezone(6)->defaultValue(new DateTimeImmutable('2025-04-19 14:11:35.123456 +02:00')), + 'time' => $columnBuilder::time()->defaultValue('14:11:35'), + 'time3' => $columnBuilder::time(3)->defaultValue(new Stringable('14:11:35.123')), + 'timetz' => $columnBuilder::timeWithTimezone()->defaultValue(new DateTime('14:11:35 +02:00')), + 'timetz6' => $columnBuilder::timeWithTimezone(6)->defaultValue(new DateTimeImmutable('14:11:35.123456 +02:00')), + 'date' => $columnBuilder::date()->defaultValue('2025-04-19'), ])->execute(); }