我试图不创建一个重复的问题,并且已经搜索了2天而没有找到似乎适用于我的情况的答案,所以我提前道歉,如果是这样的话,请求重复/愚蠢的问题。
所以我有一个用户上传excel文件的网络表单。这个excel文件需要放在我们的mySQL数据库中,就像在excel文件中一样。我已将数据库设置为匹配相同的列和标题。问题是该文件有大约260列,每个上载将包含大约100-500条记录/行。我习惯使用mysqli bind_param(),但我很难找到一种方法将其作为一个带有1个语句的数组插入,这样我就不必写出接近300个变量。我已经读过使用PDO可以更容易地绑定数组,但是尽管实现了超过15个不同的示例,但由于各种原因我无法工作。以下是我现在的代码。我对php不是很有经验,但也许有人可以指出我正确的方向。我正在使用PHPExcel来提取文件数据并创建一个行数组:
if(isset($_POST['source']) && $_POST['source'] > 0){
$source = $_POST['source'];
if($_FILES['myFile']['name']){
$error = $_FILES['myFile']['error'];
if ($error == UPLOAD_ERR_OK) {
$inputFileName = $_FILES['myFile']['tmp_name'];
include_once '../Assets/plugins/PHPExcel-1.8/Classes/PHPExcel.php';
$filetype = PHPExcel_IOFactory::identify($inputFileName);
$objReader = PHPExcel_IOFactory::createReader($filetype);
$objReader->setReadDataOnly(true);
$objPHPExcel = $objReader->load($inputFileName);
$objWorksheet = $objPHPExcel->getActiveSheet();
$highestRow = $objWorksheet->getHighestRow();
$highestColumn = $objWorksheet->getHighestColumn();
$highestColumnIndex = PHPExcel_Cell::columnIndexFromString($highestColumn);
include_once('../Auth/masterClass.php');
注意:masterClass只是一个连接函数(我没有连接问题)
$add = new master;
$con = $add->con();
switch ($source) {
case 1:
$headerData = $objWorksheet->rangeToArray('A1:'.$highestColumn.'1',NULL,TRUE,FALSE);
for ($row = 2; $row <= $highestRow; $row++) {
$table_name = 'books';
$data = array();
$rowData = $objWorksheet->rangeToArray('A'.$row.':'.$highestColumn.$row,NULL,TRUE,FALSE);
$result_set = $con->prepare("INSERT INTO `$table_name` (".implode(', ',$headerData[0]).") VALUES (:".implode(', :',$rowData[0]).")");
function bindArrayValue($sql, $array){
if(is_object($req) && ($req instanceof PDOStatement)){
foreach($array as $key => $value){
if(is_int($value)){
$param = PDO::PARAM_INT;
}elseif(is_bool($value)){
$param = PDO::PARAM_BOOL;
}elseif(is_null($value)){
$param = PDO::PARAM_NULL;
}elseif(is_string($value)){
$param = PDO::PARAM_STR;
}else{
$param = FALSE;
if($param){
$req->bindValue(":$value",$value,$param);
};
};
};
};
}
bindArrayValue($result_set,$rowData);
$result_set->execute();
// $sql = "INSERT INTO `books` (
// `id`, `title`, `author`, `status`
// ) VALUES (NULL,?,?,?)";
// if($stmt = $con->prepare($sql)){
// $stmt->bind_param("sss", $data[0], $data[1], $data[2]);
// if($stmt->execute()){
// $success = 1;
// } else {
// echo '<div class="alert alert-danger">Error: '.$sql."<br>".$con->error.'</div>';
// }
// }
}
if($success == 1){
echo '<div class="alert alert-success">File successfully saved to the database!</div>';
}
break;
default:
echo '<div class="alert alert-danger">Source match not found!</div>';
}
$con->close();
}else{
echo '<div class="alert alert-danger">File upload error!</div>';
};
}else{
echo '<div class="alert alert-danger">ERROR: File cannot upload!</div>';
};
}else{
echo '<div class="alert alert-danger">ERROR: File source not set!</div>';
};
?>
此代码告诉我我有SQL语法错误。我可以用你想要的任何东西来详细说明。
编辑:尝试“BIND ONCE”这就是我所拥有的,请指教:
case 1:
$table_name = 'books';
$headerData = $objWorksheet->rangeToArray('A1:'.$highestColumn.'1',NULL,TRUE,FALSE);
$result_set = $con->prepare("INSERT INTO $table_name ".implode(', ',$headerData[0])."=:".implode(', ',$headerData[0]).")");
bindArrayValue($result_set,$rowData);
for ($row = 2; $row <= $highestRow; $row++) {
$rowData = $objWorksheet->rangeToArray('A'.$row.':'.$highestColumn.$row,NULL,TRUE,FALSE);
function bindArrayValue($sql, $array){
if(is_object($req) && ($req instanceof PDOStatement)){
foreach($array as $key => $value){
if(is_int($value)){
$param = PDO::PARAM_INT;
}elseif(is_bool($value)){
$param = PDO::PARAM_BOOL;
}elseif(is_null($value)){
$param = PDO::PARAM_NULL;
}elseif(is_string($value)){
$param = PDO::PARAM_STR;
}else{
$param = FALSE;
if($param){
$req->bindValue(":$key",$value,$param);
};
};
};
};
}
$result_set->execute();
}
答案 0 :(得分:0)
我会使用LOAD DATA INFILE。 要使用,您需要将Excel文件另存为csv。
$sql ="LOAD DATA INFILE 'csvfile.csv'
INTO TABLE tablename
FIELDS TERMINATED BY ','
ENCLOSED BY '"'
LINES TERMINATED BY '\r\n'
IGNORE 1 LINES;"
$db->exec($sql);
答案 1 :(得分:0)
答案:好的,所以我用@Marc B的伪方向和这个方便的链接来解决这个问题:http://thisinterestsme.com/pdo-prepared-multi-inserts/
这是我的工作代码:
include_once('../Auth/masterClass.php');
$upload = new master;
$pdoObject = $upload->conn();
switch ($source) {
case 1:
$tableName = 'books';
$data = array();
$headerData = $objWorksheet->rangeToArray('A1:'.$highestColumn.'1',NULL,TRUE,FALSE);
for ($rec = 2; $rec <= $highestRow; $rec++) {
$rowData = $objWorksheet->rangeToArray('A'.$rec.':'.$highestColumn.$rec,NULL,TRUE,FALSE);
$comb_data = array_combine($headerData[0],$rowData[0]);
$data[] = $comb_data;
}
function pdoMultiInsert($tableName, $data, $pdoObject){
//Will contain SQL snippets.
$rowsSQL = array();
//Will contain the values that we need to bind.
$toBind = array();
//Get a list of column names to use in the SQL statement.
$columnNames = array_keys($data[0]);
//Loop through our $data array.
foreach($data as $arrayIndex => $row){
$params = array();
foreach($row as $columnName => $columnValue){
$param = ":" . $columnName . $arrayIndex;
$params[] = $param;
$toBind[$param] = $columnValue;
}
$rowsSQL[] = "(" . implode(", ", $params) . ")";
}
//Construct our SQL statement
$sql = "INSERT INTO `$tableName` (" . implode(", ", $columnNames) . ") VALUES " . implode(", ", $rowsSQL);
//Prepare our PDO statement.
$pdoStatement = $pdoObject->prepare($sql);
//Bind our values.
foreach($toBind as $param => $val){
$pdoStatement->bindValue($param, $val);
}
//Execute our statement (i.e. insert the data).
return $pdoStatement->execute();
}
if(pdoMultiInsert($tableName, $data, $pdoObject)){
echo '<div class="alert alert-success">File successfully saved to the database!</div>';
}
break;
default:
}