LOAD DATA INFILE不会将CSV数据上传到MySQL表中而不会出错

时间:2015-06-10 13:16:35

标签: php mysql csv

更新

我试图在phpMyAdmin的SQL选项卡中执行PHP脚本生成的查询并得到:

#7890 - Can't find file 'C:wamp    mpphpB4C4.tmp'.

它剪切了C:wamp和tmp文件名之间的路径。可能是我错误地转义了文件路径吗?:$file = $_FILES['csv']['tmp_name'];

我正在使用PHP和MySQL编写这个很酷的webapp。其功能之一是将CSV文件的内容上传到名为suites。的数据库中的表中。

CSV 文件如下所示:

1230,Cool Business,,1
3612,Not-so-cool Business Ltd.,John Smith,0

此CSV中从左到右的列含义如下:套件编号,此套件中运营的企业名称,主要联系人(可选),我是否已经去过那里?(0 - 否,1 - 是;可选也)。

名为suites的数据库表具有以下结构:

suite_id (主要), location_id (外部参考位置表),套件商家联系访问

正如您可能已经猜到的那样,我试图仅使用上面的CSV示例插入套接字表的最后4列。

我尝试使用以下 PHP 代码执行此操作:

<?php

/**
 * Class registration
 * handles the user registration
 */
class SuiteCSV
{
    /**
     * @var object $db_connection The database connection
     */
    private $db_connection = null;
    /**
     * @var array $errors Collection of error messages
     */
    public $errors = array();
    /**
     * @var array $messages Collection of success / neutral messages
     */
    public $messages = array();

    /**
     * the function "__construct()" automatically starts whenever an object of this class is created,
     * you know, when you do "$registration = new Registration();"
     */
    public function __construct()
    {
        if(isset($_POST["add_suite_csv"])){
            $this->addSuiteCSV();
        }
    }

    /**
     * handles the entire registration process. checks all error possibilities
     * and creates a new user in the database if everything is fine
     */ 
    private function addSuiteCSV()
    {
        if (empty($_POST['suite_location_csv'])) {
            $this->errors[] = "Must select location of suite";
        }else{

        // create a database connection
        $this->db_connection = new mysqli(DB_HOST, DB_USER, DB_PASS, DB_NAME);

        if (!$this->db_connection->set_charset("utf8")) {
                $this->errors[] = $this->db_connection->error;
        }

        if (!$this->db_connection->connect_errno) {
            $suite_location_csv = $this->db_connection->real_escape_string(strip_tags($_POST['suite_location_csv'], ENT_QUOTES));
            if ($_FILES['csv']['size'] > 0) {
                $file = $_FILES['csv']['tmp_name'];
                $query = <<<eof
LOAD DATA INFILE '$file'
INTO TABLE sales.suites
FIELDS TERMINATED BY ',' OPTIONALLY ENCLOSED BY '"'
LINES TERMINATED BY '\r\n'
(suite,business,contact,visited)
SET location_id = $suite_location_csv
eof;

                $query_add_suite_csv = $this->db_connection->query($query);

                if ($query_add_suite_csv) {
                    $this->messages[] = "CSV has been uploaded.";
                } else {
                    $this->errors[] = "Sorry, I couldn't upload this CSV. Try again.";
                }

                var_dump($query_add_suite_csv);


            }else{
                $this->errors[] = "Must select CSV file for upload";
            }
        }else{
            $this->errors[] = "Database connection error";
        }
    }
}
}
在这种情况下,

$ suite_location 是一个用户将从上传表单的下拉菜单中选择的值,当加载页面时,该菜单又会填充另一个PHP脚本。 $ suite_location的值是locations表中的location_id值,它在套件表中具有外键。

因此,用户选择一个位置,选择一个CSV文件并将其上传到套房表。

但没有发生任何事情。没有错误。我已经在LOAD DATA INFILE文档中查看了并尝试应用我从中理解的内容,但似乎仍然无法正常工作。

表格摘要:

<form class="form-horizontal" method="post" action="admin_add_location.php" enctype="multipart/form-data" name="addsuitecsv">
    <div class="form-group">
        <label class="control-label">Select Locations:</label>
        <div class="">
            <select size="6" name="suite_location_csv">
                    <?php $location->getLocations(); ?>
            </select>
        </div>
        <label class="control-label">Choose your file:</label>
        <div class="">
            <input name="csv" type="file" id="csv" />
        </div>
        <button class="btn btn_success" name="add_suite_csv" type="submit"><span class="glyphicon glyphicon-upload" ></span>Import CSV</button>
    </div>
</form>

添加查看PHP:

<?php
    // include the configs / constants for the database connection
    require_once("config/db.php");

    // load the login class
    require_once("classes/Login.php");

    // create a login object. when this object is created, it will do all login/logout stuff automatically
    // so this single line handles the entire login process. in consequence, you can simply ...
    $login = new Login();

    // only administrators can see
    if ($login->isUserLoggedIn() == true && $_SESSION['user_group'] == 0) {
        require_once("classes/Location.php");
        $location = new location();
        require_once("classes/Suite.php");
        $suite = new Suite();
        require_once("classes/SuiteCSV.php");
        $suitecsv = new SuiteCSV();
        include("includes/header.php");
        include("views/admin_add_location_view.php");
        include("views/admin_add_suite_view.php");
        include("views/admin_add_suite_csv_view.php");
        include("includes/footer.php");
    }else{
        echo "<h1>Access denied</h1>";
        include("views/go_back_view.php");
    }
?>

1 个答案:

答案 0 :(得分:1)

更改:

$file = $_FILES['csv']['tmp_name'];

为:

$file = addslashes($_FILES['csv']['tmp_name']);

解决了问题,现在上传了CSV。

基本上我不得不在文件路径中转义斜杠。