Merge pull request #18583 from MoonE/fix-simulate-query
Fix simulate query count
This commit is contained in:
commit
69cc0a2ff3
@ -761,7 +761,7 @@ AJAX.registerOnload('sql.js', function () {
|
||||
for (var i = 0; i < len; i++) {
|
||||
dialogContent += '<strong>' + Messages.strSQLQuery +
|
||||
'</strong>' + response.sql_data[i].sql_query +
|
||||
Messages.strMatchedRows +
|
||||
Messages.strAffectedRows +
|
||||
' <a href="' + response.sql_data[i].matched_rows_url +
|
||||
'">' + response.sql_data[i].matched_rows + '</a><br>';
|
||||
if (i < len - 1) {
|
||||
|
||||
@ -118,7 +118,6 @@ final class JavaScriptMessagesController
|
||||
|
||||
/* For Simulate DML*/
|
||||
'strSimulateDML' => __('Simulate query'),
|
||||
'strMatchedRows' => __('Matched rows:'),
|
||||
'strSQLQuery' => __('SQL query:'),
|
||||
|
||||
/* Charts */
|
||||
|
||||
@ -13,7 +13,11 @@ use PhpMyAdmin\SqlParser\Statements\DeleteStatement;
|
||||
use PhpMyAdmin\SqlParser\Statements\UpdateStatement;
|
||||
use PhpMyAdmin\SqlParser\Utils\Query;
|
||||
use PhpMyAdmin\Url;
|
||||
use PhpMyAdmin\Util;
|
||||
use Webmozart\Assert\Assert;
|
||||
|
||||
use function array_key_exists;
|
||||
use function array_reverse;
|
||||
use function implode;
|
||||
|
||||
final class SimulateDml
|
||||
@ -71,21 +75,13 @@ final class SimulateDml
|
||||
* Executes the matched_row_query and returns the resultant row count.
|
||||
*
|
||||
* @param string $matchedRowQuery SQL query
|
||||
*
|
||||
* @return int|string
|
||||
* @psalm-return int|numeric-string
|
||||
*/
|
||||
private function executeMatchedRowQuery(string $matchedRowQuery)
|
||||
private function executeMatchedRowQuery(string $matchedRowQuery): int
|
||||
{
|
||||
$this->dbi->selectDb($GLOBALS['db']);
|
||||
// Execute the query.
|
||||
$result = $this->dbi->tryQuery($matchedRowQuery);
|
||||
if (! $result) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Count the number of rows in the result set.
|
||||
return $result->numRows();
|
||||
// Execute the query.
|
||||
return (int) $this->dbi->fetchValue($matchedRowQuery);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -96,22 +92,19 @@ final class SimulateDml
|
||||
private function getSimulatedDeleteQuery(Parser $parser, DeleteStatement $statement): string
|
||||
{
|
||||
$tableReferences = Query::getTables($statement);
|
||||
$where = Query::getClause($statement, $parser->list, 'WHERE');
|
||||
if (empty($where)) {
|
||||
$where = '1';
|
||||
}
|
||||
Assert::count($tableReferences, 1, 'No joins allowed in simulation query');
|
||||
Assert::notNull($parser->list, 'Parser list not set');
|
||||
|
||||
$orderAndLimit = '';
|
||||
if (! empty($statement->order)) {
|
||||
$orderAndLimit .= ' ORDER BY ' . Query::getClause($statement, $parser->list, 'ORDER BY');
|
||||
}
|
||||
$condition = Query::getClause($statement, $parser->list, 'WHERE');
|
||||
$where = $condition === '' ? '' : ' WHERE ' . $condition;
|
||||
$order = $statement->order === null || $statement->order === []
|
||||
? ''
|
||||
: ' ORDER BY ' . Query::getClause($statement, $parser->list, 'ORDER BY');
|
||||
$limit = $statement->limit === null ? '' : ' LIMIT ' . Query::getClause($statement, $parser->list, 'LIMIT');
|
||||
|
||||
if (! empty($statement->limit)) {
|
||||
$orderAndLimit .= ' LIMIT ' . Query::getClause($statement, $parser->list, 'LIMIT');
|
||||
}
|
||||
|
||||
return 'SELECT * FROM ' . implode(', ', $tableReferences) .
|
||||
' WHERE ' . $where . $orderAndLimit;
|
||||
return 'SELECT COUNT(*) FROM (' .
|
||||
'SELECT 1 FROM ' . $tableReferences[0] . $where . $order . $limit .
|
||||
') AS `pma_tmp`';
|
||||
}
|
||||
|
||||
/**
|
||||
@ -122,33 +115,38 @@ final class SimulateDml
|
||||
private function getSimulatedUpdateQuery(Parser $parser, UpdateStatement $statement): string
|
||||
{
|
||||
$tableReferences = Query::getTables($statement);
|
||||
$where = Query::getClause($statement, $parser->list, 'WHERE');
|
||||
if (empty($where)) {
|
||||
$where = '1';
|
||||
Assert::count($tableReferences, 1, 'No joins allowed in simulation query');
|
||||
Assert::isNonEmptyList($statement->set, 'SET statements missing');
|
||||
Assert::notNull($parser->list, 'Parser list not set');
|
||||
$newValues = [];
|
||||
$oldValues = [];
|
||||
$newColumns = [];
|
||||
$oldColumns = [];
|
||||
$i = 0;
|
||||
$handledColumns = [];
|
||||
foreach (array_reverse($statement->set) as $set) {
|
||||
if (array_key_exists($set->column, $handledColumns)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$handledColumns[$set->column] = true;
|
||||
$oldValues[] = $set->column . ' AS ' . ($oldColumns[] = Util::backquote('o' . $i));
|
||||
$newValues[] = $set->value . ' AS ' . ($newColumns[] = Util::backquote('n' . $i));
|
||||
++$i;
|
||||
}
|
||||
|
||||
$columns = [];
|
||||
$diff = [];
|
||||
foreach ($statement->set as $set) {
|
||||
$columns[] = $set->column;
|
||||
$diff[] = 'NOT ' . $set->column . ' <=> (' . $set->value . ')';
|
||||
}
|
||||
$condition = Query::getClause($statement, $parser->list, 'WHERE');
|
||||
$where = $condition === '' ? '' : ' WHERE ' . $condition;
|
||||
$order = $statement->order === null || $statement->order === []
|
||||
? ''
|
||||
: ' ORDER BY ' . Query::getClause($statement, $parser->list, 'ORDER BY');
|
||||
$limit = $statement->limit === null ? '' : ' LIMIT ' . Query::getClause($statement, $parser->list, 'LIMIT');
|
||||
|
||||
if (! empty($diff)) {
|
||||
$where = '(' . $where . ') AND (' . implode(' OR ', $diff) . ')';
|
||||
}
|
||||
|
||||
$orderAndLimit = '';
|
||||
if (! empty($statement->order)) {
|
||||
$orderAndLimit .= ' ORDER BY ' . Query::getClause($statement, $parser->list, 'ORDER BY');
|
||||
}
|
||||
|
||||
if (! empty($statement->limit)) {
|
||||
$orderAndLimit .= ' LIMIT ' . Query::getClause($statement, $parser->list, 'LIMIT');
|
||||
}
|
||||
|
||||
return 'SELECT ' . implode(', ', $columns) .
|
||||
' FROM ' . implode(', ', $tableReferences) .
|
||||
' WHERE ' . $where . $orderAndLimit;
|
||||
return 'SELECT COUNT(*)' .
|
||||
' FROM (SELECT ' . implode(',', $newValues) . ') AS `pma_new`' .
|
||||
' JOIN (' .
|
||||
'SELECT ' . implode(', ', $oldValues) . ' FROM ' . $tableReferences[0] . $where . $order . $limit .
|
||||
') AS `pma_old`' .
|
||||
' WHERE NOT (' . implode(', ', $newColumns) . ') <=> (' . implode(', ', $oldColumns) . ')';
|
||||
}
|
||||
}
|
||||
|
||||
@ -224,15 +224,15 @@ class ExportJson extends ExportPlugin
|
||||
/**
|
||||
* Export to JSON
|
||||
*
|
||||
* @phpstan-param array{
|
||||
* string: array{
|
||||
* 'tables': array{
|
||||
* string: array{
|
||||
* 'columns': array{string: string}
|
||||
* }
|
||||
* }
|
||||
* }
|
||||
* }|array|null $aliases
|
||||
* @phpstan-param array<
|
||||
* string,
|
||||
* array{
|
||||
* tables: array<
|
||||
* string,
|
||||
* array{columns: array<string, string>}
|
||||
* >
|
||||
* }
|
||||
* >|null $aliases
|
||||
*/
|
||||
protected function doExportForQuery(
|
||||
DatabaseInterface $dbi,
|
||||
|
||||
@ -4535,16 +4535,6 @@ parameters:
|
||||
count: 1
|
||||
path: libraries/classes/Import/Ajax.php
|
||||
|
||||
-
|
||||
message: "#^Argument of an invalid type array\\<PhpMyAdmin\\\\SqlParser\\\\Components\\\\SetOperation\\>\\|null supplied for foreach, only iterables are supported\\.$#"
|
||||
count: 1
|
||||
path: libraries/classes/Import/SimulateDml.php
|
||||
|
||||
-
|
||||
message: "#^Parameter \\#2 \\$list of static method PhpMyAdmin\\\\SqlParser\\\\Utils\\\\Query\\:\\:getClause\\(\\) expects PhpMyAdmin\\\\SqlParser\\\\TokensList, PhpMyAdmin\\\\SqlParser\\\\TokensList\\|null given\\.$#"
|
||||
count: 6
|
||||
path: libraries/classes/Import/SimulateDml.php
|
||||
|
||||
-
|
||||
message: "#^Method PhpMyAdmin\\\\Index\\:\\:__construct\\(\\) has parameter \\$params with no value type specified in iterable type array\\.$#"
|
||||
count: 1
|
||||
@ -5830,11 +5820,6 @@ parameters:
|
||||
count: 1
|
||||
path: libraries/classes/Plugins/Export/ExportHtmlword.php
|
||||
|
||||
-
|
||||
message: "#^Method PhpMyAdmin\\\\Plugins\\\\Export\\\\ExportJson\\:\\:doExportForQuery\\(\\) has parameter \\$aliases with no value type specified in iterable type array\\.$#"
|
||||
count: 1
|
||||
path: libraries/classes/Plugins/Export/ExportJson.php
|
||||
|
||||
-
|
||||
message: "#^Method PhpMyAdmin\\\\Plugins\\\\Export\\\\ExportJson\\:\\:exportData\\(\\) has parameter \\$aliases with no value type specified in iterable type array\\.$#"
|
||||
count: 1
|
||||
@ -10915,26 +10900,6 @@ parameters:
|
||||
count: 1
|
||||
path: test/classes/Stubs/DbiDummy.php
|
||||
|
||||
-
|
||||
message: "#^PHPDoc tag @var for property PhpMyAdmin\\\\Tests\\\\Stubs\\\\DbiDummy\\:\\:\\$dummyQueries contains unresolvable type\\.$#"
|
||||
count: 1
|
||||
path: test/classes/Stubs/DbiDummy.php
|
||||
|
||||
-
|
||||
message: "#^PHPDoc tag @var for property PhpMyAdmin\\\\Tests\\\\Stubs\\\\DbiDummy\\:\\:\\$filoQueries contains unresolvable type\\.$#"
|
||||
count: 1
|
||||
path: test/classes/Stubs/DbiDummy.php
|
||||
|
||||
-
|
||||
message: "#^Property PhpMyAdmin\\\\Tests\\\\Stubs\\\\DbiDummy\\:\\:\\$dummyQueries type has no value type specified in iterable type array\\<string, mixed\\>\\.$#"
|
||||
count: 1
|
||||
path: test/classes/Stubs/DbiDummy.php
|
||||
|
||||
-
|
||||
message: "#^Property PhpMyAdmin\\\\Tests\\\\Stubs\\\\DbiDummy\\:\\:\\$filoQueries type has no value type specified in iterable type array\\<string, mixed\\>\\.$#"
|
||||
count: 1
|
||||
path: test/classes/Stubs/DbiDummy.php
|
||||
|
||||
-
|
||||
message: "#^Method PhpMyAdmin\\\\Tests\\\\Stubs\\\\ResponseRenderer\\:\\:getJSONResult\\(\\) return type has no value type specified in iterable type array\\.$#"
|
||||
count: 1
|
||||
|
||||
@ -7943,39 +7943,6 @@
|
||||
<code>$_SESSION[$GLOBALS['SESSION_KEY']]</code>
|
||||
</PossiblyInvalidArrayOffset>
|
||||
</file>
|
||||
<file src="libraries/classes/Import/SimulateDml.php">
|
||||
<MixedArgument occurrences="1">
|
||||
<code>$set->value</code>
|
||||
</MixedArgument>
|
||||
<MixedArgumentTypeCoercion occurrences="1">
|
||||
<code>$columns</code>
|
||||
</MixedArgumentTypeCoercion>
|
||||
<MixedAssignment occurrences="2">
|
||||
<code>$columns[]</code>
|
||||
<code>$set</code>
|
||||
</MixedAssignment>
|
||||
<MixedOperand occurrences="1">
|
||||
<code>$set->column</code>
|
||||
</MixedOperand>
|
||||
<MixedPropertyFetch occurrences="2">
|
||||
<code>$set->column</code>
|
||||
<code>$set->value</code>
|
||||
</MixedPropertyFetch>
|
||||
<PossiblyNullArgument occurrences="6">
|
||||
<code>$parser->list</code>
|
||||
<code>$parser->list</code>
|
||||
<code>$parser->list</code>
|
||||
<code>$parser->list</code>
|
||||
<code>$parser->list</code>
|
||||
<code>$parser->list</code>
|
||||
</PossiblyNullArgument>
|
||||
<PossiblyNullIterator occurrences="1">
|
||||
<code>$statement->set</code>
|
||||
</PossiblyNullIterator>
|
||||
<RedundantCondition occurrences="1">
|
||||
<code>empty($diff)</code>
|
||||
</RedundantCondition>
|
||||
</file>
|
||||
<file src="libraries/classes/Index.php">
|
||||
<DocblockTypeContradiction occurrences="1">
|
||||
<code>$this->packed === null</code>
|
||||
@ -9706,12 +9673,9 @@
|
||||
</PossiblyUndefinedVariable>
|
||||
</file>
|
||||
<file src="libraries/classes/Plugins/Export/ExportJson.php">
|
||||
<MixedArgument occurrences="1">
|
||||
<code>$col_as</code>
|
||||
</MixedArgument>
|
||||
<MixedAssignment occurrences="1">
|
||||
<code>$col_as</code>
|
||||
</MixedAssignment>
|
||||
<MixedArgumentTypeCoercion occurrences="1">
|
||||
<code>$aliases</code>
|
||||
</MixedArgumentTypeCoercion>
|
||||
<MixedOperand occurrences="4">
|
||||
<code>$crlf</code>
|
||||
<code>$crlf</code>
|
||||
@ -16413,71 +16377,36 @@
|
||||
</PossiblyUndefinedMethod>
|
||||
</file>
|
||||
<file src="test/classes/Stubs/DbiDummy.php">
|
||||
<InvalidDocblock occurrences="2">
|
||||
<code>private $dummyQueries = [];</code>
|
||||
<code>private $filoQueries = [];</code>
|
||||
</InvalidDocblock>
|
||||
<MissingPropertyType occurrences="2">
|
||||
<code>$dummyQueries</code>
|
||||
<code>$filoQueries</code>
|
||||
</MissingPropertyType>
|
||||
<MixedArgument occurrences="5">
|
||||
<MixedArgument occurrences="3">
|
||||
<code>$query_data['columns'] ?? []</code>
|
||||
<code>$query_data['result']</code>
|
||||
<code>$query_data['result']</code>
|
||||
<code>$this->dummyQueries</code>
|
||||
<code>$this->filoQueries</code>
|
||||
</MixedArgument>
|
||||
<MixedArrayAccess occurrences="12">
|
||||
<code>$query['used']</code>
|
||||
<MixedArrayAccess occurrences="2">
|
||||
<code>$query_data['columns'][$key]</code>
|
||||
<code>$query_data['result'][$query_data['pos']]</code>
|
||||
<code>$this->dummyQueries[$i]</code>
|
||||
<code>$this->dummyQueries[$i]</code>
|
||||
<code>$this->dummyQueries[$i]['result']</code>
|
||||
<code>$this->dummyQueries[$result - self::OFFSET_GLOBAL]</code>
|
||||
<code>$this->filoQueries[$i]</code>
|
||||
<code>$this->filoQueries[$i]</code>
|
||||
<code>$this->filoQueries[$i]</code>
|
||||
<code>$this->filoQueries[$i]['result']</code>
|
||||
<code>$this->filoQueries[$result]</code>
|
||||
</MixedArrayAccess>
|
||||
<MixedArrayAssignment occurrences="4">
|
||||
<code>$this->dummyQueries[$i]</code>
|
||||
<code>$this->filoQueries[$i]</code>
|
||||
<code>$this->filoQueries[$i]</code>
|
||||
<code>$this->filoQueries[]</code>
|
||||
</MixedArrayAssignment>
|
||||
<MixedArrayOffset occurrences="2">
|
||||
<code>$query_data['result'][$query_data['pos']]</code>
|
||||
<code>$ret[$query_data['columns'][$key]]</code>
|
||||
</MixedArrayOffset>
|
||||
<MixedAssignment occurrences="6">
|
||||
<code>$query</code>
|
||||
<MixedAssignment occurrences="4">
|
||||
<code>$query_data['pos']</code>
|
||||
<code>$ret</code>
|
||||
<code>$ret[$query_data['columns'][$key]]</code>
|
||||
<code>$unUsed[]</code>
|
||||
<code>$val</code>
|
||||
</MixedAssignment>
|
||||
<MixedInferredReturnType occurrences="3">
|
||||
<MixedInferredReturnType occurrences="2">
|
||||
<code>?array</code>
|
||||
<code>array</code>
|
||||
<code>int|numeric-string</code>
|
||||
</MixedInferredReturnType>
|
||||
<MixedOperand occurrences="1">
|
||||
<code>$query_data['pos']</code>
|
||||
</MixedOperand>
|
||||
<MixedReturnStatement occurrences="4">
|
||||
<MixedReturnStatement occurrences="2">
|
||||
<code>$cached_affected_rows ?? 0</code>
|
||||
<code>$ret</code>
|
||||
<code>$this->dummyQueries[$result - self::OFFSET_GLOBAL]</code>
|
||||
<code>$this->filoQueries[$result]</code>
|
||||
</MixedReturnStatement>
|
||||
<MixedReturnTypeCoercion occurrences="2">
|
||||
<code>$unUsed</code>
|
||||
<code>array[]</code>
|
||||
</MixedReturnTypeCoercion>
|
||||
</file>
|
||||
<file src="test/classes/Stubs/DummyResult.php">
|
||||
<MixedReturnTypeCoercion occurrences="6">
|
||||
|
||||
@ -19,12 +19,13 @@ class SimulateDmlTest extends AbstractTestCase
|
||||
/**
|
||||
* @dataProvider providerForTestGetMatchedRows
|
||||
*/
|
||||
public function testGetMatchedRows(string $sqlQuery, string $simulatedQuery): void
|
||||
public function testGetMatchedRows(string $sqlQuery, string $simulatedQuery, int $expectedMatches): void
|
||||
{
|
||||
$GLOBALS['db'] = 'PMA';
|
||||
$object = new SimulateDml($this->dbi);
|
||||
$parser = new Parser($sqlQuery);
|
||||
$this->dummyDbi->addSelectDb('PMA');
|
||||
$this->dummyDbi->addResult($simulatedQuery, [[$expectedMatches]], ['COUNT(*)']);
|
||||
|
||||
$simulatedData = $object->getMatchedRows($sqlQuery, $parser, $parser->statements[0]);
|
||||
|
||||
@ -35,26 +36,74 @@ class SimulateDmlTest extends AbstractTestCase
|
||||
]);
|
||||
|
||||
$this->assertAllSelectsConsumed();
|
||||
$this->assertAllQueriesConsumed();
|
||||
$this->assertEquals([
|
||||
'sql_query' => Generator::formatSql($sqlQuery),
|
||||
'matched_rows' => 2,
|
||||
'matched_rows' => $expectedMatches,
|
||||
'matched_rows_url' => $matchedRowsUrl,
|
||||
], $simulatedData);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return string[][]
|
||||
* @return array<string, array{string, string, int}>
|
||||
*/
|
||||
public function providerForTestGetMatchedRows(): array
|
||||
{
|
||||
return [
|
||||
'update statement' => [
|
||||
'UPDATE `table_1` SET `id` = 20 WHERE `id` > 10',
|
||||
'SELECT `id` FROM `table_1` WHERE (`id` > 10) AND (NOT `id` <=> (20))',
|
||||
'SELECT COUNT(*)' .
|
||||
' FROM (SELECT 20 AS `n0`) AS `pma_new`' .
|
||||
' JOIN (SELECT `id` AS `o0` FROM `table_1` WHERE `id` > 10) AS `pma_old`' .
|
||||
' WHERE NOT (`n0`) <=> (`o0`)',
|
||||
2,
|
||||
],
|
||||
'update statement_false_condition' => [
|
||||
'UPDATE `table_1` SET `id` = 20 WHERE 0',
|
||||
'SELECT COUNT(*)' .
|
||||
' FROM (SELECT 20 AS `n0`) AS `pma_new`' .
|
||||
' JOIN (SELECT `id` AS `o0` FROM `table_1` WHERE 0) AS `pma_old`' .
|
||||
' WHERE NOT (`n0`) <=> (`o0`)',
|
||||
0,
|
||||
],
|
||||
'update statement_no_condition' => [
|
||||
'UPDATE `table_1` SET `id` = 20',
|
||||
'SELECT COUNT(*)' .
|
||||
' FROM (SELECT 20 AS `n0`) AS `pma_new`' .
|
||||
' JOIN (SELECT `id` AS `o0` FROM `table_1`) AS `pma_old`' .
|
||||
' WHERE NOT (`n0`) <=> (`o0`)',
|
||||
7,
|
||||
],
|
||||
'update order by limit' => [
|
||||
'UPDATE `table_1` SET `id` = 20 ORDER BY `id` ASC LIMIT 3',
|
||||
'SELECT COUNT(*)' .
|
||||
' FROM (SELECT 20 AS `n0`) AS `pma_new`' .
|
||||
' JOIN (SELECT `id` AS `o0` FROM `table_1` ORDER BY `id` ASC LIMIT 3) AS `pma_old`' .
|
||||
' WHERE NOT (`n0`) <=> (`o0`)',
|
||||
3,
|
||||
],
|
||||
'update duplicate set' => [
|
||||
'UPDATE `table_1` SET `id` = 2, `id` = 1 WHERE `id` = 1',
|
||||
'SELECT COUNT(*)' .
|
||||
' FROM (SELECT 1 AS `n0`) AS `pma_new`' .
|
||||
' JOIN (SELECT `id` AS `o0` FROM `table_1` WHERE `id` = 1) AS `pma_old`' .
|
||||
' WHERE NOT (`n0`) <=> (`o0`)',
|
||||
0,
|
||||
],
|
||||
'delete statement' => [
|
||||
'DELETE FROM `table_1` WHERE `id` > 10',
|
||||
'SELECT * FROM `table_1` WHERE `id` > 10',
|
||||
'SELECT COUNT(*) FROM (SELECT 1 FROM `table_1` WHERE `id` > 10) AS `pma_tmp`',
|
||||
2,
|
||||
],
|
||||
'delete statement_false_condition' => [
|
||||
'DELETE FROM `table_1` WHERE 0',
|
||||
'SELECT COUNT(*) FROM (SELECT 1 FROM `table_1` WHERE 0) AS `pma_tmp`',
|
||||
0,
|
||||
],
|
||||
'delete statement order by limit' => [
|
||||
'DELETE FROM `table_1` ORDER BY `id` ASC LIMIT 3',
|
||||
'SELECT COUNT(*) FROM (SELECT 1 FROM `table_1` ORDER BY `id` ASC LIMIT 3) AS `pma_tmp`',
|
||||
2,
|
||||
],
|
||||
];
|
||||
}
|
||||
|
||||
@ -50,9 +50,9 @@ class DbiDummy implements DbiExtension
|
||||
* @var array
|
||||
* @phpstan-var array{
|
||||
* 'query': string,
|
||||
* 'result': ((int[]|string[]|array{string: string})[])|bool|bool[]|empty-array,
|
||||
* 'result': list<array<string|float|int|null>>|array{true}|bool,
|
||||
* 'columns'?: string[],
|
||||
* 'metadata'?: object[]|empty-array,
|
||||
* 'metadata'?: object[],
|
||||
* 'used'?: bool,
|
||||
* 'pos'?: int
|
||||
* }[]
|
||||
@ -72,9 +72,9 @@ class DbiDummy implements DbiExtension
|
||||
* @var array
|
||||
* @phpstan-var array{
|
||||
* 'query': string,
|
||||
* 'result': ((int[]|string[]|array{string: string})[])|bool|bool[]|empty-array,
|
||||
* 'result': list<array<string|float|int|null>>|bool,
|
||||
* 'columns'?: string[],
|
||||
* 'metadata'?: object[]|empty-array,
|
||||
* 'metadata'?: object[],
|
||||
* 'pos'?: int
|
||||
* }[]
|
||||
*/
|
||||
@ -493,7 +493,7 @@ class DbiDummy implements DbiExtension
|
||||
* @param array|bool $result Expected result
|
||||
* @param string[] $columns The result columns
|
||||
* @param object[] $metadata The result metadata
|
||||
* @phpstan-param array<int, array<int, array{string: string}|bool|int|string|null>|bool>|bool $result
|
||||
* @phpstan-param list<array<string|float|int|null>>|array{true}|bool $result
|
||||
*/
|
||||
public function addResult(string $query, $result, array $columns = [], array $metadata = []): void
|
||||
{
|
||||
@ -2228,16 +2228,6 @@ class DbiDummy implements DbiExtension
|
||||
'columns' => ['Name', 'Engine'],
|
||||
'result' => [['PMA_table', 'InnoDB']],
|
||||
],
|
||||
[
|
||||
'query' => 'SELECT `id` FROM `table_1` WHERE (`id` > 10) AND (NOT `id` <=> (20))',
|
||||
'columns' => ['id'],
|
||||
'result' => [['11'], ['12']],
|
||||
],
|
||||
[
|
||||
'query' => 'SELECT * FROM `table_1` WHERE `id` > 10',
|
||||
'columns' => ['column'],
|
||||
'result' => [['row1'], ['row2']],
|
||||
],
|
||||
[
|
||||
'query' => 'SELECT * FROM `PMA`.`table_1` LIMIT 1',
|
||||
'columns' => ['column'],
|
||||
|
||||
Loading…
Reference in New Issue
Block a user