У меня есть список данных в CSV, и мне нужно вставить эти данные в базу данных MySQL. Эти данные должны быть введены безопасно, например, для санитарии. Итак, я использовал объект PDO для исправления SQL-инъекции. Но он не может получить данные из файла CSV и вставляет нулевые значения.
Вот пример,
<?php
$servername = "localhost";
$username = "root";
$password = "";
try {
$conn = new PDO("mysql:host=$servername;dbname=contact_list",$username,$password);
$conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
echo "connection successfully";
}
catch(PDOException $e)
{
echo "connection Failed:" . $e -> getMessage();
}
// Create CSV to Array function
function csvToArray($filename = '', $delimiter = ',')
{
if (!file_exists($filename) || !is_readable($filename)) {
return false;
}
$header = NULL;
$result = array();
if (($handle = fopen($filename, 'r')) !== FALSE) {
while (($row = fgetcsv($handle, 1000, $delimiter)) !== FALSE) {
if (!$header)
$header = $row;
else
$result[] = array_combine($header, $row);
}
fclose($handle);
}
return $result;
}
// Insert data into database
$all_data = csvToArray('contact.csv');
foreach ($all_data as $data) {
$data = array_map(function($row){
return filter_var($row, FILTER_SANITIZE_STRING, FILTER_SANITIZE_FULL_SPECIAL_CHARS);
}, $data);
$sql = $conn->prepare("INSERT INTO contact
(title, first_name,last_name,company_name,date_of_birth,notes)
VALUES (:t, :fname, :lname,:cname,:dob,:note)");
$sql->bindParam(':t', $data[1], PDO::PARAM_STR);
$sql->bindParam(':fname', $data[2], PDO::PARAM_STR);
$sql->bindParam(':lname', $data[3], PDO::PARAM_STR);
$sql->bindParam(':cname', $data[0], PDO::PARAM_STR);
$sql->bindParam(':dob', $data[4], PDO::PARAM_STR);
$sql->bindParam(':note', $data[15], PDO::PARAM_STR);
print_r($data);
$sql->execute();
}
?>
Может ли кто-нибудь помочь мне решить эту проблему?
что возвращает print_r($all_data);
?
Включите отчет об ошибках php.net/manual/en/function.error-reporting.php и сообщите нам, что показывает.
Вы также можете импортировать CSV прямо в MySQL: dev.mysql.com/doc/refman/8.0/en/load-data.html
@ Akintunde-Rotimi Я попытался распечатать данные, чтобы увидеть, зацикливаются ли они.
@FunkFortyNiner не показывает никаких ошибок.
@JonStirling Я изменил параметр на, потому что не хочу ограничивать значение.
@JonStirling связал мой образец, о котором идет речь.
Может ли это быть так просто, как отсутствие заголовков в столбце заголовков?
А также отсутствующие названия компаний в столбце названия компании !!!!!!
@RiggsFolly Да, в любом случае он должен сохраняться в базе данных с нулевыми значениями, если это не так.
Если вы посмотрите документацию для array_combine()
, вы увидите, что его цель - построить ассоциативный массив. Вы используете эту функцию в csvToArray()
, но позже в вашем коде вы пытаетесь получить данные с помощью цифровых клавиш. Я не ожидал, что ты когда-нибудь что-нибудь вставишь.
Кстати, вы полностью сводите на нет цель подготовленных утверждений, многократно подготавливая одно и то же утверждение снова и снова. Готовься один раз и выполняй много раз. Индивидуальная привязка параметров требуется редко, почти во всех случаях вы можете предоставить данные в PDOStatement::execute()
в виде массива. Также плохой тон хранить объекты HTML в базе данных; если вам нужно вывести в HTML, вы выполняете экранирование в этой точке.
Что-то вроде этого должно сработать (при необходимости измените имена ключей массива).
$all_data = csvToArray('contact.csv');
$sql = $conn->prepare("INSERT INTO contact
(title, first_name, last_name, company_name, date_of_birth, notes)
VALUES (:t, :fname, :lname,:cname,:dob,:note)");
foreach ($all_data as $data) {
$params = [
":t" => $data["t"],
":fname" => $data["fname"],
":lname" => $data["lname"],
":dob" => $data["dob"],
":note" => $data["note"],
];
$sql->execute($params);
}
Я попробовал этот метод, изменив значение индекса массива, например $ data [0], $ data [1] .... но все равно он сохраняет нулевые значения.
Вы прочитали первый абзац моего ответа? Где я сказал, что вся ваша проблема заключается в использовании числовых индексов?
Можем ли мы увидеть несколько примеров строк в contact.csv, длина всех строк <1000?