From fd9c7e6a22a5e27cb3c96b3323a407389830d1a9 Mon Sep 17 00:00:00 2001 From: Kamil Tekiela Date: Sat, 9 Dec 2023 21:33:59 +0100 Subject: [PATCH] Add DTO ColumnInfo Signed-off-by: Kamil Tekiela --- phpstan-baseline.neon | 30 ----- psalm-baseline.xml | 70 ------------ .../database/designer/database_tables.twig | 22 ++-- src/Database/Designer.php | 104 +++++++++--------- src/Database/Designer/ColumnInfo.php | 14 +++ src/Database/Designer/Common.php | 28 ++--- 6 files changed, 86 insertions(+), 182 deletions(-) create mode 100644 src/Database/Designer/ColumnInfo.php diff --git a/phpstan-baseline.neon b/phpstan-baseline.neon index c960d48414..12b41dd1d1 100644 --- a/phpstan-baseline.neon +++ b/phpstan-baseline.neon @@ -8690,26 +8690,6 @@ parameters: count: 1 path: src/Database/CentralColumns.php - - - message: "#^Cannot access offset 'COLUMN_ID' on mixed\\.$#" - count: 2 - path: src/Database/Designer.php - - - - message: "#^Cannot access offset 'COLUMN_NAME' on mixed\\.$#" - count: 2 - path: src/Database/Designer.php - - - - message: "#^Cannot access offset 'TYPE' on mixed\\.$#" - count: 18 - path: src/Database/Designer.php - - - - message: "#^Cannot access offset int\\<0, max\\> on mixed\\.$#" - count: 20 - path: src/Database/Designer.php - - message: "#^Cannot cast mixed to string\\.$#" count: 2 @@ -8725,16 +8705,6 @@ parameters: count: 1 path: src/Database/Designer.php - - - message: "#^Parameter \\#1 \\$haystack of function str_contains expects string, mixed given\\.$#" - count: 18 - path: src/Database/Designer.php - - - - message: "#^Parameter \\#1 \\$value of function count expects array\\|Countable, mixed given\\.$#" - count: 2 - path: src/Database/Designer.php - - message: "#^Argument of an invalid type mixed supplied for foreach, only iterables are supported\\.$#" count: 3 diff --git a/psalm-baseline.xml b/psalm-baseline.xml index c8ed29dcbe..c34a41db77 100644 --- a/psalm-baseline.xml +++ b/psalm-baseline.xml @@ -4745,82 +4745,12 @@ Config::getInstance() - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - $params mixed[] - - - - $params $params diff --git a/resources/templates/database/designer/database_tables.twig b/resources/templates/database/designer/database_tables.twig index bc9d7c3c49..8521ce1ab7 100644 --- a/resources/templates/database/designer/database_tables.twig +++ b/resources/templates/database/designer/database_tables.twig @@ -63,12 +63,12 @@ {% set display_field = designerTable.getDisplayField() %} - {% for j in 0..tab_column[t_n]['COLUMN_ID']|length - 1 %} - {% set col_name = tab_column[t_n]['COLUMN_NAME'][j] %} - {% set tmp_column = t_n ~ '.' ~ tab_column[t_n]['COLUMN_NAME'][j] %} + {% for j in 0..tab_column[t_n]|length - 1 %} + {% set col_name = tab_column[t_n][j].name %} + {% set tmp_column = t_n ~ '.' ~ tab_column[t_n][j].name %} {% set click_field_param = [ designerTable.getTableName()|escape('url'), - tab_column[t_n]['COLUMN_NAME'][j]|url_encode + tab_column[t_n][j].name|url_encode ] %} {% if not designerTable.supportsForeignkeys() %} {% set click_field_param = click_field_param|merge([tables_pk_or_unique_keys[tmp_column] is defined ? 1 : 0]) %} @@ -78,15 +78,15 @@ {% set click_field_param = click_field_param|merge([tables_all_keys[tmp_column] is defined ? 1 : 0]) %} {% endif %} {% set click_field_param = click_field_param|merge([db]) %} - {% if has_query %} {% endif %} + {{- tab_column[t_n][j].name|url_encode }}">
- {% set type = columns_type[t_n ~ '.' ~ tab_column[t_n]['COLUMN_NAME'][j]] %} + {% set type = columns_type[t_n ~ '.' ~ tab_column[t_n][j].name] %} * - {{ tab_column[t_n]['COLUMN_NAME'][j] }} : {{ tab_column[t_n]['TYPE'][j] }} + {{ tab_column[t_n][j].name }} : {{ tab_column[t_n][j].type }}
{% if has_query %} diff --git a/src/Database/Designer.php b/src/Database/Designer.php index a0531a56d2..8293986b77 100644 --- a/src/Database/Designer.php +++ b/src/Database/Designer.php @@ -6,6 +6,7 @@ namespace PhpMyAdmin\Database; use PhpMyAdmin\Config; use PhpMyAdmin\ConfigStorage\Relation; +use PhpMyAdmin\Database\Designer\ColumnInfo; use PhpMyAdmin\Database\Designer\DesignerTable; use PhpMyAdmin\DatabaseInterface; use PhpMyAdmin\Message; @@ -15,7 +16,6 @@ use PhpMyAdmin\Util; use stdClass; use function __; -use function count; use function intval; use function is_array; use function json_decode; @@ -212,13 +212,13 @@ class Designer /** * Get HTML to display tables on designer page * - * @param string $db The database name from the request - * @param DesignerTable[] $designerTables The designer tables - * @param mixed[] $tabPos tables positions - * @param int $displayPage page number of the selected page - * @param mixed[] $tabColumn table column info - * @param mixed[] $tablesAllKeys all indices - * @param mixed[] $tablesPkOrUniqueKeys unique or primary indices + * @param string $db The database name from the request + * @param DesignerTable[] $designerTables The designer tables + * @param mixed[] $tabPos tables positions + * @param int $displayPage page number of the selected page + * @param list[] $tableColumnsInfo table column info + * @param mixed[] $tablesAllKeys all indices + * @param mixed[] $tablesPkOrUniqueKeys unique or primary indices * * @return string html */ @@ -227,38 +227,36 @@ class Designer array $designerTables, array $tabPos, int $displayPage, - array $tabColumn, + array $tableColumnsInfo, array $tablesAllKeys, array $tablesPkOrUniqueKeys, ): string { $GLOBALS['text_dir'] ??= null; $columnsType = []; - foreach ($designerTables as $designerTable) { - $tableName = $designerTable->getDbTableString(); - $limit = count($tabColumn[$tableName]['COLUMN_ID']); - for ($j = 0; $j < $limit; $j++) { - $tableColumnName = $tableName . '.' . $tabColumn[$tableName]['COLUMN_NAME'][$j]; + foreach ($tableColumnsInfo as $tableName => $columnsInfo) { + foreach ($columnsInfo as $columnInfo) { + $tableColumnName = $tableName . '.' . $columnInfo->name; if (isset($tablesPkOrUniqueKeys[$tableColumnName])) { $columnsType[$tableColumnName] = 'designer/FieldKey_small'; } else { $columnsType[$tableColumnName] = 'designer/Field_small'; if ( - str_contains($tabColumn[$tableName]['TYPE'][$j], 'char') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'text') + str_contains($columnInfo->type, 'char') + || str_contains($columnInfo->type, 'text') ) { $columnsType[$tableColumnName] .= '_char'; } elseif ( - str_contains($tabColumn[$tableName]['TYPE'][$j], 'int') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'float') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'double') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'decimal') + str_contains($columnInfo->type, 'int') + || str_contains($columnInfo->type, 'float') + || str_contains($columnInfo->type, 'double') + || str_contains($columnInfo->type, 'decimal') ) { $columnsType[$tableColumnName] .= '_int'; } elseif ( - str_contains($tabColumn[$tableName]['TYPE'][$j], 'date') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'time') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'year') + str_contains($columnInfo->type, 'date') + || str_contains($columnInfo->type, 'time') + || str_contains($columnInfo->type, 'year') ) { $columnsType[$tableColumnName] .= '_date'; } @@ -273,7 +271,7 @@ class Designer 'has_query' => isset($_REQUEST['query']), 'tab_pos' => $tabPos, 'display_page' => $displayPage, - 'tab_column' => $tabColumn, + 'tab_column' => $tableColumnsInfo, 'tables_all_keys' => $tablesAllKeys, 'tables_pk_or_unique_keys' => $tablesPkOrUniqueKeys, 'tables' => $designerTables, @@ -284,20 +282,20 @@ class Designer /** * Returns HTML for Designer page * - * @param string $db database in use - * @param string $getDb database in url - * @param DesignerTable[] $designerTables The designer tables - * @param mixed[] $scriptTables array on foreign key support for each table - * @param mixed[] $scriptContr initialization data array - * @param DesignerTable[] $scriptDisplayField displayed tables in designer with their display fields - * @param int $displayPage page number of the selected page - * @param bool $visualBuilderMode whether this is visual query builder - * @param string|null $selectedPage name of the selected page - * @param mixed[] $paramsArray array with class name for various buttons on side menu - * @param mixed[] $tablePositions table positions - * @param mixed[] $tabColumn table column info - * @param mixed[] $tablesAllKeys all indices - * @param mixed[] $tablesPkOrUniqueKeys unique or primary indices + * @param string $db database in use + * @param string $getDb database in url + * @param DesignerTable[] $designerTables The designer tables + * @param mixed[] $scriptTables array on foreign key support for each table + * @param mixed[] $scriptContr initialization data array + * @param DesignerTable[] $scriptDisplayField displayed tables in designer with their display fields + * @param int $displayPage page number of the selected page + * @param bool $visualBuilderMode whether this is visual query builder + * @param string|null $selectedPage name of the selected page + * @param mixed[] $paramsArray array with class name for various buttons on side menu + * @param mixed[] $tablePositions table positions + * @param list[] $tableColumnsInfo table column info + * @param mixed[] $tablesAllKeys all indices + * @param mixed[] $tablesPkOrUniqueKeys unique or primary indices * * @return string html */ @@ -313,7 +311,7 @@ class Designer string|null $selectedPage, array $paramsArray, array $tablePositions, - array $tabColumn, + array $tableColumnsInfo, array $tablesAllKeys, array $tablesPkOrUniqueKeys, ): string { @@ -321,31 +319,29 @@ class Designer $relationParameters = $this->relation->getRelationParameters(); $columnsType = []; - foreach ($designerTables as $designerTable) { - $tableName = $designerTable->getDbTableString(); - $limit = count($tabColumn[$tableName]['COLUMN_ID']); - for ($j = 0; $j < $limit; $j++) { - $tableColumnName = $tableName . '.' . $tabColumn[$tableName]['COLUMN_NAME'][$j]; + foreach ($tableColumnsInfo as $tableName => $columnsInfo) { + foreach ($columnsInfo as $columnInfo) { + $tableColumnName = $tableName . '.' . $columnInfo->name; if (isset($tablesPkOrUniqueKeys[$tableColumnName])) { $columnsType[$tableColumnName] = 'designer/FieldKey_small'; } else { $columnsType[$tableColumnName] = 'designer/Field_small'; if ( - str_contains($tabColumn[$tableName]['TYPE'][$j], 'char') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'text') + str_contains($columnInfo->type, 'char') + || str_contains($columnInfo->type, 'text') ) { $columnsType[$tableColumnName] .= '_char'; } elseif ( - str_contains($tabColumn[$tableName]['TYPE'][$j], 'int') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'float') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'double') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'decimal') + str_contains($columnInfo->type, 'int') + || str_contains($columnInfo->type, 'float') + || str_contains($columnInfo->type, 'double') + || str_contains($columnInfo->type, 'decimal') ) { $columnsType[$tableColumnName] .= '_int'; } elseif ( - str_contains($tabColumn[$tableName]['TYPE'][$j], 'date') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'time') - || str_contains($tabColumn[$tableName]['TYPE'][$j], 'year') + str_contains($columnInfo->type, 'date') + || str_contains($columnInfo->type, 'time') + || str_contains($columnInfo->type, 'year') ) { $columnsType[$tableColumnName] .= '_date'; } @@ -382,7 +378,7 @@ class Designer 'selected_page' => $selectedPage, 'params_array' => $paramsArray, 'tab_pos' => $tablePositions, - 'tab_column' => $tabColumn, + 'tab_column' => $tableColumnsInfo, 'tables_all_keys' => $tablesAllKeys, 'tables_pk_or_unique_keys' => $tablesPkOrUniqueKeys, 'designerTables' => $designerTables, diff --git a/src/Database/Designer/ColumnInfo.php b/src/Database/Designer/ColumnInfo.php new file mode 100644 index 0000000000..e9fa16aae8 --- /dev/null +++ b/src/Database/Designer/ColumnInfo.php @@ -0,0 +1,14 @@ +[] table column nfo */ public function getColumnsInfo(array $designerTables): array { - //$this->dbi->selectDb($GLOBALS['db']); $tabColumn = []; foreach ($designerTables as $designerTable) { @@ -90,17 +89,12 @@ class Common $designerTable->getTableName(), ), ); - $j = 0; - while ($row = $fieldsRs->fetchAssoc()) { - if (! isset($tabColumn[$designerTable->getDbTableString()])) { - $tabColumn[$designerTable->getDbTableString()] = []; - } - - $tabColumn[$designerTable->getDbTableString()]['COLUMN_ID'][$j] = $j; - $tabColumn[$designerTable->getDbTableString()]['COLUMN_NAME'][$j] = $row['Field']; - $tabColumn[$designerTable->getDbTableString()]['TYPE'][$j] = $row['Type']; - $tabColumn[$designerTable->getDbTableString()]['NULLABLE'][$j] = $row['Null']; - $j++; + /** + * @var string $field + * @var string $type + */ + foreach ($fieldsRs as ['Field' => $field, 'Type' => $type]) { + $tabColumn[$designerTable->getDbTableString()][] = new ColumnInfo($field, $type); } } @@ -307,12 +301,12 @@ class Common $query = 'DELETE FROM ' . Util::backquote($pdfFeature->database) . '.' . Util::backquote($pdfFeature->tableCoords) - . ' WHERE ' . Util::backquote('pdf_page_number') . ' = ' . intval($pg); + . ' WHERE ' . Util::backquote('pdf_page_number') . ' = ' . $pg; $this->dbi->queryAsControlUser($query); $query = 'DELETE FROM ' . Util::backquote($pdfFeature->database) . '.' . Util::backquote($pdfFeature->pdfPages) - . ' WHERE ' . Util::backquote('page_nr') . ' = ' . intval($pg); + . ' WHERE ' . Util::backquote('page_nr') . ' = ' . $pg; $this->dbi->queryAsControlUser($query); return true;