diff --git a/libraries/classes/Plugins/Import/ImportCsv.php b/libraries/classes/Plugins/Import/ImportCsv.php
index 2d9d4b5b1f..2d39bab03c 100644
--- a/libraries/classes/Plugins/Import/ImportCsv.php
+++ b/libraries/classes/Plugins/Import/ImportCsv.php
@@ -144,15 +144,11 @@ class ImportCsv extends AbstractImportCsv
public function doImport(array &$sql_data = [])
{
global $db, $table, $csv_terminated, $csv_enclosed, $csv_escaped,
- $csv_new_line, $csv_columns, $err_url, $import_file_name;
+ $csv_new_line, $csv_columns, $err_url;
// $csv_replace and $csv_ignore should have been here,
// but we use directly from $_POST
global $error, $timeout_passed, $finished, $message;
- $import_file_name = basename($import_file_name, '.csv');
- $import_file_name = mb_strtolower($import_file_name);
- $import_file_name = preg_replace('/[^a-zA-Z0-9_]/', '_', $import_file_name);
-
$replacements = [
'\\n' => "\n",
'\\t' => "\t",
@@ -220,61 +216,7 @@ class ImportCsv extends AbstractImportCsv
}
$buffer = '';
- $required_fields = 0;
- $sql_template = '';
- $fields = [];
- if (! $this->_getAnalyze()) {
- $sql_template = 'INSERT';
- if (isset($_POST['csv_ignore'])) {
- $sql_template .= ' IGNORE';
- }
- $sql_template .= ' INTO ' . Util::backquote($table);
-
- $tmp_fields = $GLOBALS['dbi']->getColumns($db, $table);
-
- if (empty($csv_columns)) {
- $fields = $tmp_fields;
- } else {
- $sql_template .= ' (';
- $fields = [];
- $tmp = preg_split('/,( ?)/', $csv_columns);
- foreach ($tmp as $key => $val) {
- if (count($fields) > 0) {
- $sql_template .= ', ';
- }
- /* Trim also `, if user already included backquoted fields */
- $val = trim($val, " \t\r\n\0\x0B`");
- $found = false;
- foreach ($tmp_fields as $field) {
- if ($field['Field'] == $val) {
- $found = true;
- break;
- }
- }
- if (! $found) {
- $message = Message::error(
- __(
- 'Invalid column (%s) specified! Ensure that columns'
- . ' names are spelled correctly, separated by commas'
- . ', and not enclosed in quotes.'
- )
- );
- $message->addParam($val);
- $error = true;
- break;
- }
- if (isset($field)) {
- $fields[] = $field;
- }
- $sql_template .= Util::backquote($val);
- }
- $sql_template .= ') ';
- }
-
- $required_fields = count($fields);
-
- $sql_template .= ' VALUES (';
- }
+ [$sql_template, $required_fields, $fields] = $this->getSqlTemplateAndRequiredFields($db, $table, $csv_columns);
// Defaults for parser
$i = 0;
@@ -675,51 +617,8 @@ class ImportCsv extends AbstractImportCsv
}
}
- if (isset($_REQUEST['csv_col_names'])) {
- $col_names = array_splice($rows, 0, 1);
- $col_names = $col_names[0];
- // MySQL column names can't end with a space character.
- foreach ($col_names as $key => $col_name) {
- $col_names[$key] = rtrim($col_name);
- }
- }
-
- if ((isset($col_names) && count($col_names) != $max_cols)
- || ! isset($col_names)
- ) {
- // Fill out column names
- for ($i = 0; $i < $max_cols; ++$i) {
- $col_names[] = 'COL ' . ($i + 1);
- }
- }
-
- // get new table name, if user didn't provide one, set the default name
- if (isset($_REQUEST['csv_new_tbl_name'])
- && strlen($_REQUEST['csv_new_tbl_name']) > 0
- ) {
- $tbl_name = $_REQUEST['csv_new_tbl_name'];
- } elseif (mb_strlen((string) $db)) {
- $result = $GLOBALS['dbi']->fetchResult('SHOW TABLES');
-
- // logic to get table name from filename
- // if no table then use filename as table name
- if (count($result) === 0) {
- $tbl_name = $import_file_name;
- } else {
- // check to see if {filename} as table exist
- $name_array = preg_grep('/' . $import_file_name . '/isU', $result);
- // if no use filename as table name
- if (count($name_array) === 0) {
- $tbl_name = $import_file_name;
- } else {
- // check if {filename}_ as table exist
- $name_array = preg_grep('/' . $import_file_name . '_/isU', $result);
- $tbl_name = $import_file_name . '_' . (count($name_array) + 1);
- }
- }
- } else {
- $tbl_name = $import_file_name;
- }
+ $col_names = $this->getColumnNames($col_names, $max_cols, $rows);
+ $tbl_name = $this->getTableNameFromImport((string) $db);
$tables[] = [
$tbl_name,
@@ -785,6 +684,127 @@ class ImportCsv extends AbstractImportCsv
$error = true;
}
+ private function getTableNameFromImport(string $databaseName): string
+ {
+ global $import_file_name;
+
+ $importFileName = basename($import_file_name, '.csv');
+ $importFileName = mb_strtolower($importFileName);
+ $importFileName = (string) preg_replace('/[^a-zA-Z0-9_]/', '_', $importFileName);
+
+ // get new table name, if user didn't provide one, set the default name
+ if (isset($_REQUEST['csv_new_tbl_name'])
+ && strlen($_REQUEST['csv_new_tbl_name']) > 0
+ ) {
+ return $_REQUEST['csv_new_tbl_name'];
+ }
+ if (mb_strlen($databaseName)) {
+ $result = $GLOBALS['dbi']->fetchResult('SHOW TABLES');
+
+ // logic to get table name from filename
+ // if no table then use filename as table name
+ if (count($result) === 0) {
+ return $importFileName;
+ }
+ // check to see if {filename} as table exist
+ $nameArray = preg_grep('/' . $importFileName . '/isU', $result);
+ // if no use filename as table name
+ if (count($nameArray) === 0) {
+ return $importFileName;
+ }
+ // check if {filename}_ as table exist
+ $nameArray = preg_grep('/' . $importFileName . '_/isU', $result);
+ return $importFileName . '_' . (count($nameArray) + 1);
+ }
+ return $importFileName;
+ }
+
+ private function getColumnNames(array $columnNames, int $maxCols, array $rows): array
+ {
+ if (isset($_REQUEST['csv_col_names'])) {
+ $columnNames = array_splice($rows, 0, 1);
+ $columnNames = $columnNames[0];
+ // MySQL column names can't end with a space character.
+ foreach ($columnNames as $key => $col_name) {
+ $columnNames[$key] = rtrim($col_name);
+ }
+ }
+
+ if ((isset($columnNames) && count($columnNames) != $maxCols)
+ || ! isset($columnNames)
+ ) {
+ // Fill out column names
+ for ($i = 0; $i < $maxCols; ++$i) {
+ $columnNames[] = 'COL ' . ($i + 1);
+ }
+ }
+ return $columnNames;
+ }
+
+ private function getSqlTemplateAndRequiredFields(
+ ?string $db,
+ ?string $table,
+ ?string $csvColumns
+ ): array {
+ $requiredFields = 0;
+ $sqlTemplate = '';
+ $fields = [];
+ if (! $this->_getAnalyze() && $db !== null && $table !== null) {
+ $sqlTemplate = 'INSERT';
+ if (isset($_POST['csv_ignore'])) {
+ $sqlTemplate .= ' IGNORE';
+ }
+ $sqlTemplate .= ' INTO ' . Util::backquote($table);
+
+ $tmp_fields = $GLOBALS['dbi']->getColumns($db, $table);
+
+ if (empty($csvColumns)) {
+ $fields = $tmp_fields;
+ } else {
+ $sqlTemplate .= ' (';
+ $fields = [];
+ $tmp = preg_split('/,( ?)/', $csvColumns);
+ foreach ($tmp as $key => $val) {
+ if (count($fields) > 0) {
+ $sqlTemplate .= ', ';
+ }
+ /* Trim also `, if user already included backquoted fields */
+ $val = trim($val, " \t\r\n\0\x0B`");
+ $found = false;
+ foreach ($tmp_fields as $field) {
+ if ($field['Field'] == $val) {
+ $found = true;
+ break;
+ }
+ }
+ if (! $found) {
+ $message = Message::error(
+ __(
+ 'Invalid column (%s) specified! Ensure that columns'
+ . ' names are spelled correctly, separated by commas'
+ . ', and not enclosed in quotes.'
+ )
+ );
+ $message->addParam($val);
+ $error = true;
+ break;
+ }
+ if (isset($field)) {
+ $fields[] = $field;
+ }
+ $sqlTemplate .= Util::backquote($val);
+ }
+ $sqlTemplate .= ') ';
+ }
+
+ $requiredFields = count($fields);
+
+ $sqlTemplate .= ' VALUES (';
+ }
+
+ return [$sqlTemplate, $requiredFields, $fields];
+ }
+
/**
* Read the expected column_separated_with String of length
* $csv_terminated_len from the $buffer
diff --git a/psalm-baseline.xml b/psalm-baseline.xml
index ee469e962f..1a001a5a20 100644
--- a/psalm-baseline.xml
+++ b/psalm-baseline.xml
@@ -74,6 +74,11 @@
$pieces === false
+
+
+ $name
+
+
mb_strpos($row, ' ON ')