diff --git a/libraries/classes/Controllers/Table/ChangeController.php b/libraries/classes/Controllers/Table/ChangeController.php index cff2199672..5d49e387aa 100644 --- a/libraries/classes/Controllers/Table/ChangeController.php +++ b/libraries/classes/Controllers/Table/ChangeController.php @@ -22,8 +22,8 @@ use function count; use function is_array; use function is_string; use function str_contains; +use function str_starts_with; use function strlen; -use function strpos; use function trim; /** @@ -48,26 +48,8 @@ class ChangeController extends AbstractController $GLOBALS['errorUrl'] ??= null; $GLOBALS['where_clause'] ??= null; $GLOBALS['unsaved_values'] ??= null; - $GLOBALS['insert_mode'] ??= null; - $GLOBALS['where_clause_array'] ??= null; - $GLOBALS['where_clauses'] ??= null; $GLOBALS['result'] ??= null; - $GLOBALS['rows'] ??= null; - $GLOBALS['found_unique_key'] ??= null; - $GLOBALS['after_insert'] ??= null; - $GLOBALS['comments_map'] ??= null; - $GLOBALS['table_columns'] ??= null; - $GLOBALS['timestamp_seen'] ??= null; - $GLOBALS['columns_cnt'] ??= null; - $GLOBALS['tabindex'] ??= null; - $GLOBALS['tabindex_for_value'] ??= null; - $GLOBALS['o_rows'] ??= null; - $GLOBALS['has_blob_field'] ??= null; - $GLOBALS['jsvkey'] ??= null; - $GLOBALS['vkey'] ??= null; $GLOBALS['current_result'] ??= null; - $GLOBALS['repopulate'] ??= null; - $GLOBALS['checked'] ??= null; $pageSettings = new PageSettings('Edit'); $this->response->addHTML($pageSettings->getErrorHTML()); @@ -86,22 +68,22 @@ class ChangeController extends AbstractController * Determine whether Insert or Edit and set global variables */ [ - $GLOBALS['insert_mode'], + $insertMode, $GLOBALS['where_clause'], - $GLOBALS['where_clause_array'], - $GLOBALS['where_clauses'], + $whereClauseArray, + $whereClauses, $GLOBALS['result'], - $GLOBALS['rows'], - $GLOBALS['found_unique_key'], - $GLOBALS['after_insert'], + $rows, + $foundUniqueIndex, + $afterInsert, ] = $this->insertEdit->determineInsertOrEdit( $GLOBALS['where_clause'] ?? null, $GLOBALS['db'], $GLOBALS['table'], ); // Increase number of rows if unsaved rows are more - if (! empty($GLOBALS['unsaved_values']) && count($GLOBALS['rows']) < count($GLOBALS['unsaved_values'])) { - $GLOBALS['rows'] = array_fill(0, count($GLOBALS['unsaved_values']), false); + if (! empty($GLOBALS['unsaved_values']) && count($rows) < count($GLOBALS['unsaved_values'])) { + $rows = array_fill(0, count($GLOBALS['unsaved_values']), false); } /** @@ -121,7 +103,7 @@ class ChangeController extends AbstractController $sqlQuery = $request->getParsedBodyParam('sql_query'); $GLOBALS['urlParams'] = ['db' => $GLOBALS['db'], 'sql_query' => is_string($sqlQuery) ? $sqlQuery : '']; - if (strpos($GLOBALS['goto'] ?? '', 'index.php?route=/table') === 0) { + if (str_starts_with($GLOBALS['goto'] ?? '', 'index.php?route=/table')) { $GLOBALS['urlParams']['table'] = $GLOBALS['table']; } @@ -131,7 +113,7 @@ class ChangeController extends AbstractController ); unset($GLOBALS['urlParams']); - $GLOBALS['comments_map'] = $this->insertEdit->getCommentsMap($GLOBALS['db'], $GLOBALS['table']); + $commentsMap = $this->insertEdit->getCommentsMap($GLOBALS['db'], $GLOBALS['table']); /** * START REGULAR OUTPUT @@ -151,10 +133,10 @@ class ChangeController extends AbstractController * $disp_message come from /table/replace */ if (! empty($GLOBALS['disp_message'])) { - $this->response->addHTML(Generator::getMessage($GLOBALS['disp_message'], null)); + $this->response->addHTML(Generator::getMessage($GLOBALS['disp_message'])); } - $GLOBALS['table_columns'] = $this->insertEdit->getTableColumns($GLOBALS['db'], $GLOBALS['table']); + $tableColumns = $this->insertEdit->getTableColumns($GLOBALS['db'], $GLOBALS['table']); // retrieve keys into foreign fields, if any $foreigners = $this->relation->getForeigners($GLOBALS['db'], $GLOBALS['table']); @@ -163,8 +145,8 @@ class ChangeController extends AbstractController $formParams = $this->insertEdit->getFormParametersForInsertForm( $GLOBALS['db'], $GLOBALS['table'], - $GLOBALS['where_clauses'], - $GLOBALS['where_clause_array'], + $whereClauses, + $whereClauseArray, $GLOBALS['errorUrl'], ); @@ -175,22 +157,15 @@ class ChangeController extends AbstractController // some browsers send wrongly this form to the http server. $htmlOutput = ''; - // Set if we passed the first timestamp field - $GLOBALS['timestamp_seen'] = false; - $GLOBALS['columns_cnt'] = count($GLOBALS['table_columns']); - - $GLOBALS['tabindex'] = 0; - $GLOBALS['tabindex_for_value'] = 0; - $GLOBALS['o_rows'] = 0; $GLOBALS['urlParams']['db'] = $GLOBALS['db']; $GLOBALS['urlParams']['table'] = $GLOBALS['table']; - $GLOBALS['urlParams'] = $this->urlParamsInEditMode($GLOBALS['urlParams'], $GLOBALS['where_clause_array']); + $GLOBALS['urlParams'] = $this->urlParamsInEditMode($GLOBALS['urlParams'], $whereClauseArray); - $GLOBALS['has_blob_field'] = false; - foreach ($GLOBALS['table_columns'] as $column) { + $hasBlobField = false; + foreach ($tableColumns as $column) { if ($this->insertEdit->isColumn($column, ['blob', 'tinyblob', 'mediumblob', 'longblob'])) { - $GLOBALS['has_blob_field'] = true; + $hasBlobField = true; break; } } @@ -198,7 +173,7 @@ class ChangeController extends AbstractController //Insert/Edit form //If table has blob fields we have to disable ajax. $isUpload = $GLOBALS['config']->get('enable_upload'); - $htmlOutput .= $this->insertEdit->getHtmlForInsertEditFormHeader($GLOBALS['has_blob_field'], $isUpload); + $htmlOutput .= $this->insertEdit->getHtmlForInsertEditFormHeader($hasBlobField, $isUpload); $htmlOutput .= Url::getHiddenInputs($formParams); @@ -217,67 +192,49 @@ class ChangeController extends AbstractController } $GLOBALS['plugin_scripts'] = []; - foreach ($GLOBALS['rows'] as $rowId => $currentRow) { - if (empty($currentRow)) { - $currentRow = []; - } - - $GLOBALS['jsvkey'] = (string) $rowId; - $GLOBALS['vkey'] = '[multi_edit][' . $GLOBALS['jsvkey'] . ']'; - + foreach ($rows as $rowId => $currentRow) { $GLOBALS['current_result'] = (isset($GLOBALS['result']) && is_array($GLOBALS['result']) && isset($GLOBALS['result'][$rowId]) ? $GLOBALS['result'][$rowId] : $GLOBALS['result']); - $GLOBALS['repopulate'] = []; - $GLOBALS['checked'] = true; + $repopulate = []; + $checked = true; if (isset($GLOBALS['unsaved_values'][$rowId])) { - $GLOBALS['repopulate'] = $GLOBALS['unsaved_values'][$rowId]; - $GLOBALS['checked'] = false; + $repopulate = $GLOBALS['unsaved_values'][$rowId]; + $checked = false; } - if ($GLOBALS['insert_mode'] && $rowId > 0) { - $htmlOutput .= $this->insertEdit->getHtmlForIgnoreOption($rowId, $GLOBALS['checked']); + if ($insertMode && $rowId > 0) { + $htmlOutput .= $this->insertEdit->getHtmlForIgnoreOption($rowId, $checked); } $htmlOutput .= $this->insertEdit->getHtmlForInsertEditRow( $GLOBALS['urlParams'], - $GLOBALS['table_columns'], - $GLOBALS['comments_map'], - $GLOBALS['timestamp_seen'], + $tableColumns, + $commentsMap, $GLOBALS['current_result'], - $GLOBALS['jsvkey'], - $GLOBALS['vkey'], - $GLOBALS['insert_mode'], - $currentRow, - $GLOBALS['o_rows'], - $GLOBALS['tabindex'], - $GLOBALS['columns_cnt'], + $insertMode, + $currentRow ?: [], $isUpload, $foreigners, - $GLOBALS['tabindex_for_value'], $GLOBALS['table'], $GLOBALS['db'], $rowId, $GLOBALS['text_dir'], - $GLOBALS['repopulate'], - $GLOBALS['where_clause_array'], + $repopulate, + $whereClauseArray, ); } $this->addScriptFiles($GLOBALS['plugin_scripts']); - unset($GLOBALS['unsaved_values'], $GLOBALS['checked'], $GLOBALS['repopulate'], $GLOBALS['plugin_scripts']); - - if (! isset($GLOBALS['after_insert'])) { - $GLOBALS['after_insert'] = 'back'; - } + unset($GLOBALS['unsaved_values'], $GLOBALS['plugin_scripts']); $isNumeric = InsertEdit::isWhereClauseNumeric($GLOBALS['where_clause']); $htmlOutput .= $this->template->render('table/insert/actions_panel', [ 'where_clause' => $GLOBALS['where_clause'], - 'after_insert' => $GLOBALS['after_insert'], - 'found_unique_key' => $GLOBALS['found_unique_key'], + 'after_insert' => $afterInsert ?? 'back', + 'found_unique_key' => $foundUniqueIndex, 'is_numeric' => $isNumeric, ]); @@ -286,12 +243,12 @@ class ChangeController extends AbstractController $htmlOutput .= $this->insertEdit->getHtmlForGisEditor(); // end Insert/Edit form - if ($GLOBALS['insert_mode']) { + if ($insertMode) { //Continue insertion form $htmlOutput .= $this->insertEdit->getContinueInsertionForm( $GLOBALS['table'], $GLOBALS['db'], - $GLOBALS['where_clause_array'], + $whereClauseArray, $GLOBALS['errorUrl'], ); } diff --git a/libraries/classes/Controllers/Table/ReplaceController.php b/libraries/classes/Controllers/Table/ReplaceController.php index 6f1df84fa7..ff7cb47c83 100644 --- a/libraries/classes/Controllers/Table/ReplaceController.php +++ b/libraries/classes/Controllers/Table/ReplaceController.php @@ -314,18 +314,22 @@ final class ReplaceController extends AbstractController return; } + $returnToSqlQuery = ''; + if (! empty($GLOBALS['sql_query'])) { + $GLOBALS['urlParams']['sql_query'] = $GLOBALS['sql_query']; + $returnToSqlQuery = $GLOBALS['sql_query']; + } + /** * Executes the sql query and get the result, then move back to the calling * page */ [ - $GLOBALS['urlParams'], $totalAffectedRows, $lastMessages, $warningMessages, $errorMessages, - $returnToSqlQuery, - ] = $this->insertEdit->executeSqlQuery($GLOBALS['urlParams'], $GLOBALS['query']); + ] = $this->insertEdit->executeSqlQuery($GLOBALS['query']); if ($isInsert && ($valueSets !== [] || $rowSkipped)) { $GLOBALS['message'] = Message::getMessageForInsertedRows($totalAffectedRows); diff --git a/libraries/classes/InsertEdit.php b/libraries/classes/InsertEdit.php index 6da47a7622..d86c1d40c9 100644 --- a/libraries/classes/InsertEdit.php +++ b/libraries/classes/InsertEdit.php @@ -7,6 +7,7 @@ namespace PhpMyAdmin; use PhpMyAdmin\ConfigStorage\Relation; use PhpMyAdmin\Dbal\ResultInterface; use PhpMyAdmin\Html\Generator; +use PhpMyAdmin\Plugins\IOTransformationsPlugin; use PhpMyAdmin\Plugins\TransformationsPlugin; use PhpMyAdmin\Utils\Gis; @@ -33,13 +34,14 @@ use function mb_stripos; use function mb_strlen; use function mb_strstr; use function md5; -use function method_exists; use function min; use function password_hash; use function preg_match; use function preg_replace; use function str_contains; +use function str_ends_with; use function str_replace; +use function str_starts_with; use function stripcslashes; use function stripslashes; use function strlen; @@ -77,6 +79,9 @@ class InsertEdit 'VERSION', ]; + private int $rowOffset = 0; + private int $fieldIndex = 0; + public function __construct( private DatabaseInterface $dbi, private Relation $relation, @@ -299,16 +304,14 @@ class InsertEdit /** * Analyze the table column array * - * @param mixed[] $column description of column in given table - * @param mixed[] $commentsMap comments for every column that has a comment - * @param bool $timestampSeen whether a timestamp has been seen + * @param mixed[] $column description of column in given table + * @param mixed[] $commentsMap comments for every column that has a comment * * @return mixed[] description of column in given table */ private function analyzeTableColumnsArray( array $column, array $commentsMap, - bool $timestampSeen, ): array { $column['Field_md5'] = md5($column['Field']); // True_Type contains only the type (stops at first bracket) @@ -339,7 +342,7 @@ class InsertEdit }; // can only occur once per table - $column['first_timestamp'] = $column['True_Type'] === 'timestamp' ? ! $timestampSeen : false; + $column['first_timestamp'] = $column['True_Type'] === 'timestamp'; return $column; } @@ -423,9 +426,6 @@ class InsertEdit * @param string $backupField hidden input field * @param string $columnNameAppendix the name attribute * @param string $onChangeClause onchange clause for fields - * @param int $tabindex tab index - * @param int $tabindexForValue offset for the values tabindex - * @param int $idindex id index * @param string $textDir text direction * @param string $specialCharsEncoded replaced char if the string starts * with a \r\n pair (0x0d0a) add an extra \n @@ -438,9 +438,6 @@ class InsertEdit string $backupField, string $columnNameAppendix, string $onChangeClause, - int $tabindex, - int $tabindexForValue, - int $idindex, string $textDir, string $specialCharsEncoded, string $dataType, @@ -471,9 +468,9 @@ class InsertEdit . ' rows="' . $textAreaRows . '"' . ' cols="' . $textareaCols . '"' . ' dir="' . $textDir . '"' - . ' id="field_' . $idindex . '_3"' + . ' id="field_' . $this->fieldIndex . '_3"' . ($onChangeClause ? ' onchange="' . htmlspecialchars($onChangeClause, ENT_COMPAT) . '"' : '') - . ' tabindex="' . ($tabindex + $tabindexForValue) . '"' + . ' tabindex="' . $this->fieldIndex . '"' . ' data-type="' . $dataType . '">' . $specialCharsEncoded . ''; @@ -487,9 +484,6 @@ class InsertEdit * @param string $specialChars special characters * @param int $fieldsize html field size * @param string $onChangeClause onchange clause for fields - * @param int $tabindex tab index - * @param int $tabindexForValue offset for the values tabindex - * @param int $idindex id index * @param string $dataType the html5 data-* attribute type * * @return string an html snippet @@ -500,9 +494,6 @@ class InsertEdit string $specialChars, int $fieldsize, string $onChangeClause, - int $tabindex, - int $tabindexForValue, - int $idindex, string $dataType, ): string { $theClass = 'textfield'; @@ -537,9 +528,9 @@ class InsertEdit . ($inputMinMax ? ' ' . $inputMinMax : '') . ' data-type="' . $dataType . '"' . ' class="' . $theClass . '" onchange="' . htmlspecialchars($onChangeClause, ENT_COMPAT) . '"' - . ' tabindex="' . ($tabindex + $tabindexForValue) . '"' + . ' tabindex="' . $this->fieldIndex . '"' . ($isInteger ? ' inputmode="numeric"' : '') - . ' id="field_' . $idindex . '_3">'; + . ' id="field_' . $this->fieldIndex . '_3">'; } /** @@ -607,10 +598,7 @@ class InsertEdit * @param string $backupField hidden input field * @param string $columnNameAppendix the name attribute * @param string $onChangeClause onchange clause for fields - * @param int $tabindex tab index * @param string $specialChars special characters - * @param int $tabindexForValue offset for the values tabindex - * @param int $idindex id index * @param string $textDir text direction * @param string $specialCharsEncoded replaced char if the string starts * with a \r\n pair (0x0d0a) add an extra \n @@ -627,10 +615,7 @@ class InsertEdit string $backupField, string $columnNameAppendix, string $onChangeClause, - int $tabindex, string $specialChars, - int $tabindexForValue, - int $idindex, string $textDir, string $specialCharsEncoded, string $data, @@ -649,9 +634,6 @@ class InsertEdit $backupField, $columnNameAppendix, $onChangeClause, - $tabindex, - $tabindexForValue, - $idindex, $textDir, $specialCharsEncoded, $dataType, @@ -663,9 +645,6 @@ class InsertEdit $specialChars, $fieldsize, $onChangeClause, - $tabindex, - $tabindexForValue, - $idindex, $dataType, ); } @@ -837,7 +816,7 @@ class InsertEdit (int) $extractedColumnspec['spec_in_brackets'], ); } elseif ( - (substr($column['True_Type'], 0, 9) === 'timestamp' + (str_starts_with($column['True_Type'], 'timestamp') || $column['True_Type'] === 'datetime' || $column['True_Type'] === 'time') && (str_contains($currentRow[$column['Field']], '.')) @@ -904,11 +883,11 @@ class InsertEdit if ($trueType === 'bit') { $specialChars = Util::convertBitDefaultValue($defaultValue); - } elseif (substr($trueType, 0, 9) === 'timestamp' || $trueType === 'datetime' || $trueType === 'time') { + } elseif (str_starts_with($trueType, 'timestamp') || $trueType === 'datetime' || $trueType === 'time') { $specialChars = Util::addMicroseconds($defaultValue); } elseif ($trueType === 'binary' || $trueType === 'varbinary') { $specialChars = bin2hex($defaultValue); - } elseif (substr($trueType, -4) === 'text') { + } elseif (str_ends_with($trueType, 'text')) { $textDefault = substr($defaultValue, 1, -1); $specialChars = stripcslashes($textDefault !== '' ? $textDefault : $defaultValue); } else { @@ -1031,20 +1010,12 @@ class InsertEdit /** * Executes the sql query and get the result, then move back to the calling page * - * @param mixed[] $urlParams url parameters array - * @param mixed[] $query built query from buildSqlQuery() + * @param mixed[] $query built query from buildSqlQuery() * - * @return mixed[] $url_params, $total_affected_rows, $last_messages - * $warning_messages, $error_messages, $return_to_sql_query + * @return mixed[] $total_affected_rows, $last_messages, $warning_messages, $error_messages */ - public function executeSqlQuery(array $urlParams, array $query): array + public function executeSqlQuery(array $query): array { - $returnToSqlQuery = ''; - if (! empty($GLOBALS['sql_query'])) { - $urlParams['sql_query'] = $GLOBALS['sql_query']; - $returnToSqlQuery = $GLOBALS['sql_query']; - } - $GLOBALS['sql_query'] = implode('; ', $query) . ';'; // to ensure that the query is displayed in case of // "insert as new row" and then "insert another new row" @@ -1090,7 +1061,7 @@ class InsertEdit $warningMessages = $this->getWarningMessages(); } - return [$urlParams, $totalAffectedRows, $lastMessages, $warningMessages, $errorMessages, $returnToSqlQuery]; + return [$totalAffectedRows, $lastMessages, $warningMessages, $errorMessages]; } /** @@ -1131,7 +1102,7 @@ class InsertEdit $displayField = $this->relation->getDisplayField($foreigner['foreign_db'], $foreigner['foreign_table']); // Field to display from the foreign table? - if (is_string($displayField) && strlen($displayField) > 0) { + if (is_string($displayField) && $displayField !== '') { $dispsql = 'SELECT ' . Util::backquote($displayField) . ' FROM ' . Util::backquote($foreigner['foreign_db']) . '.' . Util::backquote($foreigner['foreign_table']) @@ -1277,11 +1248,6 @@ class InsertEdit EditField $editField, ): string { if ($editField->function === 'PHP_PASSWORD_HASH') { - /** - * @see https://github.com/vimeo/psalm/issues/3350 - * - * @psalm-suppress InvalidArgument - */ $hash = password_hash($editField->value, PASSWORD_DEFAULT); return $this->dbi->quoteString($hash); @@ -1299,8 +1265,7 @@ class InsertEdit || in_array($editField->function, $this->getGisFromWKBFunctions()) ) { preg_match('/^(\'?)(.*?)\1(?:,(\d+))?$/', $editField->value, $matches); - $escapedParams = "'" . $this->dbi->escapeString($matches[2]) - . (isset($matches[3]) ? "'," . $matches[3] : "'"); + $escapedParams = $this->dbi->quoteString($matches[2]) . (isset($matches[3]) ? ',' . $matches[3] : ''); return $editField->function . '(' . $escapedParams . ')'; } @@ -1448,7 +1413,7 @@ class InsertEdit } if ($editField->type === 'hex') { - if (substr($editField->value, 0, 2) != '0x') { + if (! str_starts_with($editField->value, '0x')) { return '0x' . $editField->value; } @@ -1693,18 +1658,12 @@ class InsertEdit * @param mixed[] $column column * @param int $columnNumber column index in table_columns * @param mixed[] $commentsMap comments map - * @param bool $timestampSeen whether timestamp seen * @param ResultInterface $currentResult current result - * @param string $jsvkey javascript validation key - * @param string $vkey validation key * @param bool $insertMode whether insert mode * @param mixed[] $currentRow current row - * @param int $oRows row offset - * @param int $tabindex tab index * @param int $columnsCnt columns count * @param bool $isUpload whether upload * @param mixed[] $foreigners foreigners - * @param int $tabindexForValue tab index offset for value * @param string $table table * @param string $db database * @param int $rowId row id @@ -1718,18 +1677,12 @@ class InsertEdit array $column, int $columnNumber, array $commentsMap, - bool $timestampSeen, ResultInterface $currentResult, - string $jsvkey, - string $vkey, bool $insertMode, array $currentRow, - int $oRows, - int &$tabindex, int $columnsCnt, bool $isUpload, array $foreigners, - int $tabindexForValue, string $table, string $db, int $rowId, @@ -1740,7 +1693,7 @@ class InsertEdit string $whereClause, ): string { if (! isset($column['processed'])) { - $column = $this->analyzeTableColumnsArray($column, $commentsMap, $timestampSeen); + $column = $this->analyzeTableColumnsArray($column, $commentsMap); } $asIs = false; @@ -1765,8 +1718,9 @@ class InsertEdit //Call validation when the form submitted... $onChangeClause = 'return verificationsAfterFieldChange(' . json_encode($fieldHashMd5) . ', ' - . json_encode($jsvkey) . ',' . json_encode($column['pma_type']) . ')'; + . json_encode((string) $rowId) . ',' . json_encode($column['pma_type']) . ')'; + $vkey = '[multi_edit][' . $rowId . ']'; // Use an MD5 as an array index to avoid having special characters // in the name attribute (see bug #1746964 ) $columnNameAppendix = $vkey . '[' . $fieldHashMd5 . ']'; @@ -1810,8 +1764,7 @@ class InsertEdit $backupField = ''; } - $idindex = ($oRows * $columnsCnt) + $columnNumber + 1; - $tabindex = $idindex; + $this->fieldIndex = ($this->rowOffset * $columnsCnt) + $columnNumber + 1; // The function column // ------------------- @@ -1865,7 +1818,7 @@ class InsertEdit $currentValue = $currentRow[$column['Field']]; } - if (method_exists($transformationPlugin, 'getInputHtml')) { + if ($transformationPlugin instanceof IOTransformationsPlugin) { $transformedHtml = $transformationPlugin->getInputHtml( $column, $rowId, @@ -1873,13 +1826,9 @@ class InsertEdit $transformationOptions, $currentValue, $textDir, - $tabindex, - $tabindexForValue, - $idindex, + $this->fieldIndex, ); - } - if (method_exists($transformationPlugin, 'getScripts')) { $GLOBALS['plugin_scripts'] = array_merge( $GLOBALS['plugin_scripts'], $transformationPlugin->getScripts(), @@ -1973,9 +1922,6 @@ class InsertEdit $specialChars, min(max($column['len'], 4), $GLOBALS['cfg']['LimitChars']), $onChangeClause, - $tabindex, - $tabindexForValue, - $idindex, 'HEX', ); } @@ -1986,10 +1932,7 @@ class InsertEdit $backupField, $columnNameAppendix, $onChangeClause, - $tabindex, $specialChars, - $tabindexForValue, - $idindex, $textDir, $specialCharsEncoded, $data, @@ -2009,7 +1952,7 @@ class InsertEdit 'function_options' => $functionOptions, 'nullify_code' => $nullifyCode, 'real_null_value' => $realNullValue, - 'id_index' => $idindex, + 'id_index' => $this->fieldIndex, 'type' => $type, 'decimals' => $noDecimals, 'special_chars' => $specialChars, @@ -2058,18 +2001,11 @@ class InsertEdit * @param mixed[] $urlParams url parameters * @param mixed[][] $tableColumns table columns * @param mixed[] $commentsMap comments map - * @param bool $timestampSeen whether timestamp seen * @param ResultInterface $currentResult current result - * @param string $jsvkey javascript validation key - * @param string $vkey validation key * @param bool $insertMode whether insert mode * @param mixed[] $currentRow current row - * @param int $oRows row offset - * @param int $tabindex tab index - * @param int $columnsCnt columns count * @param bool $isUpload whether upload * @param mixed[] $foreigners foreigners - * @param int $tabindexForValue tab index offset for value * @param string $table table * @param string $db database * @param int $rowId row id @@ -2081,18 +2017,11 @@ class InsertEdit array $urlParams, array $tableColumns, array $commentsMap, - bool $timestampSeen, ResultInterface $currentResult, - string $jsvkey, - string $vkey, bool $insertMode, array $currentRow, - int &$oRows, - int &$tabindex, - int $columnsCnt, bool $isUpload, array $foreigners, - int $tabindexForValue, string $table, string $db, int $rowId, @@ -2111,7 +2040,8 @@ class InsertEdit $whereClause = $whereClauseArray[$rowId]; } - for ($columnNumber = 0; $columnNumber < $columnsCnt; $columnNumber++) { + $columnCount = count($tableColumns); + for ($columnNumber = 0; $columnNumber < $columnCount; $columnNumber++) { $tableColumn = $tableColumns[$columnNumber]; $columnMime = []; if (isset($mimeMap[$tableColumn['Field']])) { @@ -2127,18 +2057,12 @@ class InsertEdit $tableColumn, $columnNumber, $commentsMap, - $timestampSeen, $currentResult, - $jsvkey, - $vkey, $insertMode, $currentRow, - $oRows, - $tabindex, - $columnsCnt, + $columnCount, $isUpload, $foreigners, - $tabindexForValue, $table, $db, $rowId, @@ -2150,7 +2074,7 @@ class InsertEdit ); } - $oRows++; + $this->rowOffset++; return $htmlOutput . ' ' . '
' diff --git a/libraries/classes/Plugins/IOTransformationsPlugin.php b/libraries/classes/Plugins/IOTransformationsPlugin.php index 444289ab0e..bc17f4aeed 100644 --- a/libraries/classes/Plugins/IOTransformationsPlugin.php +++ b/libraries/classes/Plugins/IOTransformationsPlugin.php @@ -33,9 +33,7 @@ abstract class IOTransformationsPlugin extends TransformationsPlugin * @param mixed[] $options transformation options * @param string $value Current field value * @param string $textDir text direction - * @param int $tabIndex tab index - * @param int $tabIndexForValue offset for the values tabindex - * @param int $idIndex id index + * @param int $fieldIndex field index * * @return string the html for input field */ @@ -46,9 +44,7 @@ abstract class IOTransformationsPlugin extends TransformationsPlugin array $options, string $value, string $textDir, - int $tabIndex, - int $tabIndexForValue, - int $idIndex, + int $fieldIndex, ): string { return ''; } diff --git a/libraries/classes/Plugins/Transformations/Abs/CodeMirrorEditorTransformationPlugin.php b/libraries/classes/Plugins/Transformations/Abs/CodeMirrorEditorTransformationPlugin.php index 3221f29271..d0200c56cc 100644 --- a/libraries/classes/Plugins/Transformations/Abs/CodeMirrorEditorTransformationPlugin.php +++ b/libraries/classes/Plugins/Transformations/Abs/CodeMirrorEditorTransformationPlugin.php @@ -40,9 +40,7 @@ abstract class CodeMirrorEditorTransformationPlugin extends IOTransformationsPlu * @param mixed[] $options transformation options * @param string $value Current field value * @param string $textDir text direction - * @param int $tabIndex tab index - * @param int $tabIndexForValue offset for the values tabindex - * @param int $idIndex id index + * @param int $fieldIndex field index * * @return string the html for input field */ @@ -53,9 +51,7 @@ abstract class CodeMirrorEditorTransformationPlugin extends IOTransformationsPlu array $options, string $value, string $textDir, - int $tabIndex, - int $tabIndexForValue, - int $idIndex, + int $fieldIndex, ): string { $html = ''; if (! empty($value)) { diff --git a/libraries/classes/Plugins/Transformations/Abs/ImageUploadTransformationsPlugin.php b/libraries/classes/Plugins/Transformations/Abs/ImageUploadTransformationsPlugin.php index 52df4f0179..4b98b88aff 100644 --- a/libraries/classes/Plugins/Transformations/Abs/ImageUploadTransformationsPlugin.php +++ b/libraries/classes/Plugins/Transformations/Abs/ImageUploadTransformationsPlugin.php @@ -54,9 +54,7 @@ abstract class ImageUploadTransformationsPlugin extends IOTransformationsPlugin * @param mixed[] $options transformation options * @param string $value Current field value * @param string $textDir text direction - * @param int $tabIndex tab index - * @param int $tabIndexForValue offset for the values tabindex - * @param int $idIndex id index + * @param int $fieldIndex field index * * @return string the html for input field */ @@ -67,9 +65,7 @@ abstract class ImageUploadTransformationsPlugin extends IOTransformationsPlugin array $options, string $value, string $textDir, - int $tabIndex, - int $tabIndexForValue, - int $idIndex, + int $fieldIndex, ): string { $html = ''; $src = ''; diff --git a/libraries/classes/Plugins/Transformations/Abs/TextFileUploadTransformationsPlugin.php b/libraries/classes/Plugins/Transformations/Abs/TextFileUploadTransformationsPlugin.php index db5db0c413..ace2274a99 100644 --- a/libraries/classes/Plugins/Transformations/Abs/TextFileUploadTransformationsPlugin.php +++ b/libraries/classes/Plugins/Transformations/Abs/TextFileUploadTransformationsPlugin.php @@ -49,9 +49,7 @@ abstract class TextFileUploadTransformationsPlugin extends IOTransformationsPlug * @param mixed[] $options transformation options * @param string $value Current field value * @param string $textDir text direction - * @param int $tabIndex tab index - * @param int $tabIndexForValue offset for the values tabindex - * @param int $idIndex id index + * @param int $fieldIndex field index * * @return string the html for input field */ @@ -62,9 +60,7 @@ abstract class TextFileUploadTransformationsPlugin extends IOTransformationsPlug array $options, string $value, string $textDir, - int $tabIndex, - int $tabIndexForValue, - int $idIndex, + int $fieldIndex, ): string { $html = ''; if (! empty($value)) { diff --git a/libraries/classes/Plugins/Transformations/Input/Text_Plain_Iptobinary.php b/libraries/classes/Plugins/Transformations/Input/Text_Plain_Iptobinary.php index 6dd735dd96..30d41faab4 100644 --- a/libraries/classes/Plugins/Transformations/Input/Text_Plain_Iptobinary.php +++ b/libraries/classes/Plugins/Transformations/Input/Text_Plain_Iptobinary.php @@ -56,9 +56,7 @@ class Text_Plain_Iptobinary extends IOTransformationsPlugin * @param mixed[] $options transformation options * @param string $value Current field value * @param string $textDir text direction - * @param int $tabIndex tab index - * @param int $tabIndexForValue offset for the values tabindex - * @param int $idIndex id index + * @param int $fieldIndex field index * * @return string the html for input field */ @@ -69,9 +67,7 @@ class Text_Plain_Iptobinary extends IOTransformationsPlugin array $options, string $value, string $textDir, - int $tabIndex, - int $tabIndexForValue, - int $idIndex, + int $fieldIndex, ): string { $html = ''; $val = ''; @@ -95,8 +91,8 @@ class Text_Plain_Iptobinary extends IOTransformationsPlugin . ' size="40"' . ' dir="' . $textDir . '"' . ' class="' . $class . '"' - . ' id="field_' . $idIndex . '_3"' - . ' tabindex="' . ($tabIndex + $tabIndexForValue) . '">'; + . ' id="field_' . $fieldIndex . '_3"' + . ' tabindex="' . $fieldIndex . '">'; } /* ~~~~~~~~~~~~~~~~~~~~ Getters and Setters ~~~~~~~~~~~~~~~~~~~~ */ diff --git a/libraries/classes/Plugins/Transformations/Input/Text_Plain_Iptolong.php b/libraries/classes/Plugins/Transformations/Input/Text_Plain_Iptolong.php index 8da85a8092..d16ce8aac5 100644 --- a/libraries/classes/Plugins/Transformations/Input/Text_Plain_Iptolong.php +++ b/libraries/classes/Plugins/Transformations/Input/Text_Plain_Iptolong.php @@ -53,9 +53,7 @@ class Text_Plain_Iptolong extends IOTransformationsPlugin * @param mixed[] $options transformation options * @param string $value Current field value * @param string $textDir text direction - * @param int $tabIndex tab index - * @param int $tabIndexForValue offset for the values tabindex - * @param int $idIndex id index + * @param int $fieldIndex field index * * @return string the html for input field */ @@ -66,9 +64,7 @@ class Text_Plain_Iptolong extends IOTransformationsPlugin array $options, string $value, string $textDir, - int $tabIndex, - int $tabIndexForValue, - int $idIndex, + int $fieldIndex, ): string { $html = ''; $val = ''; @@ -87,8 +83,8 @@ class Text_Plain_Iptolong extends IOTransformationsPlugin . ' size="40"' . ' dir="' . $textDir . '"' . ' class="transform_IPToLong"' - . ' id="field_' . $idIndex . '_3"' - . ' tabindex="' . ($tabIndex + $tabIndexForValue) . '" />'; + . ' id="field_' . $fieldIndex . '_3"' + . ' tabindex="' . $fieldIndex . '" />'; } /* ~~~~~~~~~~~~~~~~~~~~ Getters and Setters ~~~~~~~~~~~~~~~~~~~~ */ diff --git a/phpstan-baseline.neon b/phpstan-baseline.neon index 5c2d8d27b4..7f98021322 100644 --- a/phpstan-baseline.neon +++ b/phpstan-baseline.neon @@ -2080,6 +2080,11 @@ parameters: count: 1 path: libraries/classes/Controllers/Table/AddFieldController.php + - + message: "#^Parameter \\#1 \\$rowId of method PhpMyAdmin\\\\InsertEdit\\:\\:getHtmlForIgnoreOption\\(\\) expects int, \\(int\\<1, max\\>\\|string\\) given\\.$#" + count: 1 + path: libraries/classes/Controllers/Table/ChangeController.php + - message: "#^Parameter \\#1 \\$sqlQuery of static method PhpMyAdmin\\\\Core\\:\\:checkSqlQuerySignature\\(\\) expects string, mixed given\\.$#" count: 1 @@ -2090,6 +2095,11 @@ parameters: count: 1 path: libraries/classes/Controllers/Table/ChangeController.php + - + message: "#^Parameter \\#11 \\$rowId of method PhpMyAdmin\\\\InsertEdit\\:\\:getHtmlForInsertEditRow\\(\\) expects int, \\(int\\|string\\) given\\.$#" + count: 1 + path: libraries/classes/Controllers/Table/ChangeController.php + - message: "#^Parameter \\#2 \\$signature of static method PhpMyAdmin\\\\Core\\:\\:checkSqlQuerySignature\\(\\) expects string, mixed given\\.$#" count: 1 @@ -4785,6 +4795,11 @@ parameters: count: 1 path: libraries/classes/InsertEdit.php + - + message: "#^Parameter \\#1 \\$haystack of function str_starts_with expects string, mixed given\\.$#" + count: 1 + path: libraries/classes/InsertEdit.php + - message: "#^Parameter \\#1 \\$optionString of method PhpMyAdmin\\\\Transformations\\:\\:getOptions\\(\\) expects string, mixed given\\.$#" count: 1 @@ -4815,11 +4830,6 @@ parameters: count: 1 path: libraries/classes/InsertEdit.php - - - message: "#^Parameter \\#1 \\$string of function substr expects string, mixed given\\.$#" - count: 1 - path: libraries/classes/InsertEdit.php - - message: "#^Parameter \\#1 \\$string of function trim expects string, mixed given\\.$#" count: 1 @@ -4845,6 +4855,11 @@ parameters: count: 1 path: libraries/classes/InsertEdit.php + - + message: "#^Parameter \\#17 \\$whereClause of method PhpMyAdmin\\\\InsertEdit\\:\\:getHtmlForInsertEditFormColumn\\(\\) expects string, mixed given\\.$#" + count: 1 + path: libraries/classes/InsertEdit.php + - message: "#^Parameter \\#2 \\$column of method PhpMyAdmin\\\\ConfigStorage\\\\Relation\\:\\:searchColumnInForeigners\\(\\) expects string, mixed given\\.$#" count: 1 @@ -4860,11 +4875,6 @@ parameters: count: 1 path: libraries/classes/InsertEdit.php - - - message: "#^Parameter \\#23 \\$whereClause of method PhpMyAdmin\\\\InsertEdit\\:\\:getHtmlForInsertEditFormColumn\\(\\) expects string, mixed given\\.$#" - count: 1 - path: libraries/classes/InsertEdit.php - - message: "#^Parameter \\#3 \\$row of static method PhpMyAdmin\\\\Util\\:\\:getUniqueCondition\\(\\) expects array\\, mixed given\\.$#" count: 1 diff --git a/psalm-baseline.xml b/psalm-baseline.xml index 13345003f9..0ca294baf2 100644 --- a/psalm-baseline.xml +++ b/psalm-baseline.xml @@ -3269,38 +3269,20 @@ - - - - - - - - - - - - - - - - - - - $isUpload + $repopulate getQueryParam('where_clause_signature')]]> $whereClause $whereClause @@ -3310,32 +3292,14 @@ $rowId - - - - - - - - - - - - - - - - - - - $isUpload + $repopulate $whereClause $whereClause @@ -3881,7 +3845,6 @@ - @@ -3941,7 +3904,6 @@ - $extraData @@ -7884,9 +7846,6 @@ - - escapeString - $urlParams @@ -7950,6 +7909,7 @@ + $currentValue $defaultValue @@ -7965,7 +7925,6 @@ $rows[$keyId] $singleQuery $singleQuery - getScripts()]]> $whereClause $whereClause @@ -8037,7 +7996,6 @@ $setSelectSize $singleQuery $specialChars - $transformedHtml $whereClause $whereClause $whereClause @@ -10274,12 +10232,6 @@ bool - - - getInputHtml - getScripts - - $nameArray === false diff --git a/test/classes/InsertEditTest.php b/test/classes/InsertEditTest.php index 8fea1fc02c..a36373be94 100644 --- a/test/classes/InsertEditTest.php +++ b/test/classes/InsertEditTest.php @@ -419,7 +419,7 @@ class InsertEditTest extends AbstractTestCase $this->insertEdit, InsertEdit::class, 'analyzeTableColumnsArray', - [$column, [], false], + [$column, []], ); $this->assertEquals($result['Field_md5'], '4342210df36bf2ff2c4e2a997a6d4089'); @@ -602,11 +602,12 @@ class InsertEditTest extends AbstractTestCase $column['is_char'] = true; $column['Type'] = 'char(10)'; $column['True_Type'] = 'char'; + (new ReflectionProperty(InsertEdit::class, 'fieldIndex'))->setValue($this->insertEdit, 2); $result = $this->callFunction( $this->insertEdit, InsertEdit::class, 'getTextarea', - [$column, 'a', 'b', '', 2, 0, 1, 'abc/', 'foobar', 'CHAR', false], + [$column, 'a', 'b', '', 'abc/', 'foobar', 'CHAR'], ); $result = $this->parseString($result); @@ -614,7 +615,7 @@ class InsertEditTest extends AbstractTestCase $this->assertStringContainsString( '', $result, ); @@ -785,22 +784,18 @@ class InsertEditTest extends AbstractTestCase 'a', 'b', 'c', - 22, '<', - 12, - 1, '/', '<', "foo\nbar", $extractedColumnSpec, - false, ], ); $this->assertEquals( "a\n" . '' . '', $result, @@ -818,15 +813,11 @@ class InsertEditTest extends AbstractTestCase 'a', 'b', 'c', - 22, '<', - 12, - 1, '/', '<', "foo\nbar", $extractedColumnSpec, - false, ], ); @@ -846,15 +837,11 @@ class InsertEditTest extends AbstractTestCase 'a', 'b', 'c', - 22, '<', - 12, - 1, '/', '<', "foo\nbar", $extractedColumnSpec, - false, ], ); @@ -874,15 +861,11 @@ class InsertEditTest extends AbstractTestCase 'a', 'b', 'c', - 22, '<', - 12, - 1, '/', '<', "foo\nbar", $extractedColumnSpec, - false, ], ); @@ -902,15 +885,11 @@ class InsertEditTest extends AbstractTestCase 'a', 'b', 'c', - 22, '<', - 12, - 1, '/', '<', "foo\nbar", $extractedColumnSpec, - false, ], ); @@ -1356,7 +1335,6 @@ class InsertEditTest extends AbstractTestCase public function testExecuteSqlQuery(): void { $query = ['SELECT * FROM `test_db`.`test_table`;', 'SELECT * FROM `test_db`.`test_table_yaml`;']; - $GLOBALS['sql_query'] = 'SELECT * FROM `test_db`.`test_table`;'; $GLOBALS['cfg']['IgnoreMultiSubmitErrors'] = false; $_POST['submit_type'] = ''; @@ -1367,11 +1345,9 @@ class InsertEditTest extends AbstractTestCase new FileListing(), new Template(), ); - $result = $this->insertEdit->executeSqlQuery([], $query); + $result = $this->insertEdit->executeSqlQuery($query); - $this->assertEquals(['sql_query' => 'SELECT * FROM `test_db`.`test_table`;'], $result[0]); $this->assertEquals([], $result[3]); - $this->assertEquals('SELECT * FROM `test_db`.`test_table`;', $result[5]); } /** @@ -1380,7 +1356,6 @@ class InsertEditTest extends AbstractTestCase public function testExecuteSqlQueryWithTryQuery(): void { $query = ['SELECT * FROM `test_db`.`test_table`;', 'SELECT * FROM `test_db`.`test_table_yaml`;']; - $GLOBALS['sql_query'] = 'SELECT * FROM `test_db`.`test_table`;'; $GLOBALS['cfg']['IgnoreMultiSubmitErrors'] = true; $_POST['submit_type'] = ''; @@ -1391,11 +1366,9 @@ class InsertEditTest extends AbstractTestCase new FileListing(), new Template(), ); - $result = $this->insertEdit->executeSqlQuery([], $query); + $result = $this->insertEdit->executeSqlQuery($query); - $this->assertEquals(['sql_query' => 'SELECT * FROM `test_db`.`test_table`;'], $result[0]); $this->assertEquals([], $result[3]); - $this->assertEquals('SELECT * FROM `test_db`.`test_table`;', $result[5]); } /** @@ -2404,8 +2377,6 @@ class InsertEditTest extends AbstractTestCase public function testGetHtmlForInsertEditFormColumn(): void { $_SESSION[' HMAC_secret '] = hash('sha1', 'test'); - $oRows = 0; - $tabindex = 0; $GLOBALS['plugin_scripts'] = []; $foreigners = ['foreign_keys_data' => []]; $tableColumn = [ @@ -2434,18 +2405,12 @@ class InsertEditTest extends AbstractTestCase $tableColumn, 0, [], - false, $resultStub, - '', - '', false, [], - &$oRows, - &$tabindex, 0, false, $foreigners, - 0, 'table', 'db', 0, @@ -2467,7 +2432,7 @@ class InsertEditTest extends AbstractTestCase $this->assertStringContainsString('Image preview here', $actual); $this->assertStringContainsString( '', @@ -2493,18 +2458,12 @@ class InsertEditTest extends AbstractTestCase $tableColumn, 0, [], - false, $resultStub, - '', - '[a][0]', true, [], - &$oRows, - &$tabindex, 0, false, $foreigners, - 0, 'table', 'db', 0, @@ -2522,7 +2481,7 @@ class InsertEditTest extends AbstractTestCase $this->assertStringContainsString('', $actual); $this->assertStringContainsString('datetime', $actual); $this->assertStringContainsString( - 'assertStringContainsString('foo', $actual); - $this->assertStringNotContainsString('bar', $actual); + $this->assertStringContainsString('bar', $actual); // insert $tableColumns = [ @@ -2737,18 +2678,11 @@ class InsertEditTest extends AbstractTestCase [], $tableColumns, [], - false, $resultStub, - '', - '', true, [], - $oRows, - $tabindex, - 3, false, $foreigners, - 0, 'table', 'db', 0, diff --git a/test/classes/Plugins/Transformations/TransformationPluginsTest.php b/test/classes/Plugins/Transformations/TransformationPluginsTest.php index e96e0497c5..de4e25b86f 100644 --- a/test/classes/Plugins/Transformations/TransformationPluginsTest.php +++ b/test/classes/Plugins/Transformations/TransformationPluginsTest.php @@ -90,7 +90,7 @@ class TransformationPluginsTest extends AbstractTestCase '
', - [[], 0, 'test', ['150'], '', 'ltr', 0, 0, 0], + [[], 0, 'test', ['150'], '', 'ltr', 0, 0], ], [ new Image_JPEG_Upload(), @@ -111,7 +111,6 @@ class TransformationPluginsTest extends AbstractTestCase 'ltr', 0, 0, - 0, ], ], // Test data for TextPlainFileupload plugin @@ -128,7 +127,7 @@ class TransformationPluginsTest extends AbstractTestCase new Text_Plain_FileUpload(), 'getInputHtml', '', - [[], 0, 'test', [], '', 'ltr', 0, 0, 0], + [[], 0, 'test', [], '', 'ltr', 0, 0], ], [ new Text_Plain_FileUpload(), @@ -137,7 +136,7 @@ class TransformationPluginsTest extends AbstractTestCase . 'value="something">', - [[], 0, '2ndtest', [], 'something', 'ltr', 0, 0, 0], + [[], 0, '2ndtest', [], 'something', 'ltr', 0, 0], ], // Test data for Text_Plain_Regexvalidation plugin [new Text_Plain_RegexValidation(), 'getName', 'Regex Validation'], @@ -150,7 +149,7 @@ class TransformationPluginsTest extends AbstractTestCase ], [new Text_Plain_RegexValidation(), 'getMIMEType', 'Text'], [new Text_Plain_RegexValidation(), 'getMIMESubtype', 'Plain'], - [new Text_Plain_RegexValidation(), 'getInputHtml', '', [[], 0, '', [], '', 'ltr', 0, 0, 0]], + [new Text_Plain_RegexValidation(), 'getInputHtml', '', [[], 0, '', [], '', 'ltr', 0, 0]], // Test data for PhpMyAdmin\Plugins\Transformations\Output\Application_Octetstream_Download plugin [new Application_Octetstream_Download(), 'getName', 'Download'], [