diff --git a/src/Database/Drivers/Engine.php b/src/Database/Drivers/Engine.php index e1294fbc4..9346162fa 100644 --- a/src/Database/Drivers/Engine.php +++ b/src/Database/Drivers/Engine.php @@ -38,7 +38,7 @@ function classifyDriverException(DriverException $e): ?string; /********************* SQL utilities ****************d*g**/ /** Escapes an identifier for use in an SQL statement. */ - function delimite(string $name): string; + function delimit(string $name): string; /** Formats a date-time value for use in an SQL statement. */ function formatDateTime(\DateTimeInterface $value): string; diff --git a/src/Database/Drivers/Engines/MSSQLEngine.php b/src/Database/Drivers/Engines/MSSQLEngine.php index fde360ceb..00ef273cb 100644 --- a/src/Database/Drivers/Engines/MSSQLEngine.php +++ b/src/Database/Drivers/Engines/MSSQLEngine.php @@ -41,7 +41,7 @@ public function classifyDriverException(Nette\Database\DriverException $e): ?str /********************* SQL ****************d*g**/ - public function delimite(string $name): string + public function delimit(string $name): string { // @see https://msdn.microsoft.com/en-us/library/ms176027.aspx return '[' . str_replace(['[', ']'], ['[[', ']]'], $name) . ']'; diff --git a/src/Database/Drivers/Engines/MySQLEngine.php b/src/Database/Drivers/Engines/MySQLEngine.php index cb003eb5f..667570535 100644 --- a/src/Database/Drivers/Engines/MySQLEngine.php +++ b/src/Database/Drivers/Engines/MySQLEngine.php @@ -52,7 +52,7 @@ public function classifyDriverException(Nette\Database\DriverException $e): ?str /********************* SQL ****************d*g**/ - public function delimite(string $name): string + public function delimit(string $name): string { // @see http://dev.mysql.com/doc/refman/5.0/en/identifiers.html return '`' . str_replace('`', '``', $name) . '`'; @@ -108,7 +108,7 @@ public function getTables(): array public function getColumns(string $table): array { $columns = []; - $rows = $this->connection->query('SHOW FULL COLUMNS FROM ' . $this->delimite($table)); + $rows = $this->connection->query('SHOW FULL COLUMNS FROM ' . $this->delimit($table)); while ($row = $rows->fetch()) { $row = array_change_key_case($row); $typeInfo = Nette\Database\Helpers::parseColumnType($row['type']); @@ -133,7 +133,7 @@ public function getColumns(string $table): array public function getIndexes(string $table): array { $indexes = []; - $rows = $this->connection->query('SHOW INDEX FROM ' . $this->delimite($table)); + $rows = $this->connection->query('SHOW INDEX FROM ' . $this->delimit($table)); while ($row = $rows->fetch()) { $id = $row['Key_name']; $indexes[$id]['name'] = $id; diff --git a/src/Database/Drivers/Engines/ODBCEngine.php b/src/Database/Drivers/Engines/ODBCEngine.php index b0ba465ed..46355ecbf 100644 --- a/src/Database/Drivers/Engines/ODBCEngine.php +++ b/src/Database/Drivers/Engines/ODBCEngine.php @@ -34,7 +34,7 @@ public function classifyDriverException(Nette\Database\DriverException $e): ?str /********************* SQL ****************d*g**/ - public function delimite(string $name): string + public function delimit(string $name): string { return '[' . str_replace(['[', ']'], ['[[', ']]'], $name) . ']'; } diff --git a/src/Database/Drivers/Engines/OracleEngine.php b/src/Database/Drivers/Engines/OracleEngine.php index b955a870a..a83216ec2 100644 --- a/src/Database/Drivers/Engines/OracleEngine.php +++ b/src/Database/Drivers/Engines/OracleEngine.php @@ -50,7 +50,7 @@ public function classifyDriverException(Nette\Database\DriverException $e): ?str /********************* SQL ****************d*g**/ - public function delimite(string $name): string + public function delimit(string $name): string { // @see http://download.oracle.com/docs/cd/B10500_01/server.920/a96540/sql_elements9a.htm return '"' . str_replace('"', '""', $name) . '"'; diff --git a/src/Database/Drivers/Engines/PostgreSQLEngine.php b/src/Database/Drivers/Engines/PostgreSQLEngine.php index 69ec6e8f7..7c6390c6f 100644 --- a/src/Database/Drivers/Engines/PostgreSQLEngine.php +++ b/src/Database/Drivers/Engines/PostgreSQLEngine.php @@ -48,7 +48,7 @@ public function classifyDriverException(Nette\Database\DriverException $e): ?str /********************* SQL ****************d*g**/ - public function delimite(string $name): string + public function delimit(string $name): string { // @see http://www.postgresql.org/docs/8.2/static/sql-syntax-lexical.html#SQL-SYNTAX-IDENTIFIERS return '"' . str_replace('"', '""', $name) . '"'; @@ -152,7 +152,7 @@ public function getColumns(string $table): array AND NOT a.attisdropped ORDER BY a.attnum - X, [$this->delimiteFQN($table)]); + X, [$this->delimitFQN($table)]); while ($row = $rows->fetch()) { $column = $row; @@ -183,7 +183,7 @@ public function getIndexes(string $table): array WHERE c1.relkind IN ('r', 'p') AND c1.oid = ?::regclass - X, [$this->delimiteFQN($table)]); + X, [$this->delimitFQN($table)]); while ($row = $rows->fetch()) { $id = $row['name']; @@ -218,7 +218,7 @@ public function getForeignKeys(string $table): array co.contype = 'f' AND cl.oid = ?::regclass AND nf.nspname = ANY (pg_catalog.current_schemas(FALSE)) - X, [$this->delimiteFQN($table)]); + X, [$this->delimitFQN($table)]); while ($row = $rows->fetch()) { $id = $row['name']; @@ -243,8 +243,8 @@ public function chooseColumnConverter(array $meta, TypeConverter $converter): ?\ /** * Converts: schema.name => "schema"."name" */ - private function delimiteFQN(string $name): string + private function delimitFQN(string $name): string { - return implode('.', array_map([$this, 'delimite'], explode('.', $name))); + return implode('.', array_map([$this, 'delimit'], explode('.', $name))); } } diff --git a/src/Database/Drivers/Engines/SQLServerEngine.php b/src/Database/Drivers/Engines/SQLServerEngine.php index 35a97e9eb..d512ac808 100644 --- a/src/Database/Drivers/Engines/SQLServerEngine.php +++ b/src/Database/Drivers/Engines/SQLServerEngine.php @@ -41,7 +41,7 @@ public function classifyDriverException(Nette\Database\DriverException $e): ?str /********************* SQL ****************d*g**/ - public function delimite(string $name): string + public function delimit(string $name): string { /** @see https://msdn.microsoft.com/en-us/library/ms176027.aspx */ return '[' . str_replace(']', ']]', $name) . ']'; diff --git a/src/Database/Drivers/Engines/SQLiteEngine.php b/src/Database/Drivers/Engines/SQLiteEngine.php index ad38833b5..ce2a22494 100644 --- a/src/Database/Drivers/Engines/SQLiteEngine.php +++ b/src/Database/Drivers/Engines/SQLiteEngine.php @@ -70,7 +70,7 @@ public function classifyDriverException(Nette\Database\DriverException $e): ?str /********************* SQL ****************d*g**/ - public function delimite(string $name): string + public function delimit(string $name): string { return '[' . strtr($name, '[]', ' ') . ']'; } @@ -143,7 +143,7 @@ public function getColumns(string $table): array X, [$table, $table])->fetch(); $columns = []; - $rows = $this->connection->query("PRAGMA table_info({$this->delimite($table)})"); + $rows = $this->connection->query("PRAGMA table_info({$this->delimit($table)})"); while ($row = $rows->fetch()) { $column = $row['name']; $pattern = "/(\"$column\"|`$column`|\\[$column\\]|$column)\\s+[^,]+\\s+PRIMARY\\s+KEY\\s+AUTOINCREMENT/Ui"; @@ -169,7 +169,7 @@ public function getColumns(string $table): array public function getIndexes(string $table): array { $indexes = []; - $rows = $this->connection->query("PRAGMA index_list({$this->delimite($table)})"); + $rows = $this->connection->query("PRAGMA index_list({$this->delimit($table)})"); while ($row = $rows->fetch()) { $id = $row['name']; $indexes[$id]['name'] = $id; @@ -178,7 +178,7 @@ public function getIndexes(string $table): array } foreach ($indexes as $index => $values) { - $res = $this->connection->query("PRAGMA index_info({$this->delimite($index)})"); + $res = $this->connection->query("PRAGMA index_info({$this->delimit($index)})"); while ($row = $res->fetch()) { $indexes[$index]['columns'][] = $row['name']; } @@ -216,7 +216,7 @@ public function getIndexes(string $table): array public function getForeignKeys(string $table): array { $keys = []; - $rows = $this->connection->query("PRAGMA foreign_key_list({$this->delimite($table)})"); + $rows = $this->connection->query("PRAGMA foreign_key_list({$this->delimit($table)})"); while ($row = $rows->fetch()) { $id = $row['id']; $keys[$id]['name'] = $id; diff --git a/src/Database/SqlPreprocessor.php b/src/Database/SqlPreprocessor.php index 3bfa4cd34..f9fb1d0ac 100644 --- a/src/Database/SqlPreprocessor.php +++ b/src/Database/SqlPreprocessor.php @@ -320,6 +320,6 @@ private function formatValue(mixed $value, ?string $mode = null): string private function delimite(string $name): string { - return implode('.', array_map($this->engine->delimite(...), explode('.', $name))); + return implode('.', array_map($this->engine->delimit(...), explode('.', $name))); } } diff --git a/src/Database/Table/Selection.php b/src/Database/Table/Selection.php index bf217e887..c8b00abb6 100644 --- a/src/Database/Table/Selection.php +++ b/src/Database/Table/Selection.php @@ -790,7 +790,7 @@ public function insert(iterable $data): ActiveRow|array|int|bool // First check sequence if (!empty($primarySequenceName) && $primaryAutoincrementKey) { - $primaryKey[$primaryAutoincrementKey] = $this->explorer->getInsertId($this->explorer->getDatabaseEngine()->delimite($primarySequenceName)); + $primaryKey[$primaryAutoincrementKey] = $this->explorer->getInsertId($this->explorer->getDatabaseEngine()->delimit($primarySequenceName)); // Autoincrement primary without sequence } elseif ($primaryAutoincrementKey) { diff --git a/src/Database/Table/SqlBuilder.php b/src/Database/Table/SqlBuilder.php index 262b0c427..29c0182b6 100644 --- a/src/Database/Table/SqlBuilder.php +++ b/src/Database/Table/SqlBuilder.php @@ -59,7 +59,7 @@ public function __construct(string $tableName, Explorer $explorer) $this->conventions = $explorer->getConventions(); $this->structure = $explorer->getStructure(); $tableNameParts = explode('.', $tableName); - $this->delimitedTable = implode('.', array_map($this->engine->delimite(...), $tableNameParts)); + $this->delimitedTable = implode('.', array_map($this->engine->delimit(...), $tableNameParts)); $this->checkUniqueTableName(end($tableNameParts), $tableName); } @@ -78,7 +78,7 @@ public function buildInsertQuery(): string public function buildUpdateQuery(): string { - $query = "UPDATE {$this->delimitedTable} SET ?set" . $this->tryDelimite($this->buildConditions()); + $query = "UPDATE {$this->delimitedTable} SET ?set" . $this->tryDelimit($this->buildConditions()); if ($this->order !== []) { $query .= ' ORDER BY ' . implode(', ', $this->order); @@ -94,7 +94,7 @@ public function buildUpdateQuery(): string public function buildDeleteQuery(): string { - $query = "DELETE FROM {$this->delimitedTable}" . $this->tryDelimite($this->buildConditions()); + $query = "DELETE FROM {$this->delimitedTable}" . $this->tryDelimit($this->buildConditions()); if ($this->limit !== null || $this->offset) { $query = $this->engine->applyLimit($query, $this->limit, $this->offset); } @@ -185,7 +185,7 @@ public function buildSelectQuery(?array $columns = null): string $query = $this->engine->applyLimit($query, $this->limit, $this->offset); - return $this->tryDelimite($query); + return $this->tryDelimit($query); } @@ -789,13 +789,13 @@ protected function buildQueryEnd(): string } - protected function tryDelimite(string $s): string + protected function tryDelimit(string $s): string { return preg_replace_callback( '#(?<=[^\w`"\[?:]|^)[a-z_][a-z0-9_]*(?=[^\w`"(\]]|$)#Di', fn(array $m): string => strtoupper($m[0]) === $m[0] ? $m[0] - : $this->engine->delimite($m[0]), + : $this->engine->delimit($m[0]), $s, ); } diff --git a/tests/Database/Explorer/SqlBuilder.tryDelimit().phpt b/tests/Database/Explorer/SqlBuilder.tryDelimit().phpt new file mode 100644 index 000000000..a2930edf2 --- /dev/null +++ b/tests/Database/Explorer/SqlBuilder.tryDelimit().phpt @@ -0,0 +1,29 @@ +getMethod('tryDelimit'); +$tryDelimit->setAccessible(true); + +Assert::same(reformat('[hello]'), $tryDelimit->invoke($sqlBuilder, 'hello')); +Assert::same(reformat(' [hello] '), $tryDelimit->invoke($sqlBuilder, ' hello ')); +Assert::same(reformat('HELLO'), $tryDelimit->invoke($sqlBuilder, 'HELLO')); +Assert::same(reformat('[HellO]'), $tryDelimit->invoke($sqlBuilder, 'HellO')); +Assert::same(reformat('[hello].[world]'), $tryDelimit->invoke($sqlBuilder, 'hello.world')); +Assert::same(reformat('[hello] [world]'), $tryDelimit->invoke($sqlBuilder, 'hello world')); +Assert::same(reformat('HELLO([world])'), $tryDelimit->invoke($sqlBuilder, 'HELLO(world)')); +Assert::same(reformat('hello([world])'), $tryDelimit->invoke($sqlBuilder, 'hello(world)')); +Assert::same('[hello]', $tryDelimit->invoke($sqlBuilder, '[hello]')); +Assert::same(reformat('::int'), $tryDelimit->invoke($sqlBuilder, '::int')); diff --git a/tests/Database/Explorer/SqlBuilder.tryDelimite().phpt b/tests/Database/Explorer/SqlBuilder.tryDelimite().phpt deleted file mode 100644 index 5aa8aaf31..000000000 --- a/tests/Database/Explorer/SqlBuilder.tryDelimite().phpt +++ /dev/null @@ -1,29 +0,0 @@ -getMethod('tryDelimite'); -$tryDelimite->setAccessible(true); - -Assert::same(reformat('[hello]'), $tryDelimite->invoke($sqlBuilder, 'hello')); -Assert::same(reformat(' [hello] '), $tryDelimite->invoke($sqlBuilder, ' hello ')); -Assert::same(reformat('HELLO'), $tryDelimite->invoke($sqlBuilder, 'HELLO')); -Assert::same(reformat('[HellO]'), $tryDelimite->invoke($sqlBuilder, 'HellO')); -Assert::same(reformat('[hello].[world]'), $tryDelimite->invoke($sqlBuilder, 'hello.world')); -Assert::same(reformat('[hello] [world]'), $tryDelimite->invoke($sqlBuilder, 'hello world')); -Assert::same(reformat('HELLO([world])'), $tryDelimite->invoke($sqlBuilder, 'HELLO(world)')); -Assert::same(reformat('hello([world])'), $tryDelimite->invoke($sqlBuilder, 'hello(world)')); -Assert::same('[hello]', $tryDelimite->invoke($sqlBuilder, '[hello]')); -Assert::same(reformat('::int'), $tryDelimite->invoke($sqlBuilder, '::int')); diff --git a/tests/Database/Row.phpt b/tests/Database/Row.phpt index c254282e8..04631da86 100644 --- a/tests/Database/Row.phpt +++ b/tests/Database/Row.phpt @@ -14,7 +14,7 @@ require __DIR__ . '/../bootstrap.php'; $connection = connectToDB(); test('numeric field', function () use ($connection) { - $row = $connection->fetch("SELECT 123 AS {$connection->getDatabaseEngine()->delimite('123')}, NULL as nullcol"); + $row = $connection->fetch("SELECT 123 AS {$connection->getDatabaseEngine()->delimit('123')}, NULL as nullcol"); Assert::same(123, $row->{123}); Assert::same(123, $row->{'123'}); Assert::true(isset($row->{123}));