0

我正在编写一个脚本,该脚本会定期将 CSV 文件上传到 MySQL 数据库中。问题是 CSV 文件中的一个字段包含用户生成的文本,其中可能包括引号和其他对 MySQL 不友好的字符。

我已经确定上传 CSV 文件的最有效方法是通过 MySQL 的“LOAD DATA INFILE”命令。这是我上传 CSV 时出现在 MyPHPAdmin 中的命令:

LOAD DATA LOCAL INFILE '/home/myfolder/tmp/property_re_1.csv' REPLACE INTO TABLE `markers`
    FIELDS TERMINATED BY ';' ENCLOSED BY '"' ESCAPED BY '\\'
    LINES TERMINATED BY '\r\n' # 2 rows affected.

简单地使用此命令加载 CSV 是行不通的,因为该进程在遇到“””时立即终止,并且“ESCAPED BY '\'”似乎没有达到其目的。

在这种情况下,我想我可能必须首先使用 PHP 以编程方式转义 CSV 文件中的引号。然后使用 SQL 中的 LOAD DATA INFILE 命令将“转义”文件加载到 MySQL 中。

我确信这是一个具有“最佳实践”解决方案的常见问题。本质上,我的脚本需要在将 CSV 文件加载到 MYSQL 表之前“清理”它。

这是我正在使用的实际 SQL 表和 CSV 文件的链接,以帮助更聪明的人围绕这个问题思考:https ://www.dropbox.com/sh/4iq10i51qlqyq8q/UjEQwvXKDA

提前感谢您的帮助。

4

1 回答 1

2

Dropbox 上的数据文件具有由 分隔的字段,,可选地由 括起来,由"分隔的\n行和包含标题行的行;而您上面的语句适用于一个文件,其字段由 分隔;,始终由 包围",行由 分隔\r\n且不包含任何标题行。

也就是说,它也适用于名为的文件data.csv,而 Dropbox 上的文件名为property_re_1.csv.

mysql> CREATE TABLE IF NOT EXISTS `markers` (
    ->    `L_ListingID` int(20) NOT NULL,
    ->    `L_Class` int(5) NOT NULL,
    ->    `L_Type_` int(10) NOT NULL,
    ->    `L_Status` varchar(10) NOT NULL,
    ->    `L_AskingPrice` float NOT NULL,
    ->    `L_Remarks` text NOT NULL,
    ->    `L_Address` varchar(50) NOT NULL,
    ->    `L_City` text NOT NULL,
    ->    `L_State` varchar(10) NOT NULL,
    ->    `LO1_OrganizationName` varchar(65) NOT NULL,
    ->    `LA1_AgentLicenseID` int(20) NOT NULL,
    ->    `LA1_UserFirstName` varchar(50) NOT NULL,
    ->    `LA1_UserLastName` varchar(50) NOT NULL,
    ->    `L_PictureCount` int(4) NOT NULL,
    ->    PRIMARY KEY (`L_ListingID`)
    ->) ENGINE=MyISAM DEFAULT CHARSET=latin1;
查询正常,0 行受影响(0.21 秒)

mysql>LOAD DATA LOCAL INFILE 'property_re_1.csv' 
    -> REPLACE INTO TABLE `markers`
    -> FIELDS TERMINATED BY ',' OPTIONALLY ENCLOSED BY '"' ESCAPED BY '\\'
    -> LINES TERMINATED BY '\n' IGNORE 1 LINES;
查询正常,315 行受影响(0.01 秒)
记录:315 删除:0 跳过:0 警告:0
于 2012-12-17T20:54:39.850 回答