Replace $analyzedSqlResults array with StatementInfo object

Signed-off-by: Maurício Meneghini Fauth <mauricio@fauth.dev>
This commit is contained in:
Maurício Meneghini Fauth 2022-05-23 19:49:54 -03:00
parent 9aa859bdd3
commit 10b937511d
No known key found for this signature in database
GPG Key ID: 6A16FD38AFC89CC8
19 changed files with 938 additions and 890 deletions

View File

@ -126,7 +126,7 @@ class QueryByExampleController extends AbstractController
);
$this->response->addHTML($sql->executeQueryAndSendQueryResponse(
null, // analyzed_sql_results
null,
false, // is_gotofile
$_POST['db'], // db
null, // table

View File

@ -715,14 +715,13 @@ final class ImportController extends AbstractController
// can choke on it so avoid parsing)
$sqlLength = mb_strlen($GLOBALS['sql_query']);
if ($sqlLength <= $GLOBALS['cfg']['MaxCharactersInDisplayedSQL']) {
[
$analyzed_sql_results,
$GLOBALS['db'],
$table_from_sql,
] = ParseAnalyze::sqlQuery($GLOBALS['sql_query'], $GLOBALS['db']);
[$statementInfo, $GLOBALS['db'], $table_from_sql] = ParseAnalyze::sqlQuery(
$GLOBALS['sql_query'],
$GLOBALS['db']
);
$GLOBALS['reload'] = $analyzed_sql_results['reload'];
$GLOBALS['offset'] = $analyzed_sql_results['offset'];
$GLOBALS['reload'] = $statementInfo->reload;
$GLOBALS['offset'] = $statementInfo->offset;
if ($GLOBALS['table'] != $table_from_sql && ! empty($table_from_sql)) {
$GLOBALS['table'] = $table_from_sql;
@ -747,19 +746,18 @@ final class ImportController extends AbstractController
foreach ($queriesToBeExecuted as $GLOBALS['sql_query']) {
// parse sql query
[
$analyzed_sql_results,
$GLOBALS['db'],
$table_from_sql,
] = ParseAnalyze::sqlQuery($GLOBALS['sql_query'], $GLOBALS['db']);
[$statementInfo, $GLOBALS['db'], $table_from_sql] = ParseAnalyze::sqlQuery(
$GLOBALS['sql_query'],
$GLOBALS['db']
);
$GLOBALS['offset'] = $analyzed_sql_results['offset'];
$GLOBALS['reload'] = $analyzed_sql_results['reload'];
$GLOBALS['offset'] = $statementInfo->offset;
$GLOBALS['reload'] = $statementInfo->reload;
// Check if User is allowed to issue a 'DROP DATABASE' Statement
if (
$this->sql->hasNoRightsToDropDatabase(
$analyzed_sql_results,
$statementInfo,
$GLOBALS['cfg']['AllowUserDropDatabase'],
$this->dbi->isSuperUser()
)
@ -779,7 +777,7 @@ final class ImportController extends AbstractController
}
$html_output .= $this->sql->executeQueryAndGetQueryResponse(
$analyzed_sql_results, // analyzed_sql_results
$statementInfo,
false, // is_gotofile
$GLOBALS['db'], // db
$GLOBALS['table'], // table

View File

@ -145,11 +145,10 @@ class SqlController extends AbstractController
/**
* Parse and analyze the query
*/
[
$analyzed_sql_results,
$GLOBALS['db'],
$GLOBALS['table_from_sql'],
] = ParseAnalyze::sqlQuery($GLOBALS['sql_query'], $GLOBALS['db']);
[$statementInfo, $GLOBALS['db'], $GLOBALS['table_from_sql']] = ParseAnalyze::sqlQuery(
$GLOBALS['sql_query'],
$GLOBALS['db']
);
if ($GLOBALS['table'] != $GLOBALS['table_from_sql'] && ! empty($GLOBALS['table_from_sql'])) {
$GLOBALS['table'] = $GLOBALS['table_from_sql'];
@ -164,7 +163,7 @@ class SqlController extends AbstractController
*/
if (
$this->sql->hasNoRightsToDropDatabase(
$analyzed_sql_results,
$statementInfo,
$GLOBALS['cfg']['AllowUserDropDatabase'],
$this->dbi->isSuperUser()
)
@ -206,7 +205,7 @@ class SqlController extends AbstractController
}
$this->response->addHTML($this->sql->executeQueryAndSendQueryResponse(
$analyzed_sql_results,
$statementInfo,
$GLOBALS['is_gotofile'],
$GLOBALS['db'],
$GLOBALS['table'],

View File

@ -259,7 +259,7 @@ class SearchController extends AbstractController
);
$this->response->addHTML($sql->executeQueryAndSendQueryResponse(
null, // analyzed_sql_results
null,
false, // is_gotofile
$GLOBALS['db'], // db
$GLOBALS['table'], // table

View File

@ -60,13 +60,13 @@ final class BrowseController extends AbstractController
);
// Parse and analyze the query
[$analyzed_sql_results, $GLOBALS['db']] = ParseAnalyze::sqlQuery($sql_query, $GLOBALS['db']);
[$statementInfo, $GLOBALS['db']] = ParseAnalyze::sqlQuery($sql_query, $GLOBALS['db']);
$this->response->addHTML(
$this->sql->executeQueryAndGetQueryResponse(
$analyzed_sql_results ?? '',
$statementInfo,
false, // is_gotofile
(string) $GLOBALS['db'], // db
$GLOBALS['db'], // db
$GLOBALS['table'], // table
null, // find_real_end
null, // sql_query_for_bookmark

View File

@ -122,7 +122,7 @@ class MultiTableQuery
);
return $sql->executeQueryAndSendQueryResponse(
null, // analyzed_sql_results
null,
false, // is_gotofile
$db, // db
null, // table

View File

@ -24,6 +24,7 @@ use PhpMyAdmin\Sql;
use PhpMyAdmin\SqlParser\Parser;
use PhpMyAdmin\SqlParser\Statements\SelectStatement;
use PhpMyAdmin\SqlParser\Utils\Query;
use PhpMyAdmin\StatementInfo;
use PhpMyAdmin\Table;
use PhpMyAdmin\Template;
use PhpMyAdmin\Theme;
@ -643,19 +644,17 @@ class Results
* "SELECT * FROM <a table> ..."
*
* @see getTableHeaders(), getColumnParams()
*
* @param array $analyzedSqlResults analyzed sql results
*/
private function isSelect(array $analyzedSqlResults): bool
private function isSelect(StatementInfo $statementInfo): bool
{
return ! ($this->properties['is_count']
|| $this->properties['is_export']
|| $this->properties['is_func']
|| $this->properties['is_analyse'])
&& ! empty($analyzedSqlResults['select_from'])
&& ! empty($analyzedSqlResults['statement']->from)
&& (count($analyzedSqlResults['statement']->from) === 1)
&& ! empty($analyzedSqlResults['statement']->from[0]->table);
&& ! empty($statementInfo->selectFrom)
&& ! empty($statementInfo->statement->from)
&& (count($statementInfo->statement->from) === 1)
&& ! empty($statementInfo->statement->from[0]->table);
}
/**
@ -778,7 +777,6 @@ class Results
*
* @see getTableHeaders()
*
* @param array $analyzedSqlResults analyzed sql results
* @param array $sortExpression sort expression
* @param array<int, string> $sortExpressionNoDirection sort expression
* without direction
@ -791,7 +789,7 @@ class Results
*/
private function getTableHeadersForColumns(
bool $hasSortLink,
array $analyzedSqlResults,
StatementInfo $statementInfo,
array $sortExpression,
array $sortExpressionNoDirection,
array $sortDirection,
@ -812,9 +810,9 @@ class Results
// Prepare Display column comments if enabled
// ($GLOBALS['cfg']['ShowBrowseComments']).
$commentsMap = $this->getTableCommentsArray($analyzedSqlResults);
$commentsMap = $this->getTableCommentsArray($statementInfo);
[$colOrder, $colVisib] = $this->getColumnParams($analyzedSqlResults);
[$colOrder, $colVisib] = $this->getColumnParams($statementInfo);
// optimize: avoid calling a method on each iteration
$numberOfColumns = $this->properties['fields_cnt'];
@ -893,7 +891,6 @@ class Results
*
* @see getTable()
*
* @param array $analyzedSqlResults analyzed sql results
* @param string $unsortedSqlQuery the unsorted sql query
* @param array $sortExpression sort expression
* @param array<int, string> $sortExpressionNoDirection sort expression without direction
@ -911,7 +908,7 @@ class Results
*/
private function getTableHeaders(
DisplayParts $displayParts,
array $analyzedSqlResults,
StatementInfo $statementInfo,
$unsortedSqlQuery,
array $sortExpression = [],
array $sortExpressionNoDirection = [],
@ -924,7 +921,7 @@ class Results
$displayParams = $this->properties['display_params'];
// Output data needed for column reordering and show/hide column
$columnOrder = $this->getDataForResettingColumnOrder($analyzedSqlResults);
$columnOrder = $this->getDataForResettingColumnOrder($statementInfo);
$displayParams['emptypre'] = 0;
$displayParams['emptyafter'] = 0;
@ -954,12 +951,12 @@ class Results
// See if we have to highlight any header fields of a WHERE query.
// Uses SQL-Parser results.
$this->setHighlightedColumnGlobalField($analyzedSqlResults);
$this->setHighlightedColumnGlobalField($statementInfo);
// Get the headers for all of the columns
$tableHeadersForColumns = $this->getTableHeadersForColumns(
$displayParts->hasSortLink,
$analyzedSqlResults,
$statementInfo,
$sortExpression,
$sortExpressionNoDirection,
$sortDirection,
@ -1138,18 +1135,16 @@ class Results
*
* @see getTableHeaders()
*
* @param array $analyzedSqlResults analyzed sql results
*
* @return array table comments
*/
private function getTableCommentsArray(array $analyzedSqlResults)
private function getTableCommentsArray(StatementInfo $statementInfo)
{
if (! $GLOBALS['cfg']['ShowBrowseComments'] || empty($analyzedSqlResults['statement']->from)) {
if (! $GLOBALS['cfg']['ShowBrowseComments'] || empty($statementInfo->statement->from)) {
return [];
}
$ret = [];
foreach ($analyzedSqlResults['statement']->from as $field) {
foreach ($statementInfo->statement->from as $field) {
if (empty($field->table)) {
continue;
}
@ -1167,15 +1162,13 @@ class Results
* Set global array for store highlighted header fields
*
* @see getTableHeaders()
*
* @param array $analyzedSqlResults analyzed sql results
*/
private function setHighlightedColumnGlobalField(array $analyzedSqlResults): void
private function setHighlightedColumnGlobalField(StatementInfo $statementInfo): void
{
$highlightColumns = [];
if (! empty($analyzedSqlResults['statement']->where)) {
foreach ($analyzedSqlResults['statement']->where as $expr) {
if (! empty($statementInfo->statement->where)) {
foreach ($statementInfo->statement->where as $expr) {
foreach ($expr->identifiers as $identifier) {
$highlightColumns[$identifier] = 'true';
}
@ -1190,17 +1183,15 @@ class Results
*
* @see getTableHeaders()
*
* @param array $analyzedSqlResults analyzed sql results
*
* @return array
*/
private function getDataForResettingColumnOrder(array $analyzedSqlResults): array
private function getDataForResettingColumnOrder(StatementInfo $statementInfo): array
{
if (! $this->isSelect($analyzedSqlResults)) {
if (! $this->isSelect($statementInfo)) {
return [];
}
[$columnOrder, $columnVisibility] = $this->getColumnParams($analyzedSqlResults);
[$columnOrder, $columnVisibility] = $this->getColumnParams($statementInfo);
$tableCreateTime = '';
$table = new Table($this->properties['table'], $this->properties['db']);
@ -1936,11 +1927,10 @@ class Results
*
* @see getTable()
*
* @param ResultInterface $dtResult the link id associated to the query
* which results have to be displayed
* @param array<string, string[]> $map the list of relations
* @param array $analyzedSqlResults analyzed sql results
* @param bool $isLimitedDisplay with limited operations or not
* @param ResultInterface $dtResult the link id associated to the query
* which results have to be displayed
* @param array<string, string[]> $map the list of relations
* @param bool $isLimitedDisplay with limited operations or not
*
* @return string html content
*
@ -1950,7 +1940,7 @@ class Results
ResultInterface $dtResult,
DisplayParts $displayParts,
array $map,
array $analyzedSqlResults,
StatementInfo $statementInfo,
$isLimitedDisplay = false
) {
// Mostly because of browser transformations, to make the row-data accessible in a plugin.
@ -1961,7 +1951,7 @@ class Results
// query without conditions to shorten URLs when needed, 200 is just
// guess, it should depend on remaining URL length
$urlSqlQuery = $this->getUrlSqlQuery($analyzedSqlResults);
$urlSqlQuery = $this->getUrlSqlQuery($statementInfo);
$displayParams = $this->properties['display_params'];
@ -1982,7 +1972,7 @@ class Results
}
// prepare to get the column order, if available
[$colOrder, $colVisib] = $this->getColumnParams($analyzedSqlResults);
[$colOrder, $colVisib] = $this->getColumnParams($statementInfo);
// Correction University of Virginia 19991216 in the while below
// Previous code assumed that all tables have keys, specifically that
@ -2044,10 +2034,10 @@ class Results
$expressions = [];
if (
isset($analyzedSqlResults['statement'])
&& $analyzedSqlResults['statement'] instanceof SelectStatement
isset($statementInfo->statement)
&& $statementInfo->statement instanceof SelectStatement
) {
$expressions = $analyzedSqlResults['statement']->expr;
$expressions = $statementInfo->statement->expr;
}
// Results from a "SELECT" statement -> builds the
@ -2154,7 +2144,7 @@ class Results
$gridEditConfig,
$colVisib,
$urlSqlQuery,
$analyzedSqlResults
$statementInfo
);
// 3. Displays the modify/delete links on the right if required
@ -2265,17 +2255,16 @@ class Results
*
* @see getTableBody()
*
* @param array $row current row data
* @param int $rowNumber the index of current row
* @param array|false $colOrder the column order false when
* a property not found false
* when a property not found
* @param array<string, string[]> $map the list of relations
* @param bool|array|string $colVisib column is visible(false);
* column isn't visible(string
* array)
* @param string $urlSqlQuery the analyzed sql query
* @param array $analyzedSqlResults analyzed sql results
* @param array $row current row data
* @param int $rowNumber the index of current row
* @param array|false $colOrder the column order false when
* a property not found false
* when a property not found
* @param array<string, string[]> $map the list of relations
* @param bool|array|string $colVisib column is visible(false);
* column isn't visible(string
* array)
* @param string $urlSqlQuery the analyzed sql query
* @psalm-param 'double-click'|'click'|'disabled' $gridEditConfig
*
* @return string html content
@ -2288,7 +2277,7 @@ class Results
string $gridEditConfig,
$colVisib,
$urlSqlQuery,
array $analyzedSqlResults
StatementInfo $statementInfo
) {
$rowValuesHtml = '';
@ -2430,10 +2419,10 @@ class Results
$expressions = [];
if (
isset($analyzedSqlResults['statement'])
&& $analyzedSqlResults['statement'] instanceof SelectStatement
isset($statementInfo->statement)
&& $statementInfo->statement instanceof SelectStatement
) {
$expressions = $analyzedSqlResults['statement']->expr;
$expressions = $statementInfo->statement->expr;
}
/**
@ -2490,7 +2479,7 @@ class Results
$conditionField,
$meta,
$map,
$analyzedSqlResults,
$statementInfo,
$transformationPlugin,
$transformOptions
);
@ -2510,7 +2499,7 @@ class Results
$conditionField,
$transformationPlugin,
$transformOptions,
$analyzedSqlResults
$statementInfo
);
} else {
// n o t n u m e r i c
@ -2524,7 +2513,7 @@ class Results
$conditionField,
$transformationPlugin,
$transformOptions,
$analyzedSqlResults
$statementInfo
);
}
@ -2620,23 +2609,26 @@ class Results
*
* @see getTableBody()
*
* @param array $analyzedSqlResults analyzed sql results
*
* @return string analyzed sql query
*/
private function getUrlSqlQuery(array $analyzedSqlResults)
private function getUrlSqlQuery(StatementInfo $statementInfo)
{
if (($analyzedSqlResults['querytype'] !== 'SELECT') || (mb_strlen($this->properties['sql_query']) < 200)) {
if (
$statementInfo->queryType !== 'SELECT'
|| mb_strlen($this->properties['sql_query']) < 200
|| $statementInfo->statement === null
|| $statementInfo->parser === null
) {
return $this->properties['sql_query'];
}
$query = 'SELECT ' . Query::getClause(
$analyzedSqlResults['statement'],
$analyzedSqlResults['parser']->list,
$statementInfo->statement,
$statementInfo->parser->list,
'SELECT'
);
$fromClause = Query::getClause($analyzedSqlResults['statement'], $analyzedSqlResults['parser']->list, 'FROM');
$fromClause = Query::getClause($statementInfo->statement, $statementInfo->parser->list, 'FROM');
if ($fromClause !== '') {
$query .= ' FROM ' . $fromClause;
@ -2650,13 +2642,11 @@ class Results
*
* @see getTableBody()
*
* @param array $analyzedSqlResults analyzed sql results
*
* @return mixed[] 2 element array - $col_order, $col_visib
*/
private function getColumnParams(array $analyzedSqlResults): array
private function getColumnParams(StatementInfo $statementInfo): array
{
if ($this->isSelect($analyzedSqlResults)) {
if ($this->isSelect($statementInfo)) {
$pmatable = new Table($this->properties['table'], $this->properties['db']);
$colOrder = $pmatable->getUiProp(Table::PROP_COLUMN_ORDER);
$fieldsCount = $this->properties['fields_cnt'];
@ -2930,13 +2920,12 @@ class Results
*
* @see getTableBody()
*
* @param string|null $column the column's value
* @param string $class the html class for column
* @param bool $conditionField the column should highlighted or not
* @param FieldMetadata $meta the meta-information about this field
* @param array<string, string[]> $map the list of relations
* @param array $analyzedSqlResults the analyzed query
* @param array $transformOptions the transformation parameters
* @param string|null $column the column's value
* @param string $class the html class for column
* @param bool $conditionField the column should highlighted or not
* @param FieldMetadata $meta the meta-information about this field
* @param array<string, string[]> $map the list of relations
* @param array $transformOptions the transformation parameters
*
* @return string the prepared cell, html content
*/
@ -2946,7 +2935,7 @@ class Results
bool $conditionField,
FieldMetadata $meta,
array $map,
array $analyzedSqlResults,
StatementInfo $statementInfo,
?TransformationsPlugin $transformationPlugin,
array $transformOptions
) {
@ -2963,7 +2952,7 @@ class Results
return $this->getRowData(
$class,
$conditionField,
$analyzedSqlResults,
$statementInfo,
$meta,
$map,
$column,
@ -2980,14 +2969,13 @@ class Results
*
* @see getTableBody()
*
* @param string|null $column the relevant column in data row
* @param string $class the html class for column
* @param FieldMetadata $meta the meta-information about this field
* @param array<string, string[]> $map the list of relations
* @param array $urlParams the parameters for generate url
* @param bool $conditionField the column should highlighted or not
* @param array $transformOptions the transformation parameters
* @param array $analyzedSqlResults the analyzed query
* @param string|null $column the relevant column in data row
* @param string $class the html class for column
* @param FieldMetadata $meta the meta-information about this field
* @param array<string, string[]> $map the list of relations
* @param array $urlParams the parameters for generate url
* @param bool $conditionField the column should highlighted or not
* @param array $transformOptions the transformation parameters
*
* @return string the prepared data cell, html content
*/
@ -3000,7 +2988,7 @@ class Results
bool $conditionField,
?TransformationsPlugin $transformationPlugin,
$transformOptions,
array $analyzedSqlResults
StatementInfo $statementInfo
) {
if ($column === null) {
return $this->buildNullDisplay($class, $conditionField, $meta);
@ -3039,7 +3027,7 @@ class Results
return $this->getRowData(
$class,
$conditionField,
$analyzedSqlResults,
$statementInfo,
$meta,
$map,
$wktval,
@ -3067,7 +3055,7 @@ class Results
return $this->getRowData(
$class,
$conditionField,
$analyzedSqlResults,
$statementInfo,
$meta,
$map,
$wkbval,
@ -3097,14 +3085,13 @@ class Results
*
* @see getTableBody()
*
* @param string|null $column the relevant column in data row
* @param string $class the html class for column
* @param FieldMetadata $meta the meta-information about the field
* @param array<string, string[]> $map the list of relations
* @param array $urlParams the parameters for generate url
* @param bool $conditionField the column should highlighted or not
* @param array $transformOptions the transformation parameters
* @param array $analyzedSqlResults the analyzed query
* @param string|null $column the relevant column in data row
* @param string $class the html class for column
* @param FieldMetadata $meta the meta-information about the field
* @param array<string, string[]> $map the list of relations
* @param array $urlParams the parameters for generate url
* @param bool $conditionField the column should highlighted or not
* @param array $transformOptions the transformation parameters
*
* @return string the prepared data cell, html content
*/
@ -3117,7 +3104,7 @@ class Results
bool $conditionField,
?TransformationsPlugin $transformationPlugin,
$transformOptions,
array $analyzedSqlResults
StatementInfo $statementInfo
) {
$originalLength = 0;
@ -3224,7 +3211,7 @@ class Results
return $this->getRowData(
$class,
$conditionField,
$analyzedSqlResults,
$statementInfo,
$meta,
$map,
$column,
@ -3376,23 +3363,22 @@ class Results
/**
* Prepare a table of results returned by a SQL query.
*
* @param ResultInterface $dtResult the link id associated to the query
* which results have to be displayed
* @param array $analyzedSqlResults analyzed sql results
* @param bool $isLimitedDisplay With limited operations or not
* @param ResultInterface $dtResult the link id associated to the query
* which results have to be displayed
* @param bool $isLimitedDisplay With limited operations or not
*
* @return string Generated HTML content for resulted table
*/
public function getTable(
ResultInterface $dtResult,
DisplayParts $displayParts,
array $analyzedSqlResults,
StatementInfo $statementInfo,
$isLimitedDisplay = false
) {
// The statement this table is built for.
if (isset($analyzedSqlResults['statement'])) {
if (isset($statementInfo->statement)) {
/** @var SelectStatement $statement */
$statement = $analyzedSqlResults['statement'];
$statement = $statementInfo->statement;
} else {
$statement = null;
}
@ -3410,7 +3396,7 @@ class Results
$isInnodb = (isset($showTable['Type'])
&& $showTable['Type'] === self::TABLE_TYPE_INNO_DB);
if ($isInnodb && Sql::isJustBrowsing($analyzedSqlResults, true)) {
if ($isInnodb && Sql::isJustBrowsing($statementInfo, true)) {
$preCount = '~';
$afterCount = Generator::showHint(
Sanitize::sanitizeMessage(
@ -3471,7 +3457,7 @@ class Results
if ($displayParts->hasNavigationBar) {
$message = $this->setMessageInformation(
$sortedColumnMessage,
$analyzedSqlResults,
$statementInfo,
$total,
$posNext,
$preCount,
@ -3488,7 +3474,7 @@ class Results
}
// 2.3 Prepare the navigation bars
if ($this->properties['table'] === '' && $analyzedSqlResults['querytype'] === 'SELECT') {
if ($this->properties['table'] === '' && $statementInfo->queryType === 'SELECT') {
// table does not always contain a real table name,
// for example in MySQL 5.0.x, the query SHOW STATUS
// returns STATUS as a table name
@ -3498,16 +3484,20 @@ class Results
$unsortedSqlQuery = '';
$sortByKeyData = [];
// can the result be sorted?
if ($displayParts->hasSortLink && isset($analyzedSqlResults['statement'])) {
if (
$displayParts->hasSortLink
&& $statementInfo->statement !== null
&& $statementInfo->parser !== null
) {
$unsortedSqlQuery = Query::replaceClause(
$analyzedSqlResults['statement'],
$analyzedSqlResults['parser']->list,
$statementInfo->statement,
$statementInfo->parser->list,
'ORDER BY',
''
);
// Data is sorted by indexes only if there is only one table.
if ($this->isSelect($analyzedSqlResults)) {
if ($this->isSelect($statementInfo)) {
$sortByKeyData = $this->getSortByKeyDropDown(
$sortExpression,
$unsortedSqlQuery
@ -3547,7 +3537,7 @@ class Results
// 3. ----- Prepare the results table -----
$headers = $this->getTableHeaders(
$displayParts,
$analyzedSqlResults,
$statementInfo,
$unsortedSqlQuery,
$sortExpression,
$sortExpressionNoDirection,
@ -3555,17 +3545,17 @@ class Results
$isLimitedDisplay
);
$body = $this->getTableBody($dtResult, $displayParts, $map, $analyzedSqlResults, $isLimitedDisplay);
$body = $this->getTableBody($dtResult, $displayParts, $map, $statementInfo, $isLimitedDisplay);
$this->properties['display_params'] = null;
// 4. ----- Prepares the link for multi-fields edit and delete
$bulkLinks = $this->getBulkLinks($dtResult, $analyzedSqlResults, $displayParts->deleteLink);
$bulkLinks = $this->getBulkLinks($dtResult, $statementInfo, $displayParts->deleteLink);
// 5. ----- Prepare "Query results operations"
$operations = [];
if (($printView === null || $printView != '1') && ! $isLimitedDisplay) {
$operations = $this->getResultsOperations($displayParts->hasPrintLink, $analyzedSqlResults);
$operations = $this->getResultsOperations($displayParts->hasPrintLink, $statementInfo);
}
$relationParameters = $this->relation->getRelationParameters();
@ -3727,7 +3717,6 @@ class Results
* @see getTable()
*
* @param string $sortedColumnMessage the message for sorted column
* @param array $analyzedSqlResults the analyzed query
* @param int $total the total number of rows returned by
* the SQL query without any
* programmatically appended LIMIT clause
@ -3739,7 +3728,7 @@ class Results
*/
private function setMessageInformation(
string $sortedColumnMessage,
array $analyzedSqlResults,
StatementInfo $statementInfo,
$total,
$posNext,
string $preCount,
@ -3747,9 +3736,9 @@ class Results
) {
$unlimNumRows = $this->properties['unlim_num_rows']; // To use in isset()
if (! empty($analyzedSqlResults['statement']->limit)) {
$firstShownRec = $analyzedSqlResults['statement']->limit->offset;
$rowCount = $analyzedSqlResults['statement']->limit->rowCount;
if (! empty($statementInfo->statement->limit)) {
$firstShownRec = $statementInfo->statement->limit->offset;
$rowCount = $statementInfo->statement->limit->rowCount;
if ($rowCount < $total) {
$lastShownRec = $firstShownRec + $rowCount - 1;
@ -3883,16 +3872,15 @@ class Results
*
* @see getTable()
*
* @param ResultInterface $dtResult the link id associated to the query which
* results have to be displayed
* @param array $analyzedSqlResults analyzed sql results
* @param ResultInterface $dtResult the link id associated to the query which
* results have to be displayed
* @psalm-param DisplayParts::NO_DELETE|DisplayParts::DELETE_ROW|DisplayParts::KILL_PROCESS $deleteLink
*
* @psalm-return array{has_export_button:bool, clause_is_unique:mixed}|array<empty, empty>
*/
private function getBulkLinks(
ResultInterface $dtResult,
array $analyzedSqlResults,
StatementInfo $statementInfo,
int $deleteLink
): array {
if ($deleteLink !== DisplayParts::DELETE_ROW) {
@ -3905,8 +3893,8 @@ class Results
$expressions = [];
if (isset($analyzedSqlResults['statement']) && $analyzedSqlResults['statement'] instanceof SelectStatement) {
$expressions = $analyzedSqlResults['statement']->expr;
if (isset($statementInfo->statement) && $statementInfo->statement instanceof SelectStatement) {
$expressions = $statementInfo->statement->expr;
}
/**
@ -3926,7 +3914,7 @@ class Results
$dtResult->seek(0);
return [
'has_export_button' => $analyzedSqlResults['querytype'] === 'SELECT',
'has_export_button' => $statementInfo->queryType === 'SELECT',
'clause_is_unique' => $clauseIsUnique,
];
}
@ -3936,8 +3924,6 @@ class Results
*
* @see getTable()
*
* @param array $analyzedSqlResults analyzed sql results
*
* @psalm-return array{
* has_export_link: bool,
* has_geometry: bool,
@ -3956,7 +3942,7 @@ class Results
*/
private function getResultsOperations(
bool $hasPrintLink,
array $analyzedSqlResults
StatementInfo $statementInfo
): array {
$urlParams = [
'db' => $this->properties['db'],
@ -3974,16 +3960,16 @@ class Results
// (most probably PROCEDURE ANALYSE()) it makes no sense to
// display the Export link).
if (
($analyzedSqlResults['querytype'] === self::QUERY_TYPE_SELECT)
&& empty($analyzedSqlResults['procedure'])
($statementInfo->queryType === self::QUERY_TYPE_SELECT)
&& empty($statementInfo->isProcedure)
) {
if (count($analyzedSqlResults['select_tables']) === 1) {
if (count($statementInfo->selectTables) === 1) {
$urlParams['single_table'] = 'true';
}
// In case this query doesn't involve any tables,
// implies only raw query is to be exported
if (! $analyzedSqlResults['select_tables']) {
if (! $statementInfo->selectTables) {
$urlParams['raw_query'] = 'true';
}
@ -4011,10 +3997,10 @@ class Results
}
return [
'has_procedure' => ! empty($analyzedSqlResults['procedure']),
'has_procedure' => ! empty($statementInfo->isProcedure),
'has_geometry' => $geometryFound,
'has_print_link' => $hasPrintLink,
'has_export_link' => $analyzedSqlResults['querytype'] === self::QUERY_TYPE_SELECT,
'has_export_link' => $statementInfo->queryType === self::QUERY_TYPE_SELECT,
'url_params' => $urlParams,
];
}
@ -4153,25 +4139,24 @@ class Results
* @see getDataCellForNumericColumns(), getDataCellForGeometryColumns(),
* getDataCellForNonNumericColumns(),
*
* @param string $class css classes for the td element
* @param bool $conditionField whether the column is a part of the where clause
* @param array $analyzedSqlResults the analyzed query
* @param FieldMetadata $meta the meta-information about the field
* @param array<string, string[]> $map the list of relations
* @param string $data data
* @param string $displayedData data that will be displayed (maybe be chunked)
* @param string $nowrap 'nowrap' if the content should not be wrapped
* @param string $whereComparison data for the where clause
* @param array $transformOptions options for transformation
* @param bool $isFieldTruncated whether the field is truncated
* @param string $originalLength of a truncated column, or ''
* @param string $class css classes for the td element
* @param bool $conditionField whether the column is a part of the where clause
* @param FieldMetadata $meta the meta-information about the field
* @param array<string, string[]> $map the list of relations
* @param string $data data
* @param string $displayedData data that will be displayed (maybe be chunked)
* @param string $nowrap 'nowrap' if the content should not be wrapped
* @param string $whereComparison data for the where clause
* @param array $transformOptions options for transformation
* @param bool $isFieldTruncated whether the field is truncated
* @param string $originalLength of a truncated column, or ''
*
* @return string formatted data
*/
private function getRowData(
string $class,
bool $conditionField,
array $analyzedSqlResults,
StatementInfo $statementInfo,
FieldMetadata $meta,
array $map,
$data,
@ -4195,8 +4180,8 @@ class Results
$transformationPlugin !== null
);
if (! empty($analyzedSqlResults['statement']->expr)) {
foreach ($analyzedSqlResults['statement']->expr as $expr) {
if (! empty($statementInfo->statement->expr)) {
foreach ($statementInfo->statement->expr as $expr) {
if (empty($expr->alias) || empty($expr->column)) {
continue;
}

View File

@ -23,26 +23,26 @@ class ParseAnalyze
* @param string $sqlQuery the query to parse
* @param string $db the current database
*
* @return array
* @return array<int, StatementInfo|string>
* @psalm-return array{StatementInfo, string, string}
*/
public static function sqlQuery($sqlQuery, $db)
public static function sqlQuery(string $sqlQuery, string $db): array
{
// @todo: move to returned results (also in all the calling chain)
$GLOBALS['unparsed_sql'] = $sqlQuery;
// Get details about the SQL query.
$analyzedSqlResults = Query::getAll($sqlQuery);
$info = Query::getAll($sqlQuery);
$table = '';
// If the targeted table (and database) are different than the ones that is
// currently browsed, edit `$db` and `$table` to match them so other elements
// (page headers, links, navigation panel) can be updated properly.
if (! empty($analyzedSqlResults['select_tables'])) {
if (! empty($info['select_tables'])) {
// Previous table and database name is stored to check if it changed.
$previousDb = $db;
if (count($analyzedSqlResults['select_tables']) > 1) {
if (count($info['select_tables']) > 1) {
/**
* @todo if there are more than one table name in the Select:
@ -52,25 +52,21 @@ class ParseAnalyze
*/
$table = '';
} else {
$table = $analyzedSqlResults['select_tables'][0][0];
if (! empty($analyzedSqlResults['select_tables'][0][1])) {
$db = $analyzedSqlResults['select_tables'][0][1];
$table = $info['select_tables'][0][0] ?? '';
if (isset($info['select_tables'][0][1])) {
$db = $info['select_tables'][0][1];
}
}
// There is no point checking if a reload is required if we already decided
// There is no point checking if a reloading is required if we already decided
// to reload. Also, no reload is required for AJAX requests.
$response = ResponseRenderer::getInstance();
if (empty($analyzedSqlResults['reload']) && ! $response->isAjax()) {
if (empty($info['reload']) && ! $response->isAjax()) {
// NOTE: Database names are case-insensitive.
$analyzedSqlResults['reload'] = strcasecmp($db, $previousDb) != 0;
$info['reload'] = strcasecmp($db, $previousDb) !== 0;
}
}
return [
$analyzedSqlResults,
$db,
$table,
];
return [StatementInfo::fromArray($info), $db, $table];
}
}

View File

@ -82,24 +82,27 @@ class Sql
/**
* Handle remembered sorting order, only for single table query
*
* @param string $db database name
* @param string $table table name
* @param array $analyzedSqlResults the analyzed query results
* @param string $fullSqlQuery SQL query
* @param string $db database name
* @param string $table table name
* @param string $fullSqlQuery SQL query
*/
private function handleSortOrder(
$db,
$table,
array &$analyzedSqlResults,
StatementInfo $statementInfo,
&$fullSqlQuery
): void {
): StatementInfo {
if ($statementInfo->statement === null || $statementInfo->parser === null) {
return $statementInfo;
}
$tableObject = new Table($table, $db);
if (empty($analyzedSqlResults['order'])) {
if (empty($statementInfo->order)) {
// Retrieving the name of the column we should sort after.
$sortCol = $tableObject->getUiProp(Table::PROP_SORTED_COLUMN);
if (empty($sortCol)) {
return;
return $statementInfo;
}
// Remove the name of the table from the retrieved field name.
@ -111,38 +114,42 @@ class Sql
// Create the new query.
$fullSqlQuery = Query::replaceClause(
$analyzedSqlResults['statement'],
$analyzedSqlResults['parser']->list,
$statementInfo->statement,
$statementInfo->parser->list,
'ORDER BY ' . $sortCol
);
// TODO: Avoid reparsing the query.
$analyzedSqlResults = Query::getAll($fullSqlQuery);
$statementInfo = StatementInfo::fromArray(Query::getAll($fullSqlQuery));
} else {
// Store the remembered table into session.
$tableObject->setUiProp(
Table::PROP_SORTED_COLUMN,
Query::getClause(
$analyzedSqlResults['statement'],
$analyzedSqlResults['parser']->list,
$statementInfo->statement,
$statementInfo->parser->list,
'ORDER BY'
)
);
}
return $statementInfo;
}
/**
* Append limit clause to SQL query
*
* @param array $analyzedSqlResults the analyzed query results
*
* @return string limit clause appended SQL query
*/
private function getSqlWithLimitClause(array $analyzedSqlResults)
private function getSqlWithLimitClause(StatementInfo $statementInfo)
{
if ($statementInfo->statement === null || $statementInfo->parser === null) {
return '';
}
return Query::replaceClause(
$analyzedSqlResults['statement'],
$analyzedSqlResults['parser']->list,
$statementInfo->statement,
$statementInfo->parser->list,
'LIMIT ' . $_SESSION['tmpval']['pos'] . ', '
. $_SESSION['tmpval']['max_rows']
);
@ -341,103 +348,86 @@ class Sql
}
/**
* Function to check whether to remember the sorting order or not
*
* @param array $analyzedSqlResults the analyzed query and other variables set
* after analyzing the query
* Function to check whether to remember the sorting order or not.
*/
private function isRememberSortingOrder(array $analyzedSqlResults): bool
private function isRememberSortingOrder(StatementInfo $statementInfo): bool
{
return isset($analyzedSqlResults['select_expr'], $analyzedSqlResults['select_tables'])
&& $GLOBALS['cfg']['RememberSorting']
&& ! ($analyzedSqlResults['is_count']
|| $analyzedSqlResults['is_export']
|| $analyzedSqlResults['is_func']
|| $analyzedSqlResults['is_analyse'])
&& $analyzedSqlResults['select_from']
&& (empty($analyzedSqlResults['select_expr'])
|| ((count($analyzedSqlResults['select_expr']) === 1)
&& ($analyzedSqlResults['select_expr'][0] === '*')))
&& count($analyzedSqlResults['select_tables']) === 1;
return $GLOBALS['cfg']['RememberSorting']
&& ! ($statementInfo->isCount
|| $statementInfo->isExport
|| $statementInfo->isFunction
|| $statementInfo->isAnalyse)
&& $statementInfo->selectFrom
&& (empty($statementInfo->selectExpression)
|| ((count($statementInfo->selectExpression) === 1)
&& ($statementInfo->selectExpression[0] === '*')))
&& count($statementInfo->selectTables) === 1;
}
/**
* Function to check whether the LIMIT clause should be appended or not
*
* @param array $analyzedSqlResults the analyzed query and other variables set
* after analyzing the query
* Function to check whether the LIMIT clause should be appended or not.
*/
private function isAppendLimitClause(array $analyzedSqlResults): bool
private function isAppendLimitClause(StatementInfo $statementInfo): bool
{
// Assigning LIMIT clause to an syntactically-wrong query
// is not needed. Also we would want to show the true query
// and the true error message to the query executor
return (isset($analyzedSqlResults['parser'])
&& count($analyzedSqlResults['parser']->errors) === 0)
return (isset($statementInfo->parser)
&& count($statementInfo->parser->errors) === 0)
&& ($_SESSION['tmpval']['max_rows'] !== 'all')
&& ! ($analyzedSqlResults['is_export']
|| $analyzedSqlResults['is_analyse'])
&& ($analyzedSqlResults['select_from']
|| $analyzedSqlResults['is_subquery'])
&& empty($analyzedSqlResults['limit']);
&& ! ($statementInfo->isExport
|| $statementInfo->isAnalyse)
&& ($statementInfo->selectFrom
|| $statementInfo->isSubquery)
&& empty($statementInfo->limit);
}
/**
* Function to check whether this query is for just browsing
*
* @param array<string, mixed> $analyzedSqlResults the analyzed query and other variables set
* after analyzing the query
* @param bool|null $findRealEnd whether the real end should be found
* @param bool|null $findRealEnd whether the real end should be found
*/
public static function isJustBrowsing(array $analyzedSqlResults, ?bool $findRealEnd): bool
public static function isJustBrowsing(StatementInfo $statementInfo, ?bool $findRealEnd): bool
{
return ! $analyzedSqlResults['is_group']
&& ! $analyzedSqlResults['is_func']
&& empty($analyzedSqlResults['union'])
&& empty($analyzedSqlResults['distinct'])
&& $analyzedSqlResults['select_from']
&& (count($analyzedSqlResults['select_tables']) === 1)
&& (empty($analyzedSqlResults['statement']->where)
|| (count($analyzedSqlResults['statement']->where) === 1
&& $analyzedSqlResults['statement']->where[0]->expr === '1'))
&& empty($analyzedSqlResults['group'])
return ! $statementInfo->isGroup
&& ! $statementInfo->isFunction
&& empty($statementInfo->union)
&& empty($statementInfo->distinct)
&& $statementInfo->selectFrom
&& (count($statementInfo->selectTables) === 1)
&& (empty($statementInfo->statement->where)
|| (count($statementInfo->statement->where) === 1
&& $statementInfo->statement->where[0]->expr === '1'))
&& empty($statementInfo->group)
&& ! isset($findRealEnd)
&& ! $analyzedSqlResults['is_subquery']
&& ! $analyzedSqlResults['join']
&& empty($analyzedSqlResults['having']);
&& ! $statementInfo->isSubquery
&& ! $statementInfo->join
&& empty($statementInfo->having);
}
/**
* Function to check whether the related transformation information should be deleted
*
* @param array $analyzedSqlResults the analyzed query and other variables set
* after analyzing the query
* Function to check whether the related transformation information should be deleted.
*/
private function isDeleteTransformationInfo(array $analyzedSqlResults): bool
private function isDeleteTransformationInfo(StatementInfo $statementInfo): bool
{
return ! empty($analyzedSqlResults['querytype'])
&& (($analyzedSqlResults['querytype'] === 'ALTER')
|| ($analyzedSqlResults['querytype'] === 'DROP'));
return ! empty($statementInfo->queryType)
&& (($statementInfo->queryType === 'ALTER')
|| ($statementInfo->queryType === 'DROP'));
}
/**
* Function to check whether the user has rights to drop the database
*
* @param array $analyzedSqlResults the analyzed query and other variables set
* after analyzing the query
* @param bool $allowUserDropDatabase whether the user is allowed to drop db
* @param bool $isSuperUser whether this user is a superuser
* @param bool $allowUserDropDatabase whether the user is allowed to drop db
* @param bool $isSuperUser whether this user is a superuser
*/
public function hasNoRightsToDropDatabase(
array $analyzedSqlResults,
StatementInfo $statementInfo,
$allowUserDropDatabase,
$isSuperUser
): bool {
return ! $allowUserDropDatabase
&& isset($analyzedSqlResults['drop_database'])
&& $analyzedSqlResults['drop_database']
&& ! $isSuperUser;
return ! $allowUserDropDatabase && $statementInfo->dropDatabase && ! $isSuperUser;
}
/**
@ -675,11 +665,10 @@ class Sql
* Function to count the total number of rows for the same 'SELECT' query without
* the 'LIMIT' clause that may have been programmatically added
*
* @param int|string $numRows number of rows affected/changed by the query
* @param bool $justBrowsing whether just browsing or not
* @param string $db the current database
* @param string $table the current table
* @param array $analyzedSqlResults the analyzed query and other variables set after analyzing the query
* @param int|string $numRows number of rows affected/changed by the query
* @param bool $justBrowsing whether just browsing or not
* @param string $db the current database
* @param string $table the current table
* @psalm-param int|numeric-string $numRows
*
* @return int|string unlimited number of rows
@ -690,14 +679,14 @@ class Sql
bool $justBrowsing,
string $db,
string $table,
array $analyzedSqlResults
StatementInfo $statementInfo
) {
/* Shortcut for not analyzed/empty query */
if ($analyzedSqlResults === []) {
if ($statementInfo->statement === null || $statementInfo->parser === null) {
return 0;
}
if (! $this->isAppendLimitClause($analyzedSqlResults)) {
if (! $this->isAppendLimitClause($statementInfo)) {
// if we did not append a limit, set this to get a correct
// "Showing rows..." message
// $_SESSION['tmpval']['max_rows'] = 'all';
@ -707,7 +696,7 @@ class Sql
// result are less than max_rows to display, there is no need
// to count total rows for that query again
$unlimNumRows = $_SESSION['tmpval']['pos'] + $numRows;
} elseif ($analyzedSqlResults['querytype'] === 'SELECT' || $analyzedSqlResults['is_subquery']) {
} elseif ($statementInfo->queryType === 'SELECT' || $statementInfo->isSubquery) {
// c o u n t q u e r y
// If we are "just browsing", there is only one table (and no join),
@ -736,8 +725,8 @@ class Sql
->countRecords(true);
}
} else {
$statement = $analyzedSqlResults['statement'];
$tokenList = $analyzedSqlResults['parser']->list;
$statement = $statementInfo->statement;
$tokenList = $statementInfo->parser->list;
$replaces = [
// Remove ORDER BY to decrease unnecessary sorting time
[
@ -770,7 +759,6 @@ class Sql
/**
* Function to handle all aspects relating to executing the query
*
* @param array $analyzedSqlResults analyzed sql results
* @param string $fullSqlQuery full sql query
* @param bool $isGotoFile whether to go to a file
* @param string $db current database
@ -788,7 +776,7 @@ class Sql
* }
*/
private function executeTheQuery(
array $analyzedSqlResults,
StatementInfo $statementInfo,
$fullSqlQuery,
$isGotoFile,
string $db,
@ -847,13 +835,13 @@ class Sql
// Gets the number of rows affected/returned
// (This must be done immediately after the query because
// mysql_affected_rows() reports about the last query done)
$numRows = $this->getNumberOfRowsAffectedOrChanged($analyzedSqlResults['is_affected'], $result);
$numRows = $this->getNumberOfRowsAffectedOrChanged($statementInfo->isAffected, $result);
$profilingResults = Profiling::getInformation($this->dbi);
$justBrowsing = self::isJustBrowsing($analyzedSqlResults, $findRealEnd ?? null);
$justBrowsing = self::isJustBrowsing($statementInfo, $findRealEnd ?? null);
$unlimNumRows = $this->countQueryResults($numRows, $justBrowsing, $db, $table ?? '', $analyzedSqlResults);
$unlimNumRows = $this->countQueryResults($numRows, $justBrowsing, $db, $table ?? '', $statementInfo);
$this->cleanupRelations($db, $table ?? '', $_POST['dropped_column'] ?? null, ! empty($_POST['purge']));
@ -887,17 +875,16 @@ class Sql
/**
* Delete related transformation information
*
* @param string $db current database
* @param string $table current table
* @param array $analyzedSqlResults analyzed sql results
* @param string $db current database
* @param string $table current table
*/
private function deleteTransformationInfo(string $db, string $table, array $analyzedSqlResults): void
private function deleteTransformationInfo(string $db, string $table, StatementInfo $statementInfo): void
{
if (! isset($analyzedSqlResults['statement'])) {
if (! isset($statementInfo->statement)) {
return;
}
$statement = $analyzedSqlResults['statement'];
$statement = $statementInfo->statement;
if ($statement instanceof AlterStatement) {
if (
! empty($statement->altered[0])
@ -914,19 +901,18 @@ class Sql
/**
* Function to get the message for the no rows returned case
*
* @param string|null $messageToShow message to show
* @param array $analyzedSqlResults analyzed sql results
* @param int|string $numRows number of rows
* @param string|null $messageToShow message to show
* @param int|string $numRows number of rows
*/
private function getMessageForNoRowsReturned(
?string $messageToShow,
array $analyzedSqlResults,
StatementInfo $statementInfo,
$numRows
): Message {
if ($analyzedSqlResults['querytype'] === 'DELETE"') {
if ($statementInfo->queryType === 'DELETE"') {
$message = Message::getMessageForDeletedRows($numRows);
} elseif ($analyzedSqlResults['is_insert']) {
if ($analyzedSqlResults['querytype'] === 'REPLACE') {
} elseif ($statementInfo->isInsert) {
if ($statementInfo->queryType === 'REPLACE') {
// For REPLACE we get DELETED + INSERTED row count,
// so we have to call it affected
$message = Message::getMessageForAffectedRows($numRows);
@ -946,7 +932,7 @@ class Sql
$inserted->addParam($insertId + $numRows - 1);
$message->addMessage($inserted);
}
} elseif ($analyzedSqlResults['is_affected']) {
} elseif ($statementInfo->isAffected) {
$message = Message::getMessageForAffectedRows($numRows);
// Ok, here is an explanation for the !$is_select.
@ -956,7 +942,7 @@ class Sql
// fact that $message_to_show is sent for every case.
// The $message_to_show containing a success message and sent with
// the form should not have priority over errors
} elseif ($messageToShow && $analyzedSqlResults['querytype'] !== 'SELECT') {
} elseif ($messageToShow && $statementInfo->queryType !== 'SELECT') {
$message = Message::rawSuccess(htmlspecialchars($messageToShow));
} elseif (! empty($GLOBALS['show_as_php'])) {
$message = Message::success(__('Showing as PHP code'));
@ -996,7 +982,6 @@ class Sql
* 6-> When searching using the SEARCH tab which returns zero results
* 7-> When changing the structure of the table except change operation
*
* @param array $analyzedSqlResults analyzed sql results
* @param string $db current database
* @param string|null $table current table
* @param string|null $messageToShow message to show
@ -1012,7 +997,7 @@ class Sql
* @return string html
*/
private function getQueryResponseForNoResultsReturned(
array $analyzedSqlResults,
StatementInfo $statementInfo,
string $db,
?string $table,
?string $messageToShow,
@ -1024,14 +1009,14 @@ class Sql
$sqlQuery,
?string $completeQuery
): string {
if ($this->isDeleteTransformationInfo($analyzedSqlResults)) {
$this->deleteTransformationInfo($db, $table ?? '', $analyzedSqlResults);
if ($this->isDeleteTransformationInfo($statementInfo)) {
$this->deleteTransformationInfo($db, $table ?? '', $statementInfo);
}
if (isset($extraData['error'])) {
$message = Message::rawError($extraData['error']);
} else {
$message = $this->getMessageForNoRowsReturned($messageToShow, $analyzedSqlResults, $numRows);
$message = $this->getMessageForNoRowsReturned($messageToShow, $statementInfo, $numRows);
}
$queryMessage = Generator::getMessage($message, $GLOBALS['sql_query'], 'success');
@ -1056,7 +1041,7 @@ class Sql
$response = ResponseRenderer::getInstance();
$response->addJSON($extraData ?? []);
if (empty($analyzedSqlResults['is_select']) || isset($extraData['error'])) {
if (empty($statementInfo->isSelect) || isset($extraData['error'])) {
return $queryMessage;
}
@ -1078,7 +1063,7 @@ class Sql
$numRows,
null,
$result,
$analyzedSqlResults,
$statementInfo,
true
);
@ -1120,7 +1105,7 @@ class Sql
'db' => $db,
'table' => $table,
'sql_query' => $sqlQuery,
'is_procedure' => ! empty($analyzedSqlResults['procedure']),
'is_procedure' => ! empty($statementInfo->isProcedure),
]);
}
@ -1170,7 +1155,6 @@ class Sql
* @param int|string $numRows number of rows
* @param array|null $showTable table definitions
* @param ResultInterface|false|null $result result of the executed query
* @param array $analyzedSqlResults analyzed sql results
* @param bool $isLimitedDisplay Show only limited operations or not
* @psalm-param int|numeric-string $unlimNumRows
* @psalm-param int|numeric-string $numRows
@ -1183,14 +1167,14 @@ class Sql
$numRows,
?array $showTable,
$result,
array $analyzedSqlResults,
StatementInfo $statementInfo,
$isLimitedDisplay = false
): string {
$printView = isset($_POST['printview']) && $_POST['printview'] == '1' ? '1' : null;
$tableHtml = '';
$isBrowseDistinct = ! empty($_POST['is_browse_distinct']);
if ($analyzedSqlResults['is_procedure']) {
if ($statementInfo->isProcedure) {
do {
if ($result === null) {
$result = $this->dbi->storeResult();
@ -1210,17 +1194,17 @@ class Sql
$displayResultsObject->setProperties(
$numRows,
$fieldsMeta,
$analyzedSqlResults['is_count'],
$analyzedSqlResults['is_export'],
$analyzedSqlResults['is_func'],
$analyzedSqlResults['is_analyse'],
$statementInfo->isCount,
$statementInfo->isExport,
$statementInfo->isFunction,
$statementInfo->isAnalyse,
$numRows,
$fieldsCount,
$GLOBALS['querytime'],
$GLOBALS['text_dir'],
$analyzedSqlResults['is_maint'],
$analyzedSqlResults['is_explain'],
$analyzedSqlResults['is_show'],
$statementInfo->isMaint,
$statementInfo->isExplain,
$statementInfo->isShow,
$showTable,
$printView,
$editable,
@ -1240,7 +1224,7 @@ class Sql
$tableHtml .= $displayResultsObject->getTable(
$result,
$displayParts,
$analyzedSqlResults,
$statementInfo,
$isLimitedDisplay
);
}
@ -1258,17 +1242,17 @@ class Sql
$displayResultsObject->setProperties(
$unlimNumRows,
$fieldsMeta,
$analyzedSqlResults['is_count'],
$analyzedSqlResults['is_export'],
$analyzedSqlResults['is_func'],
$analyzedSqlResults['is_analyse'],
$statementInfo->isCount,
$statementInfo->isExport,
$statementInfo->isFunction,
$statementInfo->isAnalyse,
$numRows,
$fieldsCount,
$GLOBALS['querytime'],
$GLOBALS['text_dir'],
$analyzedSqlResults['is_maint'],
$analyzedSqlResults['is_explain'],
$analyzedSqlResults['is_show'],
$statementInfo->isMaint,
$statementInfo->isExplain,
$statementInfo->isShow,
$showTable,
$printView,
$editable,
@ -1279,7 +1263,7 @@ class Sql
$tableHtml .= $displayResultsObject->getTable(
$result,
$displayParts,
$analyzedSqlResults,
$statementInfo,
$isLimitedDisplay
);
}
@ -1366,7 +1350,6 @@ class Sql
* Function to display results when the executed query returns non empty results
*
* @param ResultInterface|false|null $result executed query results
* @param array $analyzedSqlResults analysed sql results
* @param string $db current database
* @param string|null $table current table
* @param array|null $sqlData sql data
@ -1385,7 +1368,7 @@ class Sql
*/
private function getQueryResponseForResultsReturned(
$result,
array $analyzedSqlResults,
StatementInfo $statementInfo,
string $db,
?string $table,
?array $sqlData,
@ -1432,7 +1415,7 @@ class Sql
$updatableView = false;
$statement = $analyzedSqlResults['statement'] ?? null;
$statement = $statementInfo->statement;
if ($statement instanceof SelectStatement) {
if ($statement->expr && $statement->expr[0]->expr === '*' && $table) {
$_table = new Table($table, $db);
@ -1440,9 +1423,9 @@ class Sql
}
if (
$analyzedSqlResults['join']
|| $analyzedSqlResults['is_subquery']
|| count($analyzedSqlResults['select_tables']) !== 1
$statementInfo->join
|| $statementInfo->isSubquery
|| count($statementInfo->selectTables) !== 1
) {
$justOneTable = false;
}
@ -1526,7 +1509,7 @@ class Sql
$numRows,
$GLOBALS['showtable'],
$result,
$analyzedSqlResults
$statementInfo
);
$bookmarkSupportHtml = '';
@ -1563,7 +1546,6 @@ class Sql
/**
* Function to execute the query and send the response
*
* @param array|null $analyzedSqlResults analysed sql results
* @param bool $isGotoFile whether goto file or not
* @param string $db current database
* @param string|null $table current table
@ -1579,7 +1561,7 @@ class Sql
* @param string|null $completeQuery complete query
*/
public function executeQueryAndSendQueryResponse(
$analyzedSqlResults,
?StatementInfo $statementInfo,
$isGotoFile,
string $db,
?string $table,
@ -1594,19 +1576,15 @@ class Sql
$sqlQuery,
$completeQuery
): string {
if ($analyzedSqlResults == null) {
if ($statementInfo === null) {
// Parse and analyze the query
[
$analyzedSqlResults,
$db,
$tableFromSql,
] = ParseAnalyze::sqlQuery($sqlQuery, $db);
[$statementInfo, $db, $tableFromSql] = ParseAnalyze::sqlQuery($sqlQuery, $db);
$table = $tableFromSql ?: $table;
}
return $this->executeQueryAndGetQueryResponse(
$analyzedSqlResults, // analyzed_sql_results
$statementInfo,
$isGotoFile, // is_gotofile
$db, // db
$table, // table
@ -1626,7 +1604,6 @@ class Sql
/**
* Function to execute the query and send the response
*
* @param array $analyzedSqlResults analysed sql results
* @param bool $isGotoFile whether goto file or not
* @param string $db current database
* @param string|null $table current table
@ -1644,7 +1621,7 @@ class Sql
* @return string html
*/
public function executeQueryAndGetQueryResponse(
array $analyzedSqlResults,
StatementInfo $statementInfo,
$isGotoFile,
string $db,
?string $table,
@ -1668,13 +1645,12 @@ class Sql
// Handling is also not required if we came from the "Sort by key"
// drop-down.
if (
$analyzedSqlResults !== []
&& $this->isRememberSortingOrder($analyzedSqlResults)
&& empty($analyzedSqlResults['union'])
$this->isRememberSortingOrder($statementInfo)
&& empty($statementInfo->union)
&& ! isset($_POST['sort_by_key'])
) {
if (! isset($_SESSION['sql_from_query_box'])) {
$this->handleSortOrder($db, $table, $analyzedSqlResults, $sqlQuery);
$statementInfo = $this->handleSortOrder($db, $table, $statementInfo, $sqlQuery);
} else {
unset($_SESSION['sql_from_query_box']);
}
@ -1694,8 +1670,8 @@ class Sql
$fullSqlQuery = $sqlQuery;
// Do append a "LIMIT" clause?
if ($this->isAppendLimitClause($analyzedSqlResults)) {
$fullSqlQuery = $this->getSqlWithLimitClause($analyzedSqlResults);
if ($this->isAppendLimitClause($statementInfo)) {
$fullSqlQuery = $this->getSqlWithLimitClause($statementInfo);
}
$GLOBALS['reload'] = $this->hasCurrentDbChanged($db);
@ -1708,7 +1684,7 @@ class Sql
$profilingResults,
$extraData,
] = $this->executeTheQuery(
$analyzedSqlResults,
$statementInfo,
$fullSqlQuery,
$isGotoFile,
$db,
@ -1725,9 +1701,9 @@ class Sql
$warningMessages = $this->operations->getWarningMessagesArray();
// No rows returned -> move back to the calling page
if (($numRows == 0 && $unlimNumRows == 0) || $analyzedSqlResults['is_affected']) {
if (($numRows == 0 && $unlimNumRows == 0) || $statementInfo->isAffected) {
$htmlOutput = $this->getQueryResponseForNoResultsReturned(
$analyzedSqlResults,
$statementInfo,
$db,
$table,
$messageToShow,
@ -1743,7 +1719,7 @@ class Sql
// At least one row is returned -> displays a table with results
$htmlOutput = $this->getQueryResponseForResultsReturned(
$result,
$analyzedSqlResults,
$statementInfo,
$db,
$table,
$sqlData,

View File

@ -0,0 +1,232 @@
<?php
declare(strict_types=1);
namespace PhpMyAdmin;
use PhpMyAdmin\SqlParser\Parser;
use PhpMyAdmin\SqlParser\Statement;
/**
* @psalm-immutable
*/
class StatementInfo
{
/** @var bool */
public $distinct;
/** @var bool */
public $dropDatabase;
/** @var bool */
public $group;
/** @var bool */
public $having;
/** @var bool */
public $isAffected;
/** @var bool */
public $isAnalyse;
/** @var bool */
public $isCount;
/** @var bool */
public $isDelete;
/** @var bool */
public $isExplain;
/** @var bool */
public $isExport;
/** @var bool */
public $isFunction;
/** @var bool */
public $isGroup;
/** @var bool */
public $isInsert;
/** @var bool */
public $isMaint;
/** @var bool */
public $isProcedure;
/** @var bool */
public $isReplace;
/** @var bool */
public $isSelect;
/** @var bool */
public $isShow;
/** @var bool */
public $isSubquery;
/** @var bool */
public $join;
/** @var bool */
public $limit;
/** @var bool */
public $offset;
/** @var bool */
public $order;
/** @var string|false */
public $queryType;
/** @var bool */
public $reload;
/** @var bool */
public $selectFrom;
/** @var bool */
public $union;
/** @var Parser|null */
public $parser;
/** @var Statement|null */
public $statement;
/**
* @var array<int, array<int, string|null>>
* @psalm-var list<array{string|null, string|null}>
*/
public $selectTables;
/**
* @var array<int, string|null>
* @psalm-var list<string|null>
*/
public $selectExpression;
/**
* @param string|false $queryType
* @param array<int, array<int, string|null>> $selectTables
* @param array<int, string|null> $selectExpression
* @psalm-param list<array{string|null, string|null}> $selectTables
* @psalm-param list<string|null> $selectExpression
*/
private function __construct(
bool $distinct,
bool $dropDatabase,
bool $group,
bool $having,
bool $isAffected,
bool $isAnalyse,
bool $isCount,
bool $isDelete,
bool $isExplain,
bool $isExport,
bool $isFunction,
bool $isGroup,
bool $isInsert,
bool $isMaint,
bool $isProcedure,
bool $isReplace,
bool $isSelect,
bool $isShow,
bool $isSubquery,
bool $join,
bool $limit,
bool $offset,
bool $order,
$queryType,
bool $reload,
bool $selectFrom,
bool $union,
?SqlParser\Parser $parser,
?SqlParser\Statement $statement,
array $selectTables,
array $selectExpression
) {
$this->distinct = $distinct;
$this->dropDatabase = $dropDatabase;
$this->group = $group;
$this->having = $having;
$this->isAffected = $isAffected;
$this->isAnalyse = $isAnalyse;
$this->isCount = $isCount;
$this->isDelete = $isDelete;
$this->isExplain = $isExplain;
$this->isExport = $isExport;
$this->isFunction = $isFunction;
$this->isGroup = $isGroup;
$this->isInsert = $isInsert;
$this->isMaint = $isMaint;
$this->isProcedure = $isProcedure;
$this->isReplace = $isReplace;
$this->isSelect = $isSelect;
$this->isShow = $isShow;
$this->isSubquery = $isSubquery;
$this->join = $join;
$this->limit = $limit;
$this->offset = $offset;
$this->order = $order;
$this->queryType = $queryType;
$this->reload = $reload;
$this->selectFrom = $selectFrom;
$this->union = $union;
$this->parser = $parser;
$this->statement = $statement;
$this->selectTables = $selectTables;
$this->selectExpression = $selectExpression;
}
/**
* @param array<string, array<int, array<int, string|null>|string|null>|bool|string|Parser|Statement> $info
* @psalm-param array{
* distinct: bool,
* drop_database: bool,
* group: bool,
* having: bool,
* is_affected: bool,
* is_analyse: bool,
* is_count: bool,
* is_delete: bool,
* is_explain: bool,
* is_export: bool,
* is_func: bool,
* is_group: bool,
* is_insert: bool,
* is_maint: bool,
* is_procedure: bool,
* is_replace: bool,
* is_select: bool,
* is_show: bool,
* is_subquery: bool,
* join: bool,
* limit: bool,
* offset: bool,
* order: bool,
* querytype: (
* 'ALTER'|'ANALYZE'|'CALL'|'CHECK'|'CHECKSUM'|'CREATE'|'DELETE'|'DROP'|
* 'EXPLAIN'|'INSERT'|'LOAD'|'OPTIMIZE'|'REPAIR'|'REPLACE'|'SELECT'|'SET'|'SHOW'|'UPDATE'|false
* ),
* reload: bool,
* select_from: bool,
* union: bool,
* parser?: Parser,
* statement?: Statement,
* select_tables?: list<array{string|null, string|null}>,
* select_expr?: list<string|null>
* } $info
*/
public static function fromArray(array $info): self
{
return new self(
$info['distinct'],
$info['drop_database'],
$info['group'],
$info['having'],
$info['is_affected'],
$info['is_analyse'],
$info['is_count'],
$info['is_delete'],
$info['is_explain'],
$info['is_export'],
$info['is_func'],
$info['is_group'],
$info['is_insert'],
$info['is_maint'],
$info['is_procedure'],
$info['is_replace'],
$info['is_select'],
$info['is_show'],
$info['is_subquery'],
$info['join'],
$info['limit'],
$info['offset'],
$info['order'],
$info['querytype'],
$info['reload'],
$info['select_from'],
$info['union'],
$info['parser'] ?? null,
$info['statement'] ?? null,
$info['select_tables'] ?? [],
$info['select_expr'] ?? []
);
}
}

View File

@ -2770,26 +2770,11 @@ parameters:
count: 2
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getBulkLinks\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getColumnParams\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getCommentForRow\\(\\) has parameter \\$commentsMap with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getDataCellForGeometryColumns\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getDataCellForGeometryColumns\\(\\) has parameter \\$transformOptions with no value type specified in iterable type array\\.$#"
count: 1
@ -2800,11 +2785,6 @@ parameters:
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getDataCellForNonNumericColumns\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getDataCellForNonNumericColumns\\(\\) has parameter \\$transformOptions with no value type specified in iterable type array\\.$#"
count: 1
@ -2815,21 +2795,11 @@ parameters:
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getDataCellForNumericColumns\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getDataCellForNumericColumns\\(\\) has parameter \\$transformOptions with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getDataForResettingColumnOrder\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getDataForResettingColumnOrder\\(\\) return type has no value type specified in iterable type array\\.$#"
count: 1
@ -2850,16 +2820,6 @@ parameters:
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getResultsOperations\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getRowData\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getRowData\\(\\) has parameter \\$transformOptions with no value type specified in iterable type array\\.$#"
count: 1
@ -2875,11 +2835,6 @@ parameters:
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getRowValues\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getRowValues\\(\\) has parameter \\$colOrder with no value type specified in iterable type array\\.$#"
count: 1
@ -2920,31 +2875,11 @@ parameters:
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getTable\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getTableBody\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getTableCommentsArray\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getTableCommentsArray\\(\\) return type has no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getTableHeaders\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getTableHeaders\\(\\) has parameter \\$sortDirection with no value type specified in iterable type array\\.$#"
count: 1
@ -2960,11 +2895,6 @@ parameters:
count: 2
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getTableHeadersForColumns\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getTableHeadersForColumns\\(\\) has parameter \\$sortDirection with no value type specified in iterable type array\\.$#"
count: 1
@ -2985,11 +2915,6 @@ parameters:
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:getUrlSqlQuery\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:handleNonPrintableContents\\(\\) has parameter \\$transformOptions with no value type specified in iterable type array\\.$#"
count: 1
@ -3010,21 +2935,6 @@ parameters:
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:isSelect\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:setHighlightedColumnGlobalField\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Method PhpMyAdmin\\\\Display\\\\Results\\:\\:setMessageInformation\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Display/Results.php
-
message: "#^Offset 3 does not exist on array\\{string\\|null, string\\|null, string\\|null\\}\\.$#"
count: 1
@ -5370,11 +5280,6 @@ parameters:
count: 1
path: libraries/classes/OutputBuffering.php
-
message: "#^Method PhpMyAdmin\\\\ParseAnalyze\\:\\:sqlQuery\\(\\) return type has no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/ParseAnalyze.php
-
message: "#^Method PhpMyAdmin\\\\Partitioning\\\\Maintenance\\:\\:analyze\\(\\) return type has no value type specified in iterable type array\\.$#"
count: 1
@ -7510,31 +7415,11 @@ parameters:
count: 1
path: libraries/classes/Setup/Index.php
-
message: "#^Cannot access property \\$where on mixed\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:countQueryResults\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:countQueryResults\\(\\) should return int\\|numeric\\-string but returns mixed\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:deleteTransformationInfo\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:executeQueryAndGetQueryResponse\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:executeQueryAndGetQueryResponse\\(\\) has parameter \\$extraData with no value type specified in iterable type array\\.$#"
count: 1
@ -7545,11 +7430,6 @@ parameters:
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:executeQueryAndSendQueryResponse\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:executeQueryAndSendQueryResponse\\(\\) has parameter \\$extraData with no value type specified in iterable type array\\.$#"
count: 1
@ -7560,11 +7440,6 @@ parameters:
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:executeTheQuery\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:executeTheQuery\\(\\) has parameter \\$extraData with no value type specified in iterable type array\\.$#"
count: 1
@ -7590,26 +7465,11 @@ parameters:
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:getHtmlForSqlQueryResultsTable\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:getHtmlForSqlQueryResultsTable\\(\\) has parameter \\$showTable with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:getMessageForNoRowsReturned\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:getQueryResponseForNoResultsReturned\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:getQueryResponseForNoResultsReturned\\(\\) has parameter \\$extraData with no value type specified in iterable type array\\.$#"
count: 1
@ -7620,11 +7480,6 @@ parameters:
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:getQueryResponseForResultsReturned\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:getQueryResponseForResultsReturned\\(\\) has parameter \\$profilingResults with no value type specified in iterable type array\\.$#"
count: 1
@ -7635,41 +7490,11 @@ parameters:
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:getSqlWithLimitClause\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:getValuesForColumn\\(\\) return type has no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:handleSortOrder\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:hasNoRightsToDropDatabase\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:isAppendLimitClause\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:isDeleteTransformationInfo\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:isRememberSortingOrder\\(\\) has parameter \\$analyzedSqlResults with no value type specified in iterable type array\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Method PhpMyAdmin\\\\Sql\\:\\:resultSetContainsUniqueKey\\(\\) has parameter \\$fieldsMeta with no value type specified in iterable type array\\.$#"
count: 1
@ -7715,11 +7540,6 @@ parameters:
count: 1
path: libraries/classes/Sql.php
-
message: "#^Parameter \\#1 \\$var of function count expects array\\|Countable, mixed given\\.$#"
count: 1
path: libraries/classes/Sql.php
-
message: "#^Parameter \\#2 \\$foreign_field of method PhpMyAdmin\\\\ConfigStorage\\\\Relation\\:\\:foreignDropdown\\(\\) expects string, mixed given\\.$#"
count: 1
@ -9327,7 +9147,7 @@ parameters:
-
message: "#^Method PhpMyAdmin\\\\Tests\\\\Display\\\\ResultsTest\\:\\:dataProviderForTestGetDataCellForNonNumericColumns\\(\\) return type has no value type specified in iterable type array\\.$#"
count: 4
count: 3
path: test/classes/Display/ResultsTest.php
-
@ -9350,11 +9170,6 @@ parameters:
count: 2
path: test/classes/Display/ResultsTest.php
-
message: "#^Method PhpMyAdmin\\\\Tests\\\\Display\\\\ResultsTest\\:\\:dataProviderForTestSetHighlightedColumnGlobalField\\(\\) return type has no value type specified in iterable type array\\.$#"
count: 1
path: test/classes/Display/ResultsTest.php
-
message: "#^Method PhpMyAdmin\\\\Tests\\\\Display\\\\ResultsTest\\:\\:dataProviderGetSortOrderHiddenInputs\\(\\) return type has no value type specified in iterable type array\\.$#"
count: 1
@ -9370,11 +9185,6 @@ parameters:
count: 1
path: test/classes/Display/ResultsTest.php
-
message: "#^Method PhpMyAdmin\\\\Tests\\\\Display\\\\ResultsTest\\:\\:testGetDataCellForNonNumericColumns\\(\\) has parameter \\$analyzed_sql_results with no value type specified in iterable type array\\.$#"
count: 1
path: test/classes/Display/ResultsTest.php
-
message: "#^Method PhpMyAdmin\\\\Tests\\\\Display\\\\ResultsTest\\:\\:testGetDataCellForNonNumericColumns\\(\\) has parameter \\$map with no value type specified in iterable type array\\.$#"
count: 1
@ -9450,16 +9260,6 @@ parameters:
count: 1
path: test/classes/Display/ResultsTest.php
-
message: "#^Method PhpMyAdmin\\\\Tests\\\\Display\\\\ResultsTest\\:\\:testSetHighlightedColumnGlobalField\\(\\) has parameter \\$analyzed_sql with no value type specified in iterable type array\\.$#"
count: 1
path: test/classes/Display/ResultsTest.php
-
message: "#^Method PhpMyAdmin\\\\Tests\\\\Display\\\\ResultsTest\\:\\:testSetHighlightedColumnGlobalField\\(\\) has parameter \\$output with no value type specified in iterable type array\\.$#"
count: 1
path: test/classes/Display/ResultsTest.php
-
message: "#^Parameter \\#1 \\$string of function htmlspecialchars_decode expects string, mixed given\\.$#"
count: 1
@ -10370,16 +10170,6 @@ parameters:
count: 1
path: test/classes/SqlTest.php
-
message: "#^Parameter \\#1 \\$analyzedSqlResults of method PhpMyAdmin\\\\Sql\\:\\:hasNoRightsToDropDatabase\\(\\) expects array, mixed given\\.$#"
count: 3
path: test/classes/SqlTest.php
-
message: "#^Parameter \\#1 \\$analyzedSqlResults of static method PhpMyAdmin\\\\Sql\\:\\:isJustBrowsing\\(\\) expects array\\<string, mixed\\>, mixed given\\.$#"
count: 3
path: test/classes/SqlTest.php
-
message: "#^Method PhpMyAdmin\\\\Tests\\\\StorageEngineTest\\:\\:providerGetEngine\\(\\) return type has no value type specified in iterable type array\\.$#"
count: 1

View File

@ -9,6 +9,7 @@ parameters:
bootstrapFiles:
- test/phpstan-constants.php
stubFiles:
- test/stubs/Query.stub
- test/stubs/uploadprogress.stub
excludePaths:
- examples/openid.php

View File

@ -2251,7 +2251,7 @@
<InvalidArrayOffset occurrences="1">
<code>$GLOBALS['cfg']['AllowUserDropDatabase']</code>
</InvalidArrayOffset>
<MixedArgument occurrences="19">
<MixedArgument occurrences="17">
<code>$GLOBALS['cfg']['AllowUserDropDatabase']</code>
<code>$GLOBALS['cfg']['MemoryLimit']</code>
<code>$GLOBALS['format']</code>
@ -2259,14 +2259,12 @@
<code>$GLOBALS['import_file']</code>
<code>$GLOBALS['import_notice']</code>
<code>$GLOBALS['local_import_file']</code>
<code>$GLOBALS['table']</code>
<code>$_POST['bkm_label']</code>
<code>$_POST['bkm_label']</code>
<code>$_POST['bookmark_variable']</code>
<code>$_POST['sql_query']</code>
<code>$_POST['sql_query']</code>
<code>$_SESSION['Import_message']['go_back_url']</code>
<code>$analyzed_sql_results</code>
<code>$die['error']</code>
<code>$die['sql']</code>
<code>$importHandle ?? null</code>
@ -2276,15 +2274,11 @@
<code>$GLOBALS['urlParams']</code>
<code>$parameter</code>
</MixedArgumentTypeCoercion>
<MixedArrayAccess occurrences="10">
<MixedArrayAccess occurrences="6">
<code>$_FILES['import_file']['name']</code>
<code>$_FILES['import_file']['name']</code>
<code>$_FILES['import_file']['tmp_name']</code>
<code>$_SESSION['Import_message']['go_back_url']</code>
<code>$analyzed_sql_results['offset']</code>
<code>$analyzed_sql_results['offset']</code>
<code>$analyzed_sql_results['reload']</code>
<code>$analyzed_sql_results['reload']</code>
<code>$die['error']</code>
<code>$die['sql']</code>
</MixedArrayAccess>
@ -2300,7 +2294,7 @@
<code>$_SESSION['Import_message']['message']</code>
<code>$_SESSION['Import_message']['message']</code>
</MixedArrayAssignment>
<MixedAssignment occurrences="42">
<MixedAssignment occurrences="36">
<code>$GLOBALS['MAX_FILE_SIZE']</code>
<code>$GLOBALS['active_page']</code>
<code>$GLOBALS['ajax_reload']</code>
@ -2323,12 +2317,8 @@
<code>$GLOBALS['msg']</code>
<code>$GLOBALS['my_die']</code>
<code>$GLOBALS['noplugin']</code>
<code>$GLOBALS['offset']</code>
<code>$GLOBALS['offset']</code>
<code>$GLOBALS['read_multiply']</code>
<code>$GLOBALS['reload']</code>
<code>$GLOBALS['reload']</code>
<code>$GLOBALS['reload']</code>
<code>$GLOBALS['reset_charset']</code>
<code>$GLOBALS['result']</code>
<code>$GLOBALS['run_query']</code>
@ -2336,8 +2326,6 @@
<code>$GLOBALS['skip_queries']</code>
<code>$GLOBALS['sql_file']</code>
<code>$GLOBALS['sql_query_disabled']</code>
<code>$GLOBALS['table']</code>
<code>$GLOBALS['table']</code>
<code>$GLOBALS['timeout_passed']</code>
<code>$GLOBALS['timestamp']</code>
<code>$GLOBALS['urlParams']['local_import_file']</code>
@ -3102,13 +3090,11 @@
<InvalidArrayOffset occurrences="1">
<code>$GLOBALS['cfg']['AllowUserDropDatabase']</code>
</InvalidArrayOffset>
<MixedArgument occurrences="20">
<MixedArgument occurrences="15">
<code>$GLOBALS['cfg']['AllowUserDropDatabase']</code>
<code>$GLOBALS['db']</code>
<code>$GLOBALS['db']</code>
<code>$GLOBALS['db']</code>
<code>$GLOBALS['db']</code>
<code>$GLOBALS['db']</code>
<code>$GLOBALS['disp_message'] ?? null</code>
<code>$GLOBALS['errorUrl']</code>
<code>$GLOBALS['errorUrl']</code>
@ -3117,19 +3103,16 @@
<code>$GLOBALS['message_to_show'] ?? null</code>
<code>$GLOBALS['sql_query']</code>
<code>$GLOBALS['sql_query']</code>
<code>$GLOBALS['table']</code>
<code>$GLOBALS['table']</code>
<code>$_GET['sql_query']</code>
<code>$_GET['sql_signature']</code>
<code>$_POST['bkm_fields']</code>
<code>$analyzed_sql_results</code>
</MixedArgument>
<MixedArrayAccess occurrences="3">
<code>$GLOBALS['ajax_reload']['reload']</code>
<code>$_POST['bkm_fields']['bkm_label']</code>
<code>$_POST['bkm_fields']['bkm_label']</code>
</MixedArrayAccess>
<MixedAssignment occurrences="18">
<MixedAssignment occurrences="17">
<code>$GLOBALS['ajax_reload']</code>
<code>$GLOBALS['back']</code>
<code>$GLOBALS['db']</code>
@ -3144,7 +3127,6 @@
<code>$GLOBALS['sql_query']</code>
<code>$GLOBALS['sql_query']</code>
<code>$GLOBALS['sql_query']</code>
<code>$GLOBALS['table']</code>
<code>$GLOBALS['table_from_sql']</code>
<code>$GLOBALS['unlim_num_rows']</code>
<code>$GLOBALS['unlim_num_rows']</code>
@ -3887,16 +3869,12 @@
</MixedAssignment>
</file>
<file src="libraries/classes/Controllers/Table/Structure/BrowseController.php">
<MixedArgument occurrences="2">
<code>$analyzed_sql_results ?? ''</code>
<MixedArgument occurrences="1">
<code>$sval</code>
</MixedArgument>
<MixedAssignment occurrences="1">
<code>$sval</code>
</MixedAssignment>
<PossiblyInvalidArgument occurrences="1">
<code>$analyzed_sql_results ?? ''</code>
</PossiblyInvalidArgument>
</file>
<file src="libraries/classes/Controllers/Table/Structure/CentralColumnsAddController.php">
<MixedArgument occurrences="1">
@ -4274,7 +4252,7 @@
</MixedAssignment>
</file>
<file src="libraries/classes/Controllers/Table/ZoomSearchController.php">
<MixedArgument occurrences="21">
<MixedArgument occurrences="20">
<code>$_POST['db']</code>
<code>$_POST['table']</code>
<code>$_POST['where_clause']</code>
@ -4285,7 +4263,6 @@
<code>$dataLabel</code>
<code>$dataLabel</code>
<code>$foreignData['foreign_field']</code>
<code>$foreignData['foreign_field']</code>
<code>$properties['type']</code>
<code>$selected_operator</code>
<code>$this-&gt;columnNames[$column_index]</code>
@ -5094,8 +5071,7 @@
</PossiblyNullReference>
</file>
<file src="libraries/classes/Database/MultiTableQuery.php">
<MixedArgument occurrences="3">
<code>$db</code>
<MixedArgument occurrences="2">
<code>$table</code>
<code>$table</code>
</MixedArgument>
@ -5995,19 +5971,15 @@
<InvalidArrayOffset occurrences="1">
<code>$delUrlParams</code>
</InvalidArrayOffset>
<MixedArgument occurrences="49">
<InvalidIterator occurrences="2">
<code>$statementInfo-&gt;statement-&gt;expr</code>
<code>$statementInfo-&gt;statement-&gt;where</code>
</InvalidIterator>
<MixedArgument occurrences="42">
<code>$_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['pos'] / $_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['query']</code>
<code>$_SESSION['tmpval']['query']</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['select_tables']</code>
<code>$analyzedSqlResults['statement']</code>
<code>$analyzedSqlResults['statement']</code>
<code>$analyzedSqlResults['statement']</code>
<code>$analyzedSqlResults['statement']-&gt;from</code>
<code>$clause</code>
<code>$clauseIsUnique</code>
<code>$clauseIsUnique</code>
@ -6037,6 +6009,7 @@
<code>$sortExpressionNoDirection[$indexInExpression]</code>
<code>$sortExpressionNoDirection[$indexInExpression]</code>
<code>$sqlQuery</code>
<code>$statementInfo-&gt;statement-&gt;from</code>
<code>$total</code>
<code>$urlParams['where_clause']</code>
<code>$whereClause</code>
@ -6046,15 +6019,14 @@
<code>(int) $this-&gt;properties['unlim_num_rows'] / $_SESSION['tmpval']['max_rows']</code>
<code>empty($field-&gt;database) ? $this-&gt;properties['db'] : $field-&gt;database</code>
</MixedArgument>
<MixedArgumentTypeCoercion occurrences="6">
<code>$analyzedSqlResults</code>
<MixedArgumentTypeCoercion occurrences="5">
<code>$linkingUrlParams</code>
<code>$row</code>
<code>$sortDirection</code>
<code>$sortExpression</code>
<code>$urlParams</code>
</MixedArgumentTypeCoercion>
<MixedArrayAccess occurrences="65">
<MixedArrayAccess occurrences="62">
<code>$_SESSION['tmpval']['display_binary']</code>
<code>$_SESSION['tmpval']['display_binary']</code>
<code>$_SESSION['tmpval']['display_binary']</code>
@ -6078,7 +6050,6 @@
<code>$_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['pftext']</code>
<code>$_SESSION['tmpval']['pftext']</code>
<code>$_SESSION['tmpval']['pftext']</code>
@ -6088,8 +6059,6 @@
<code>$_SESSION['tmpval']['pos']</code>
<code>$_SESSION['tmpval']['pos']</code>
<code>$_SESSION['tmpval']['pos']</code>
<code>$_SESSION['tmpval']['pos']</code>
<code>$_SESSION['tmpval']['pos']</code>
<code>$_SESSION['tmpval']['possible_as_geometry']</code>
<code>$_SESSION['tmpval']['query']</code>
<code>$_SESSION['tmpval']['query']</code>
@ -6196,7 +6165,7 @@
<code>$row[$sortedColumnIndex]</code>
<code>$row[$sortedColumnIndex]</code>
</MixedArrayTypeCoercion>
<MixedAssignment occurrences="53">
<MixedAssignment occurrences="47">
<code>$GLOBALS['row']</code>
<code>$GLOBALS['theme']</code>
<code>$_SESSION['tmpval']['geoOption']</code>
@ -6214,16 +6183,11 @@
<code>$expr</code>
<code>$field</code>
<code>$file</code>
<code>$firstShownRec</code>
<code>$firstShownRec</code>
<code>$firstShownRec</code>
<code>$hiddenFields['session_max_rows']</code>
<code>$i</code>
<code>$i</code>
<code>$identifier</code>
<code>$index</code>
<code>$lastShownRec</code>
<code>$lastShownRec</code>
<code>$linkingUrlParams[$new_param['param_info']]</code>
<code>$m</code>
<code>$meta-&gt;name</code>
@ -6238,7 +6202,6 @@
<code>$query['relational_display']</code>
<code>$rel</code>
<code>$relationalDisplay</code>
<code>$rowCount</code>
<code>$rowInfo[mb_strtolower($fieldsMeta[$m]-&gt;orgname)]</code>
<code>$sessionMaxRows</code>
<code>$sessionMaxRows</code>
@ -6251,11 +6214,14 @@
<code>$whereClauseMap[$rowNumber][$meta-&gt;orgtable]</code>
<code>$whereClauseMap[$rowNumber][$this-&gt;properties['table']]</code>
</MixedAssignment>
<MixedInferredReturnType occurrences="1">
<code>Message</code>
</MixedInferredReturnType>
<MixedMethodCall occurrences="2">
<code>new $className()</code>
<code>new $this-&gt;transformationInfo[$dbLower][$tblLower][$nameLower][1]()</code>
</MixedMethodCall>
<MixedOperand occurrences="13">
<MixedOperand occurrences="11">
<code>$_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['pos']</code>
@ -6266,27 +6232,17 @@
<code>$displaySize[0]</code>
<code>$displaySize[1]</code>
<code>$file</code>
<code>$firstShownRec</code>
<code>$firstShownRec</code>
<code>$sortExpressionNoDirection[$indexInExpression]</code>
</MixedOperand>
<MixedPropertyFetch occurrences="16">
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['statement']-&gt;expr</code>
<code>$analyzedSqlResults['statement']-&gt;from</code>
<code>$analyzedSqlResults['statement']-&gt;from</code>
<code>$analyzedSqlResults['statement']-&gt;from[0]-&gt;table</code>
<code>$analyzedSqlResults['statement']-&gt;limit</code>
<code>$analyzedSqlResults['statement']-&gt;limit-&gt;offset</code>
<code>$analyzedSqlResults['statement']-&gt;limit-&gt;rowCount</code>
<code>$analyzedSqlResults['statement']-&gt;where</code>
<MixedPropertyFetch occurrences="8">
<code>$expr-&gt;alias</code>
<code>$expr-&gt;column</code>
<code>$expr-&gt;column</code>
<code>$expr-&gt;identifiers</code>
<code>$field-&gt;database</code>
<code>$field-&gt;table</code>
<code>$statementInfo-&gt;statement-&gt;from[0]-&gt;table</code>
<code>$statementInfo-&gt;statement-&gt;limit-&gt;offset</code>
</MixedPropertyFetch>
<MixedReturnTypeCoercion occurrences="6">
<code>$map</code>
@ -6325,10 +6281,20 @@
<code>(string) $fieldsMeta[$i]-&gt;name</code>
<code>(string) $fieldsMeta[$i]-&gt;name</code>
</RedundantCastGivenDocblockType>
<RedundantCondition occurrences="1">
<code>empty($statementInfo-&gt;statement-&gt;from)</code>
</RedundantCondition>
<RedundantConditionGivenDocblockType occurrences="2">
<code>$firstStatement-&gt;order</code>
<code>isset($meta-&gt;internalMediaType)</code>
</RedundantConditionGivenDocblockType>
<UnusedParam occurrences="5">
<code>$afterCount</code>
<code>$posNext</code>
<code>$preCount</code>
<code>$sortedColumnMessage</code>
<code>$total</code>
</UnusedParam>
</file>
<file src="libraries/classes/Encoding.php">
<DocblockTypeContradiction occurrences="3">
@ -7647,23 +7613,12 @@
<code>$server['ssl']</code>
<code>$server['ssl_verify']</code>
</InvalidArrayOffset>
<MixedArgument occurrences="19">
<MixedArgument occurrences="8">
<code>$GLOBALS['special_message']</code>
<code>$GLOBALS['special_message']</code>
<code>$alt</code>
<code>$defaultFunction</code>
<code>$field['True_Type']</code>
<code>$queryBase</code>
<code>$queryBase</code>
<code>$queryBase</code>
<code>$sqlQuery</code>
<code>$sqlQuery</code>
<code>$sqlQuery</code>
<code>$sqlQuery</code>
<code>$sqlQuery</code>
<code>$sqlQuery</code>
<code>$sqlQuery</code>
<code>$sqlQuery</code>
<code>$subvalue</code>
<code>$title</code>
<code>$value</code>
@ -7683,17 +7638,14 @@
<code>$_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['pos']</code>
</MixedArrayAssignment>
<MixedAssignment occurrences="12">
<MixedAssignment occurrences="9">
<code>$GLOBALS['data']</code>
<code>$alt</code>
<code>$defaultFunction</code>
<code>$defaultFunction</code>
<code>$defaultFunction</code>
<code>$queryBase</code>
<code>$sqlQuery</code>
<code>$subvalue</code>
<code>$title</code>
<code>$urlParams['sql_query']</code>
<code>$value</code>
<code>$value</code>
</MixedAssignment>
@ -7703,10 +7655,9 @@
<MixedMethodCall occurrences="1">
<code>getDisplay</code>
</MixedMethodCall>
<MixedOperand occurrences="4">
<MixedOperand occurrences="3">
<code>$GLOBALS['using_bookmark_message']-&gt;getDisplay()</code>
<code>$attributes['class']</code>
<code>$sqlQuery</code>
<code>$value</code>
</MixedOperand>
<MixedReturnStatement occurrences="1">
@ -9070,20 +9021,6 @@
<code>$content</code>
</PropertyNotSetInConstructor>
</file>
<file src="libraries/classes/ParseAnalyze.php">
<MixedArgument occurrences="2">
<code>$analyzedSqlResults['select_tables']</code>
<code>$db</code>
</MixedArgument>
<MixedArrayAccess occurrences="2">
<code>$analyzedSqlResults['select_tables'][0]</code>
<code>$analyzedSqlResults['select_tables'][0]</code>
</MixedArrayAccess>
<MixedAssignment occurrences="2">
<code>$db</code>
<code>$table</code>
</MixedAssignment>
</file>
<file src="libraries/classes/Partitioning/Maintenance.php">
<MixedArrayAccess occurrences="4">
<code>$row['Table']</code>
@ -13034,41 +12971,12 @@
<LessSpecificReturnStatement occurrences="1">
<code>$unlimNumRows</code>
</LessSpecificReturnStatement>
<MixedArgument occurrences="47">
<MixedArgument occurrences="15">
<code>$_POST[$requestIndex]</code>
<code>$_POST['bkm_label']</code>
<code>$_POST['dropped_column'] ?? null</code>
<code>$_POST['table_create_time'] ?? null</code>
<code>$analyzedSqlResults</code>
<code>$analyzedSqlResults['is_affected']</code>
<code>$analyzedSqlResults['is_analyse']</code>
<code>$analyzedSqlResults['is_analyse']</code>
<code>$analyzedSqlResults['is_count']</code>
<code>$analyzedSqlResults['is_count']</code>
<code>$analyzedSqlResults['is_explain']</code>
<code>$analyzedSqlResults['is_explain']</code>
<code>$analyzedSqlResults['is_export']</code>
<code>$analyzedSqlResults['is_export']</code>
<code>$analyzedSqlResults['is_func']</code>
<code>$analyzedSqlResults['is_func']</code>
<code>$analyzedSqlResults['is_maint']</code>
<code>$analyzedSqlResults['is_maint']</code>
<code>$analyzedSqlResults['is_show']</code>
<code>$analyzedSqlResults['is_show']</code>
<code>$analyzedSqlResults['parser']-&gt;errors</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['select_expr']</code>
<code>$analyzedSqlResults['select_tables']</code>
<code>$analyzedSqlResults['select_tables']</code>
<code>$analyzedSqlResults['select_tables']</code>
<code>$analyzedSqlResults['statement']</code>
<code>$analyzedSqlResults['statement']</code>
<code>$analyzedSqlResults['statement']</code>
<code>$analyzedSqlResults['statement']-&gt;where</code>
<code>$columns[$indexColumnName]['Extra']</code>
<code>$db</code>
<code>$extraData['error']</code>
<code>$fieldInfoResult[0]['Type']</code>
<code>$foreignData['foreign_field']</code>
@ -13076,19 +12984,15 @@
<code>$oneResult['Duration']</code>
<code>$oneResult['Status']</code>
<code>$sortCol</code>
<code>$statement</code>
<code>$table</code>
<code>$tokenList</code>
<code>$unlimNumRows</code>
<code>$unlimNumRows</code>
<code>Message::sanitize($warning)</code>
</MixedArgument>
<MixedArgumentTypeCoercion occurrences="3">
<code>$analyzedSqlResults</code>
<MixedArgumentTypeCoercion occurrences="2">
<code>$showTable</code>
<code>$showTable</code>
</MixedArgumentTypeCoercion>
<MixedArrayAccess occurrences="17">
<MixedArrayAccess occurrences="16">
<code>$_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['max_rows']</code>
<code>$_SESSION['tmpval']['max_rows']</code>
@ -13096,8 +13000,6 @@
<code>$_SESSION['tmpval']['pos']</code>
<code>$_SESSION['tmpval']['pos']</code>
<code>$_SESSION['tmpval']['pos']</code>
<code>$analyzedSqlResults['select_expr'][0]</code>
<code>$analyzedSqlResults['statement']-&gt;where[0]</code>
<code>$fieldInfoResult[0]['Type']</code>
<code>$oneResult['Duration']</code>
<code>$oneResult['Duration']</code>
@ -13106,6 +13008,7 @@
<code>$oneResult['Duration']</code>
<code>$oneResult['Duration']</code>
<code>$oneResult['Status']</code>
<code>$statementInfo-&gt;statement-&gt;where[0]</code>
</MixedArrayAccess>
<MixedArrayAssignment occurrences="2">
<code>$_SESSION['tmpval']['pos']</code>
@ -13114,7 +13017,7 @@
<MixedArrayTypeCoercion occurrences="1">
<code>$columns[$indexColumnName]</code>
</MixedArrayTypeCoercion>
<MixedAssignment occurrences="21">
<MixedAssignment occurrences="16">
<code>$maxRows</code>
<code>$oneFieldMeta</code>
<code>$oneMeta</code>
@ -13126,11 +13029,6 @@
<code>$profiling['total_time']</code>
<code>$resultSetColumnNames[]</code>
<code>$sortCol</code>
<code>$statement</code>
<code>$statement</code>
<code>$statement</code>
<code>$table</code>
<code>$tokenList</code>
<code>$unlimNumRows</code>
<code>$unlimNumRows</code>
<code>$unlimNumRows</code>
@ -13153,16 +13051,10 @@
<code>$oneResult['Duration']</code>
<code>$profiling['chart'][$status]</code>
</MixedOperand>
<MixedPropertyFetch occurrences="9">
<code>$analyzedSqlResults['parser']-&gt;errors</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['parser']-&gt;list</code>
<code>$analyzedSqlResults['statement']-&gt;where</code>
<code>$analyzedSqlResults['statement']-&gt;where[0]-&gt;expr</code>
<MixedPropertyFetch occurrences="3">
<code>$oneFieldMeta-&gt;table</code>
<code>$oneMeta-&gt;name</code>
<code>$statementInfo-&gt;statement-&gt;where[0]-&gt;expr</code>
</MixedPropertyFetch>
<MixedReturnStatement occurrences="4">
<code>$pos</code>
@ -15146,42 +15038,10 @@
</MixedInferredReturnType>
</file>
<file src="test/classes/Display/ResultsTest.php">
<MixedArgument occurrences="20">
<code>$analyzedSqlResults</code>
<code>$analyzedSqlResults</code>
<code>$analyzedSqlResults['is_analyse']</code>
<code>$analyzedSqlResults['is_analyse']</code>
<code>$analyzedSqlResults['is_count']</code>
<code>$analyzedSqlResults['is_count']</code>
<code>$analyzedSqlResults['is_explain']</code>
<code>$analyzedSqlResults['is_explain']</code>
<code>$analyzedSqlResults['is_export']</code>
<code>$analyzedSqlResults['is_export']</code>
<code>$analyzedSqlResults['is_func']</code>
<code>$analyzedSqlResults['is_func']</code>
<code>$analyzedSqlResults['is_maint']</code>
<code>$analyzedSqlResults['is_maint']</code>
<code>$analyzedSqlResults['is_show']</code>
<code>$analyzedSqlResults['is_show']</code>
<MixedArgument occurrences="4">
<code>$output</code>
<code>$output</code>
</MixedArgument>
<MixedArrayAccess occurrences="14">
<code>$analyzedSqlResults['is_analyse']</code>
<code>$analyzedSqlResults['is_analyse']</code>
<code>$analyzedSqlResults['is_count']</code>
<code>$analyzedSqlResults['is_count']</code>
<code>$analyzedSqlResults['is_explain']</code>
<code>$analyzedSqlResults['is_explain']</code>
<code>$analyzedSqlResults['is_export']</code>
<code>$analyzedSqlResults['is_export']</code>
<code>$analyzedSqlResults['is_func']</code>
<code>$analyzedSqlResults['is_func']</code>
<code>$analyzedSqlResults['is_maint']</code>
<code>$analyzedSqlResults['is_maint']</code>
<code>$analyzedSqlResults['is_show']</code>
<code>$analyzedSqlResults['is_show']</code>
</MixedArrayAccess>
<MixedArrayAssignment occurrences="10">
<code>$_SESSION['tmpval']['display_binary']</code>
<code>$_SESSION['tmpval']['display_binary']</code>
@ -15200,8 +15060,7 @@
<code>$output</code>
<code>$output</code>
</MixedAssignment>
<MixedInferredReturnType occurrences="6">
<code>array</code>
<MixedInferredReturnType occurrences="5">
<code>array</code>
<code>array</code>
<code>array</code>
@ -16149,18 +16008,6 @@
</MixedArrayAccess>
</file>
<file src="test/classes/SqlTest.php">
<MixedArgument occurrences="6">
<code>$this-&gt;parseAndAnalyze('DROP DATABASE db')</code>
<code>$this-&gt;parseAndAnalyze('DROP TABLE tbl')</code>
<code>$this-&gt;parseAndAnalyze('SELECT * FROM db.tbl')</code>
<code>$this-&gt;parseAndAnalyze('SELECT * FROM tbl WHERE 1')</code>
<code>$this-&gt;parseAndAnalyze('SELECT * from tbl')</code>
<code>$this-&gt;parseAndAnalyze('SELECT * from tbl1, tbl2 LIMIT 0, 10')</code>
</MixedArgument>
<MixedAssignment occurrences="2">
<code>$analyzed_sql_results</code>
<code>$analyzed_sql_results</code>
</MixedAssignment>
<MixedInferredReturnType occurrences="1">
<code>array</code>
</MixedInferredReturnType>

View File

@ -26,6 +26,7 @@
</projectFiles>
<stubs>
<file name="test/stubs/Query.stub"/>
<file name="test/stubs/uploadprogress.stub"/>
</stubs>
@ -305,6 +306,7 @@
text_dir: string,
token_mismatch: bool,
token_provided: bool,
unparsed_sql?: string,
urlParams: array,
username: string,
xml_export_triggers: bool,

View File

@ -15,8 +15,8 @@ use PhpMyAdmin\ParseAnalyze;
use PhpMyAdmin\Plugins\Transformations\Output\Text_Plain_External;
use PhpMyAdmin\Plugins\Transformations\Text_Plain_Link;
use PhpMyAdmin\Plugins\TransformationsPlugin;
use PhpMyAdmin\SqlParser\Parser;
use PhpMyAdmin\SqlParser\Utils\Query;
use PhpMyAdmin\StatementInfo;
use PhpMyAdmin\Template;
use PhpMyAdmin\Tests\AbstractTestCase;
use PhpMyAdmin\Transformations;
@ -82,18 +82,12 @@ class ResultsTest extends AbstractTestCase
*/
public function testisSelect(): void
{
$parser = new Parser('SELECT * FROM pma');
$this->assertTrue(
$this->callFunction(
$this->object,
DisplayResults::class,
'isSelect',
[
[
'statement' => $parser->statements[0],
'select_from' => true,
],
]
[StatementInfo::fromArray(Query::getAll('SELECT * FROM pma'))]
)
);
}
@ -368,45 +362,21 @@ class ResultsTest extends AbstractTestCase
);
}
/**
* Data provider for testSetHighlightedColumnGlobalField
*
* @return array parameters and output
*/
public function dataProviderForTestSetHighlightedColumnGlobalField(): array
{
$parser = new Parser('SELECT * FROM db_name WHERE `db_name`.`tbl`.id > 0 AND `id` < 10');
return [
[
['statement' => $parser->statements[0]],
[
'db_name' => 'true',
'tbl' => 'true',
'id' => 'true',
],
],
];
}
/**
* Test setHighlightedColumnGlobalField
*
* @param array $analyzed_sql the analyzed query
* @param array $output setting value of setHighlightedColumnGlobalField
*
* @dataProvider dataProviderForTestSetHighlightedColumnGlobalField
*/
public function testSetHighlightedColumnGlobalField(array $analyzed_sql, array $output): void
public function testSetHighlightedColumnGlobalField(): void
{
$query = 'SELECT * FROM db_name WHERE `db_name`.`tbl`.id > 0 AND `id` < 10';
$this->callFunction(
$this->object,
DisplayResults::class,
'setHighlightedColumnGlobalField',
[$analyzed_sql]
[StatementInfo::fromArray(Query::getAll($query))]
);
$this->assertEquals($output, $this->object->properties['highlight_columns']);
$this->assertEquals([
'db_name' => 'true',
'tbl' => 'true',
'id' => 'true',
], $this->object->properties['highlight_columns']);
}
/**
@ -633,7 +603,6 @@ class ResultsTest extends AbstractTestCase
* bool,
* TransformationsPlugin|null,
* array,
* array,
* string
* }}
*/
@ -684,7 +653,6 @@ class ResultsTest extends AbstractTestCase
false,
null,
['https://www.example.com/'],
[],
'class="disableAjax">[BLOB - 4 B]</a>'
. '</td>' . "\n",
],
@ -698,7 +666,6 @@ class ResultsTest extends AbstractTestCase
false,
$transformation_plugin,
[],
[],
'<td class="text-start grid_edit transformed hex">'
. '1001'
. '</td>' . "\n",
@ -713,7 +680,6 @@ class ResultsTest extends AbstractTestCase
false,
$transformation_plugin,
[],
[],
'<td data-decimals="0"' . "\n"
. ' data-type="string"' . "\n"
. ' class="grid_edit null">' . "\n"
@ -730,7 +696,6 @@ class ResultsTest extends AbstractTestCase
false,
null,
[],
[],
'<td data-decimals="0" data-type="string" '
. 'data-originallength="11" '
. 'class="grid_edit pre_wrap">foo bar baz</td>' . "\n",
@ -745,7 +710,6 @@ class ResultsTest extends AbstractTestCase
false,
$transformation_plugin_external,
[],
[],
'<td data-decimals="0" data-type="string" '
. 'data-originallength="11" '
. 'class="grid_edit text-nowrap transformed">foo bar baz</td>' . "\n",
@ -760,7 +724,6 @@ class ResultsTest extends AbstractTestCase
false,
null,
[],
[],
'<td data-decimals="0" data-type="datetime" '
. 'data-originallength="19" '
. 'class="grid_edit text-nowrap">2020-09-20 16:35:00</td>' . "\n",
@ -769,16 +732,15 @@ class ResultsTest extends AbstractTestCase
}
/**
* @param string $protectBinary all|blob|noblob|no
* @param string|null $column the relevant column in data row
* @param string $class the html class for column
* @param object $meta the meta-information about the field
* @param array $map the list of relations
* @param array $_url_params the parameters for generate url
* @param bool $condition_field the column should highlighted or not
* @param array $transform_options the transformation parameters
* @param array $analyzed_sql_results the analyzed query
* @param string $output the output of this function
* @param string $protectBinary all|blob|noblob|no
* @param string|null $column the relevant column in data row
* @param string $class the html class for column
* @param object $meta the meta-information about the field
* @param array $map the list of relations
* @param array $_url_params the parameters for generate url
* @param bool $condition_field the column should highlighted or not
* @param array $transform_options the transformation parameters
* @param string $output the output of this function
*
* @dataProvider dataProviderForTestGetDataCellForNonNumericColumns
*/
@ -792,7 +754,6 @@ class ResultsTest extends AbstractTestCase
bool $condition_field,
?TransformationsPlugin $transformation_plugin,
array $transform_options,
array $analyzed_sql_results,
string $output
): void {
$_SESSION['tmpval']['display_binary'] = true;
@ -800,6 +761,7 @@ class ResultsTest extends AbstractTestCase
$_SESSION['tmpval']['relational_display'] = false;
$GLOBALS['cfg']['LimitChars'] = 50;
$GLOBALS['cfg']['ProtectBinary'] = $protectBinary;
$statementInfo = $this->createStub(StatementInfo::class);
$this->assertStringContainsString(
$output,
$this->callFunction(
@ -815,7 +777,7 @@ class ResultsTest extends AbstractTestCase
$condition_field,
$transformation_plugin,
$transform_options,
$analyzed_sql_results,
$statementInfo,
]
)
);
@ -906,7 +868,7 @@ class ResultsTest extends AbstractTestCase
'disabled',
false,
$query,
Query::getAll($query),
StatementInfo::fromArray(Query::getAll($query)),
]
);
@ -1319,7 +1281,7 @@ class ResultsTest extends AbstractTestCase
$object = new DisplayResults($this->dbi, $GLOBALS['db'], $GLOBALS['table'], 1, '', $query);
$object->properties['unique_id'] = 1234567890;
[$analyzedSqlResults] = ParseAnalyze::sqlQuery($query, $GLOBALS['db']);
[$statementInfo] = ParseAnalyze::sqlQuery($query, $GLOBALS['db']);
$fieldsMeta = [
new FieldMetadata(
MYSQLI_TYPE_DECIMAL,
@ -1333,17 +1295,17 @@ class ResultsTest extends AbstractTestCase
$object->setProperties(
3,
$fieldsMeta,
$analyzedSqlResults['is_count'],
$analyzedSqlResults['is_export'],
$analyzedSqlResults['is_func'],
$analyzedSqlResults['is_analyse'],
$statementInfo->isCount,
$statementInfo->isExport,
$statementInfo->isFunction,
$statementInfo->isAnalyse,
3,
count($fieldsMeta),
1.234,
'ltr',
$analyzedSqlResults['is_maint'],
$analyzedSqlResults['is_explain'],
$analyzedSqlResults['is_show'],
$statementInfo->isMaint,
$statementInfo->isExplain,
$statementInfo->isShow,
null,
null,
true,
@ -1376,7 +1338,7 @@ class ResultsTest extends AbstractTestCase
]);
$this->assertNotFalse($dtResult);
$actual = $object->getTable($dtResult, $displayParts, $analyzedSqlResults);
$actual = $object->getTable($dtResult, $displayParts, $statementInfo);
$template = new Template();
@ -1599,7 +1561,7 @@ class ResultsTest extends AbstractTestCase
$object = new DisplayResults($dbi, $GLOBALS['db'], $GLOBALS['table'], 1, '', $query);
$object->properties['unique_id'] = 1234567890;
[$analyzedSqlResults] = ParseAnalyze::sqlQuery($query, $GLOBALS['db']);
[$statementInfo] = ParseAnalyze::sqlQuery($query, $GLOBALS['db']);
$fieldsMeta = [
new FieldMetadata(
MYSQLI_TYPE_LONG,
@ -1614,17 +1576,17 @@ class ResultsTest extends AbstractTestCase
$object->setProperties(
2,
$fieldsMeta,
$analyzedSqlResults['is_count'],
$analyzedSqlResults['is_export'],
$analyzedSqlResults['is_func'],
$analyzedSqlResults['is_analyse'],
$statementInfo->isCount,
$statementInfo->isExport,
$statementInfo->isFunction,
$statementInfo->isAnalyse,
2,
count($fieldsMeta),
1.234,
'ltr',
$analyzedSqlResults['is_maint'],
$analyzedSqlResults['is_explain'],
$analyzedSqlResults['is_show'],
$statementInfo->isMaint,
$statementInfo->isExplain,
$statementInfo->isShow,
null,
null,
true,
@ -1657,7 +1619,7 @@ class ResultsTest extends AbstractTestCase
]);
$this->assertNotFalse($dtResult);
$actual = $object->getTable($dtResult, $displayParts, $analyzedSqlResults);
$actual = $object->getTable($dtResult, $displayParts, $statementInfo);
$template = new Template();

View File

@ -0,0 +1,59 @@
<?php
declare(strict_types=1);
namespace PhpMyAdmin\Tests;
use PhpMyAdmin\ParseAnalyze;
use PhpMyAdmin\ResponseRenderer;
use PhpMyAdmin\StatementInfo;
/**
* @covers \PhpMyAdmin\ParseAnalyze
*/
class ParseAnalyzeTest extends AbstractTestCase
{
public function testSqlQuery(): void
{
$GLOBALS['lang'] = 'en';
ResponseRenderer::getInstance()->setAjax(false);
$GLOBALS['unparsed_sql'] = '';
$actual = ParseAnalyze::sqlQuery('SELECT * FROM `sakila`.`actor`', 'sakila_test');
/** @psalm-suppress TypeDoesNotContainType */
$this->assertSame('SELECT * FROM `sakila`.`actor`', $GLOBALS['unparsed_sql']);
$this->assertCount(3, $actual);
$this->assertInstanceOf(StatementInfo::class, $actual[0]);
$this->assertSame('sakila', $actual[1]);
$this->assertSame('actor', $actual[2]);
$this->assertTrue($actual[0]->reload);
$this->assertNotEmpty($actual[0]->selectTables);
$this->assertSame([['actor', 'sakila']], $actual[0]->selectTables);
$this->assertNotEmpty($actual[0]->selectExpression);
$this->assertSame(['*'], $actual[0]->selectExpression);
}
public function testSqlQuery2(): void
{
$GLOBALS['lang'] = 'en';
ResponseRenderer::getInstance()->setAjax(false);
$GLOBALS['unparsed_sql'] = '';
$actual = ParseAnalyze::sqlQuery('SELECT `first_name`, `title` FROM `actor`, `film`', 'sakila');
/** @psalm-suppress TypeDoesNotContainType */
$this->assertSame('SELECT `first_name`, `title` FROM `actor`, `film`', $GLOBALS['unparsed_sql']);
$this->assertCount(3, $actual);
$this->assertInstanceOf(StatementInfo::class, $actual[0]);
$this->assertSame('sakila', $actual[1]);
$this->assertSame('', $actual[2]);
$this->assertFalse($actual[0]->reload);
$this->assertNotEmpty($actual[0]->selectTables);
$this->assertSame([['actor', null], ['film', null]], $actual[0]->selectTables);
$this->assertNotEmpty($actual[0]->selectExpression);
$this->assertSame(['`first_name`', '`title`'], $actual[0]->selectExpression);
}
}

View File

@ -72,11 +72,12 @@ class SqlTest extends AbstractTestCase
$GLOBALS['_SESSION']['tmpval']['pos'] = 1;
$GLOBALS['_SESSION']['tmpval']['max_rows'] = 2;
$analyzed_sql_results = $this->parseAndAnalyze('SELECT * FROM test LIMIT 0, 10');
$this->assertEquals(
'SELECT * FROM test LIMIT 1, 2 ',
$this->callFunction($this->sql, Sql::class, 'getSqlWithLimitClause', [&$analyzed_sql_results])
);
$this->assertEquals('SELECT * FROM test LIMIT 1, 2 ', $this->callFunction(
$this->sql,
Sql::class,
'getSqlWithLimitClause',
[ParseAnalyze::sqlQuery('SELECT * FROM test LIMIT 0, 10', $GLOBALS['db'])[0]]
));
}
/**
@ -89,31 +90,31 @@ class SqlTest extends AbstractTestCase
$this->assertTrue(
$this->callFunction($this->sql, Sql::class, 'isRememberSortingOrder', [
$this->parseAndAnalyze('SELECT * FROM tbl'),
ParseAnalyze::sqlQuery('SELECT * FROM tbl', $GLOBALS['db'])[0],
])
);
$this->assertFalse(
$this->callFunction($this->sql, Sql::class, 'isRememberSortingOrder', [
$this->parseAndAnalyze('SELECT col FROM tbl'),
ParseAnalyze::sqlQuery('SELECT col FROM tbl', $GLOBALS['db'])[0],
])
);
$this->assertFalse(
$this->callFunction($this->sql, Sql::class, 'isRememberSortingOrder', [
$this->parseAndAnalyze('SELECT 1'),
ParseAnalyze::sqlQuery('SELECT 1', $GLOBALS['db'])[0],
])
);
$this->assertFalse(
$this->callFunction($this->sql, Sql::class, 'isRememberSortingOrder', [
$this->parseAndAnalyze('SELECT col1, col2 FROM tbl'),
ParseAnalyze::sqlQuery('SELECT col1, col2 FROM tbl', $GLOBALS['db'])[0],
])
);
$this->assertFalse(
$this->callFunction($this->sql, Sql::class, 'isRememberSortingOrder', [
$this->parseAndAnalyze('SELECT COUNT(*) from tbl'),
ParseAnalyze::sqlQuery('SELECT COUNT(*) from tbl', $GLOBALS['db'])[0],
])
);
}
@ -128,13 +129,13 @@ class SqlTest extends AbstractTestCase
$this->assertTrue(
$this->callFunction($this->sql, Sql::class, 'isAppendLimitClause', [
$this->parseAndAnalyze('SELECT * FROM tbl'),
ParseAnalyze::sqlQuery('SELECT * FROM tbl', $GLOBALS['db'])[0],
])
);
$this->assertFalse(
$this->callFunction($this->sql, Sql::class, 'isAppendLimitClause', [
$this->parseAndAnalyze('SELECT * from tbl LIMIT 0, 10'),
ParseAnalyze::sqlQuery('SELECT * from tbl LIMIT 0, 10', $GLOBALS['db'])[0],
])
);
}
@ -145,17 +146,17 @@ class SqlTest extends AbstractTestCase
$GLOBALS['_SESSION']['tmpval']['max_rows'] = 10;
$this->assertTrue(Sql::isJustBrowsing(
$this->parseAndAnalyze('SELECT * FROM db.tbl'),
ParseAnalyze::sqlQuery('SELECT * FROM db.tbl', $GLOBALS['db'])[0],
null
));
$this->assertTrue(Sql::isJustBrowsing(
$this->parseAndAnalyze('SELECT * FROM tbl WHERE 1'),
ParseAnalyze::sqlQuery('SELECT * FROM tbl WHERE 1', $GLOBALS['db'])[0],
null
));
$this->assertFalse(Sql::isJustBrowsing(
$this->parseAndAnalyze('SELECT * from tbl1, tbl2 LIMIT 0, 10'),
ParseAnalyze::sqlQuery('SELECT * from tbl1, tbl2 LIMIT 0, 10', $GLOBALS['db'])[0],
null
));
}
@ -167,19 +168,19 @@ class SqlTest extends AbstractTestCase
{
$this->assertTrue(
$this->callFunction($this->sql, Sql::class, 'isDeleteTransformationInfo', [
$this->parseAndAnalyze('ALTER TABLE tbl DROP COLUMN col'),
ParseAnalyze::sqlQuery('ALTER TABLE tbl DROP COLUMN col', $GLOBALS['db'])[0],
])
);
$this->assertTrue(
$this->callFunction($this->sql, Sql::class, 'isDeleteTransformationInfo', [
$this->parseAndAnalyze('DROP TABLE tbl'),
ParseAnalyze::sqlQuery('DROP TABLE tbl', $GLOBALS['db'])[0],
])
);
$this->assertFalse(
$this->callFunction($this->sql, Sql::class, 'isDeleteTransformationInfo', [
$this->parseAndAnalyze('SELECT * from tbl'),
ParseAnalyze::sqlQuery('SELECT * from tbl', $GLOBALS['db'])[0],
])
);
}
@ -191,7 +192,7 @@ class SqlTest extends AbstractTestCase
{
$this->assertTrue(
$this->sql->hasNoRightsToDropDatabase(
$this->parseAndAnalyze('DROP DATABASE db'),
ParseAnalyze::sqlQuery('DROP DATABASE db', $GLOBALS['db'])[0],
false,
false
)
@ -199,7 +200,7 @@ class SqlTest extends AbstractTestCase
$this->assertFalse(
$this->sql->hasNoRightsToDropDatabase(
$this->parseAndAnalyze('DROP TABLE tbl'),
ParseAnalyze::sqlQuery('DROP TABLE tbl', $GLOBALS['db'])[0],
false,
false
)
@ -207,7 +208,7 @@ class SqlTest extends AbstractTestCase
$this->assertFalse(
$this->sql->hasNoRightsToDropDatabase(
$this->parseAndAnalyze('SELECT * from tbl'),
ParseAnalyze::sqlQuery('SELECT * from tbl', $GLOBALS['db'])[0],
false,
false
)
@ -342,16 +343,6 @@ class SqlTest extends AbstractTestCase
);
}
/**
* @return mixed
*/
private function parseAndAnalyze(string $sqlQuery)
{
[$analyzedSqlResults] = ParseAnalyze::sqlQuery($sqlQuery, $GLOBALS['db']);
return $analyzedSqlResults;
}
public function dataProviderCountQueryResults(): array
{
// sql query
@ -552,8 +543,6 @@ class SqlTest extends AbstractTestCase
$_SESSION['tmpval'] = $sessionTmpVal;
$analyzed_sql_results = $sqlQuery === null ? [] : $this->parseAndAnalyze($sqlQuery);
$result = $this->callFunction(
$this->sql,
Sql::class,
@ -563,7 +552,7 @@ class SqlTest extends AbstractTestCase
$justBrowsing,
'my_dataset',// db
'company_users',// table
$analyzed_sql_results,
ParseAnalyze::sqlQuery($sqlQuery ?? '', $GLOBALS['db'])[0],
]
);
$this->assertSame($expectedNumRows, $result);

View File

@ -0,0 +1,159 @@
<?php
declare(strict_types=1);
namespace PhpMyAdmin\Tests;
use PhpMyAdmin\SqlParser\Parser;
use PhpMyAdmin\StatementInfo;
use PHPUnit\Framework\TestCase;
/**
* @covers \PhpMyAdmin\StatementInfo
*/
class StatementInfoTest extends TestCase
{
public function testFromArray(): void
{
$parser = new Parser('SELECT * FROM `sakila`.`actor`');
$statement = $parser->statements[0];
$info = [
'distinct' => false,
'drop_database' => false,
'group' => false,
'having' => false,
'is_affected' => false,
'is_analyse' => false,
'is_count' => false,
'is_delete' => false,
'is_explain' => false,
'is_export' => false,
'is_func' => false,
'is_group' => false,
'is_insert' => false,
'is_maint' => false,
'is_procedure' => false,
'is_replace' => false,
'is_select' => true,
'is_show' => false,
'is_subquery' => false,
'join' => false,
'limit' => false,
'offset' => false,
'order' => false,
'querytype' => 'SELECT',
'reload' => false,
'select_from' => true,
'union' => false,
'parser' => $parser,
'statement' => $statement,
'select_tables' => [['actor', null]],
'select_expr' => ['*'],
];
$statementInfo = StatementInfo::fromArray($info);
$this->assertFalse($statementInfo->distinct);
$this->assertFalse($statementInfo->dropDatabase);
$this->assertFalse($statementInfo->group);
$this->assertFalse($statementInfo->having);
$this->assertFalse($statementInfo->isAffected);
$this->assertFalse($statementInfo->isAnalyse);
$this->assertFalse($statementInfo->isCount);
$this->assertFalse($statementInfo->isDelete);
$this->assertFalse($statementInfo->isExplain);
$this->assertFalse($statementInfo->isExport);
$this->assertFalse($statementInfo->isFunction);
$this->assertFalse($statementInfo->isGroup);
$this->assertFalse($statementInfo->isInsert);
$this->assertFalse($statementInfo->isMaint);
$this->assertFalse($statementInfo->isProcedure);
$this->assertFalse($statementInfo->isReplace);
$this->assertTrue($statementInfo->isSelect);
$this->assertFalse($statementInfo->isShow);
$this->assertFalse($statementInfo->isSubquery);
$this->assertFalse($statementInfo->join);
$this->assertFalse($statementInfo->limit);
$this->assertFalse($statementInfo->offset);
$this->assertFalse($statementInfo->order);
$this->assertSame('SELECT', $statementInfo->queryType);
$this->assertFalse($statementInfo->reload);
$this->assertTrue($statementInfo->selectFrom);
$this->assertFalse($statementInfo->union);
$this->assertNotNull($statementInfo->parser);
$this->assertNotNull($statementInfo->statement);
$this->assertNotEmpty($statementInfo->selectTables);
$this->assertNotEmpty($statementInfo->selectExpression);
$this->assertSame($info['parser'], $statementInfo->parser);
$this->assertSame($info['statement'], $statementInfo->statement);
$this->assertSame($info['select_tables'], $statementInfo->selectTables);
$this->assertSame($info['select_expr'], $statementInfo->selectExpression);
}
public function testFromArrayWithEmptyStatement(): void
{
$info = [
'distinct' => false,
'drop_database' => false,
'group' => false,
'having' => false,
'is_affected' => false,
'is_analyse' => false,
'is_count' => false,
'is_delete' => false,
'is_explain' => false,
'is_export' => false,
'is_func' => false,
'is_group' => false,
'is_insert' => false,
'is_maint' => false,
'is_procedure' => false,
'is_replace' => false,
'is_select' => false,
'is_show' => false,
'is_subquery' => false,
'join' => false,
'limit' => false,
'offset' => false,
'order' => false,
'querytype' => false,
'reload' => false,
'select_from' => false,
'union' => false,
];
$statementInfo = StatementInfo::fromArray($info);
$this->assertFalse($statementInfo->distinct);
$this->assertFalse($statementInfo->dropDatabase);
$this->assertFalse($statementInfo->group);
$this->assertFalse($statementInfo->having);
$this->assertFalse($statementInfo->isAffected);
$this->assertFalse($statementInfo->isAnalyse);
$this->assertFalse($statementInfo->isCount);
$this->assertFalse($statementInfo->isDelete);
$this->assertFalse($statementInfo->isExplain);
$this->assertFalse($statementInfo->isExport);
$this->assertFalse($statementInfo->isFunction);
$this->assertFalse($statementInfo->isGroup);
$this->assertFalse($statementInfo->isInsert);
$this->assertFalse($statementInfo->isMaint);
$this->assertFalse($statementInfo->isProcedure);
$this->assertFalse($statementInfo->isReplace);
$this->assertFalse($statementInfo->isSelect);
$this->assertFalse($statementInfo->isShow);
$this->assertFalse($statementInfo->isSubquery);
$this->assertFalse($statementInfo->join);
$this->assertFalse($statementInfo->limit);
$this->assertFalse($statementInfo->offset);
$this->assertFalse($statementInfo->order);
$this->assertFalse($statementInfo->queryType);
$this->assertFalse($statementInfo->reload);
$this->assertFalse($statementInfo->selectFrom);
$this->assertFalse($statementInfo->union);
$this->assertNull($statementInfo->parser);
$this->assertNull($statementInfo->statement);
$this->assertEmpty($statementInfo->selectTables);
$this->assertEmpty($statementInfo->selectExpression);
}
}

53
test/stubs/Query.stub Normal file
View File

@ -0,0 +1,53 @@
<?php
namespace PhpMyAdmin\SqlParser;
class Core {}
class Parser extends Core {}
abstract class Statement {}
namespace PhpMyAdmin\SqlParser\Utils;
use PhpMyAdmin\SqlParser\Parser;
use PhpMyAdmin\SqlParser\Statement;
class Query
{
/**
* @param string $query
* @return array{
* distinct: bool,
* drop_database: bool,
* group: bool,
* having: bool,
* is_affected: bool,
* is_analyse: bool,
* is_count: bool,
* is_delete: bool,
* is_explain: bool,
* is_export: bool,
* is_func: bool,
* is_group: bool,
* is_insert: bool,
* is_maint: bool,
* is_procedure: bool,
* is_replace: bool,
* is_select: bool,
* is_show: bool,
* is_subquery: bool,
* join: bool,
* limit: bool,
* offset: bool,
* order: bool,
* querytype: ('ALTER'|'ANALYZE'|'CALL'|'CHECK'|'CHECKSUM'|'CREATE'|'DELETE'|'DROP'|'EXPLAIN'|'INSERT'|'LOAD'|'OPTIMIZE'|'REPAIR'|'REPLACE'|'SELECT'|'SET'|'SHOW'|'UPDATE'|false),
* reload: bool,
* select_from: bool,
* union: bool,
* parser?: Parser,
* statement?: Statement,
* select_tables?: list<array{string|null, string|null}>,
* select_expr?: list<string|null>
* }
*/
public static function getAll($query);
}